PDA

View Full Version : Select blocks by name and insertion point?


keelay711
2005-01-05, 12:52 AM
OK, I admit it... LISP is kicking my... I am getting totally confused about using "ssget" and manipulating dotted pair lists...

Here's the question:
How do I select all blocks named "Myblock" that have their insertion points outside of a given circle's radius?

I am looking at a solution using Pythagorean Theorem, where I find the distance from the center of the circle to the insertion point of each block, and then compare to the circle's center. The math is simple enough, but I haven't the foggiest idea how to code it.

(setq selection_set (ssget "x" '(2 . "Myblock") (10 . ???)))
??? needs to be outside the circle.

Please help me. If I can get this tool to work (as part of a larger program), it would alleviate alot of headaches in the office. When the program is complete, I will post it with complete documentation for ya'll to laugh at.

RobertB
2005-01-05, 01:06 AM
I cannot think of a way to do it by a circle. A rectangle, sure, but not a circle.

It would be better to gather the full selection set of Myblock, then iterate thru the set, removing items that fall inside your circle.

kennet.sjoberg
2005-01-05, 01:24 AM
( selection_set (ssget "x" '(2 . "Myblock") (10 . ???)))
??? needs to be outside the circle.
hmmm.. You have to reformulate,,, the (10 . ???) IS the insertionpoint of the block,

You may find all "MyBlock" with the ssget option "x", and the center of any circle
and do the phytagoras with some of the closest block to the circle . . .
but is that an option ? Do You have many blocks and circles ?

: ) Happy Computing !

kennet

ps.
moderators, is anybody working to find the problem with the [ Spell Check ] ?
see forum feedback
ds.

Mike.Perry
2005-01-05, 09:13 AM
ps.
moderators, is anybody working to find the problem with the [ Spell Check ] ? see forum feedback
ds.Hi Kennet

Please refer to Richard Binning's latest response on this matter -

RE: Spell Checker gone bad? (http://forums.augi.com/showthread.php?p=76146#post76146)

Thanks, Mike

Forum Moderator

kennet.sjoberg
2005-01-05, 02:09 PM
How do I select all blocks named "Myblock" that have their insertion points outside of a given circle's radius?

..ooohh yes, You can select all "MyBlock" with the ssget "x" option,
then check each of them if the distance from the block origo to the selected circle origo is less than the circle radius.
If that is true you simple exclude the block from the selectionset, all other blocks is outside the circle.
Here is a working code for You to start with :

(setq SelSet (ssget "X" '((0 . "INSERT" ) (2 . "MyBlock" ))) )
(setq CirEnt (entsel "Please choose the circle : " ))
(setq CirOrg (cdr (assoc 10 (entget (car CirEnt )))) )
(setq CirRad (cdr (assoc 40 (entget (car CirEnt )))) )
(setq Index 0 )
(while (ssname SelSet Index )
(setq BlOrg (cdr (assoc 10 (entget (ssname SelSet Index )))) )
(if (< (distance CirOrg BlOrg ) CirRad )
(progn
(ssdel (ssname SelSet Index ) SelSet )
(setq Index Index ) ; jump the index
)
(progn
(princ (strcat "\nBlock number " (itoa Index ) " is outside the circle" ) )
(setq Index (1+ Index ) ) ; step the index
)
)
)

You can try if the selection is ok with :
(command "._select" SelSet "" ) and (command "._move" "P" "" )

: ) Happy Computing !

kennet

keelay711
2005-01-27, 09:53 PM
Thanks for you help everyone. I havent had much opportunity to lisp for awhile. Too much "real" work getting in the way. Yall know how that is.

Here's the basic deal I was trying to solve. I wanted to create an array of column within a circular boundary.
I was initially trying to program as I draft it: IE: array the block to my best guess of how many rows/columns, then erase any blocks that landed outside my boundary.

With the computer doing he work now, perhaps a better way would be to avoid array all together...

Check point (origin+X, origin+Y), if inside the boundary, then insert block.
Check point (origin+2X, origin+Y), etc... until point is found to be outside boundary... then
Check point (origin+X, origin+2Y)..etc
Check point (origin+2X, origin+2Y)..etc
Continue to check each point until Y is false (outside of boundary), then exit out of loop

Could do this for each quadrant of the circle, or then mirror a selection set of the blocks from the circle origin.

Am I making any sense to anyone? I just haven't yet found the time to learn the keys of lisp to get this to work.

Thank you for any and all help past and present.

keelay711
2005-01-27, 09:56 PM
Thanks for you help everyone. I havent had much opportunity to lisp for awhile. Too much "real" work getting in the way. Yall know how that is. This program is quite complex (for me). I will try to incorporate the code you have generously offered.

If it helps at all, I shall attempt to clarify again.

Here's the basic deal I was trying to solve. I wanted to create an array of column within a circular boundary.
I was initially trying to program as I draft it: IE: array the block to my best guess of how many rows/columns, then erase any blocks that landed outside my boundary.

With the computer doing he work now, perhaps a better way would be to avoid array all together...

Check point (origin+X, origin+Y), if inside the boundary, then insert block.
Check point (origin+2X, origin+Y), etc... until point is found to be outside boundary... then
Check point (origin+X, origin+2Y)..etc
Check point (origin+2X, origin+2Y)..etc
Continue to check each point until Y is false (outside of boundary), then exit out of loop

Could do this for each quadrant of the circle, or then mirror a selection set of the blocks from the circle origin.

Am I making any sense to anyone? I just haven't yet found the time to learn the keys of lisp to get this to work.

Thank you for any and all help past and present.

kennet.sjoberg
2005-01-28, 12:22 AM
OK keelay711

1. Cut and past my code in to Notepad
2. Replace ( in line 1 ) "MyBlock" with the name of the block you are trying to insert inside the " ".
3. In AutoCAD create a circle that represent the boundary for the array.
4. Copy and paste the code from Notepad [Ctrl+A] [Ctrl+C] into AutoCads Command window ( ..yes ! ) [Ctrl+V]
5. and select the circle that represent the boundary for the array you created earlier.
If you have named your block name correct, and selected the newly created boundary circle
you will have all the blocks inside the selected boundary circle bind to SelSet = previous.

You can try in AutoCADs command window, if the selected blocks are the one you want, by typing
Command: (command "._move" "P" "" ) or (command "._erase" "P" "" ) just to see if the selected blocks are OK.

If OK, it is a piece of cake to make a comfortable command of the code, do not hesitate to respond

: ) Happy Computing !

kennet

( please, do not bee sulky if the post is to ... careful )

bhaugi
2006-10-11, 07:49 PM
Thanks to Mike Perry for a link to this thread and for all who responded... nearly 2 years later drilled through and found this to resolve a similar problem I was having, which was trying to select a specific block on a layer, ultimately to delete.

Bruce

kennet.sjoberg
2006-10-11, 10:20 PM
. . .select a specific block on a layer, ultimately to delete.
Hi Bruce, this code do erase all "MyBlock" on "MyLayer"

(command "._erase" (ssget "_X" '((0 . "INSERT")(2 . "MyBlock")(8 . "MyLayer"))) "" )


: ) Happy Computing !

kennet

T.Willey
2006-10-11, 11:07 PM
Hi Bruce, this code do erase all "MyBlock" on "MyLayer"

(command "._erase" (ssget "_X" '((0 . "INSERT")(2 . "MyBlock")(8 . "MyLayer"))) "" )


: ) Happy Computing !

kennet
FYI.....
Not if they are not in the current space (layout). If you run this from model space, and you have some inserted in paper space, the paper space will not be erased.

kennet.sjoberg
2006-10-11, 11:46 PM
FYI.....
Not if they are not in the current space (layout). If you run this from model space, and you have some inserted in paper space, the paper space will not be erased.
I know that, and that is good sometimes

: ) Happy Computing !

kennet

bhaugi
2006-10-12, 04:56 PM
FYI.....
Not if they are not in the current space (layout). If you run this from model space, and you have some inserted in paper space, the paper space will not be erased.

Good point. Thanks again for everyone's input.

Bruce

kpblc2000
2006-10-13, 07:01 AM
Try this:
(defun blockerase (block-name)
(vl-load-com)
(if (tblobjname "block" block-name)
(progn
(foreach ent
(mapcar
'vlax-ename->vla-object
(vl-remove-if
'listp
(mapcar
'cadr
(ssnamex
(ssget "_X" (list (cons 0 "INSERT") (cons 2 block-name)))
) ;_ end of ssnamex
) ;_ end of mapcar
) ;_ end of vl-remove-if
) ;_ end of mapcar
(vl-catch-all-apply '(lambda () (vla-erase ent)))
) ;_ end of foreach
(repeat 2 (vla-purgeall (vla-get-activedocument (vlax-get-acad-object))))
) ;_ end of progn
) ;_ end of if
(princ)
) ;_ end of defun
Call parameters: block-name - name of erasing block.

T.Willey
2006-10-13, 05:37 PM
kpblc200

I don't think this line will work.
(vl-catch-all-apply '(lambda () (vla-erase ent)))
I think it has to be
(vl-catch-all-apply '(lambda () (vla-Delete ent)))

kpblc2000
2006-10-16, 06:17 AM
May be, but (vla-erase) works correctly...

T.Willey
2006-10-16, 05:46 PM
May be, but (vla-erase) works correctly...
You are correct. I learned something new. Thanks.

peter
2006-10-17, 02:03 PM
If you know the circle and have its entitiy name or object you can create a selection set using this routine.

objCircle is the circle object or entity name and the sngIncrement is the number of facets of the cross polyline. The larger the more accurate, the smaller the faster. It just turns the circle into a multifaceted polygon that closely approximates the circle.



With this and the other help you have recieved you can create the large selection set and remove the selection set created by this routine and you have it.

The syntax is for example: (SSCircle (car (entsel "\nSelect Circle: ")) 100)

Peter


(defun SSCircle (objCircle sngIncrement / lstPoints sngStep)
(if (= (type objCircle) 'ENAME)
(setq objCircle (vlax-ename->vla-object objCircle)))
(setq sngStep (/ (* 2 pi) sngIncrement)
sngPosition 0.0
)
(repeat sngIncrement
(setq lstPoints (cons (vlax-curve-getpointatparam objCircle sngPosition) lstPoints)
sngPosition (+ sngPosition sngStep)
)
)
(ssget "cp" lstPoints)
)