Jump to content

Lisp to create specific pline at specified point


jweber

Recommended Posts

I'm doing my best to learn lisp, and have a desire to write a lisp to draw a pline at a specified point, and then choose to orient that entity right or left.

 

(defun c:bb (/ cm sm op ang c1 c2)
 (setq cm (getvar 'CMDECHO))
 (setvar 'CMDECHO 0)  
 (setq sm (getvar 'OSMODE))  
 (setq op (getpoint "\nSelect insertion point"))
 (setq ang (getangle op "\nWhich way? "))
 (cond ((< ang 1.57079)
        (setq c1 (list (+(car op) 0.75)(cadr op) 0.0))
        (setq c2 (list (car c1)(+(cadr c1) -8.0) 0.0))
        (setvar 'OSMODE 0)
       )
       ((> ang 1.57079)
        (setq c1 (list (+(car op) -0.75)(cadr op) 0.0))
        (setq c2 (list (car c1)(+(cadr c1) -8.0) 0.0))
        (setvar 'OSMODE 0)
       )
 )

 (command "_pline" op c1 c2 "")

 (setvar 'OSMODE sm)
 (setvar 'CMDECHO cm)
(princ)
)

 

I've managed to write the above code to achieve my desired result, but for the sake of learning, I'm asking for some input on achieving the same result as above, but with better code. Specifically, if I could, say, create a rectangle, or any other object by specifying the insertion point, but then be able to choose any angle to orient that entity around the insertion point, that would be awesome!

 

My goal in asking is to learn- like I said, I wrote the above code to achieve my goal, but would like to learn more- so if any answers could contain at least some guidance, I would be grateful. Thanks!!

Link to comment
Share on other sites

I think I would lean towards something like this :

 

[b][color=BLACK]([/color][/b]defun c:bb2 [b][color=FUCHSIA]([/color][/b]/ op an c1 c1 pl ed[b][color=FUCHSIA])[/color][/b]
 [b][color=FUCHSIA]([/color][/b]initget 1[b][color=FUCHSIA])[/color][/b]
 [b][color=FUCHSIA]([/color][/b]setq op [b][color=NAVY]([/color][/b]getpoint [color=#2f4f4f]"\nInsertion Point:   "[/color][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]initget 1[b][color=FUCHSIA])[/color][/b]
 [b][color=FUCHSIA]([/color][/b]setq an [b][color=NAVY]([/color][/b]getangle op [color=#2f4f4f]"\nDirection Angle:   "[/color][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]cond [b][color=NAVY]([/color][/b][b][color=MAROON]([/color][/b]<= [b][color=GREEN]([/color][/b]* pi 0.5[b][color=GREEN])[/color][/b] an [b][color=GREEN]([/color][/b]* pi 1.5[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b]
        [b][color=MAROON]([/color][/b]setq c1 [b][color=GREEN]([/color][/b]polar op pi 0.75[b][color=GREEN])[/color][/b]
              c2 [b][color=GREEN]([/color][/b]polar c1 [b][color=BLUE]([/color][/b]* pi 1.5[b][color=BLUE])[/color][/b] 8.0[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b]
       [b][color=NAVY]([/color][/b]T
        [b][color=MAROON]([/color][/b]setq c1 [b][color=GREEN]([/color][/b]polar op 0.0 0.75[b][color=GREEN])[/color][/b]
              c2 [b][color=GREEN]([/color][/b]polar c1 [b][color=BLUE]([/color][/b]* pi 0.5[b][color=BLUE])[/color][/b] 8.0[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]setq pl [b][color=NAVY]([/color][/b]list op c1 c2[b][color=NAVY])[/color][/b]
       ed [b][color=NAVY]([/color][/b]list [b][color=MAROON]([/color][/b]cons 0 [color=#2f4f4f]"LWPOLYLINE"[/color][b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 100 [color=#2f4f4f]"AcDbEntity"[/color][b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 100 [color=#2f4f4f]"AcDbPolyline"[/color][b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 90 [b][color=GREEN]([/color][/b]length pl[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]
  [b][color=FUCHSIA]([/color][/b]foreach v [b][color=NAVY]([/color][/b]reverse pl[b][color=NAVY])[/color][/b]
     [b][color=NAVY]([/color][/b]setq ed [b][color=MAROON]([/color][/b]append ed [b][color=GREEN]([/color][/b]list [b][color=BLUE]([/color][/b]cons 10 v[b][color=BLUE])[/color][/b][b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]
  [b][color=FUCHSIA]([/color][/b]entmake ed[b][color=FUCHSIA])[/color][/b]
  [b][color=FUCHSIA]([/color][/b]prin1[b][color=FUCHSIA])[/color][/b][b][color=BLACK])[/color][/b]

 

 

HTH -David

Link to comment
Share on other sites

Thanks David- I appreciate your input, especially the use of pi (I couldn't quite seem to get the correct punctuation when I tried) and the polar function. Would you mind explaining how the last part of the code actually draws the p-line? I don't see how c1 and c2, etc. are implemented...

Link to comment
Share on other sites

This would the static version

 

[b][color=BLACK]([/color][/b]defun c:bb3 [b][color=FUCHSIA]([/color][/b]/ op an c1 c2 ed[b][color=FUCHSIA])[/color][/b]
 [b][color=FUCHSIA]([/color][/b]initget 1[b][color=FUCHSIA])[/color][/b]
 [b][color=FUCHSIA]([/color][/b]setq op [b][color=NAVY]([/color][/b]getpoint [color=#2f4f4f]"\nInsertion Point:   "[/color][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]initget 1[b][color=FUCHSIA])[/color][/b]
 [b][color=FUCHSIA]([/color][/b]setq an [b][color=NAVY]([/color][/b]getangle op [color=#2f4f4f]"\nDirection Angle:   "[/color][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]cond [b][color=NAVY]([/color][/b][b][color=MAROON]([/color][/b]<= [b][color=GREEN]([/color][/b]* pi 0.5[b][color=GREEN])[/color][/b] an [b][color=GREEN]([/color][/b]* pi 1.5[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b]
        [b][color=MAROON]([/color][/b]setq c1 [b][color=GREEN]([/color][/b]polar op pi 0.75[b][color=GREEN])[/color][/b]
              c2 [b][color=GREEN]([/color][/b]polar c1 [b][color=BLUE]([/color][/b]* pi 1.5[b][color=BLUE])[/color][/b] 8.0[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b]
       [b][color=NAVY]([/color][/b]T
        [b][color=MAROON]([/color][/b]setq c1 [b][color=GREEN]([/color][/b]polar op 0.0 0.75[b][color=GREEN])[/color][/b]
              c2 [b][color=GREEN]([/color][/b]polar c1 [b][color=BLUE]([/color][/b]* pi 0.5[b][color=BLUE])[/color][/b] 8.0[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]setq ed [b][color=NAVY]([/color][/b]list [b][color=MAROON]([/color][/b]cons 0 [color=#2f4f4f]"LWPOLYLINE"[/color][b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 100 [color=#2f4f4f]"AcDbEntity"[/color][b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 100 [color=#2f4f4f]"AcDbPolyline"[/color][b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 90 3[b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 10 op[b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 10 c1[b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 10 c2[b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]
  [b][color=FUCHSIA]([/color][/b]entmake ed[b][color=FUCHSIA])[/color][/b]
  [b][color=FUCHSIA]([/color][/b]prin1[b][color=FUCHSIA])[/color][/b][b][color=BLACK])[/color][/b]

 

 

With bb2, the point list pl can be dynamic, any number of vertices ( min 2 )

 

You could also add starting and ending widths for the pline very easily

 

Arc segments ( bulges ) would be much more difficult.

 

HTH -David

Link to comment
Share on other sites

David, Thanks again- having multiple examples of code that vary with key differences is the most effective way for me to understand and write lisp's of my own, so I'm thankful for your time!

Link to comment
Share on other sites

You're welcome.

 

This is pretty much how I learned to code. Only it was before the internet was supported by any decent peer to peer forums, only Compuserve and Cadalyst magazine. And then there where various hard copy books ( my preference )

 

It is still best to learn by one's self motivation ( IMHO ). Just look what Lee Mac has accomplished since maybe 2009.

 

And thank CadTutor for providing this site for support and supervision for an open forum that is not full of flames and personal conflicts.

 

Feel free to make inquiries and / or explanations. This is a great resource for your education.

 

-David

Link to comment
Share on other sites

@BIGAL, Thanks for your input!! Again, more examples of code to achieve a result is so helpful!

 

Through some exercises, I've found some ways to build on David's code which might be helpful-

 

To create a pline and then close it, adding the following code, after (entmake ed) will achieve that.

   (setq cp (vlax-ename->vla-object (entlast)))
  (vla-put-closed cp :vlax-true)

 

Adding the following code, after (cons 100 "AcDbPolyline") (order matters) will specify a layer for the pline

(cons 8 "YOUR_LAYER_NAME")

 

And if you want to select the previously created pline for manipulation, say, to use it in a TRIM command, add the following code, after (entmake ed)

   (setq tr (entlast))
  (command "trim" tr "" pause)

 

------Here's a new inquiry- We are using POLAR to draw the pline, but how would you go about creating an entity, a rectangle for example, at a user specified insertion point AND user specified angle? For the sake of this thread, could we create it using the above method for creating a pline and closing it? Is it possible (or feasible) to have the constructed entity rotate visibly with the cursor (around the insertion point), the same as the ROTATE command? Not sure if what I'm asking is possible, just interested! Thanks!!!!

Link to comment
Share on other sites

Re Rectang do just that use the Rectang command in a lisp it only needs two points so, base point, angle, length of side or length of angle line. Rotate use Rotate "Last" and base pt. Which method for the rectang ?

Link to comment
Share on other sites

Here goes-- In an attempt to try and pay forward some of what I've gained from this site, I've built on much of the code in this thread to build a useful example. This lisp asks for two user points (lower left corner and upper right corner of a rectangle) and then constructs 4 closed lwpolylines (window trim for example) around the rectangle.

(defun c:wt (/ tw p1 p2 p3 p4 p5 p6 p7 p8 p9 p10 r1 r2 r3 r4 c1 ed) ;;Window Trim
 (initget 1)
 (setq pll (getpoint "\nLower Left Corner: ")
       pur (getpoint "\nUpper Right Corner: "))
 

 (setq tw 3 ;; Specify Trim Width
    	p1 (polar pll pi tw)
       p2 (polar pur 0.0 tw)
p3 (list (car pur)(cadr pll) 0.0)
p4 (list (car pll)(cadr pur) 0.0)
p5 (polar p4 pi tw)
p6 (polar p3 0.0 tw)
p7 (polar p2 (/ pi 2) tw)
p8 (polar p5 (/ pi 2) tw)
p9 (polar p1 (* pi 1.5) tw)
p10 (polar p6 (* pi 1.5) tw)

r1 (list p1 pll p4 p5)
r2 (list p3 pur p2 p6)
r3 (list p2 p5 p8 p7)
r4 (list p1 p6 p10 p9)
       )
 (foreach x (list r1 r2 r3 r4)
    (setq c1 x
          ed (list (cons 0 "LWPOLYLINE")
                   (cons 100 "AcDbEntity")
                   (cons 100 "AcDbPolyline")
                   (cons 8 "LINE-THIN")
                   (cons 90 (length c1))
            (cons 70 1)))
    (foreach v (reverse c1)   
      (setq ed (append ed (list (cons 10 v)))))
    (entmake ed))  
 (princ))

window_trim.jpg

Edited by jweber
Link to comment
Share on other sites

Re Rectang do just that use the Rectang command in a lisp it only needs two points so, base point, angle, length of side or length of angle line. Rotate use Rotate "Last" and base pt. Which method for the rectang ?

 

Ok, so a rectangle was a poor example; pick any number of objects someone would need, a pline with 3 or 5 or 10 vertices. My thought on the angle was choosing an angle, in the same fashion as David's first code, but rather than drawing orthagonally like he did there, using the chosen angle to base the pline on... --->

  
 (setq op (getpoint "\nInsertion Point:   "))
 (setq an (getangle op "\nDirection Angle: "))
 (setq c1 (polar op an 0.75)
       c2 (polar c1 (+ (/ pi 2) an) 8.0))

:ouch:As I was considering what I was asking, I think I answered my own question. I was just thinking there was another (better) way, but that seems to do what I had in mind...

Link to comment
Share on other sites

RE Rectangle

 

There is a lot of ways to skin that cat :

 

[color=#8b4513];;;ROTATED LWPOLYLINE RECTANGLE[/color]
[b][color=BLACK]([/color][/b]defun c:bb4 [b][color=FUCHSIA]([/color][/b]/ ll ur dl da mp ul lr ra rll rlr rur rul pl ed[b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]initget 1[b][color=FUCHSIA])[/color][/b]
 [b][color=FUCHSIA]([/color][/b]setq ll [b][color=NAVY]([/color][/b]getpoint [color=#2f4f4f]"\nLower Left:   "[/color][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]
 [b][color=FUCHSIA]([/color][/b]setq ll [b][color=NAVY]([/color][/b]list [b][color=MAROON]([/color][/b]car ll[b][color=MAROON])[/color][/b] [b][color=MAROON]([/color][/b]cadr ll[b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]initget 1[b][color=FUCHSIA])[/color][/b]
 [b][color=FUCHSIA]([/color][/b]setq ur [b][color=NAVY]([/color][/b]getcorner ll [color=#2f4f4f]"\nUpper Right:   "[/color][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]setq dl [b][color=NAVY]([/color][/b]distance ll ur[b][color=NAVY])[/color][/b]
       da [b][color=NAVY]([/color][/b]angle ll ur[b][color=NAVY])[/color][/b]
       mp [b][color=NAVY]([/color][/b]polar ll da [b][color=MAROON]([/color][/b]* dl 0.5[b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b]
       ul [b][color=NAVY]([/color][/b]polar ll [b][color=MAROON]([/color][/b]* pi 0.5[b][color=MAROON])[/color][/b] [b][color=MAROON]([/color][/b]* dl [b][color=GREEN]([/color][/b]sin da[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b]
       lr [b][color=NAVY]([/color][/b]polar ll [b][color=MAROON]([/color][/b]* pi 0.0[b][color=MAROON])[/color][/b] [b][color=MAROON]([/color][/b]* dl [b][color=GREEN]([/color][/b]cos da[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]grdraw ll ur 1 6[b][color=FUCHSIA])[/color][/b]
 [b][color=FUCHSIA]([/color][/b]grvecs [b][color=NAVY]([/color][/b]list -1 ll lr -2 lr ur -3 ur ul -4 ul ll[b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]initget 1[b][color=FUCHSIA])[/color][/b]
 [b][color=FUCHSIA]([/color][/b]setq ra [b][color=NAVY]([/color][/b]getangle mp [color=#2f4f4f]"\nRectangle Rotation Angle:   "[/color][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]setq rll [b][color=NAVY]([/color][/b]polar mp [b][color=MAROON]([/color][/b]+ [b][color=GREEN]([/color][/b]angle mp ll[b][color=GREEN])[/color][/b] ra[b][color=MAROON])[/color][/b] [b][color=MAROON]([/color][/b]distance mp ll[b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b]
       rlr [b][color=NAVY]([/color][/b]polar mp [b][color=MAROON]([/color][/b]+ [b][color=GREEN]([/color][/b]angle mp lr[b][color=GREEN])[/color][/b] ra[b][color=MAROON])[/color][/b] [b][color=MAROON]([/color][/b]distance mp lr[b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b]
       rur [b][color=NAVY]([/color][/b]polar mp [b][color=MAROON]([/color][/b]+ [b][color=GREEN]([/color][/b]angle mp ur[b][color=GREEN])[/color][/b] ra[b][color=MAROON])[/color][/b] [b][color=MAROON]([/color][/b]distance mp ur[b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b]
       rul [b][color=NAVY]([/color][/b]polar mp [b][color=MAROON]([/color][/b]+ [b][color=GREEN]([/color][/b]angle mp ul[b][color=GREEN])[/color][/b] ra[b][color=MAROON])[/color][/b] [b][color=MAROON]([/color][/b]distance mp ul[b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]setq pl [b][color=NAVY]([/color][/b]list rll rlr rur rul[b][color=NAVY])[/color][/b]
       ed [b][color=NAVY]([/color][/b]list [b][color=MAROON]([/color][/b]cons 0 [color=#2f4f4f]"LWPOLYLINE"[/color][b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 100 [color=#2f4f4f]"AcDbEntity"[/color][b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 8 [color=#2f4f4f]"LINE-THIN"[/color][b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 100 [color=#2f4f4f]"AcDbPolyline"[/color][b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 90 [b][color=GREEN]([/color][/b]length pl[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 70 1[b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 38 0[b][color=MAROON])[/color][/b]
                [b][color=MAROON]([/color][/b]cons 39 0[b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]foreach v [b][color=NAVY]([/color][/b]reverse pl[b][color=NAVY])[/color][/b]
     [b][color=NAVY]([/color][/b]setq ed [b][color=MAROON]([/color][/b]append ed [b][color=GREEN]([/color][/b]list [b][color=BLUE]([/color][/b]cons 10 v[b][color=BLUE])[/color][/b][b][color=BLUE]([/color][/b]cons 40 0[b][color=BLUE])[/color][/b][b][color=BLUE]([/color][/b]cons 41 0[b][color=BLUE])[/color][/b][b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]entmake ed[b][color=FUCHSIA])[/color][/b]

 [b][color=FUCHSIA]([/color][/b]prin1[b][color=FUCHSIA])[/color][/b][b][color=BLACK])[/color][/b]

 

 

-David

Link to comment
Share on other sites

Is this correct?:

(cons 90 (+ 1 (length c1)))

I added that because after adding (cons 70 1), I was receiving an error, and I assumed it may have had to do with not having enough vertices. Adding that allowed me to create a closed lwpolyline, but I just went back and checked again, and I must have fixed it elsewhere, because now it works with (cons 90 (length cl))).

 

I will update my code, thanks!

Link to comment
Share on other sites

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...