Jump to content
mjavy7

Print Tabs Names (or export)

Recommended Posts

Hello All.

I need help with AutoCAD 2013

I have multiple drawings with 100's of tabs inside, I would like to either export or print out all of the tab names.

 

If anyone knows a way to do this, I would love to hear about it.

 

Thank you in advanced,

Javier

Share this post


Link to post
Share on other sites

Here's a simple example for the active document:

 

(defun c:Tabs ()
 (prompt "\nTab Names: ")
 (foreach layout (layoutlist)
   (print layout)
 )
 (princ)
)

Share this post


Link to post
Share on other sites

now how do I use this? LOL

Sorry man, this is a bit over my head.

If you could please explain how to use this code, I would highly appreciate it.

If there is already a place in here were it is explained let me know and I will go there to learn.

Share this post


Link to post
Share on other sites

No worries; we all start somewhere. :beer:

 

First, to use LISP code posted on forums, simply copy + paste the code into an empty text file, and save with a .LSP file extension. See this tutorial for loading LISP routines.

 

 

 

After posting that quick sample above, I re-read your post, and saw that you said you're needing to process multiple drawings, so I thought I'd provide a 'Batch Report' routine... Once you've created the LISP file, and loaded the code into your drawing, simply invoke by entering BFINDTABS EXPORTLAYOUT Command.

 

 

 

[Edit :: 2013-04-19]

 

Modified code to allow for Active (current drawing), or Browse (single/multiple drawing) selection.

 

I have added a DOSLIB dependency specifically to gain access to multiple file selection offered by DOS_GETFILEM function. Please download DOSLIB here, and use ARXLOAD to load your version's ARX file.

 

This modification also provides a LISP callable function BBOX:ExportLayout.

 

Multiple miscellaneous items corrected as well, such as non-localized variable, and non-essential code included by mistake when pulling from another routine.

 

Additional handling needed for open / read-only Documents.

 

 

 

(vl-load-com)

(defun BBOX:ExportLayout (dwgs / *error* BBOX:GetDate BBOX:GetTime
                              BBOX:WriteData acApp oDocuments oShell path
                              filePath dbxDoc file openDoc oLayouts layoutName
                             )

 (defun *error* (msg)
   (if file
     (close file)
   )
   (if oShell
     (vlax-release-object oShell)
   )
   (if dbxDoc
     (vlax-release-object dbxDoc)
   )
   (cond ((not msg))                                                   ; Normal exit
         ((member msg '("Function cancelled" "quit / exit abort")))    ; <esc> or (quit)
         ((princ (strcat "\n** Error: " msg " ** ")))                  ; Fatal error, display it
   )
   (princ)
 )

 (defun BBOX:GetDate (date)
   (setq date (mapcar '(lambda (x) (itoa x)) date))
   (strcat (nth 0 date) "-" (nth 1 date) "-" (nth 3 date))
 )

 (defun BBOX:GetTime (date / hr mn)
   (setq hr (nth 4 date))
   (setq mn (itoa (nth 5 date)))
   (if (= 1 (strlen mn))
     (setq mn (strcat "0" mn))
   )
   (cond ((> 12 hr) (strcat (itoa hr) ":" mn " AM"))
         ((strcat (itoa (- hr 12)) ":" mn " PM"))
   )
 )

 (defun BBOX:WriteData (path dwg layoutName file / filePath date)
   (write-line
     (vl-string-right-trim
       ","
       (apply
         'strcat
         (mapcar
           '(lambda (x) (strcat x ","))
           (list (setq filePath (strcat path dwg))
                 (if (setq date (vl-file-systime filePath))
                   (BBOX:GetDate date)
                   "{ Read-Only }"
                 )
                 (if date
                   (BBOX:GetTime date)
                   "{ Read-Only }"
                 )
                 layoutName
           )
         )
       )
     )
     file
   )
 )

 (if (and (setq acApp (vlax-get-acad-object))
          (setq oDocuments (vla-get-documents acApp))
          (setq oShell (vla-getinterfaceobject
                         acApp
                         "Shell.Application"
                       )
          )
          (setq path (car dwgs))
          (setq filePath
                 (strcat
                   (vl-filename-directory
                     (vl-filename-mktemp)
                   )
                   "\\Export Layout Report_"
                   (menucmd
                     "M=$(edtime,$(getvar,date),YYYY-MO-DD)"
                   )
                   ".csv"
                 )
          )
          (princ "\nWorking, please wait...")
          (princ)
          (setq dbxDoc (vla-getinterfaceobject
                         acApp
                         (strcat "ObjectDBX.AxDbDocument."
                                 (substr (getvar 'acadver) 1 2)
                         )
                       )
          )
     )
   (progn
     (setq file (open filePath "w"))
     (write-line "Directory Searched:" file)
     (write-line path file)
     (write-line "" file)
     (write-line "Drawing:,Date:,Time:,Layout Name:" file)
     (foreach dwg (cdr dwgs)
       (if (not (vl-catch-all-error-p
                  (setq openDoc (vl-catch-all-apply
                                  'vla-item
                                  (list oDocuments dwg)
                                )
                  )
                )
           )
         (setq oLayouts (vla-get-layouts openDoc))
         (progn
           (vl-catch-all-apply
             'vla-open
             (list dbxDoc (strcat path dwg))
           )
           (setq oLayouts (vla-get-layouts dbxDoc))
         )
       )
       (vlax-for oLayout oLayouts
         (if (/= "Model" (setq layoutName (vla-get-name oLayout)))
           (BBOX:WriteData path dwg layoutName file)
         )
       )
     )
     (princ "Done.")
     (princ)
     (setq file (close file))
     (vlax-invoke oShell 'open filePath)
     (*error* nil)
   )
   (cond
     (filePath
      (*error*
        "Unable to create \"ObjectDBX.AxDbDocument\" Object"
      )
     )
     (acApp
      (*error* "Unable to create \"Shell.Application\" Object")
     )
   )
 )
)

(defun c:ExportLayout (/ opt dwgs)

 (initget "Active Browse")
 (if
   (not
     (setq opt
            (getkword
              "\nWhat drawing would you like to process [Active/Browse]<Active>: "
            )
     )
   )
    (setq opt "Active")
 )

 (cond ((= "Active" opt)
        (if (= 1 (getvar 'dwgtitled))
          (BBOX:ExportLayout
            (list (getvar 'dwgprefix) (getvar 'dwgname))
          )
          (prompt "\n** Drawing not saved ** ")
        )
       )
       ((= "Browse" opt)
        (if (setq dwgs
                   (dos_getfilem
                     "Select Drawings"
                     (getvar 'dwgprefix)                               ;<-- default path here
                     "Drawing files (*.dwg)|*.dwg"
                   )
            )
          (BBOX:ExportLayout dwgs)
        )
       )
 )
 (princ)
)

 

Inspired by a favorite routine of mine, BFIND, from Lee. :)

Edited by BlackBox

Share this post


Link to post
Share on other sites

:thumbsup:

You are the man!!

They both work great but I must say the second one is very impressive!!!

This is exactly what I need!!!

Share this post


Link to post
Share on other sites
Here's a simple example for the active document:

 

(defun c:Tabs ()
 (prompt "\nTab Names: ")
 (foreach layout (layoutlist)
   (print layout)
 )
 (princ)
)

 

How hard is to make this code export the list to excel like the second code?

Share this post


Link to post
Share on other sites
How hard is to make this code export the list to excel like the second code?

 

You mean, where it only prompts for a single drawing, rather than a directory of?

 

Or do you mean no prompt at all; as in it only works on the drawing open when invoked?

Share this post


Link to post
Share on other sites

A very simplified version

 

(defun c:Tabs ()
(setq fname "C:\acadtemp\mytabs")
(setq fo (open fname "w")) 
(prompt "\nTab Names: ")
 (foreach layout (layoutlist)
   (print layout)
(write-line layout fo) 
 )
(close fo)
 (princ)
)
;just open file mytabs in excel

Share this post


Link to post
Share on other sites
You mean, where it only prompts for a single drawing, rather than a directory of?

 

Or do you mean no prompt at all; as in it only works on the drawing open when invoked?

 

Either way it works for me, what ever is easier for you. I can work with either.

Share this post


Link to post
Share on other sites
A very simplified version

 

Thank you.

This one works but adds a few steps to my process. Since I have to do many files, I have to go thru explorer, copy file to different location, rename and modify.

The previous code (BTABS) automatically spits out and excell file ready for saving which makes it more user friendly. I am not trying to discredit your effort....I do appreciate it.

Share this post


Link to post
Share on other sites
Either way it works for me, what ever is easier for you. I can work with either.

 

Why pick one, when you can do both... Code revised here... Please read the [Edit ...] Comments closely. :thumbsup:

Share this post


Link to post
Share on other sites

The previous code (BTABS) automatically spits out and excell file ready for saving which makes it more user friendly.

 

Just to clarify, the code I offered actually generates a .CSV file, and uses Shell.Application to open the resultant file in one's own default application for .CSV files... In your case, that's Excel, others who do not have Office may find that Notepad opens the file, etc.... That's the part I credit my learning to Lee (not that he invented it, the code was there before his time, but I personally learned this 'trick' from him :geek:).

 

In any event, I hope that makes (more?) sense to you now. :beer:

Share this post


Link to post
Share on other sites

 

[Edit :: 2013-04-19]

 

Modified code to allow for Active (current drawing), or Browse (single/multiple drawing) selection.

 

I have added a DOSLIB dependency specifically to gain access to multiple file selection offered by DOS_GETFILEM function. Please download DOSLIB here, and use ARXLOAD to load your version's ARX file.

 

Ok, this is also a bit over my head so here is what I got so far:

1. I created a *.lsp file with the code provided

2. I went to the link and downloaded the DOSLIB files and double cliked in the *.EXE file.

3. In Auto CAD loaded my new *.lsp file and added the folder to the support search path.

 

The part that looses me is the ARX... is shouls I rename the *.lsp to *.ARX? and in autocad loaded with the ARX command?

Share this post


Link to post
Share on other sites
Ok, this is also a bit over my head so here is what I got so far:

1. I created a *.lsp file with the code provided

2. I went to the link and downloaded the DOSLIB files and double cliked in the *.EXE file.

3. In Auto CAD loaded my new *.lsp file and added the folder to the support search path.

 

The part that looses me is the ARX... is shouls I rename the *.lsp to *.ARX? and in autocad loaded with the ARX command?

 

See the ARXLOAD function (linked above) to load DOSLIB's ARX file... Then the dependent function (dos_getfilem) will be available... Either use the DOSLIB Command, or an ARXLOAD call in your Acad.lsp to ensure that DOSLIB's ARX file is loaded each time you start AutoCAD.

 

** Note - ObjectARX files (C++ for AutoCAD), like .NET assemblies, need only be loaded once per session, so no need to add to AcadDoc.lsp

Share this post


Link to post
Share on other sites

I am doing something work and I dont know what...

 

Command:

EXPORTLAYOUT

What drawing would you like to process [Active/Browse]: B

Working, please wait...

** Error: bad argument type: consp nil **

Command:

 

...I choose the drawing file that I need and it comes back with a bad argument.

Any advise?

Share this post


Link to post
Share on other sites

While successful in my limited tests, I always chose files that were not read-only... It appears that the routine doesn't obtain SysTime on read-only files... Looking at a work around and will post back shortly.

Share this post


Link to post
Share on other sites

Problem fixed. :thumbsup:... Revised code here.

 

 

 

The issue was in handling Documents that were either already open in one's own session, or those read-only (open by others) causing vl-File-SysTime to return Nil. So, I built in some checking for that, but then needed to add some code to check for Documents open in one's own session to also avoid attempts to open a second time (it's already open, and then ObjectDBX tries to open which caused some undesirable results).

 

Again, all fixed AFAIK, so please let me know what issues (if any) you might encounter... I may come back to streamline a bit, but that will come later. Sorry for any confusion.

 

Cheers

Share this post


Link to post
Share on other sites

Hello!

 

 

I know this is a couple years old, but the solution offered by BlackBox works for me. Thank you. Hopefully you're all still around and will respond.

 

 

When using the "browse" option, is it possible to select a top-level folder and process all the drawing files within it and all its sub-folders? I have about 27,000 files whose layout tab names I'd like to export, but they exist in a mess of folders, sub-folders, and so on.

 

 

Thanks again!

 

 

Juan

Share this post


Link to post
Share on other sites
Hello!

 

 

I know this is a couple years old, but the solution offered by BlackBox works for me. Thank you. Hopefully you're all still around and will respond.

 

 

When using the "browse" option, is it possible to select a top-level folder and process all the drawing files within it and all its sub-folders? I have about 27,000 files whose layout tab names I'd like to export, but they exist in a mess of folders, sub-folders, and so on.

 

 

Thanks again!

 

Welcome to CADTutor! :)

 

I'm glad you found the code helpful.

 

Yes, the code could be revised to iterate all drawings in all sub-directories using ObjectDBX, however I would advise against this due to the fact that it would essentially lock up your session, overflowing the memory stack, or even if successful, would take an immeasurable amount of time depending on workstation specs.

 

That said, it is technically possible using LISP... If you're serious about actually wanting to process that amount of data, I'd instead suggest we power this functionality over to .NET API for performance gains alone, let alone the ability to batch process in parallel (multiple instances at once), in addition to in series (one-at-a-time).

 

Just turning in for a few hours of shut eye, as I have to be back at the office soon, but wanted to make this quick reply.

 

Cheers

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×