Jump to content

Recommended Posts

Posted

I have a model in autocad where i want to have autolisp select a group of blocks defined either by location relative to the WCS or a customized UCS, and then rotate them 90 degrees relative to the current UCS. I am trying to use SSGET to select the blocks, but I cant seem to get the syntax right. For example, I want to be able to have autocad select all objects where their base points are located at Z > 0.

 

I was able to define the selection set in both filters and in qselect but I dont see any way to have autocad run those functions through the command prompt making those efforts futile.

Any help would greatly be appreciated.

  • Replies 33
  • Created
  • Last Reply

Top Posters In This Topic

  • Lee Mac

    16

  • Stermaj

    16

  • SEANT

    2

Posted

Perhaps:

 

(defun c:selObj (/ ss ent)
 (if (setq ss (ssget "X" (list (cons 0 "INSERT")
                               (if (getvar "CTAB")(cons 410 (getvar "CTAB"))
                                 (cons 67 (- 1 (getvar "TILEMODE")))))))
   (progn
     (foreach ent (mapcar 'cadr (ssnamex ss))
       (if (not (> (cadddr (assoc 10 (entget ent))) 0))
         (ssdel ent ss)))
     (if (not (zerop (sslength ss)))
       (command "_rotate" ss "" pause pause)))
   (princ "\n<!> No Blocks Found <!>"))
 (princ))

Posted

Wow that did exactly what i needed it to do. Thank you so much for your help!

Posted

No Probs,

 

If you have any questions on the code - just shout :D

 

Lee

Posted

I modified your code for each axis by changing the CADDDR to CADDR and CADR so I can use it for each axis as necessary. I noticed though that if a block is moved by one function to say, below the z axis, running the code again still selects that block even though its z position is negative now. Am i missing something that would clear the list and have it rescan to determine which blocks meet the criteria to be selected?

Posted

Not sure I quite follow you - the selection set is localised, so is set to nil upon completion of the function.

Posted

I am animating a rubiks cube, and I am writing commands to rotate sides. Basically, I loaded both lisp files and then i manually run each command. running the oranger function rotates all the blocks located at higher than 10 in the z axis (the orange side of the cube), then i run redr and it rotates the blocks found lower than -10 in the y axis (the red side of the cube). if i run oranger again, it selects the same block set it did the first time oranger ran even though redr switched blocks around. What this means for the cube is, some blocks that are no longer on the orange face are still being selected for some reason, while others on the orange side are not. The blocks that do get selected end up being slid though blocks that are stationary. The following is the code i have for the selection and rotation. the c:COLORucs commands call another function that simply establishes a ucs so the rotation occurs in the correct plane.

 

Thanks again for all your help!

-Jon

 

 

(defun c:yellowr ()

(setq oldosn (getvar "osmode"))

(setvar "osmode" 0)

(c:yellowucs)

(setq pt1 (LIST 0 0 0))

 

(if (setq ss (ssget "X" (list (cons 0 "INSERT")

(if (getvar "CTAB")(cons 410 (getvar "CTAB"))

(cons 67 (- 1 (getvar "TILEMODE")))))))

(progn

(foreach ent (mapcar 'cadr (ssnamex ss))

(if (not (

(ssdel ent ss)))

(if (not (zerop (sslength ss)))

(repeat 9

(command "_rotate" ss "" pt1 -10)

)

)

)

(princ "\n No Blocks Found "))

(setvar "osmode" oldosn)

)

 

(defun c:oranger ()

(setq oldosn (getvar "osmode"))

(setvar "osmode" 0)

(c:orangeucs)

(setq pt1 (LIST 0 0 0))

 

(if (setq ss (ssget "X" (list (cons 0 "INSERT")

(if (getvar "CTAB")(cons 410 (getvar "CTAB"))

(cons 67 (- 1 (getvar "TILEMODE")))))))

(progn

(foreach ent (mapcar 'cadr (ssnamex ss))

(if (not (> (cadddr (assoc 10 (entget ent))) 10))

(ssdel ent ss)))

(if (not (zerop (sslength ss)))

(repeat 9

(command "_rotate" ss "" pt1 -10)

)

)

)

(princ "\n No Blocks Found "))

(setvar "osmode" oldosn)

)

 

(defun c:redr ()

(setq oldosn (getvar "osmode"))

(setvar "osmode" 0)

(c:reducs)

(setq pt1 (LIST 0 0 0))

 

(if (setq ss (ssget "X" (list (cons 0 "INSERT")

(if (getvar "CTAB")(cons 410 (getvar "CTAB"))

(cons 67 (- 1 (getvar "TILEMODE")))))))

(progn

(foreach ent (mapcar 'cadr (ssnamex ss))

(if (not (

(ssdel ent ss)))

(if (not (zerop (sslength ss)))

(repeat 9

(command "_rotate" ss "" pt1 -10)

)

)

)

(princ "\n No Blocks Found "))

(setvar "osmode" oldosn)

)

 

(defun c:purpler ()

(setq oldosn (getvar "osmode"))

(setvar "osmode" 0)

(c:purpleucs)

(setq pt1 (LIST 0 0 0))

 

(if (setq ss (ssget "X" (list (cons 0 "INSERT")

(if (getvar "CTAB")(cons 410 (getvar "CTAB"))

(cons 67 (- 1 (getvar "TILEMODE")))))))

(progn

(foreach ent (mapcar 'cadr (ssnamex ss))

(if (not (> (caddr (assoc 10 (entget ent))) 10))

(ssdel ent ss)))

(if (not (zerop (sslength ss)))

(repeat 9

(command "_rotate" ss "" pt1 -10)

)

)

)

(princ "\n No Blocks Found "))

(setvar "osmode" oldosn)

)

Posted

OK, try this - I have commented the code as to the possible errors:

 

(defun c:yellowr  (/ oldosn ss)  ;;  Make sure you localise the variables!
 (setq oldosn (getvar "osmode"))
 (setvar "osmode" 0)
 (yellowucs)  ; Shouldn't need (c:xxx), just (xxx)
 (if (setq ss (ssget "X"
                     (list (cons 0 "INSERT")
                           (if (getvar "CTAB")
                             (cons 410 (getvar "CTAB"))
                             (cons 67 (- 1 (getvar "TILEMODE")))))))
   (progn
     (foreach ent  (mapcar 'cadr (ssnamex ss))
       (if (not (< (cadddr (assoc 10 (entget ent))) -10)) ;; Z value less than -10
         (ssdel ent ss)))
     (if (not (zerop (sslength ss)))
       (repeat 9
         (command "_rotate" ss "" '(0 0 0) -10))))  ; Don't feel the need for variable "pt1"
   (princ "\n<!> No Blocks Found <!>"))
 (setvar "osmode" oldosn)
 (princ))  ; Make sure you exit cleanly

(defun c:oranger  (/ oldosn ss)
 (setq oldosn (getvar "osmode"))
 (setvar "osmode" 0)
 (orangeucs)
 (if (setq ss (ssget "X"
                     (list (cons 0 "INSERT")
                           (if (getvar "CTAB")
                             (cons 410 (getvar "CTAB"))
                             (cons 67 (- 1 (getvar "TILEMODE")))))))
   (progn
     (foreach ent  (mapcar 'cadr (ssnamex ss))
       (if (not (> (cadddr (assoc 10 (entget ent))) 10)) ;; Z value greater than 10
         (ssdel ent ss)))
     (if (not (zerop (sslength ss)))
       (repeat 9
         (command "_rotate" ss "" '(0 0 0) -10))))
   (princ "\n<!> No Blocks Found <!>"))
 (setvar "osmode" oldosn)
 (princ))

(defun c:redr  (/ oldosn ss)
 (setq oldosn (getvar "osmode"))
 (setvar "osmode" 0)
 (reducs)
 (if (setq ss (ssget "X"
                     (list (cons 0 "INSERT")
                           (if (getvar "CTAB")
                             (cons 410 (getvar "CTAB"))
                             (cons 67 (- 1 (getvar "TILEMODE")))))))
   (progn
     (foreach ent  (mapcar 'cadr (ssnamex ss))
       (if (not (< (caddr (assoc 10 (entget ent))) -10)) ;; Y value less than -10
         (ssdel ent ss)))
     (if (not (zerop (sslength ss)))
       (repeat 9
         (command "_rotate" ss "" '(0 0 0) -10))))
   (princ "\n<!> No Blocks Found <!>"))
 (setvar "osmode" oldosn)
 (princ))

(defun c:purpler  (/ oldosn ss)
 (setq oldosn (getvar "osmode"))
 (setvar "osmode" 0)
 (purpleucs)
 (if (setq ss (ssget "X"
                     (list (cons 0 "INSERT")
                           (if (getvar "CTAB")
                             (cons 410 (getvar "CTAB"))
                             (cons 67 (- 1 (getvar "TILEMODE")))))))
   (progn
     (foreach ent  (mapcar 'cadr (ssnamex ss))
       (if (not (> (caddr (assoc 10 (entget ent))) 10)) ;; Y value greater than 10
         (ssdel ent ss)))
     (if (not (zerop (sslength ss)))
       (repeat 9
         (command "_rotate" ss "" '(0 0 0) -10))))
   (princ "\n<!> No Blocks Found <!>"))
 (setvar "osmode" oldosn)
 (princ))

Make sure that you localise your variables so that they are set to nil when the program completes.

 

You have used "ss" in every code, so this could be causing the problem.

 

Also, remember to add "princ" to exit cleanly.

 

Let me know how you get on. :)

 

Lee

Posted

I tried that, its still shifting the wrong blocks. It doesnt seem to do it consistently though. For every function, if its the 1st one i try, then it works, but things break down once i start doing several after eachother. Is there a way i can send u the autocad file itself? its too large for the forum limits.

UCS.lsp

rotation.lsp

Posted

I would use this:

 

You don't need a new ucs function for every colour if they are all doing the same thing - just one function requiring an argument.

 

Also, the variable ss was not localised in the first function.

 

One more thing, why the repeats? why not just rotate by 90 degrees?

rotation.lsp

Posted

Well for the UCS's i plan on having other commands refer to them so i thought i might as well make it a separate function but i guess i can switch those back. as far as the repeats goes, i wanted to give it a frame rate so you can watch the sides as they turn instead of it instantly shifting. I did correct the initializing ss in the 1st function though, thanks for the catch. In your original code, i am wondering, what does the part of the code in that first if statement do:

 

(if (setq ss (ssget "X" (list (cons 0 "INSERT")

(if (getvar "CTAB")(cons 410 (getvar "CTAB"))

(cons 67 (- 1 (getvar "TILEMODE")))))))

 

I know ssget "x" selects everything, but i dont follow what the rest does. Thanks again for all your help, i really appreciate it. Is there a way i can send u the dwg file?

Posted

You can zip the file, or send it to my email address which I shall PM to you :)

 

As for the other bit of code:

 

[b][color=RED]([/color][/b][b][color=BLUE]if[/color][/b] [b][color=RED]([/color][/b][b][color=BLUE]setq[/color][/b] ss [b][color=RED]([/color][/b][b][color=BLUE]ssget[/color][/b] [b][color=#ff00ff]"X"[/color][/b]  [i][color=#990099]; Scan the whole Database[/color][/i]
                   [b][color=RED]([/color][/b][b][color=BLUE]list[/color][/b]  [i][color=#990099]; Make a Filter List[/color][/i]
                     [b][color=RED]([/color][/b][b][color=BLUE]cons[/color][/b] [b][color=#009900]0[/color][/b] [b][color=#ff00ff]"INSERT"[/color][/b][b][color=RED])[/color][/b]  [i][color=#990099]; Get Blocks (and Xrefs)[/color][/i]
                         [b][color=RED]([/color][/b][b][color=BLUE]if[/color][/b] [b][color=RED]([/color][/b][b][color=BLUE]getvar[/color][/b] [b][color=#ff00ff]"CTAB"[/color][/b][b][color=RED])[/color][/b]  [i][color=#990099]; If there is a variable CTAB[/color][/i]
                           [b][color=RED]([/color][/b][b][color=BLUE]cons[/color][/b] [b][color=#009900]410[/color][/b] [b][color=RED]([/color][/b][b][color=BLUE]getvar[/color][/b] [b][color=#ff00ff]"CTAB"[/color][/b][b][color=RED])[/color][/b][b][color=RED])[/color][/b] [i][color=#990099]; Use it[/color][/i]
                           [b][color=RED]([/color][/b][b][color=BLUE]cons[/color][/b] [b][color=#009900]67[/color][/b] [b][color=RED]([/color][/b][b][color=BLUE]-[/color][/b] [b][color=#009900]1[/color][/b] [b][color=RED]([/color][/b][b][color=BLUE]getvar[/color][/b] [b][color=#ff00ff]"TILEMODE"[/color][/b][b][color=RED])[/color][/b][b][color=RED])[/color][/b][b][color=RED])[/color][/b][b][color=RED])[/color][/b][b][color=RED])[/color][/b][b][color=RED])[/color][/b][b][color=RED])[/color][/b]  [i][color=#990099]; Otherwise use TILEMODE[/color][/i]

 

 

AutoCAD R14 didn't have CTAB, so to set the space you have to use TILEMODE, hence I have accounted for all versions.

Posted

I can't seem to PM you - I think you may have restricted it on your accout - try zipping the dwg file.

Posted

I posted the file to a website i run:

nyu.edu/clubs/shalhevet/Cube_8.dwg

Posted

I think I may have cracked it-- didn't need the file after all really.

 

I think there may be one thing we're overlooking, when you retrieve the selectionset, the points that are referenced and tested in the IF statement are in WCS not UCS (just thought you might not be aware)....

 

Not sure if that affects things..

Posted

I planned for that, i actually reset the UCS to the WCS before running ssget just in case there would be a conflict, and then later only when it does the rotation does it restore the specific ucs for that case, and that really is only to establish the plane of rotation.

Posted

Well I'm stumped as to why its not performing as you want it to.

 

There is nothing else I can think of that would be causing it to fail. - when you run each function, it is the same as if you had run only the one, so I can't see how one function would be affecting the other. :huh:

Posted

Could it be that the coordinates of each block aren't being updated in the database? If so, is there possibly another set of criteria for the selection process?

Posted
Could it be that the coordinates of each block aren't being updated in the database? If so, is there possibly another set of criteria for the selection process?

 

No I don't think that would be the case.

 

I'm puzzled, as each function is a stand-alone function, then you could have manually rotated those blocks, and then run the function and it would be the same circumstances.

 

Perhaps try this - rotate the blocks manually as if you were running one of the functions, then try running a different function.

 

Other than that, i'm out of ideas :(

 

Lee

Posted

Yeah, rotating the blocks manually, and then running one of the functions still causes problems. could the lookup criteria be the issue?

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.


×
×
  • Create New...