Someone asked me earlier today how to iteratively change the color of entities inside blocks.
The following code uses a recursive helper function to iterate down through the contents of a block, changing the various entities (other than block references, for which we simply recurse) to a specified colour.
Here's the C# code:
using Autodesk.AutoCAD.ApplicationServices;
using Autodesk.AutoCAD.DatabaseServices;
using Autodesk.AutoCAD.EditorInput;
using Autodesk.AutoCAD.Runtime;
using Autodesk.AutoCAD.Colors;
namespace BlockTest
{
public class BlockCmds
{
[CommandMethod("CC")]
public void ChangeColor()
{
Document doc =
Application.DocumentManager.MdiActiveDocument;
Database db = doc.Database;
Editor ed = doc.Editor;
PromptIntegerResult pr =
ed.GetInteger(
"\nEnter color index to change all entities to: "
);
if (pr.Status == PromptStatus.OK)
{
short newColorIndex = (short)pr.Value;
ObjectId msId;
Transaction tr =
doc.TransactionManager.StartTransaction();
using (tr)
{
BlockTable bt =
(BlockTable)tr.GetObject(
db.BlockTableId,
OpenMode.ForRead
);
msId =
bt[BlockTableRecord.ModelSpace];
// Not needed, but quicker than aborting
tr.Commit();
}
int count =
ChangeNestedEntitiesToColor(msId, newColorIndex);
ed.Regen();
ed.WriteMessage(
"\nChanged {0} entit{1} to color {2}.",
count,
count == 1 ? "y" : "ies",
newColorIndex
);
}
}
private int ChangeNestedEntitiesToColor(
ObjectId btrId, short colorIndex)
{
int changedCount = 0;
Document doc =
Application.DocumentManager.MdiActiveDocument;
Database db = doc.Database;
Editor ed = doc.Editor;
Transaction tr =
doc.TransactionManager.StartTransaction();
using (tr)
{
BlockTableRecord btr =
(BlockTableRecord)tr.GetObject(
btrId,
OpenMode.ForRead
);
foreach (ObjectId entId in btr)
{
Entity ent =
tr.GetObject(entId, OpenMode.ForRead)
as Entity;
if (ent != null)
{
BlockReference br = ent as BlockReference;
if (br != null)
{
// Recurse for nested blocks
changedCount +=
ChangeNestedEntitiesToColor(
br.BlockTableRecord,
colorIndex
);
}
else
{
if (ent.ColorIndex != colorIndex)
{
changedCount++;
// Entity is only open for read
ent.UpgradeOpen();
ent.ColorIndex = colorIndex;
ent.DowngradeOpen();
}
}
}
}
tr.Commit();
}
return changedCount;
}
}
}