I don't understand creating selection lists
(setq ss (ssget "X" '((0 . "INSERT") (66 . 1)))
sl (sslength ss)
So you have a selection list of all the blocks in the dwg with attributes.
Some of the blocks have tags "CIRCUIT" and "TCIRCUIT" and "SCIRCUIT"
These tags contain values like "1" "2" "MS3" etc
I would like to create a new list containing all the blocks with those 3 tags
containing a value "2" for example.
So I assume you have to work through the "SS" list 3 times collecting the blocks
containing the target values and then append them into a new list.
Then run your main program using that new list. If I run my main program having manually
selected the blocks I want it works fine. So I assume if I create a new list
with just the blocks I want that will solve the problem.
I don't want to have to manually select the blocks because I could miss some and they are difficult
to find on a cluttered dwg. Any help to understand lists would be much appreciated.
Solved! Go to Solution.
Solved by hmsilva. Go to Solution.
Hi robd,
one way to get a selection set with the INSERTS that have the three TAGs and Values...
Untested...
(vl-load-com) (defun c:demo (/ get_atts att att_lst enm i ss) ;; Function to build a dotted pair list from attributes ;; '((TAG . value)(TAG . value)) (defun get_atts (enm / att obj) (if (or (and (eq (type enm) 'ENAME) (setq obj (vlax-ename->vla-object enm)) (eq (vla-get-hasattributes obj) :vlax-true) ) (and (eq (type enm) 'VLA-OBJECT) (setq obj enm) (eq (vla-get-hasattributes obj) :vlax-true) ) ) (mapcar '(lambda (att) (cons (vla-get-TagString att) (vla-get-TextString att)) ) (vlax-invoke obj "GetAttributes") ) ) ) ;; ------- Main code ------- ;; test for a valid selection set (if (setq ss (ssget "_X" '((0 . "INSERT") (66 . 1)))) ;; if valid, then (progn ;;repeat the number of inserts in the ss selection set (repeat (setq i (sslength ss)) ;; get the insert ename using the index i ;; starting from the last and subtracting ;; one in each repetition (setq enm (ssname ss (setq i (1- i)))) ;; get a list with all attributes and values ;; using get_atts and as argument the ename (setq att_lst (get_atts enm)) ;; test if all the three TAGs and Values are not members from the list (if (not (and (vl-position '("CIRCUIT" . "3") att_lst) (vl-position '("TCIRCUIT" . "3") att_lst) (vl-position '("SCIRCUIT" . "3") att_lst) ) ) ;; delet that ename from ss selection set (ssdel enm ss) ) ) ;; test if selection set length is bigger then 0 (if (> (sslength ss) 0) ;; if true (progn ;; here you process the selection set ;; I did use the sssetfirst only as a visual aid... (sssetfirst nil ss) ) ;; if not true (alert "The current dwg don't have INSERTS with the three TAGs and Values... ") ) ) ;; if there is no valid selection set (alert "The current dwg don't have INSERTS with ATRIBUTES... ") ) (princ) )
Hope this helps,
Henrique
Thank you Henrique,
I'll have a go with yours, I have been trying ssadd but can't get that to work see below, very frustrated!
**********************
;Set Make new slection set of all blocks containing specified circuit
(defun trap (er) ;error trapping
(princ "\nPROGRAM ABORTED ")
(princ er)
(setq *error* olderr)
(princ)
)
(defun c:makelist (/ newlist)
(graphscr)
(setq olderr *error*
*error* trap)
(setq chkcircuit (getstring 2 "\nEnter circuit.. "))
(setq ss (ssget "X" '((0 . "INSERT") (66 . 1)))
sl (sslength ss)
ct 0
ctr 0)
(repeat sl
(setq e1 (ssname ss ct))
(setq ck 2)
(while (not (equal ck "SEQEND"))
(setq e1 (entnext e1)
e2 (entget e1)
ck (cdr (assoc 0 e2)))
(if (= (cdr (assoc 2 e2)) "CIRCUIT") ;check for CIRCUIT attribute
(progn
(if (= (cdr (assoc 1 e2)) chkcircuit) ;make sure this blocks CIRCUIT is value in chkcircuit
(progn
(setq newlist (ssadd (cdr (assoc -1 e2)))) ;have tried many variations of this line
(setq lgth (sslength newlist))
(print lgth)
(setq ctr (+ ctr 1))
)
)
)
)
)
(setq ct (+ ct 1))
)
(princ ctr)
(princ " Blocks were added to new list: ")
(princ circuit)
(restore)
)
Hi robd,
it's not a list, it is a selection set...
Untested...
(defun c:test (/ chkcircuit circuit ck ct ctr e1 e2 lgth newss sl ss) (if (and (setq chkcircuit (getstring 2 "\nEnter circuit.. ")) (setq ss (ssget "X" '((0 . "INSERT") (66 . 1)))) ) (progn (setq sl (sslength ss) ct 0 ctr 0 ;; start a new selection set newss (ssadd) ) (repeat sl (setq e1 (ssname ss ct)) (setq ck 2) (while (not (equal ck "SEQEND")) (setq e1 (entnext e1) e2 (entget e1) ck (cdr (assoc 0 e2)) ) (if (= (cdr (assoc 2 e2)) "CIRCUIT") ;check for CIRCUIT attribute (if (= (cdr (assoc 1 e2)) chkcircuit) ;make sure this blocks CIRCUIT is value in chkcircuit (progn (ssadd (ssname ss ct) newss) ; add to selection set ss1 (setq lgth (sslength newss)) (print lgth) (setq ctr (+ ctr 1)) ) ) ) ) (setq ct (+ ct 1)) ) (princ "\n"); new line (princ ctr) (princ " Blocks were added to new selection set: ") ;(princ circuit) ) ) (princ) )
Hope this helps,
Henrique
That looks so good and neat! Can't wait to try it first thing tomorrow morning, thank you so much Henrique......
YES! it works I appended my working program that depended on picking the fittings with the required circuits to your program which created the new selection set depending on a specified circuit and it works perfectly now. Simply entering a circuit number sets all the fittings with that circuit number to a new circuit and control. I'm sure that process of creating a new selection set will be very useful in autolisp, Thank you again Henrique!
Can't find what you're looking for? Ask the community or share your knowledge.