Visual LISP, AutoLISP and General Customization
cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

Update blocks & attributes LISP

39 REPLIES 39
SOLVED
Reply
Message 1 of 40
Klingi162
17053 Views, 39 Replies

Update blocks & attributes LISP

Hey guys,

 

I'm new in this forum and l would need your help.

I'm using a blocklibrary, where I stored all my blocks, most of them have attributes.

Now I'd like to simplify my workflow and want to update the blocks that I inserted in a drawing trough LISP.

 

Is there a way to update all  inserted blocks and attributes of the whole drawing a once? The idea is, that the LISP checks the whole blocklibrary and updates the inserted blocks that to not match with the once from the library.

 

thanks for your help! Smiley Happy

39 REPLIES 39
Message 2 of 40
3wood
in reply to: Klingi162

Welcome aboard!

Usually people use xrefs instead insert standard blocks.

I think we can skip the step of comparing block definition, just search the whole drawing, if there is any block name exists in the library, just insert it from the library and redefine the block in the drawing.

Message 3 of 40
Klingi162
in reply to: 3wood

hey,

thanks for the quick reply.

The thing is I got many blocks in the drawing and don't want to search for every single block seperately.

We also want to use it in the office. so if I tell my colleges that I changed a block, they just need to press a shortcut and every block (including its attributes) is updated. therefore its the only way to make it with a LISP that compares the blocks from its library...

Message 4 of 40
3wood
in reply to: Klingi162

I guess there is way to attach additional information to each block definition to indicate its version (I saw it in AutoCAD Architectural?), but I am not familar with the method. Let's wait for other people's help.

Message 5 of 40
Lee_Mac
in reply to: Klingi162

The following code will redefine all blocks in the drawing for which a drawing file of the same name is found either within a specific directory, or within an AutoCAD Support File Search Path (SFSP):

 

;; Redefine All Blocks  -  Lee Mac
(defun c:redefall ( / bln dir doc dwg lst obj org spc )

    (setq dir nil) ;; Directory of Block Library; nil to use Support Path

    (if dir
        (setq dir (strcat (vl-string-right-trim "\\" (vl-string-translate "/" "\\" dir)) "\\"))
        (setq dir "")
    )
    (cond
        (   (= 4 (logand 4 (cdr (assoc 70 (tblsearch "layer" (getvar 'clayer))))))
            (princ "\nCurrent layer locked.")
        )
        (   (setq doc (vla-get-activedocument (vlax-get-acad-object))
                  spc (vla-get-modelspace doc)
                  org (vlax-3D-point 0 0)
            )
            (vlax-for blk (vla-get-blocks doc)
                (if
                    (and
                        (= :vlax-false (vla-get-isxref blk))
                        (= :vlax-false (vla-get-islayout blk))
                        (not (wcmatch (setq bln (vla-get-name blk)) "`**,_*,*|*"))
                        (setq dwg (findfile (strcat dir bln ".dwg")))
                    )
                    (progn
                        (setq obj (vla-insertblock spc org dwg 1.0 1.0 1.0 0.0))
                        (if (= :vlax-true (vla-get-hasattributes obj))
                            (setq lst (vl-list* "," bln lst))
                        )
                        (vla-delete obj)
                    )
                )
            )
            (if lst (vl-cmdf "_.attsync" "_N" (apply 'strcat (cdr lst))))
            (vla-regen doc acallviewports)
        )
    )
    (princ)
)
(vl-load-com) (princ)

 

Alter the value of the dir variable to source blocks from a specific directory, or set this variable to nil (the current value) to source blocks from the AutoCAD SFSP or working directory.

Message 6 of 40
Klingi162
in reply to: Lee_Mac

hey Lee Mac,

 

thanks for the code.

It looks like that's the one I was looking for. The only problem is, that its for an english autoCAD version. I guess for an german one I would need to put some "_" somewhere in front of the comands I guess (but where??? Smiley Sad), because when I run the script, AutoCAD just says: regenerating model

 

 

my second point is the directory of the block library: do you right it like that? -->

 

(setq dir "I:\AutoCAD block Library")

 

sorry for this questions but I'm not that fit with scripting.

Message 7 of 40
Lee_Mac
in reply to: Klingi162


@Klingi162 wrote:

The only problem is, that its for an english autoCAD version. I guess for an german one I would need to put some "_" somewhere in front of the comands I guess, because when I run the script, AutoCAD just says: regenerating model


 

The program should work with all language versions of AutoCAD - the drawing will be automatically regenerated after all blocks have been redefined.

 


@Klingi162 wrote:

my second point is the directory of the block library: do you right it like that? -->

 

(setq dir "I:\AutoCAD block Library")

 


 

Not quite -

 

Since the backslash character is an escape character in AutoLISP, you will need to use either single forward slashes or double-backslashes for filepath delimiters, e.g.:

 

(setq dir "I:\\AutoCAD block Library")

 Or alternatively:

 

(setq dir "I:/AutoCAD block Library")

 

I hope this helps!

Message 8 of 40
Klingi162
in reply to: Lee_Mac

It seems, that I'm still doing something wrong.

 

This is how I do it:

I load your LISP with "appload" and when I run the comand "redefall" it doesn't update my blocks from the library at all.

I checked it because I added some lines in the block and in the drawing where I inserted it I tried the LISP and the new lines didn't show up. only when I manually insert the block again you see the update.

The only result is "Regenerating model".

 

what am I doing wrong? Smiley Indifferent

Message 9 of 40
Lee_Mac
in reply to: Klingi162

I can report that the program is performing successfully in my testing, so perhaps the configuration is incorrect - please try this 'verbose' version which will provide more feedback to the user:

 

;; Redefine All Blocks  -  Lee Mac
(defun c:redefall ( / bln dir doc dwg lst obj org spc )

    (setq dir "I:\\AutoCAD block Library") ;; Directory of Block Library; nil to use Support Path

    (if dir
        (setq dir (strcat (vl-string-right-trim "\\" (vl-string-translate "/" "\\" dir)) "\\"))
        (setq dir "")
    )
    (cond
        (   (= 4 (logand 4 (cdr (assoc 70 (tblsearch "layer" (getvar 'clayer))))))
            (princ "\nCurrent layer locked.")
        )
        (   (setq doc (vla-get-activedocument (vlax-get-acad-object))
                  spc (vla-get-modelspace doc)
                  org (vlax-3D-point 0 0)
            )
            (terpri)
            (vlax-for blk (vla-get-blocks doc)
                (if
                    (and
                        (= :vlax-false (vla-get-isxref blk))
                        (= :vlax-false (vla-get-islayout blk))
                        (not (wcmatch (setq bln (vla-get-name blk)) "`**,_*,*|*"))
                    )
                    (if (setq dwg (findfile (strcat dir bln ".dwg")))
                        (progn
                            (princ (strcat "Redefining block: " dwg "\n"))
                            (setq obj (vla-insertblock spc org dwg 1.0 1.0 1.0 0.0))
                            (if (= :vlax-true (vla-get-hasattributes obj))
                                (setq lst (vl-list* "," bln lst))
                            )
                            (vla-delete obj)
                        )
                        (princ (strcat "Unable to locate block: " dir bln ".dwg\n"))
                    )
                )
            )
            (if lst
                (progn
                    (princ "Synchronising attributes for redefined blocks...\n")
                    (vl-cmdf "_.attsync" "_N" (apply 'strcat (cdr lst)))
                )
            )
            (textscr)
            (vla-regen doc acallviewports)
        )
    )
    (princ)
)
(vl-load-com) (princ)
Message 10 of 40
Klingi162
in reply to: Lee_Mac

thanks, but no change. Smiley Sad

It just writes "Unable to locate block: I:\\AutoCAD block Library\testblock.dwg

 

Is it possible to integrate the LISP in any other way than trough "appload"?

Does it have a problem, because I'm using AutoCAD 2010 Architecture?

 

thanks for your patience

Message 11 of 40
Lee_Mac
in reply to: Klingi162


@Klingi162 wrote:

thanks, but no change. Smiley Sad

It just writes "Unable to locate block: I:\\AutoCAD block Library\testblock.dwg


 

This would indicate that there is no drawing with filename testblock.dwg residing within the directory I:\AutoCAD block Library - can you confirm that this drawing is present?

 

Have you altered the program in any way?

Message 12 of 40
bhull1985
in reply to: Lee_Mac

Well there's also two \\ after I: and then there's only one \ after Block Library

Maybe that is why..

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Please use code tags and credit where credit is due. Accept as solution, if solved. Let's keep it trim people!
Message 13 of 40
Klingi162
in reply to: Lee_Mac

I didn't change anything from your file...well I changed the filepath to a new location, just to try if this makes any change.

The new blocklibrary is now " I:\AutoCAD Blöcke\template\"

 

this is what appeared when i run the LISP:

 

Befehl: REDEFALL

Unable to locate block: I:\AutoCAD Blöcke\template\Adler.dwg
Unable to locate block: I:\AutoCAD Blöcke\template\adler logo.dwg
Unable to locate block: I:\AutoCAD Blöcke\template\Bemassungsstricherl.dwg
Unable to locate block: I:\AutoCAD Blöcke\template\A$C553C1C71.dwg
Regeneriert Layout.
Regeneriert Modell.

 

so I opend a new file to be sure that I didn't miss any blocks and just inserted one specific block. now only this appears:

 

Befehl: redefall

Regeneriert Modell.

 

so far so good, but it still doesn't update any changes from this one block file...

so when I for example add some lines in the block and save it and then I run the Lisp in the file where I inserted this specific block and no lines show up.

Message 14 of 40
Lee_Mac
in reply to: Klingi162


@Klingi162 wrote:

this is what appeared when i run the LISP:

 

Befehl: REDEFALL

Unable to locate block: I:\AutoCAD Blöcke\template\Adler.dwg
Unable to locate block: I:\AutoCAD Blöcke\template\adler logo.dwg
Unable to locate block: I:\AutoCAD Blöcke\template\Bemassungsstricherl.dwg
Unable to locate block: I:\AutoCAD Blöcke\template\A$C553C1C71.dwg


 

Can you confirm that the drawing files (Adler.dwg / adler logo.dwg / etc.) are present in the folder I:\AutoCAD Blöcke\template?

Message 15 of 40
Klingi162
in reply to: Lee_Mac

I already changed it, so all the blocks are present.

 

still this:

 

Befehl: redefall


Regeneriert Layout.
Regeneriert Modell.

 

nothing else shows up. I already tried everything, but won't work. Smiley Sad

Message 16 of 40
Lee_Mac
in reply to: Klingi162


@Klingi162 wrote:

I already changed it, so all the blocks are present.

 

still this:

 

Befehl: redefall


Regeneriert Layout.
Regeneriert Modell.

 

nothing else shows up. I already tried everything, but won't work. Smiley Sad


I'm not really sure what else to suggest... Smiley Frustrated

 

Providing that there are non-anonymous block definitions in your drawing, you should be receiving some messages whether the blocks can be found or not...

 

Message 17 of 40
Klingi162
in reply to: Lee_Mac

Hey Lee,

 

I found one of your old scripts in an other forum and this one works perfectly. It doesn't do the whole trick but maybe you can help me to add the last step. The only thing thats missing is the part that say to replace every block from a specific folder path. Now it just replaces only the blocks that I really put in one by one...

The Rest works great...half way there!!! Smiley Happy

 

Thats your Code:

 

(defun c:ReDef ( / *error* oc spc doc block b )
(vl-load-com)
;; © Lee Mac 2010

;; Full filename needed if block is not in the support path
(setq BlocksToRedefine
'(
"I:\\AutoCAD Blöcke\\Template\\Support\\__Ausführung_A0.dwg"
"I:\\AutoCAD Blöcke\\Template\\Support\\__Ausführung_A1.dwg"
"I:\\AutoCAD Blöcke\\Template\\Support\\__Ausführung_A2.dwg"
)
)

(defun *error* ( msg )
(and oc (setvar 'CMDECHO oc))
(or (wcmatch (strcase msg) "*BREAK,*CANCEL*,*EXIT*")
(princ (strcat "\n** Error: " msg " **")))
(princ)
)

(setq spc
(vlax-get (vla-get-ActiveDocument (vlax-get-acad-object))
(if (= 1 (getvar 'CVPORT)) 'PaperSpace 'ModelSpace)
)
)

(setq oc (getvar 'CMDECHO)) (setvar 'CMDECHO 0)

(foreach block BlocksToRedefine
(if (setq b (findfile (strcat block (if (not (vl-filename-extension block)) ".dwg" ""))))
(progn
(vla-delete
(vla-insertblock spc
(vlax-3D-point '(0. 0. 0.)) b 1. 1. 1. 0.
)
)
(vl-cmdf "_.attsync" "_N" (vl-filename-base b))
)
(princ (strcat "\n** Cannot Find Block: " block " **"))
)
)

(setvar 'CMDECHO oc)
(princ)
)

 

If you could tell me which part I have to replace everything works like a miracle

 

Thx already for your great help Lee! 

Message 18 of 40
Lee_Mac
in reply to: Klingi162


@Klingi162 wrote:

'(
"I:\\AutoCAD Blöcke\\Template\\Support\\__Ausführung_A0.dwg"
"I:\\AutoCAD Blöcke\\Template\\Support\\__Ausführung_A1.dwg"
"I:\\AutoCAD Blöcke\\Template\\Support\\__Ausführung_A2.dwg"
)


 

Now I see that your block names start with underscores - the previous program was excluding any blocks with an underscore prefix (since these are usually dimension style blocks).

 

Try the following code:

 

;; Redefine All Blocks  -  Lee Mac
(defun c:redefall ( / bln dir doc dwg lst obj org spc )

    (setq dir "I:\\AutoCAD Blöcke\\Template\\Support") ;; Directory of Block Library; nil to use Support Path

    (if dir
        (setq dir (strcat (vl-string-right-trim "\\" (vl-string-translate "/" "\\" dir)) "\\"))
        (setq dir "")
    )
    (cond
        (   (= 4 (logand 4 (cdr (assoc 70 (tblsearch "layer" (getvar 'clayer))))))
            (princ "\nCurrent layer locked.")
        )
        (   (setq doc (vla-get-activedocument (vlax-get-acad-object))
                  spc (vla-get-modelspace doc)
                  org (vlax-3D-point 0 0)
            )
            (terpri)
            (vlax-for blk (vla-get-blocks doc)
                (if
                    (and
                        (= :vlax-false (vla-get-isxref blk))
                        (= :vlax-false (vla-get-islayout blk))
                        (not (wcmatch (setq bln (vla-get-name blk)) "`**,*|*"))
                    )
                    (if (setq dwg (findfile (strcat dir bln ".dwg")))
                        (progn
                            (princ (strcat "Redefining block: " dwg "\n"))
                            (setq obj (vla-insertblock spc org dwg 1.0 1.0 1.0 0.0))
                            (if (= :vlax-true (vla-get-hasattributes obj))
                                (setq lst (vl-list* "," bln lst))
                            )
                            (vla-delete obj)
                        )
                        (princ (strcat "Unable to locate block: " dir bln ".dwg\n"))
                    )
                )
            )
            (if lst
                (progn
                    (princ "Synchronising attributes for redefined blocks...\n")
                    (vl-cmdf "_.attsync" "_N" (apply 'strcat (cdr lst)))
                )
            )
            (textscr)
            (vla-regen doc acallviewports)
        )
    )
    (princ)
)
(vl-load-com) (princ)

 

Message 19 of 40
Klingi162
in reply to: Lee_Mac

Hey Lee Mac,

 

I didn't look in the forum for quite a while and just noticed, that you already answered a while a go. 

Your new script works like a miracle (whouldn't expect different 😉 ), thanks a lot for that. It does exactly what it should do. Smiley Happy

 

I appreciate that.

I'm going to donate on your site and hope you keep on going to help us Neebies!

 

Cheers Klingi

Message 20 of 40
CADbloke
in reply to: Lee_Mac

This is brilliant ... but the ATTYNC part didn't work for me until I changed these parts ...

 

-      (setq lst (vl-list* "," bln lst))
+     (setq lst (vl-list* bln lst))

 ...and ...

- (vl-cmdf "_.attsync" "_N" (apply 'strcat (cdr lst)))

+++
(foreach blk lst (vl-cmdf "_.attsync" "_N" blk)
);foreach

 ... and , of course, added "blk" to the locals declaration at the top of the file.

 

Thanks for writing the Lee, you're a Leegend. 😉

- - - - - - -
working on all sorts of things including www.tvCAD.tv & www.CADreplace.com

Can't find what you're looking for? Ask the community or share your knowledge.

Post to forums  

Autodesk Design & Make Report

”Boost