PDA

View Full Version : How to Close Drawings


BoKirra
2009-03-31, 02:08 AM
Hi ALL,

Supposed I have 5 drawings opened.
I'm now working on a drawing, say it's active.
How to close the other 4 inactive drawings without
any drawing name inputs at command prompt?

Your helps are much appreciated.

mweaver
2009-03-31, 03:23 AM
Try this:(vlax-for doc (vla-get-documents(vlax-get-acad-object))
(if (= doc (vla-get-activedocument(vlax-get-acad-object)))
nil
(progn
(if (or
(= 0 (getvar "dbmod"))
(= :vlax-false (vla-get-readonly doc))
)
(vl-catch-all-apply 'vla-close (list doc :vlax-false))
(vl-catch-all-apply 'vla-close (list doc :vlax-true))
)
)
)
)

This has had very little testing, but has worked through what testing I have given it.

BoKirra
2009-03-31, 08:15 AM
Try this:(vlax-for doc (vla-get-documents(vlax-get-acad-object))
(if (= doc (vla-get-activedocument(vlax-get-acad-object)))
nil
(progn
(if (or
(= 0 (getvar "dbmod"))
(= :vlax-false (vla-get-readonly doc))
)
(vl-catch-all-apply 'vla-close (list doc :vlax-false))
(vl-catch-all-apply 'vla-close (list doc :vlax-true))
)
)
)
)

This has had very little testing, but has worked through what testing I have given it.
Thank you very much.
But is there a possibility to do the same job without using VLISP?
The problem is I only know a little about VLISP. :Oops:

mweaver
2009-03-31, 12:49 PM
Thank you very much.
But is there a possibility to do the same job without using VLISP?
The problem is I only know a little about VLISP. :Oops:

You have to iterate the documents collection. To do this you will need to use vlisp or vba.

If you tried the code I posted and couldn't get it to work, put (vl-load-com) somewhere in front of it.

Take the plunge into vlisp - come over to the dark side - there is great power in the force:-)

BoKirra
2009-04-01, 02:51 AM
You have to iterate the documents collection. To do this you will need to use vlisp or vba.

If you tried the code I posted and couldn't get it to work, put (vl-load-com) somewhere in front of it.

Thanks again.
Another question, what if I want to close one inactive drawing only?
Of course, in this case the code will ask me to input the drawing name.

Take the plunge into vlisp - come over to the dark side - there is great power in the force:smile:

I'll take more candles before jumping into the dark. :lol:
I mean I'll learn it soon.

mweaver
2009-04-01, 05:15 AM
Thanks again.
Another question, what if I want to close one inactive drawing only?
Of course, in this case the code will ask me to input the drawing name.

I'll take more candles before jumping into the dark. :lol:
I mean I'll learn it soon.

Let's look at a couple of ways of doing this. First, I would build a subroutine that would close a drawing based on the name of the drawing:
(defun CloseSpecifiedDwg (FileName / docs doc OurDoc)
(vl-load-com)
(setq
FileName (if (wcmatch (strcase FileName) "*.DWG") FileName (strcat FileName ".DWG"))
docs (vla-get-documents (vlax-get-acad-object))
;the collection of all of the currently open drawings
doc (vla-get-activedocument (vlax-get-acad-object)) ;the active drawing
;;Get the document we want to close
;;wrap this in a vl-catch-all-apply
;;in case the drawing isn't open
OurDoc (vl-catch-all-apply
'vla-item
(list docs 1);filename)
)
)
(if (vl-catch-all-error-p OurDoc)
;;then the drawing isn't open, notify the operator
(princ (strcat "\nCan't close " FileName " because it isn't open."))
;;else, close it
(vla-close OurDoc :vlax-true)
)
(vlax-release-object OurDoc)
(vlax-release-object Doc)
(vlax-release-object Docs)
)

Then we could call it with a this, which will prompt for the drawing name:
(defun c:CloseDwg1 (/ FileName)
(setq FileName (getstring T "\nEnter name of drawing to close: "))
(CloseSpecifiedDwg FileName)
(princ)
)

This will work, but leaves a lot of room for error - typos, spelling, etc;. With a bit more code we could present the user with a "menu" on the text screen:

(defun c:CloseDwg2 (/)
(vl-load-com)
(setq
docs (vla-get-documents (vlax-get-acad-object))
;the collection of all of the currently open drawings
doc (vla-get-activedocument (vlax-get-acad-object)) ;the active drawing
indx 1
)
;;Create a list of the names of all the open drawings
(princ "\n\n Enter the drawing number to close")
(vlax-for dwg docs
(princ (strcat "\n" (itoa indx) ".\t" (vla-get-name dwg)))
(setq indx (1+ indx))
)
(princ "\n")
(textscr)
(setq OurDwgIndex (getint))
(if (and
(< (1- OurDwgIndex) (vla-get-count docs))
(< 0 OurDwgIndex)
)
(closeSpecifiedDwg (vla-get-name (vla-item docs (1- OurDwgIndex))))
)
(vlax-release-object Docs)
)


Which will switch to the text screen and show a menu similar to the following:

Enter the drawing number to close
1. Drawing1.dwg
2. Drawing4.dwg
3. Drawing5.dwg
4. Drawing6.dwg
5. Drawing7.dwg
6. Drawing8.dwg

I hope this helps show that routines that use vlisp functions don't have to be too complex.

BoKirra
2009-04-01, 05:51 AM
Let's look at a couple of ways of doing this. First, I would build a subroutine that would close a drawing based on the name of the drawing:
(defun CloseSpecifiedDwg (FileName / docs doc OurDoc)
(vl-load-com)
(setq
FileName (if (wcmatch (strcase FileName) "*.DWG") FileName (strcat FileName ".DWG"))
docs (vla-get-documents (vlax-get-acad-object))
;the collection of all of the currently open drawings
doc (vla-get-activedocument (vlax-get-acad-object)) ;the active drawing
;;Get the document we want to close
;;wrap this in a vl-catch-all-apply
;;in case the drawing isn't open
OurDoc (vl-catch-all-apply
'vla-item
(list docs 1);filename)
)
)
(if (vl-catch-all-error-p OurDoc)
;;then the drawing isn't open, notify the operator
(princ (strcat "\nCan't close " FileName " because it isn't open."))
;;else, close it
(vla-close OurDoc :vlax-true)
)
(vlax-release-object OurDoc)
(vlax-release-object Doc)
(vlax-release-object Docs)
)

Then we could call it with a this, which will prompt for the drawing name:
(defun c:CloseDwg1 (/ FileName)
(setq FileName (getstring T "\nEnter name of drawing to close: "))
(CloseSpecifiedDwg FileName)
(princ)
)

This will work, but leaves a lot of room for error - typos, spelling, etc;. With a bit more code we could present the user with a "menu" on the text screen:

(defun c:CloseDwg2 (/)
(vl-load-com)
(setq
docs (vla-get-documents (vlax-get-acad-object))
;the collection of all of the currently open drawings
doc (vla-get-activedocument (vlax-get-acad-object)) ;the active drawing
indx 1
)
;;Create a list of the names of all the open drawings
(princ "\n\n Enter the drawing number to close")
(vlax-for dwg docs
(princ (strcat "\n" (itoa indx) ".\t" (vla-get-name dwg)))
(setq indx (1+ indx))
)
(princ "\n")
(textscr)
(setq OurDwgIndex (getint))
(if (and
(< (1- OurDwgIndex) (vla-get-count docs))
(< 0 OurDwgIndex)
)
(closeSpecifiedDwg (vla-get-name (vla-item docs (1- OurDwgIndex))))
)
(vlax-release-object Docs)
)


Which will switch to the text screen and show a menu similar to the following:

Enter the drawing number to close
1. Drawing1.dwg
2. Drawing4.dwg
3. Drawing5.dwg
4. Drawing6.dwg
5. Drawing7.dwg
6. Drawing8.dwg

I hope this helps show that routines that use vlisp functions don't have to be too complex.
WOW!
What a great help!
I don't know how to say something else but "THANKS, WONDERFUL, INCREDIBLE..."
:Puffy::Puffy::Puffy:

mweaver
2009-04-01, 01:45 PM
I'm glad to help.

Mike