.NET

.NET

Reply
Active Contributor
xdbk07
Posts: 42
Registered: ‎11-06-2012
Message 1 of 3 (386 Views)
Accepted Solution

search and work with atribute block in current space

386 Views, 2 Replies
12-04-2012 05:08 PM

Hi everybody,

I want to search and replace value of block reference in layout1. But I do not want to replace that block in layout2 or layout3. Please tell me how can I do?

Thanks,

Here is the final working code (in C#). Use DeveloperFusion to convert to VB.NET. This code will find and replace only attributes of block references in a given layout name. If you don't specify layout name (empty string), it will find and replace block attribute values in the whole drawing database.

 

[CommandMethod("FindReplaceAttributeValues")]
public static void FindReplaceAttributeValues()
{
Document document = Application.DocumentManager.MdiActiveDocument;
Database db = document.Database;
Editor editor = document.Editor;
editor.WriteMessage("Replace all found block attribute values.\n");
PromptResult findResult = editor.GetString("Find text: ");
PromptResult replaceResult = editor.GetString("Replace text: ");
string findText = findResult.StringResult;
string replaceText = replaceResult.StringResult;
string layoutName = "Layout1"; // Target layout name to find block attributes
FindReplaceAttributeValues(db, findText, replaceText, layoutName);
}
public static int FindReplaceAttributeValues(Database db, string findText, string replaceText, string layoutName = "")
{
int count = 0;
if (string.IsNullOrEmpty(findText))
return count;
if (replaceText == null)
replaceText = string.Empty;
using (Transaction trans = db.TransactionManager.StartTransaction())
{
var blockTable = (BlockTable)trans.GetObject(db.BlockTableId, OpenMode.ForRead);
foreach (ObjectId objectId in blockTable)
{
var btr = (BlockTableRecord)trans.GetObject(objectId, OpenMode.ForRead);
if (btr.Name.StartsWith("*")) // Search for Model and Paper spaces
{
if (layoutName != "")
{
// Check layout for each block table record
if (btr.IsLayout)
{
var layout = (Layout)trans.GetObject(btr.LayoutId, OpenMode.ForRead);
if (!layout.LayoutName.Equals(layoutName, StringComparison.OrdinalIgnoreCase))
continue; // skip the current loop, move to the next block table record
}
}
foreach (ObjectId id in btr)
{
var entity = trans.GetObject(id, OpenMode.ForRead);
if (entity is BlockReference)
{
var blockRef = (BlockReference)entity;
AttributeCollection attributeCollection = blockRef.AttributeCollection;
foreach (ObjectId attributeId in attributeCollection)
{
var attRef = (AttributeReference)trans.GetObject(attributeId, OpenMode.ForRead);
if (attRef.TextString.Equals(findText, StringComparison.OrdinalIgnoreCase))
{
attRef.UpgradeOpen();
attRef.TextString = replaceText;
attRef.AdjustAlignment(HostApplicationServices.WorkingDatabase);
attRef.DowngradeOpen();
count++;
}
}
}
}
}
}
trans.Commit();
}
return count;
}

 

-Khoa

 

Mentor
khoa.ho
Posts: 224
Registered: ‎09-15-2011
Message 2 of 3 (382 Views)

Re: search and work with atribute block in current space

12-04-2012 05:42 PM in reply to: xdbk07

Hi,

If you have a layout name (Layout1, Layout2…), you can get its block table record of this layout. Then search for all block references in this block table record. For each block reference, loop through each attribute reference in the attribute collection (use BlockReference.AttributeCollection), compare its attribute TextString with the search value. If it is equal, change it with the replace value.

The following method will get the block table record ObjectId of a given layout name:

public static ObjectId GetSpaceId(Database db, string layoutName)
{
    using (Transaction trans = db.TransactionManager.StartTransaction())
    {
        var layoutDict = (DBDictionary)trans.GetObject(db.LayoutDictionaryId, OpenMode.ForRead);
        ObjectId layoutId = layoutDict.GetAt(layoutName);
        var layout = (Layout)trans.GetObject(layoutId, OpenMode.ForRead);
        return layout.BlockTableRecordId;
    }
}

 

-Khoa

Mentor
khoa.ho
Posts: 224
Registered: ‎09-15-2011
Message 3 of 3 (361 Views)

Re: search and work with atribute block in current space

12-04-2012 10:46 PM in reply to: xdbk07

Here is the final working code (in C#). Use DeveloperFusion to convert to VB.NET. This code will find and replace only attributes of block references in a given layout name. If you don't specify layout name (empty string), it will find and replace block attribute values in the whole drawing database.

 

[CommandMethod("FindReplaceAttributeValues")]
public static void FindReplaceAttributeValues()
{
    Document document = Application.DocumentManager.MdiActiveDocument;
    Database db = document.Database;
    Editor editor = document.Editor;
    
    editor.WriteMessage("Replace all found block attribute values.\n");
    PromptResult findResult = editor.GetString("Find text: ");
    PromptResult replaceResult = editor.GetString("Replace text: ");
    string findText = findResult.StringResult;
    string replaceText = replaceResult.StringResult;
    
    string layoutName = "Layout1"; // Target layout name to find block attributes

    FindReplaceAttributeValues(db, findText, replaceText, layoutName);
}

public static int FindReplaceAttributeValues(Database db, string findText, string replaceText, string layoutName = "")
{
    int count = 0;
    if (string.IsNullOrEmpty(findText))
        return count;
    if (replaceText == null)
        replaceText = string.Empty;
    using (Transaction trans = db.TransactionManager.StartTransaction())
    {
        var blockTable = (BlockTable)trans.GetObject(db.BlockTableId, OpenMode.ForRead);
        foreach (ObjectId objectId in blockTable)
        {
            var btr = (BlockTableRecord)trans.GetObject(objectId, OpenMode.ForRead);
            if (btr.Name.StartsWith("*"))    // Search for Model and Paper spaces
            {
                if (layoutName != "")
                {
                    // Check layout for each block table record
                    if (btr.IsLayout)
                    {
                        var layout = (Layout)trans.GetObject(btr.LayoutId, OpenMode.ForRead);
                        if (!layout.LayoutName.Equals(layoutName, StringComparison.OrdinalIgnoreCase))
                            continue;    // skip the current loop, move to the next block table record
                    }
                }
                foreach (ObjectId id in btr)
                {
                    var entity = trans.GetObject(id, OpenMode.ForRead);
                    if (entity is BlockReference)
                    {
                        var blockRef = (BlockReference)entity;
                        AttributeCollection attributeCollection = blockRef.AttributeCollection;
                        foreach (ObjectId attributeId in attributeCollection)
                        {
                            var attRef = (AttributeReference)trans.GetObject(attributeId, OpenMode.ForRead);
                            if (attRef.TextString.Equals(findText, StringComparison.OrdinalIgnoreCase))
                            {
                                attRef.UpgradeOpen();
                                attRef.TextString = replaceText;
                                attRef.AdjustAlignment(HostApplicationServices.WorkingDatabase);
                                attRef.DowngradeOpen();
                                count++;
                            }
                        }
                    }
                }
            }
        }
        trans.Commit();
    }
    return count;
}

 

-Khoa

 

Post to the Community

Have questions about Autodesk products? Ask the community.

New Post
Announcements
Do you have 60 seconds to spare? The Autodesk Community Team is revamping our site ranking system and we want your feedback! Please click here to launch the 5 question survey. As always your input is greatly appreciated.