Need to select several times to make 2 blocks

Need to select several times to make 2 blocks

Anonymous
Not applicable
859 Views
8 Replies
Message 1 of 9

Need to select several times to make 2 blocks

Anonymous
Not applicable

Hi masters!!

 

I am trying to make a lisp to make 2 blocks of a single selection. I will be using it for rebar reinforcement plans.

 

The issue comes when need to select until 4 times the drawing so it can make the blocks. And the last step to move the circles to another layer doesnt work.

 

In the first step i make a block of horizontal rebars

Second setp i do the same for vertical rebars

3rd step is to move all the circles in 4 layers to another layer. It seems not working because the blocks are already done.

 

Does anyone how to solve it?

 

I am working with autocad in spanish, so some parts are wrotten to work in spanish.

 

 

Thanks in advance!

0 Likes
860 Views
8 Replies
Replies (8)
Message 2 of 9

ronjonp
Mentor
Mentor

If you want to change the layer, perhaps us "LA" instead of "C" ?

  ;;(command "_chprop" circx "" "C" "_EST-ARM-REP" "")
  (command "_chprop" circx "" "LA" "_EST-ARM-REP" "")

Try this:

(defun c:blk (/ blocknamex blocknamey circx circy longitudinal numberx numbery transversal)
					;BLOCK FOR REBARS IN X
  (if
    (and (setq longitudinal
		(ssget
		  '((8
		     .
		     "_EST-4-arm_sup_X,_EST-4-arm_sup_X_rot,_EST-2-arm_inf_X,_EST-2-arm_inf_X_rot,_EST-2-arm_inf_X_dist,_EST-2-arm_inf_X_linea,_EST-4-arm_sup_X_dist,_EST-4-arm_sup_X_linea"
		    )
		   )
		)
	 )
	 (setq circx (ssget '((0 . "circle") (8 . "_EST-2-arm_inf_X_linea,_EST-4-arm_sup_X_linea"))))
    )
     (progn ;; moved the chprop before they are turned into a block
	    (command "_chprop" circx "" "LA" "_EST-ARM-REP" "")
	    (setq numberx 1
		  blocknamex
		   (strcat "ARM_LONG" (itoa numberx))
	    )
	    (while (tblsearch "BLOCK" blocknamex)
	      (setq blocknamex (strcat "ARM_LONG" (itoa (setq numberx (1+ numberx)))))
	    )
	    (command "_.-Block" blocknamex "0,0" longitudinal "")
	    (command "_.-insert" blocknamex "0,0" "" "" "")
     )
  )					;BLOCK FOR REBARS IN Y
  (if
    (and (setq transversal
		(ssget
		  '((8
		     .
		     "_EST-3-arm_inf_Y,_EST-3-arm_inf_Y_dist,_EST-3-arm_inf_Y_linea,_EST-3-arm_inf_Y_rot,_EST-5-arm_sup_Y,_EST-5-arm_sup_Y_dist,_EST-5-arm_sup_Y_linea,_EST-5-arm_sup_Y_rot"
		    )
		   )
		)
	 )
	 (setq circy (ssget '((0 . "circle") (8 . "_EST-3-arm_inf_Y_linea,_EST-5-arm_sup_Y_linea"))))
    )
     (progn ;; moved the chprop before they are turned into a block
	    (command "_chprop" circy "" "LA" "_EST-ARM-REP" "")
	    (setq numbery 1
		  blocknamey
		   (strcat "ARM_TRANS" (itoa numbery))
	    )
	    (while (tblsearch "BLOCK" blocknamey)
	      (setq blocknamey (strcat "ARM_TRANS" (itoa (setq numbery (1+ numbery)))))
	    )
	    (command "_.-Block" blocknamey "0,0" transversal "")
	    (command "_.-insert" blocknamey "0,0" "" "" "")
     )
  )
  (princ)
)

 

Message 3 of 9

Anonymous
Not applicable

Thanks for your help @ronjonp . It works!

 

But i need to select 4 times all the items so it may make the blocks. Maybe because there are 4 SSGET functions? Is there any way to use SSGET of a parameter?

 

_chprop must be in spanish. So it mus be, otherwhise it doesnt work. 

(command "_chprop" circx "" "C" "_EST-ARM-REP" "")

I will leave the DWG so you could see what i need. Also the last LISP with the "C" modification

 

Thank you!

 

0 Likes
Message 4 of 9

ВeekeeCZ
Consultant
Consultant

Use an underscore prior to English expressions in commands to make it work in Spanish acad.

Note: Fix X vs Y, long vs trans... I've probably mixed it up.

Not tested. Your dwg is too complex for me to recognize if the result is correct.

 

(defun c:blk ( / ss sp n bn)

  (if (setq ss (ssget (list (cons 8 (strcat
				      "_EST-4-arm_sup_X,_EST-4-arm_sup_X_rot,_EST-2-arm_inf_X,_EST-2-arm_inf_X_rot,_EST-2-arm_inf_X_dist,_EST-2-arm_inf_X_linea,_EST-4-arm_sup_X_dist,_EST-4-arm_sup_X_linea,"
				      "_EST-3-arm_inf_Y,_EST-3-arm_inf_Y_dist,_EST-3-arm_inf_Y_linea,_EST-3-arm_inf_Y_rot,_EST-5-arm_sup_Y,_EST-5-arm_sup_Y_dist,_EST-5-arm_sup_Y_linea,_EST-5-arm_sup_Y_rot")))))
    (progn

      (setvar 'clayer "0") ; set current layer which blocks will be inserted to.
            
      (if (and (setq sp (ssget "_P" '((0 . "CIRCLE") (8 . "_EST-2-arm_inf_X_linea,_EST-4-arm_sup_X_linea,_EST-3-arm_inf_Y_linea,_EST-5-arm_sup_Y_linea"))))
	       (or (tblsearch "LAYER" "_EST-ARM-REP")
		   (vl-cmdf "_.LAYER" "_New" "_EST-ARM-REP" ""))
	       )
	(command "_.CHPROP" sp "" "_Layer" "_EST-ARM-REP" ""))

     (if (setq sp (acet-ss-ssget-filter ss '((8 . "*_Y_*"))))
	(progn
	  (setq n 1
		bn (strcat "ARM_TRANS" (itoa n)))
	  (while (tblsearch "BLOCK" bn)
	    (setq bn (strcat "ARM_TRANS" (itoa (setq n (1+ n))))))

	  (command "_.BLOCK" bn "_non" '(0 0) sp ""
		   "_.INSERT" bn "_Scale" 1 "_Rot" 0 "_non" '(0 0))))

      (if (setq sp (acet-ss-ssget-filter ss '((8 . "*_X_*"))))
	(progn
	  (setq n 1
		bn (strcat "ARM_LONG" (itoa n)))
	  (while (tblsearch "BLOCK" bn)
	    (setq bn (strcat "ARM_LONG" (itoa (setq n (1+ n))))))

	  (command "_.BLOCK" bn "_non" '(0 0) sp ""
		   "_.INSERT" bn "_Scale" 1 "_Rot" 0 "_non" '(0 0))))

      ))
    (princ)
)

 

Message 5 of 9

Kent1Cooper
Consultant
Consultant
....  never mind -- I misunderstood....

This part threw me off:

 

"3rd step is to move all the circles in 4 layers to another layer. It seems not working because the blocks are already done."

 

That made me think the Circles were part of the Blocks, but looking more closely I see they are not.  I don't see what the relationship is between defining the Blocks and the selection sets of Circles.

Kent Cooper, AIA
0 Likes
Message 6 of 9

Kent1Cooper
Consultant
Consultant

@Kent1Cooper wrote:
....  never mind -- I misunderstood....

.... That made me think the Circles were part of the Blocks, but looking more closely I see they are not.  I don't see what the relationship is between defining the Blocks and the selection sets of Circles.


 

Okay, so now  I'm seeing that the Layers for the Circles are among the Layers for the other selection, so the Circles could be [and would be if it can be done with one overall selection] part of the Blocks.

 

BIG QUESTION:

I think you can shortcut a lot of the selection, but it depends on other Layers, etc.  Would this:

(setq ss ; overall selection
(ssget '((8 . "_EST-[2345]-arm_???_[XY],_EST-[24]-arm_???_[XY]_rot,_EST-[24]-arm_???_[XY]_dist,_EST-[24]-arm_???_[XY]_linea")))) ;; [2345] for any of those, ??? for either "inf" or "sup", [XY] for either "X" or "Y"
); setq

find all the things you want in one big overall selection, without also finding things you don't want?  If so, you could step through that and assign the things in it to appropriate sub-sets depending on their Layers and whether they're Circles.  Is that worth pursuing?

Kent Cooper, AIA
0 Likes
Message 7 of 9

Kent1Cooper
Consultant
Consultant

If I am correct in assuming that:
A)  you want the Circles on their original Layers  inside the Block definitions, but also want them to exist afterwards on the other Layer; and

B)  you don't  want the other parts to exist afterwards, since they will be removed in the process of the Block definition [when in a (command) function] and you haven't mentioned anything about keeping them; and

C)  the answer to the BIG QUESTION in my previous Reply is Yes;

then try this [untested]:

(defun c:blk
(/ ss longitudinal circX transversal circY ent edata numberX numberY BlocknameX BlocknameY) (setq ss (ssget '((8 . "_EST-[2345]-arm_@@@_[XY],_EST-[2345]-arm_@@@_[XY]_rot,_EST-[2345]-arm_@@@_[XY]_dist,_EST-[2345]-arm_@@@_[XY]_linea")))) ;; overall single selection -- [2345] for any of those, @@@ for either "inf" or "sup", [XY] for either "X" or "Y" longitudinal (ssadd); initially empty [also next 3 lines] circX (ssadd) transversal (ssadd) circY (ssadd) ); setq (repeat (setq n (sslength ss)); step through selection (setq ent (ssname ss (setq n (1- n))) edata (entget ent); entity data list for type and Layer ); setq (ssadd ent ; put into one of the selection sets (if (wcmatch (cdr (assoc 8 edata)) "*X*") longitudinal ; then transversal ; else ); if ); ssadd (if (member '(0 . "CIRCLE") edata) (ssadd ent ; then -- also put into one of the Circle selection sets (cond ;; [could be simplified to (if) if there would be no Circles on other Layer(s)] ((wcmatch (cdr (assoc 8 edata)) "*X_linea") circX) ((wcmatch (cdr (assoc 8 edata)) "*Y_linea") circY) ); cond ); ssadd ); if [no else -- do nothing if not a Circle] ); repeat ;BLOCK FOR REBARS IN X (setq numberX 1); [slightly shortened way of determining Block name] (while (tblsearch "BLOCK" (setq BlocknameX (strcat "ARM_LONG" (itoa numberX)))) (setq numberX (1+ numberX)) ); while (command "_.Block" BlocknameX "0,0" longitudinal "" "_.insert" BlocknameX "0,0" "" "" "" "_.oops" ; bring back objects used for Block ); command ;BLOCK FOR REBARS IN Y (setq numberY 1) (while (tblsearch "BLOCK" (setq BlocknameY (strcat "ARM_TRANS" (itoa numberY)))) (setq numberY (1+ numberY)) ); while (command "_.Block" BlocknameY "0,0" transversal "" "_.insert" BlocknameY "0,0" "" "" "" "_.oops" ; bring back objects used for Block ); command ;MOVE CIRCLES TO ANOTHER LAYER (command "_.chprop" circX circY "" "_layer" "_EST-ARM-REP" ""
;; can do both sets [remaining from OOPS commands above] together "_.erase" longitudinal transversal "_remove" circX circY ""
;; remove all except Circles ); command (princ) ); defun 

 [If my assumption B) above is incorrect, and you do want the other-than-Circle parts retained afterwards, omit the Erase command line entirely.]

Kent Cooper, AIA
0 Likes
Message 8 of 9

Anonymous
Not applicable

Thank you guys for your help! I managed to solve the lisp. I attache the solution.

 

Thanks @ВeekeeCZ for your lisp. It helped me to see that i dont need so many variable. Also creating the layer, just in the case its not in the drawing. But should be. But there was something i havent been able to find which didnt work correctly. It was working perfectly but some layers were out of the block. Fixed the layers you pointed me, but it still didnt work. 

 

Anyway i used the function?  "acet-ss-ssget-filter ss", to select something of al already stablished selection. But its not marked as blue, so i dont know what it really is. Tried to find information about it but i didnt find anything.

 

@Kent1Cooper yes, the main problem is that the circles were already in the block, so i couldnt move. I didnt know you couldnt change something inside a block instead of you already had a list of items in the block. I wanted set a block with all the elements in X in their original layers, but the circles changed to a different layer: _EST-arm-rep. Thanks for your help!

 

 

 

0 Likes
Message 9 of 9

ВeekeeCZ
Consultant
Consultant

...

Anyway i used the function?  "acet-ss-ssget-filter ss", to select something of al already stablished selection. But its not marked as blue, so i dont know what it really is. Tried to find information about it but i didnt find anything.

...


 

These functions are not build-in and documented but are distributed as part of Express tools. Some of them were documented (I think by users), but that's just a minor part of quite a long list of functions. Look HERE  on theswamp.org.

 

Anyway, it not the only way how to filter a selection set.

The simplist is the one that you can also see in my code...

(setq ss (ssget))

(setq sp (ssget "_P" '((0 . "CIRCLE"))))

...but then the sp become "previous" so...

(setq spp (ssget "_P" '((8 . "0")))) ; from sp now

 

Now you can re-highlight the origial selection...

(sssetfirst nil ss)

(setq sc (ssget "_I" '((0 . "CIRCLE")))) ; from ss

(setq sl (ssget "_I" '((0 . "LINE")))) ; still from ss

 

Or just iterate through a selection set and check (the entity type) manually as Kent did.

 

0 Likes