Block rename VBA

Anonymous

Block rename VBA

Anonymous
Not applicable

Hi !

I would like to change the name of the selected block (one block). I know how to change the name of all the blocks in the drawing, but I'm not looking for this solution.

Any suggestions ?

Thank you so much for your help!

0 Likes
Reply
4,985 Views
16 Replies
Replies (16)

Anonymous
Not applicable

hi

 

user the commande lyne : rename.  (sr my acad is is french so my cmd is 'renommer'

 

this rename the bloc ou style etc.. it is very usefull

 

0 Likes

Anonymous
Not applicable

Hi,

Thank you for your answer but this function changes the name of all the blocks in the drawing.

For example:

If I have 10 blocks with name "ddd" and I use function "rename" than I have 10 blocks with new name but I do not want to change  name for every blocks. For example I want to change name for 3 block, than I want to have 7 block with old name and 3 blocks with new name.

 

0 Likes

norman.yuan
Mentor
Mentor

Since we are discussing in programming forum, we'd better make sure to use correct technical terms. I believe you want to rename block reference (AcadBlockReference), not the block definition (AcadBlock).

 

Yes, you can rename block reference inserted in drawing to a different block name, AS LONG AS there is a block defined in the drawing that has that name. The effect of renaming a block reference is that the block refernce with the orginal name would be erased from the drawing and a new block reference to the block definition with the targeting name would be then created with the same insertion point/scale/rotation...

 

If you try to rename a block reference to a name that no block definition in the drawing bearing that name, an exception ("Key not found") would occur.

 

In your case of having 10 block references with a given name (e.g. name inherited from its block definition), if you want to rename 3 of them to another block definition's name, you need some code to distiguish that 3 block references first, for example, pick it one by one. Some quick code like this (didnot test-run in Acad, though):

 

Dim ent as AcadEntity

Dim blk As AcadBlockReference

Dim pt As Variant

Dim i As Integer

Do

    ''Pick block reference

    ThisDrawing.Utility.GetEntity ent, pt, vbcr & "Pick a block AAA:"

    If TypeOf ent Is AcadBlockReference Then

        Set blk=ent

        If Ucase(blk.Name)="AAA" Then

            blk.Name="BBB" 'The MUST be a block "BBB" defined in this drawing first

            i=i+1

        Else

           ThsDrawing.Utility.Prompt vbcr & "Picked block is not block AAA!"

        End If

    Else

        ThisDrawing.Utility.Prompt vbcr & "Picked entity is not a block reference!"

    End If

Loop While (i<3)

 

Obviously, you need to catch the exception if user hit "ESC", so that you can jump out from the Do...Loop.

 

Norman Yuan

Drive CAD With Code

EESignature

0 Likes

Anonymous
Not applicable

Thank you for your help. Now I know where it was a mistake.

0 Likes

Anonymous
Not applicable

Good morning!

 

This is a bit late, but I'm hoping you may be able to have with an similar issue I'm encountering right now:

I am trying to build code from Excel VBA to rename blocks in CAD, so far I have this but it's not working I getting " Run Time Error '450' : Wrong Number of Arguements or Invalid Property Assignment". I'll drop the code and hopefully you can help me? In this example I am trying to change the block name to "ABC123".

 

Thank you!

Sub DynBlockRename()
    'Dim dybprop As Variant, i As Integer
    Dim dynblock As AcadEntity
    Dim ThisDrawing As AcadDocument
    'Dim InsertionPoint(0 To 2)  As Double
    Set ThisDrawing = AcadApplication.ActiveDocument
    For Each dynblock In ThisDrawing.ModelSpace  'Starts looping through all blocks
        If dynblock.ObjectName = "AcDbBlockReference" Then 'Check if BlockRef, yes
            If dynblock.IsDynamicBlock Then         'Check to see if it is a Dynamic Block
               dybprop = dynblock.GetDynamicBlockProperties
                If dynblock.EffectiveName = "FSM4L- INCH INCREMENT_DONE_01" Then 'Finds Dynamic Block NAME
                    'If dynblock.EffectiveName Like "FSM4L*" Then     THIS WOULD FIND ALL THAT START WITH SAME NAME
                    dynblock.EffectiveName = "ABC123"
                            ThisDrawing.Regen acActiveViewport
                End If
            End If
        End If
    Next

End Sub

 

0 Likes

ed57gmc
Mentor
Mentor

Two things,

1. the comment you added after the If statement is not preceded by a single quote to mark it as a comment.

2. You don't rename a block reference, you need to rename the block definition, an AcadBlock object. The EffectiveName property is read-only.

Ed


Did you find this post helpful? Feel free to Like this post.
Did your question get successfully answered? Then click on the ACCEPT SOLUTION button.
How to post your code.

EESignature

0 Likes

norman.yuan
Mentor
Mentor

Why do you want to rename anonymous block generated by AutoCAD automatically due to the dynamic property value applied to a block reference? IMO, you SHOULD NOT DO this, or you risk losing AutoCAD's control of managing dynamic blocks in a drawing. Do not do it!

Norman Yuan

Drive CAD With Code

EESignature

0 Likes

Anonymous
Not applicable

Good morning Norman,

 

Thank you for the concern but I think I didn't translate myself clearly, I do not want to rename anonymous blocks, I want to rename a certain block within the dwg, so I am trying to write the code to read something like 

" If BlockName = "FSM4L- INCH INCREMENT_DONE_01"

     Then Rename.BlockName = "ABC123"   ".

I think "Rename.BlockName" is not a real thing, but I'm sure you get the concept now. I just want the code to look throughout the drawing, see if there's a block named one thing and rename it to another. Do you think you can help with this?

Thank you!

0 Likes

norman.yuan
Mentor
Mentor

Sorry, I still not quite understand your question clearly, because your code CLEARLY shows you want to rename a dynamic block reference. So, here are my thoughts:

 

1. If you intended target is dynamic block reference, I'd say, do not do it. The "EffectiveName" property is read-only, because dynamic block reference is usually a reference to anonymous block, which is created/managed by AutoCAD automatically.

 

2. If it is regular block reference, yes, you can rename its "Name" property, but the new name MUST BE an existing block definition's name; or you would run into error. In this case, the renaming is actually changing the block reference to ANOTHER block definition, because "Name" property of AcadBlockReference is from the block definition, indicating which block definition it is referenced to, this, changing its name, you point this block reference to a different block definition. I am not sure if this is what you want to do.

 

Norman Yuan

Drive CAD With Code

EESignature

0 Likes

Anonymous
Not applicable

Hi Norman, 

 

Thank you for bearing with me, I probably made things confusing by the way I wrote the code, I took a code I have for changing the visibility of a dynamic block and tried to modify it to work for renaming blocks and that's where the confusion is coming from.

 

What I need is a code that changes the name of a block. Let's say I do "Insert", "Browse", select my dwg to insert as a block (block being named same as dwg file) AND THEN I need the code to go ahead and rename it that block. 

 

I'll attach a dwg of the block already inserted and the dwg of the block. 

 

If you could help me that would be wonderful, once again, thank you for your patience!

0 Likes

norman.yuan
Mentor
Mentor

OK, if we ignore the code you posted previously, and take what you said here, then things get clearer and simpler. However, I still have to make thing absolutely clear on what you want:

 

You insert a block from file, say, "MyBlock1.dwg" with Insert command, into say, current drawing in AutoCAD. The net result of that is:

1. A block definition named as "MyBlock1" is created in the drawing;

2. A block reference to this block definition is created in current space (model, or paper), this block reference ALSO has name "MyBlock1".

3. Now you want to run a piece of code that change the block name from "MyBlock1" to, say, "MyBlock2".

 

Now it is not very clear on your intention: rename the block definition, or block reference.

 

1. Rename block definition. In this case, once a block definition is renamed (of course you cannot use a new name that has already exists in block table), all block references to this definition (0 or more) will automatically has the new block name and remain as references to this definition. If this is what you want to do, then the code would be very simple:

 

Dim blk As AcadBlock

For Each blk in ThisDrawing.Blocks

    If UCase(blk.Name)="[WHATEVER]" Then

        blk.Name = "[NEW_NAME]" '''' As long as the new name is not duplicated

        Exit For

    End If

Next

 

After this code, if there are block references of this block definition in drawing, they will automatically get new block name. That is, changing block definition's name would change the names of all block references (to this definition).

 

2. Rename block reference. Theoretically, block reference name is is definition's name and should be "Read-only". However, in AutoCAD COM API, AcadBlockReference's "Name" property is used to track which block definition it is referenced to, thus it is changeable, meaning if the name is changed (to another existing block definition's name), you literally change the block reference to point to a DIFFERENT block definition. I suspect this is not what you are after.

 

 

 

Norman Yuan

Drive CAD With Code

EESignature

0 Likes

Anonymous
Not applicable

Good morning Norman, 

 

I hope you had a great Thanksgiving, over the last few days I tweaked the code you initially provided me in order to work for me and I'll drop it down below in case

Sub Rename_Blocks()
Dim acadApp As Object
Dim acadBlock As Object
Dim acadDoc As Object
Dim ThisDrawing As AcadDocument
Dim BlockName As String

    On Error Resume Next
    Set acadApp = GetObject(, "AutoCAD.Application")
    If acadApp Is Nothing Then
        Set acadApp = CreateObject("AutoCAD.Application")
        acadApp.Visible = True
    End If
    
   
    If acadApp Is Nothing Then
        MsgBox "Sorry, it was impossible to start AutoCAD!", vbCritical, "AutoCAD Error"
        Exit Sub
    End If
    On Error GoTo 0
    
    
    On Error Resume Next
    Set acadDoc = acadApp.ActiveDocument
    If acadDoc Is Nothing Then
        Set acadDoc = acadApp.Documents.Add
    End If
    On Error GoTo 0
    
    Set ThisDrawing = AcadApplication.ActiveDocument
    For Each acadBlock In ThisDrawing.Blocks

    'If BlockName = "FSM4L- INCH INCREMENT_DONE_01" Then
     If UCase(BlockName) = "FSM4L- INCH INCREMENT_DONE_01" Then
        'BlockName = "Block1" ' As long as the new name is not duplicated
        BlockName = "Block1"
        Set acadBlock = acadDoc.ModelSpace.InsertBlock(InsertionPoint, BlockName, _
                                BlockScale.X, BlockScale.Y, BlockScale.Z, RotationAngle * 0.0174532925)

    Exit For

    End If

    Next

End Sub

you or anyone else might be looking for the same thing.

 

Thank you for your patience and all your help Norman!

0 Likes

Anonymous
Not applicable

Hey Norman,

 

False alert, I have been trying to use the code I posted yesterday and it turns out it's not working at all. I have been trying to use/ fix it since 5 am this morning but whenever I run the code, it doesn't crash but nothing is changing to the drawing. I am stepping into the code step by step and I believe it's not recognizing the " If UCase (BlockName) = "FSM4L- INCH INCREMENT_DONE_01" Then". The "ThisDrawing" component of this code recognizes that the current drawing does include this block but the "BlockName" isn't catching onto that so it's unable to change it afterward. Do you think you can help with this?

 

Thank you in advance!

0 Likes

Anonymous
Not applicable

Hey Norman,

 

False alert, I have been trying to use the code I posted yesterday and it turns out it's not working at all. I have been trying to use/ fix it since 5 am this morning but whenever I run the code, it doesn't crash but nothing is changing to the drawing. I am stepping into the code step by step and I believe it's not recognizing the " If UCase (BlockName) = "FSM4L- INCH INCREMENT_DONE_01" Then". The "ThisDrawing" component of this code recognizes that the current drawing does include this block but the "BlockName" isn't catching onto that so it's unable to change it afterward. Do you think you can help with this?

 

Thank you in advance!

0 Likes

norman.yuan
Mentor
Mentor

If you step through your code and look into the value of this variable "BlockName", you would have found it is empty: it is declared but never given a value, so there is where it went wrong:

    For Each acadBlock In ThisDrawing.Blocks
     If UCase(BlockName) = "FSM4L- INCH INCREMENT_DONE_01" Then
        'BlockName = "Block1" ' As long as the new name is not duplicated
        BlockName = "Block1"
        Set acadBlock = acadDoc.ModelSpace.InsertBlock(InsertionPoint, BlockName, _
                                BlockScale.X, BlockScale.Y, BlockScale.Z, RotationAngle * 0.0174532925)

        Exit For
End If
Next

As you can see, you compare an empty string to a string value, so, nothing runs inside the "If... Then". So, ALWAYS DO debugging first. If you place a break point inside the If.. clause, you would have immediately noticed that the break point would not be hit, and the If... condition is wrong.

 

Also, you meant to RENAME block, not a string value (BlockName). So the code really should be something like:

    Dim BlockName As String
'' The new block name you want the block to be renamed 
'' However, you may want to loop through the AcadBlocks collection to
'' make sure the name does not already exist.
BlockName = "Block1"
... ...
... ...
For Each acadBlock In ThisDrawing.Blocks If UCase(acadBlock.Name) = "FSM4L- INCH INCREMENT_DONE_01" Then acadBlock.Name = BlockName Set acadBlock = acadDoc.ModelSpace.InsertBlock(InsertionPoint, BlockName, _ BlockScale.X, BlockScale.Y, BlockScale.Z, RotationAngle * 0.0174532925) Exit For End If Next    

Again, do debugging your code by placing break point somewhere in your code and use F8/local window to step through the code; most likely than not, you would fix code error easier, faster.

 

Norman Yuan

Drive CAD With Code

EESignature

0 Likes

Anonymous
Not applicable
Option Explicit


Private Type ScaleFactor
    X As Double
    Y As Double
    Z As Double
End Type

Sub RENAME3()
     
    
    Dim acadApp                 As Object
    Dim acadDoc                 As Object
    Dim acadBlock               As Object
    Dim LastRow                 As Long
    Dim i                       As Long
    Dim InsertionPoint(0 To 2)  As Double
    Dim BlockName               As String
    Dim BlockScale              As ScaleFactor
    Dim RotationAngle           As Double
    Dim thisdrawing As AcadDocument
    
   
   ' With ThisWorkbook.Worksheets("Patterns").Activate
        'LastRow = Worksheets("Patterns").Cells(Rows.Count, "A").End(xlUp).Row
    'End With
        
   
    'If LastRow < 2 Then
     '   MsgBox "There are no coordinates for the insertion point!", vbCritical, "Insertion Point Error"
      '  Exit Sub
    'End If
    
   
    On Error Resume Next
    Set acadApp = GetObject(, "AutoCAD.Application")
    If acadApp Is Nothing Then
        Set acadApp = CreateObject("AutoCAD.Application")
        acadApp.Visible = True
    End If
    
   
    If acadApp Is Nothing Then
        MsgBox "Sorry, it was impossible to start AutoCAD!", vbCritical, "AutoCAD Error"
        Exit Sub
    End If
    On Error GoTo 0
    
    
    On Error Resume Next
    Set acadDoc = acadApp.ActiveDocument
    If acadDoc Is Nothing Then
        Set acadDoc = acadApp.Documents.Add
    End If
    On Error GoTo 0

    
    If acadDoc.ActiveSpace = 0 Then
        acadDoc.ActiveSpace = 1
    End If
    
    On Error Resume Next
    
    Set thisdrawing = AcadApplication.ActiveDocument
For Each acadBlock In thisdrawing.Blocks

    If UCase(acadBlock.Name) = "FSM4L- INCH INCREMENT_DONE_01" Then

        acadBlock.Name = "ABC123" ' As long as the new name is not duplicated

        Exit For

    End If

Next
    
    
    acadApp.ZoomExtents

    
    Set acadBlock = Nothing
    Set acadDoc = Nothing
    Set acadApp = Nothing
    
    


End Sub








Hey Norman! I'm not exactly sure what I did, but somehow I ran the old code I had and it's working perfectly now but I will definitively go and update the blockname string to have a certain value and allocate it where necessary, that'll keep things cleaner. Once again a million thank you's Norman, lifesaver!

0 Likes