Looks like it works ... i checked on few DWG and it works correct...last problem are rotations. Does anybody know how to get rotation from nested block? because blockreference rotation doesn't have property TransformBy
[CommandMethod("ScanBlocks")]
public void ScanBlocks()
{
Document doc = Application.DocumentManager.MdiActiveDocument;
Database db = doc.Database;
using (DocumentLock acLckDoc = doc.LockDocument())//lock mother window
{
using (Transaction tr = db.TransactionManager.StartTransaction())
{
RXClass blockReferenceType = RXClass.GetClass(typeof(BlockReference));
DBDictionary layouts = (DBDictionary)tr.GetObject(db.LayoutDictionaryId, OpenMode.ForRead);
foreach (var lay in layouts)
{
if (lay.Key.ToLower() == "model")
{
Layout layout = (Layout)tr.GetObject(lay.Value, OpenMode.ForRead);
BlockTableRecord btr = (BlockTableRecord)tr.GetObject(layout.BlockTableRecordId, OpenMode.ForRead);
foreach (ObjectId id in btr)
{
if (id.ObjectClass == blockReferenceType)
{
BlockReference baseBlock = (BlockReference)tr.GetObject(id, OpenMode.ForRead);
List<DrawingElement> test = new List<DrawingElement>();
List<BlockReference> parentReferenceList = new List<BlockReference>();
int level = 0;
LoopNestedBlocks(test, tr, baseBlock, parentReferenceList, ref level);
if (baseBlock.Name == "BaseBlock") /*A$C70C23CFC*/
{
foreach (DrawingElement item in test)
{
Debug.Print(item.BlocName + " " + item.Cordinate.Position.X + " " + item.Cordinate.Position.Y + " " + item.Cordinate.Position.Z);
}
}
}
}
}
}
}
}
}
class DrawingElement
{
public string BlocName { get; set; }
public PointTransformed Cordinate { get; set; }
}
class PointTransformed
{
public Point3d Position { get; set; }
public Boolean IsNull { get; set; } = true;
public double Rotation { get; set; }
}
private static void LoopNestedBlocks(List<DrawingElement> currentList, Transaction trParent, BlockReference brCurrent, List<BlockReference> parentReferenceList, ref int parentLevel)
{
try
{
BlockTableRecord btr = (BlockTableRecord)trParent.GetObject(brCurrent.BlockTableRecord, OpenMode.ForRead);
if (btr != null)
{
List<DrawingElement> subList = new List<DrawingElement>();
int currentBlockLevel = 0;
GetCurrentLevel(brCurrent, trParent, ref currentBlockLevel, parentReferenceList);
if (currentBlockLevel != parentReferenceList.Count)
parentReferenceList.RemoveRange(currentBlockLevel, parentReferenceList.Count - currentBlockLevel);
Point3d currentBlockPosition = brCurrent.Position;
for (int i = parentReferenceList.Count; i > 0; i--)
{
BlockReference parentBlockRef = parentReferenceList[i - 1];
currentBlockPosition = currentBlockPosition.TransformBy(parentBlockRef.BlockTransform);
}
PointTransformed pointCurrent;
pointCurrent = new PointTransformed()
{
Position = currentBlockPosition,
IsNull = false
};
DrawingElement currentElement = new DrawingElement()
{
Cordinate = pointCurrent,
BlocName = brCurrent.Name
};
currentList.Add(currentElement);
parentReferenceList.Add(brCurrent);
parentLevel = currentBlockLevel;
foreach (ObjectId id in btr)
{
Entity childEntity = (Entity)trParent.GetObject(id, OpenMode.ForRead);
if (childEntity is BlockReference)
LoopNestedBlocks(currentList, trParent, (BlockReference)childEntity, parentReferenceList, ref parentLevel);
}
}
}
catch { }
}
private static void GetCurrentLevel(BlockReference btr, Transaction trParent, ref int currentLevel, List<BlockReference> parentReferenceList)
{
try
{
BlockReference parent = null;
BlockTableRecord owner = (BlockTableRecord)trParent.GetObject(btr.OwnerId, OpenMode.ForRead);
foreach (ObjectId parentId in owner.GetBlockReferenceIds(true, false))
{
parent = (BlockReference)trParent.GetObject(parentId, OpenMode.ForRead);
if (parentReferenceList.Contains(parent))
{
break;
}
}
if (parent != null)
{
currentLevel++;
GetCurrentLevel(parent, trParent, ref currentLevel, parentReferenceList);
}
}
catch { }
}
...