Jump to content

Lisp to insert points along polyline at endpoints & midpoints


Quango1

Recommended Posts

Hi,

 

I've been looking for a while for the solutions to this and haven't come across one yet.

is there a lisp routine that will automatically places points at every endpoint and midpoint of a polyline?

 

I know C3D has an option to do this for just the endpoints but not aware if there is one for both mid and endpoints.

 

Thanks,

Link to comment
Share on other sites

Should be what your looking for.

 

(defun C:PP (/ SS vla SPT MPT EPT)
  (prompt "\nSelect Polylines")
  (if (setq SS (ssget '((0 . "*POLYLINE"))))
    (foreach poly (vl-remove-if 'listp (mapcar 'cadr (ssnamex SS)))
      (setq vla (vlax-ename->vla-object poly)
            SPT (vlax-curve-getStartPoint vla)
            MPT (vlax-curve-getPointAtDist vla (/ (vlax-get-property vla 'length) 2.0))
            EPT (vlax-curve-getendpoint vla)
      )
      (entmake (list '(0 . "POINT") (cons 10 SPT)))
      (entmake (list '(0 . "POINT") (cons 10 MPT)))
      (entmake (list '(0 . "POINT") (cons 10 EPT)))
    )
  )
  (princ)
)

 

Edited by mhupp
dang princ
  • Like 3
Link to comment
Share on other sites

Another way to approach the same goal.

(defun c:Test ( / sel int ent get )
  ;; Tharwat - 8.Feb.2022	;;
  (and (princ "\nSelect polylines to locate points on end points and center : ")
       (setq int -1 sel (ssget '((0 . "LWPOLYLINE"))))
       (while (setq int (1+ int) ent (ssname sel int))
         (setq get (entget ent))
         (foreach pt (list (cdr (assoc 10 get))
                           (cdr (assoc 10 (reverse get)))
                           (vlax-curve-getpointatdist ent (/ (vlax-curve-getdistatpoint ent
                                                               (vlax-curve-getendpoint ent)) 2.0)))
           (entmake (list '(0 . "POINT") (cons 10 pt)))
           )
         )
       )
  (princ)
  ) (vl-load-com)

 

  • Like 1
Link to comment
Share on other sites

Thanks for getting back to me, I think I misworded what I needed the lisp to do.

 

is it possible for the points to be placed at every node on the polyline as well as the midpoint between the vertices? 

For example:

image.thumb.png.3599f5defff43951070830ade7ef7da6.png

Link to comment
Share on other sites

18 hours ago, Quango1 said:

 

I know C3D has an option to do this for just the endpoints but not aware if there is one for both mid and endpoints.

 

Hi
Which version C3D  are you working on?

Link to comment
Share on other sites

Try this, 

 

It works by drawing temporary plines each 1 element of your selection, and using Tharwats code to plot points at their end and mid points.

 

EDITED... it adds multiple points at the end of each vertex, just need to do a small modification later

 

Apparently Tuesdays I have to work as well as Monday, who knew? Will come back to look at this later

 

 

(defun c:test ( / endpoint curve midpoints ss acount mycount ent entdesc pt)
  (vl-load-com)
;;Get verticies, Points: 10 and Curve: 42
  (princ "\nSelect polylines : ")
  (setq ss (ssget '((0 . "LWPOLYLINE"))))
  (setq acount 0)
  (while (< acount (sslength ss))
    (setq endpoint (list))
    (setq curve (list))
    (setq ent (ssname ss acount))
    (setq entdesc (entget ent))

    (foreach x entdesc
      (if (= (car x) 10) (setq endpoint (append endpoint (list (cdr x)))) )
      (if (= (car x) 42) (setq curve (append curve (list (cdr x)))) )
    )

;;Make temporary plines & get mid points
    (setq mycount 1)
    (while (< mycount (length endpoint))
      (entmake (list (cons 0 "LWPOLYLINE")
                 (cons 100 "AcDbEntity")
                 (cons 100 "AcDbPolyline")
                 (cons 90 2)
                 (cons 70 0)
                 (cons 10 (nth (- mycount 1) endpoint))
                 (cons 42 (nth (- mycount 1) curve))
                 (cons 10 (nth mycount endpoint))
      )) ;;end entmake
      (setq ent (entlast))
      (setq get (entget ent))

;;From Tharwart
      (foreach pt (list (cdr (assoc 10 get))
        (vlax-curve-getpointatdist ent (/ (vlax-curve-getdistatpoint ent (vlax-curve-getendpoint ent)) 2.0)))
        (entmake (list '(0 . "POINT") (cons 10 pt)))
      ) ;end for each

      (entdel ent) ;;delete temp pline
      (setq mycount (+ mycount 1))
    ) ; end while

    (entmake (list '(0 . "POINT") (cons 10 (last endpoint))))
    (setq acount (+ acount 1))
  ) ; end while
  (princ)
)

 

Edited by Steven P
  • Like 2
Link to comment
Share on other sites

I think this should be enough. < untested >. :) 

(defun c:Test ( / sel int ent get inc)
  ;;----------------------------------------------------;;
  ;; Author : Tharwat Al Choufi	- 8.Feb.2022		;;
  ;; website: https://autolispprograms.wordpress.com	;;
  ;;----------------------------------------------------;;
  (and (princ "\nSelect polylines to locate points on end and mid points : ")
       (setq int -1 sel (ssget '((0 . "LWPOLYLINE"))))
       (while (setq int (1+ int) ent (ssname sel int))
         (setq get (entget ent)
               inc -1
               )
         (foreach pt get
           (and (= (car pt) 10)
                (setq inc (1+ inc))
                (foreach ins (list (vlax-curve-getpointatparam ent inc)
                                   (vlax-curve-getpointatparam ent (- inc 0.5))
                                   )
                  (and ins (entmake (list '(0 . "POINT") (cons 10 ins))))
                  )
                )
           )
         )
       )
  (princ)
  ) (vl-load-com)

 

  • Like 2
Link to comment
Share on other sites

1 hour ago, devitg said:

What DYNAMO stand for ??

Dynamo is an addon program in addition to Civil 3D It works fun and free to change In the code with better results

 Uses Api or com api for cad or civil 3d 

Link to comment
Share on other sites

On 2/8/2022 at 10:29 AM, Steven P said:

It works by drawing temporary plines each 1 element of your selection, and using Tharwats code to plot points at their end and mid points.

 

@Steven P When I read this it reminded me of something i came across in visual lisp. the funcion vlax-invoke with 'explode does explode the selected item into individual entity's. but it also leaves the original too. this builds off that and takes the start point and mid point of each entity. Then deletes them leaving only the original polyline and points.

 

2 problems arc's starting point seems to be depended of something other then the polyline direction.

   And if you select an open polyline the end pt isn't created.

 

Uses thwarts point creation

(defun C:Foo (/ SS)
  (vl-load-com)
  (princ "\nSelect polylines : ")
  (setq SS (ssget '((0 . "LWPOLYLINE"))))
  (foreach e (vl-remove-if 'listp (mapcar 'cadr (ssnamex SS)))
    (setq poly (vlax-invoke (vlax-ename->vla-object e) 'explode))
    (foreach ent poly
      (foreach pt (list (vlax-curve-getStartPoint ent) ;Tharwat
                  (vlax-curve-getpointatdist ent (/ (vlax-curve-getdistatpoint ent (vlax-curve-getendpoint ent)) 2.00)))
          (entmake (list '(0 . "POINT") (cons 10 pt)))
      ) ;end foreach
      (vla-delete ent)
    )   ;end foreach
  )     ;end foreach
  (princ)
)
  • Like 2
Link to comment
Share on other sites

Another:

(defun c:foo (/ n p s)
  (if (setq s (ssget '((0 . "LWPOLYLINE"))))
    (foreach e (vl-remove-if 'listp (mapcar 'cadr (ssnamex s)))
      (setq n 0)
      (while (setq p (vlax-curve-getpointatparam e n))
	(entmakex (list '(0 . "POINT") (cons 10 p)))
	(setq n (+ n 0.5))
      )
    )
  )
  (princ)
)

 

Edited by ronjonp
  • Like 5
Link to comment
Share on other sites

  • 1 year later...
On 08/02/2022 at 16:56, Tharwat said:

I think this should be enough. < untested >. :) 

(defun c:Test ( / sel int ent get inc)
  ;;----------------------------------------------------;;
  ;; Author : Tharwat Al Choufi	- 8.Feb.2022		;;
  ;; website: https://autolispprograms.wordpress.com	;;
  ;;----------------------------------------------------;;
  (and (princ "\nSelect polylines to locate points on end and mid points : ")
       (setq int -1 sel (ssget '((0 . "LWPOLYLINE"))))
       (while (setq int (1+ int) ent (ssname sel int))
         (setq get (entget ent)
               inc -1
               )
         (foreach pt get
           (and (= (car pt) 10)
                (setq inc (1+ inc))
                (foreach ins (list (vlax-curve-getpointatparam ent inc)
                                   (vlax-curve-getpointatparam ent (- inc 0.5))
                                   )
                  (and ins (entmake (list '(0 . "POINT") (cons 10 ins))))
                  )
                )
           )
         )
       )
  (princ)
  ) (vl-load-com)

 

Hi,

 

This is great and will save me a lot of time, i am very new to lisps and coding etc, how would someone modify the above to only put points at the endpoints and not midpoints?

 

Thanks very much.

 

Tom

Link to comment
Share on other sites

9 hours ago, Tomh111 said:

Hi,

 

This is great and will save me a lot of time, i am very new to lisps and coding etc, how would someone modify the above to only put points at the endpoints and not midpoints?

 

Thanks very much.

 

Tom

Glad to hear that. :) 

Here is the modified codes for you to work only with the original vertices of selected polylines.

(defun c:Test (/ sel int ent get)
  ;;----------------------------------------------------;;
  ;; Author : Tharwat Al Choufi	- 8.Feb.2022		;;
  ;; website: https://autolispprograms.wordpress.com	;;
  ;;----------------------------------------------------;;
  (and (princ "\nSelect polylines to locate points on vertices : ")
       (setq int -1 sel (ssget '((0 . "LWPOLYLINE"))))
       (or (not (zerop (getvar 'PDMODE))) (setvar 'PDMODE 3))
       (while (setq int (1+ int)
                    ent (ssname sel int)
              )
         (setq get (entget ent))
         (foreach pt get
           (and (= (car pt) 10)
                (entmake (list '(0 . "POINT") pt))
           )
         )
       )
  )
  (princ)
)

 

  • Like 1
Link to comment
Share on other sites

  • 4 weeks later...

Hello @Tharwat

 

Would you mind helping me with a similar but complex problem? I need to add small lines (45º angle relative to polyline) only on outwards vertex of polylines like this:

 

image.png.f1a1984b8ff48770304ae2499e9ca3da.png

 

Also if selected object is a circle I need to add 4 small lines in 45º angle like this:

image.png.3a585fd2759f8ece1651d6366ac7cb88.png

 

Hope you can help me here!

 

Regards,

Pablo

Link to comment
Share on other sites

Hello, to add these oriented 45 deg. lines is simple on circles but on polylines needs more codes with entirely different approach. 

Sorry I am busy at the meantime. 

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