Alter LISP Routine to work for multiple object selection

Alter LISP Routine to work for multiple object selection

DanielBellLSTC
Participant Participant
1,131 Views
9 Replies
Message 1 of 10

Alter LISP Routine to work for multiple object selection

DanielBellLSTC
Participant
Participant

Hi all,

 

Total novice at writing LISP routines, so advice is appreciated.

 

I use the attached routine (produced by another user, ASMI) to extract the XYZ coordinate information of 3D polylines and write them out into a CSV format.

 

It's very useful, but the snag is that to extract multiple objects to the same CSV file you must rerun the command and click each 3D polyline individually. Each selected line is then added to the end of the CSV file with an XYZ header line (example attached.)

 

It would be so much more efficient if i could multi select/window select multiple objects and the routine does exactly the same job of creating the attached example without having to click multiple times.

 

Anyone have any thoughts, or can anyone alter the routine to account for this?

 

Many thanks in advance!

 

Dan

 

 

0 Likes
Accepted solutions (1)
1,132 Views
9 Replies
Replies (9)
Message 2 of 10

EnM4st3r
Advocate
Advocate

instead of entsel use ssget and then process the selectionset.
Preferably open and close the file outside of the ss processing to avoid repeatedly opening and closing the same file

0 Likes
Message 3 of 10

EnM4st3r
Advocate
Advocate

to get the selectionset you can use ssget with filter for polylines so:

 

(setq ss (ssget '((0 . "POLYLINE"))))

 

 This you could process like this: (or any other selectionset processing method)

 

(setq ss (ssget '((0 . "POLYLINE"))))
(setq i 0)
(while (< i (sslength ss))
  (setq ent (ssname ss i)) ; ent is your single polyline like cPl in your original code
  
  ; your code here 
  
  (setq i (1+ i))
)

 

So within that while you could use your Extract_3DPoly_Vertexes and the write-line functions

0 Likes
Message 4 of 10

CADaSchtroumpf
Advisor
Advisor

Might this interest you?

(defun l-coor2l-pt (lst flag / )
  (if lst
    (cons
      (list
        (car lst)
        (cadr lst)
        (if flag
          (+ (if (vlax-property-available-p ename 'Elevation) (vlax-get ename 'Elevation) 0.0) (caddr lst))
          (if (vlax-property-available-p ename 'Elevation) (vlax-get ename 'Elevation) 0.0)
        )
      )
      (l-coor2l-pt (if flag (cdddr lst) (cddr lst)) flag)
    )
  )
)
(defun c:ptdef2csv ( / ss dxf_cod mod_sel n lremov file_name cle f_open key_sep str_sep oldim ename l_pt l_pr nbs)
  (princ "\nChoosing a model object for filtering: ")
  (while
    (null
      (setq ss
        (ssget "_+.:E:S"
          (list
            '(0 . "*LINE,POINT,ARC,CIRCLE,ELLIPSE,INSERT")
            (cons 67 (if (eq (getvar "CVPORT") 1) 1 0))
            (cons 410 (if (eq (getvar "CVPORT") 1) (getvar "CTAB") "Model"))
          )
        )
      )
    )
    (princ "\nThis is not a valid object for this function!")
  )
  (vl-load-com)
  (setq dxf_cod (entget (ssname ss 0)))
  (foreach m (foreach n dxf_cod (if (not (member (car n) '(0 67 410 8 6 62 48 420 70))) (setq lremov (cons (car n) lremov))))
    (setq dxf_cod (vl-remove (assoc m dxf_cod) dxf_cod))
  )
  (initget "Single All Manual")
  (if (eq (setq mod_sel (getkword "\nFiltered selection mode, choice [Single/All/Manual]<Manual>: ")) "Single")
    (setq n -1)
    (if (eq mod_sel "All")
        (setq ss (ssget "_X" dxf_cod) n -1)
        (setq ss (ssget dxf_cod) n -1)
    )
  )
  (setq file_name (getfiled "Name of the file to create ?: " (strcat (substr (getvar "dwgname") 1 (- (strlen (getvar "dwgname")) 3)) "csv") "csv" 37))
  (if (null file_name) (exit))
  (if (findfile file_name)
    (progn
      (prompt "\nFile already exists!")
      (initget "Add Replace Cancel")
      (setq cle
        (getkword "\nData in file? [Add/Replace/Cancel] <R>: ")
      )
      (cond
        ((eq cle "Add")
          (setq cle "a")
        )
        ((or (eq cle "Replace") (eq cle ()))
          (setq cle "w")
        )
        (T (exit))
      )
      (setq f_open (open file_name cle))
    )
    (setq f_open (open file_name "w"))
  )
  (initget "SPace Comma SEmicolon Tab")
  (setq key_sep (getkword "\nSeparator [SPace/Comma/SEmicolon/Tab]? <SEmicolon>: "))
  (cond
    ((eq key_sep "SPpace") (setq str_sep " "))
    ((eq key_sep "Comma") (setq str_sep ","))
    ((eq key_sep "Tab") (setq str_sep "\t"))
    (T (setq str_sep ";"))
  )
; (setq str_sep (vl-registry-read "HKEY_CURRENT_USER\\Control Panel\\International" "sList"))
  (setq oldim (getvar "dimzin"))
  (setvar "dimzin" 0)
  (write-line (strcat "Handle" str_sep "registration number" str_sep "Entity Type" str_sep "X coordinate" str_sep "Y coordinate" str_sep "Z coordinate") f_open)
  (repeat (sslength ss)
    (setq ename (vlax-ename->vla-object (ssname ss (setq n (1+ n)))) l_pt nil)
    (setq l_pr (list 'StartPoint 'EndPoint 'Center 'InsertionPoint 'Coordinates 'FitPoints) nbs 0)
    (foreach n l_pr
      (if (vlax-property-available-p ename n)
        (setq l_pt
          (if (or (eq n 'Coordinates) (eq n 'FitPoints))
            (append
              (if (eq (vla-get-ObjectName ename) "AcDbPolyline")
                (l-coor2l-pt (vlax-get ename n) nil)
                (if (and (eq n 'FitPoints) (zerop (vlax-get ename 'FitTolerance)))
                  (l-coor2l-pt (vlax-get ename 'ControlPoints) T)
                  (l-coor2l-pt (vlax-get ename n) T)
                )
              )
              l_pt
            )
            (cons (vlax-get ename n) l_pt)
          )
        )
      )
    )
    (foreach n l_pt
      (write-line
        (strcat
          "'" (vlax-get ename 'Handle) str_sep
          (itoa (setq nbs (1+ nbs))) str_sep
          (vlax-get ename 'ObjectName) str_sep
          (rtos (car n) 2 3) str_sep
          (rtos (cadr n) 2 3) str_sep
          (rtos (caddr n) 2 3)
        )
        f_open
      )
    )
    (write-line "" f_open)
  )
  (close f_open)
  (setvar "dimzin" oldim)
  (prin1)
)
0 Likes
Message 5 of 10

DanielBellLSTC
Participant
Participant
Hi,
Thanks for this; sorry that i'm a total newb, but would you mind being a bit more specific as to how i would implement this?
I have the sad issue of knowing exactly what i want but not the knowledge of how i get it haha
0 Likes
Message 6 of 10

DanielBellLSTC
Participant
Participant
Hi, thanks for this.
I would initially like to just retrofit a solution to the existing system due to familiarity, but if that's not achievable i will definitely give this a go !
0 Likes
Message 7 of 10

Kent1Cooper
Consultant
Consultant

Try the attaced revision [UNTESTED].

I put two semicolons ;; at the beginning of lines in the original that are no longer applicable, and I put two semicolons ;; at the ends of lines I added or altered or repositioned.

It asks the User to select objects [accepting only 3D Polylines, so you could window a whole area, etc.], but it could easily be made to find all 3D Polylines in the drawing for you, without User selection.  That would mean it could do it over multiple spaces without changing space to be able to pick things.

Kent Cooper, AIA
0 Likes
Message 8 of 10

DanielBellLSTC
Participant
Participant
Hi there,
ALMOST perfect! The selection is right and the CSV comes out nicely, the only issue is i still need the XYZ line breaks between each entity/3D polyline......we have a modeler that reads this data and separates the coordinates from the CSV into individual "strings" and it needs that XYZ line to differentiate them.
0 Likes
Message 9 of 10

Kent1Cooper
Consultant
Consultant
Accepted solution

Ah -- I misunderstood.  An easy adjustment -- try the attached tweak.

Kent Cooper, AIA
0 Likes
Message 10 of 10

DanielBellLSTC
Participant
Participant
Absolutely spot on!
Thanks very much.....your notes in the file are a help as well.
0 Likes