Jump to content

Need help with Visual lisp with respect to layers, switching to model space, exploding and data extraction.


Chandrakanth
 Share

Recommended Posts

As I am not a great user of AutoCAD and visual lisp on a daily to daily basis, I am looking for help of how to use visual lisp effectively for a smooth work flow at our organization. The following are the points where I need help.

1. To switch on only particular layers of need and leave remaining off.

2. Switching to model space in a layout to access the objects.

3. To explode the objects in a layout.

4. To extract the data of the objects like text, dimension values, content present in the titles and title box in to an excel sheet.

Link to comment
Share on other sites

Hi @Chandrakanth

 

Your topic is very wide, so I'll just start with the #1. There are a couple methods:

 

The first method uses AutoCAD commands and plain AutoLISP to perform the actions. For simplicity this isolate method uses the "ON" and "OFF" for layers since using "FREEZE" has issues with the current active layer and layer "0". Note: Error handling is not included.

;; Method 1 using AutoCAD commands
(defun C:ISLM1 (/ i l ll ls oe ss)
   ;;Mark an Undo
   (command "._Undo" "_Begin")
   ; Save the value of CMDECO system var. and turn it off
   (setq oe (getvar "cmdecho"))
   (setvar "cmdecho" 0)
   ; Prompt to select objects
   (princ "\nSelect objects on Layers to Keep on: ")
   ; If a Selection set is made.
   (if (setq ss (ssget))
      ; iterate through the selection and get the layer names and add to list "ll".
      (repeat (sslength ss)
         (setq l (cdr (assoc 8 (entget (ssname ss (if i i (setq i 0))))))
               i (1+ i)
         )
         (if (not (member l ll))(setq ll (cons l ll)))
      )
   )
   ; If list ll (layer list) exists,
   (if ll
      (progn
         ; turn all the layers off. Respond "Y" to turning off layer "0"
         (command "._-layer" "_OFF" "*" "_y" "")
         ; combine the list of layers into a string separated by commas.
         (setq ls
            (apply 'strcat
               (cons (car ll)(mapcar '(lambda (x)(strcat "," x)) (cdr ll)))
            )
         )
         ; Turn back on the selected layers.
         (command "._-layer" "_ON" ls "")
      )
   )
   ; reset the CMDECHO system variable
   (setvar "cmdecho" oe)
   ; end the undo mark.
   (command "_undo" "_End")
   ; suppress return value (exit quietly)
   (princ)
)

 

The second method uses ActiveX Visual LISP methods. This has less lines of code and does not require CMDECHO to be turned off. Again using OFF and ON for layers to avoid issues with freezing layer "0" and current active layer. Note: Error handling is not included.

(defun C:ISLM2 (/ d i l ll ss)
   ;; Load Visual LISP functionality
   (vl-load-com)
   ; Create an Undo Mark
   (vla-StartUndoMark (setq d (vla-get-activedocument (vlax-get-acad-object))))
   ; Prompt for a selection set
   (princ "\nSelect objects on Layers to Keep on: ")
   ; If items are selected,
   (if (setq ss (ssget))
      ; Create a list of layers from the selection set.
      (repeat (sslength ss)
         (setq l (cdr (assoc 8 (entget (ssname ss (if i i (setq i 0))))))
               i (1+ i)
         )
         (if (not (member l ll))(setq ll (cons l ll)))
      )
   )
   ;; If the layer list exists,
   (if ll
      ;; Iterate through the layer collection and turn off any layer that does not match the layer list.
      (vlax-for l (vla-get-layers d)
         (if (not (member (vla-get-name l) ll))(vla-put-Layeron l :vlax-false))
      )
   )
   ; End the undo mark.
   (vla-EndUndoMark d)
   (princ)
)

 

I hope this helps with your first question. If I have time I will circle around to more.

Edited by pkenewell
corrected typos
Link to comment
Share on other sites

@Chandrakanth

 

7 hours ago, Chandrakanth said:

2. Switching to model space in a layout to access the objects.

3. To explode the objects in a layout.

4. To extract the data of the objects like text, dimension values, content present in the titles and title box in to an excel sheet.

 

Questions for items #2 through 4

#2: You need to explain better what you mean. Are you talking about switching back to to the Model tab, zoomed to the layout window area, or just working in modelspace within the layout viewport? If it is the latter, all you have to do is double-click the left mouse button inside the viewport. 

#3: I do not know what you mean by "Explode" objects in a viewport. You can't explode objects in a viewport. You can switch to Modelspace and explode objects like blocks and polylines. 

#4: This is also a huge topic with several different methods depending on what type of items. For example, for Block attributes (whether blocks or Title Blocks), there are already several programs made for this, from express tools ATTIN and ATTOUT, to others made on this site and several other sources. Do a search on this site and you will find something. Here is an Example by a great contributor to this site - @Lee Mac.

 

Edited by pkenewell
Added example, corrected typos.
Link to comment
Share on other sites

#2 agree use dbl click, or type MS or Mspace. Note Ps or Pspace returns, there are some others as well, if you want to go to "Model" layout can do a shortcut (setvar 'ctab "Model")

 

I have also a GOTO which does as it implies goes to a layout via enter a number, Model is 0.

 

#4 yes can be done and send direct to excel. Like wise do a google lots of times requested.

Edited by BIGAL
Link to comment
Share on other sites

12 hours ago, pkenewell said:

Hi @Chandrakanth

 

Your topic is very wide, so I'll just start with the #1. There are a couple methods:

 

The first method uses AutoCAD commands and plain AutoLISP to perform the actions. For simplicity this isolate method uses the "ON" and "OFF" for layers since using "FREEZE" has issues with the current active layer and layer "0". Note: Error handling is not included.

;; Method 1 using AutoCAD commands
(defun C:ISLM1 (/ i l ll ls oe ss)
   ;;Mark an Undo
   (command "._Undo" "_Begin")
   ; Save the value of CMDECO system var. and turn it off
   (setq oe (getvar "cmdecho"))
   (setvar "cmdecho" 0)
   ; Prompt to select objects
   (princ "\nSelect objects on Layers to Keep on: ")
   ; If a Selection set is made.
   (if (setq ss (ssget))
      ; iterate through the selection and get the layer names and add to list "ll".
      (repeat (sslength ss)
         (setq l (cdr (assoc 8 (entget (ssname ss (if i i (setq i 0))))))
               i (1+ i)
         )
         (if (not (member l ll))(setq ll (cons l ll)))
      )
   )
   ; If list ll (layer list) exists,
   (if ll
      (progn
         ; turn all the layers off. Respond "Y" to turning off layer "0"
         (command "._-layer" "_OFF" "*" "_y" "")
         ; combine the list of layers into a string separated by commas.
         (setq ls
            (apply 'strcat
               (cons (car ll)(mapcar '(lambda (x)(strcat "," x)) (cdr ll)))
            )
         )
         ; Turn back on the selected layers.
         (command "._-layer" "_ON" ls "")
      )
   )
   ; reset the CMDECHO system variable
   (setvar "cmdecho" oe)
   ; end the undo mark.
   (command "_undo" "_End")
   ; suppress return value (exit quietly)
   (princ)
)

 

The second method uses ActiveX Visual LISP methods. This has less lines of code and does not require CMDECHO to be turned off. Again using OFF and ON for layers to avoid issues with freezing layer "0" and current active layer. Note: Error handling is not included.

(defun C:ISLM2 (/ d i l ll ss)
   ;; Load Visual LISP functionality
   (vl-load-com)
   ; Create an Undo Mark
   (vla-StartUndoMark (setq d (vla-get-activedocument (vlax-get-acad-object))))
   ; Prompt for a selection set
   (princ "\nSelect objects on Layers to Keep on: ")
   ; If items are selected,
   (if (setq ss (ssget))
      ; Create a list of layers from the selection set.
      (repeat (sslength ss)
         (setq l (cdr (assoc 8 (entget (ssname ss (if i i (setq i 0))))))
               i (1+ i)
         )
         (if (not (member l ll))(setq ll (cons l ll)))
      )
   )
   ;; If the layer list exists,
   (if ll
      ;; Iterate through the layer collection and turn off any layer that does not match the layer list.
      (vlax-for l (vla-get-layers d)
         (if (not (member (vla-get-name l) ll))(vla-put-Layeron l :vlax-false))
      )
   )
   ; End the undo mark.
   (vla-EndUndoMark d)
   (princ)
)

 

I hope this helps with your first question. If I have time I will circle around to more.

@pkenewell Firstly Thank You so much for responding and helping. I am trying to use lisp in a way that I can switch on the particular layer/layers by calling the layer's name in the command and not using the mouse to go and select the particular layer.

 

Link to comment
Share on other sites

11 hours ago, pkenewell said:

@Chandrakanth

 

 

Questions for items #2 through 4

#2: You need to explain better what you mean. Are you talking about switching back to to the Model tab, zoomed to the layout window area, or just working in modelspace within the layout viewport? If it is the latter, all you have to do is double-click the left mouse button inside the viewport. 

#3: I do not know what you mean by "Explode" objects in a viewport. You can't explode objects in a viewport. You can switch to Modelspace and explode objects like blocks and polylines. 

#4: This is also a huge topic with several different methods depending on what type of items. For example, for Block attributes (whether blocks or Title Blocks), there are already several programs made for this, from express tools ATTIN and ATTOUT, to others made on this site and several other sources. Do a search on this site and you will find something. Here is an Example by a great contributor to this site - @Lee Mac.

 

 For #2: I am looking for the latter the double click to shift to model space with in the view port. I basically do not want to double click and want to know if there is a way by using lisp if I can give a command to switch to the model space and I THINK MSpace(MS) does the job as someone have suggested me in this thread.

For #3: I mean explode objects in a model spacce (my bad sorry). So to explode I need to drag the mouse and select the objects. I am looking for a way if there is something that I can use to explode the objects by giving a direct command or using lisp.

For #4: I will surely look in to the site of @LeeMac and try to find a way.

Link to comment
Share on other sites

1 hour ago, BIGAL said:

#2 agree use dbl click, or type MS or Mspace. Note Ps or Pspace returns, there are some others as well, if you want to go to "Model" layout can do a shortcut (setvar 'ctab "Model")

 

I have also a GOTO which does as it implies goes to a layout via enter a number, Model is 0.

 

#4 yes can be done and send direct to excel. Like wise do a google lots of times requested.

@Thank You @BIGAL for responding and helping. I have used your Mspace suggestion and that is what exactly I am looking for. Also can You help me if there is some command or lisp that I can use to explode the objects in the model space without selecting the objects with the help of mouse. 

Link to comment
Share on other sites

13 hours ago, pkenewell said:

Hi @Chandrakanth

 

Your topic is very wide, so I'll just start with the #1. There are a couple methods:

 

The first method uses AutoCAD commands and plain AutoLISP to perform the actions. For simplicity this isolate method uses the "ON" and "OFF" for layers since using "FREEZE" has issues with the current active layer and layer "0". Note: Error handling is not included.

;; Method 1 using AutoCAD commands
(defun C:ISLM1 (/ i l ll ls oe ss)
   ;;Mark an Undo
   (command "._Undo" "_Begin")
   ; Save the value of CMDECO system var. and turn it off
   (setq oe (getvar "cmdecho"))
   (setvar "cmdecho" 0)
   ; Prompt to select objects
   (princ "\nSelect objects on Layers to Keep on: ")
   ; If a Selection set is made.
   (if (setq ss (ssget))
      ; iterate through the selection and get the layer names and add to list "ll".
      (repeat (sslength ss)
         (setq l (cdr (assoc 8 (entget (ssname ss (if i i (setq i 0))))))
               i (1+ i)
         )
         (if (not (member l ll))(setq ll (cons l ll)))
      )
   )
   ; If list ll (layer list) exists,
   (if ll
      (progn
         ; turn all the layers off. Respond "Y" to turning off layer "0"
         (command "._-layer" "_OFF" "*" "_y" "")
         ; combine the list of layers into a string separated by commas.
         (setq ls
            (apply 'strcat
               (cons (car ll)(mapcar '(lambda (x)(strcat "," x)) (cdr ll)))
            )
         )
         ; Turn back on the selected layers.
         (command "._-layer" "_ON" ls "")
      )
   )
   ; reset the CMDECHO system variable
   (setvar "cmdecho" oe)
   ; end the undo mark.
   (command "_undo" "_End")
   ; suppress return value (exit quietly)
   (princ)
)

 

The second method uses ActiveX Visual LISP methods. This has less lines of code and does not require CMDECHO to be turned off. Again using OFF and ON for layers to avoid issues with freezing layer "0" and current active layer. Note: Error handling is not included.

(defun C:ISLM2 (/ d i l ll ss)
   ;; Load Visual LISP functionality
   (vl-load-com)
   ; Create an Undo Mark
   (vla-StartUndoMark (setq d (vla-get-activedocument (vlax-get-acad-object))))
   ; Prompt for a selection set
   (princ "\nSelect objects on Layers to Keep on: ")
   ; If items are selected,
   (if (setq ss (ssget))
      ; Create a list of layers from the selection set.
      (repeat (sslength ss)
         (setq l (cdr (assoc 8 (entget (ssname ss (if i i (setq i 0))))))
               i (1+ i)
         )
         (if (not (member l ll))(setq ll (cons l ll)))
      )
   )
   ;; If the layer list exists,
   (if ll
      ;; Iterate through the layer collection and turn off any layer that does not match the layer list.
      (vlax-for l (vla-get-layers d)
         (if (not (member (vla-get-name l) ll))(vla-put-Layeron l :vlax-false))
      )
   )
   ; End the undo mark.
   (vla-EndUndoMark d)
   (princ)
)

 

I hope this helps with your first question. If I have time I will circle around to more.

@pkenewellThank You for the code really appreciate that. I am exactly looking for something like this. I wanted to have the layers (TEXT,DIMENSIONS,TITLE,TITLE BLOCK) on in my drawing and rest of the layers off. I wanted to do that by typing a command and not by selecting the objects with the mouse. 

Link to comment
Share on other sites

I have figured out how to get the first three points that I have asked. I wanted to know how could I extract the data from a particular layout without using the mouse drag to select all the objects.

 

Link to comment
Share on other sites

5 hours ago, Chandrakanth said:

I have figured out how to get the first three points that I have asked. I wanted to know how could I extract the data from a particular layout without using the mouse drag to select all the objects.

 

 

In a LISP to select al the objects on a layer, use ssget "X" - see this link here http://lee-mac.com/ssget.html 

 

Lee Macs MacAtt is a good routine to extract title data - but for the rest we might need a little more for exactly what data to extract (for example, a text might have the text itself, a layer it is written on, its location, height, font and so on). The list of entities given by (ssget  ) can be a starting point. Use the assoc command with (entget (ssname  'selection set' 'position') ) to take the data you need, save to a list and then at the end of the routine write all that to excel - loads of examples out there but to help we might need some information what you want the output to be.

Link to comment
Share on other sites

Ok in lisp you can make very simple defuns that use CAD commands so for layers on/off you need to look at the "-layer" command note the "-" in front of layer. This turns off the dialouge layers method and asks for manual input.

 

If you type -layer this appears lots of options

image.thumb.png.b9ad6370b899799abe3814fbd80117ac.png

 

ok so the sequence is

s TEXT OFF * Y ON TEXT,DIMENSIONS,TITLE,TITLE BLOCK

 

in Lisp

(defun c:mylay ( / )
(command "-layer" "S" "TEXT" "OFF" "*" "" "ON" "DIMENSIONS,TITLE,TITLE BLOCK" "")
)

 

Do you know how to autoload a lisp program on start up ?

Link to comment
Share on other sites

12 hours ago, Steven P said:

 

In a LISP to select al the objects on a layer, use ssget "X" - see this link here http://lee-mac.com/ssget.html 

 

Lee Macs MacAtt is a good routine to extract title data - but for the rest we might need a little more for exactly what data to extract (for example, a text might have the text itself, a layer it is written on, its location, height, font and so on). The list of entities given by (ssget  ) can be a starting point. Use the assoc command with (entget (ssname  'selection set' 'position') ) to take the data you need, save to a list and then at the end of the routine write all that to excel - loads of examples out there but to help we might need some information what you want the output to be.

Thank You @Steven P for responding. Let me run through the steps of what exactly I  need so that You have a clarity. I have the required layers ON in my drawing layout of which I need to extract the data. Now if it is in a normal case I would just type in data extraction and follow all those steps the wizard asks me to. But I do not want to do that. Instead I want to extract the data with a single command and the data should be extracted from the present layout I am working on containing all the objects, content/value of the object(for example dimension value in case if the object is dimension etc.,), their x,y and z positions. Please do respond if You want to understand more about the case. Thank You once again for reaching out and helping.  

Link to comment
Share on other sites

2 hours ago, BIGAL said:

Ok in lisp you can make very simple defuns that use CAD commands so for layers on/off you need to look at the "-layer" command note the "-" in front of layer. This turns off the dialouge layers method and asks for manual input.

 

If you type -layer this appears lots of options

image.thumb.png.b9ad6370b899799abe3814fbd80117ac.png

 

ok so the sequence is

s TEXT OFF * Y ON TEXT,DIMENSIONS,TITLE,TITLE BLOCK

 

in Lisp

(defun c:mylay ( / )
(command "-layer" "S" "TEXT" "OFF" "*" "" "ON" "DIMENSIONS,TITLE,TITLE BLOCK" "")
)

 

Do you know how to autoload a lisp program on start up ?

yeah @BIGAL figured how I can use the -layer command to switch on and off multiple or all layers at a time and then for switching between the model space and the paper space using the MS and PS. and then used the explode selecting all objects to separate the objects I need. Now I am trying to figure out how I can extract the data from a particular layout having all the data of the objects included. Usually I just do the DX and then follow the steps the data extraction wizard asks me to. But I wanted to do that using a single command or very few steps possible where I would not use the mouse clicking. Thank You for the response. Get back to me If You have anything with this data extraction.

Link to comment
Share on other sites

4 hours ago, BIGAL said:

Ok in lisp you can make very simple defuns that use CAD commands so for layers on/off you need to look at the "-layer" command note the "-" in front of layer. This turns off the dialouge layers method and asks for manual input.

 

If you type -layer this appears lots of options

image.thumb.png.b9ad6370b899799abe3814fbd80117ac.png

 

ok so the sequence is

s TEXT OFF * Y ON TEXT,DIMENSIONS,TITLE,TITLE BLOCK

 

in Lisp

(defun c:mylay ( / )
(command "-layer" "S" "TEXT" "OFF" "*" "" "ON" "DIMENSIONS,TITLE,TITLE BLOCK" "")
)

 

Do you know how to autoload a lisp program on start up ?

@Bigal Actually I do not know anything about lisp. As part of a project that we are are working on with a construction company have to use autocad to make the workflow smooth. So the data extraction is the last step as part of it. So I am trying to figure out a way extracting the data with a single command or minimum steps involved.

 

Link to comment
Share on other sites

Looking at this, do you have a dataextraction template set up to your requirements?

 

You can run -dataextraction which runs the command through the command line rather than through a dialogue box and so it can be run through a LISP

 

Maybe try that, in LISP maybe

 

(command "-dataextraction" filepath "Yes")

 

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

 Share

×
×
  • Create New...