Copy & rotate the easy way with LISP
In contrast to the .NET example I pointed you to in the last episode of this blog, here is a simple example of a LISP command used to Copy & Rotate objects:
(defun c:copyrotate (/ slset pt1 pt2) (prompt "Select entities to Copy and Rotate:") (setq sset (ssget)) (setq pt1 (getpoint "Specify copy base point:"))(terpri) (setq pt2 (getpoint pt1 "Specify copy second point:"))(terpri) (command ".copy" sset "" pt1 pt1 ".move" sset "" pt1 pt2 ".redraw") (setq pt2 (getpoint "Specify rotate base point:"))(terpri) (command ".rotate" sset "" pt2) )
Now that’s a short program! Like I mentioned above, this “command” combines the Move and Rotate commands in to a single command.
The same program, with comments:
In LISP, the semi-colon marks a comment line, so anything after is not processed.
(defun c:copyrotate (/ slset pt1 pt2) ;defines the Command function “copyrotate” (prompt "Select entities to Copy and Rotate:") ;prompt the user on the Command Line (setq sset (ssget)) ;prompt the user to select objects ;variable containing the objects is “sset” (setq pt1 (getpoint "Specify copy base point:"))(terpri) ;get copy base point “pt1” (setq pt2 (getpoint pt1 "Specify copy second point:"))(terpri) ;get copy second point “pt2” (command ".copy" sset "" pt1 pt1 ".move" sset "" pt1 pt2 ".redraw") ;copy objects in place and move previous away… ;easiest way to copy and rotate a newly created group of objects (setq pt2 (getpoint "Specify rotate base point:"))(terpri) ;get rotate base point... as a side note, ;I prefer to use the base point from the original copy as the rotation center ;to do that, simply remove or comment out the line above “;(setq pt2 “ (command ".rotate" sset "" pt2) ;rotate previously moved group ) ;close the function
To improve the usability of our function, we could add a “while” loop (to keep asking for more selections), and give angular options, turn Osnaps or Ortho on/off, etc…
Is a LISP routine too much?
Having presented this, I will tell you that there are many cases where a LISP routine can be over-kill. If you are simply executing a string of commands that don’t require “manipulation” of the data between functions, or where the entry of data is consistent, then menu macros can be even more efficient than LISP. But, menu macros can’t be designed with choices and they can be “brittle” – that is, easy to break – as they can’t handle errors. My recommendation? Here’s a bit of a hybrid – it’s a one-line LISP routine:
*^c^c(command “Select” pause “copy” “p” “” “@” “@” “move” “p” “” pause pause “rotate” “p” “” “@” pause)
This simple, yet elegant LISP “macro” functions exactly as the program above, with the added automatic function repeat (*^c^c), and gives all the dynamic graphical user feedback of a sophisticated program. Simply add an icon to one of your menus using the CUI interface and plug the line above into the command string, and you have a super cool copy / rotate function.
The right tool for the job
You might be thinking that it’s just as easy to use Grips in BricsCAD and right-click to cycle through all the options. My reply would be to remind you that I’m (really) old school, and while I use Grips often, I also know the Esc key has always been the first key to die from abuse on my keyboard (OK, not really). The main point here is to make sure you are using the right tool for the job, and while there are certainly valid uses for .NET applications, I can’t bring myself to write pages of compiled code when I can do the job cleanly with a few lines of LISP.
Hopefully, this introduction has peaked your interest. I think that you will find some useful tips/suggestions as you dive into the world of LISP. Remember, it’s all about getting your design work done quickly and accurately. What better way than using the features built into BricsCAD to make it work your way?