You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

AutoCAD .NET API(C#)合并DXF块问题:丢失原块结构与颜色

解决AutoCAD .NET合并块丢失结构与颜色的问题

问题根源

  1. 块结构丢失:原代码直接提取块内实体复制到新块,未保留原块的嵌套引用关系,应通过创建BlockReference插入原块来保留结构
  2. 颜色丢失:浅克隆未完整复制实体特性,且未处理图层、线型等依赖资源;部分实体颜色继承自图层,需确保属性正确传递
  3. 错误遍历特殊空间:原代码遍历所有BlockTableRecord,包含模型空间、布局空间等系统空间,导致冗余或错误实体

修正后的代码

using Autodesk.AutoCAD.ApplicationServices;
using Autodesk.AutoCAD.DatabaseServices;
using Autodesk.AutoCAD.Runtime;
using Autodesk.AutoCAD.Geometry;

namespace CombineBlockTableRecords
{
    public class Commands
    {
        [CommandMethod("CombineBlocks")]
        public void CombineBlocks()
        {
            Document doc = Application.DocumentManager.MdiActiveDocument;
            Database db = doc.Database;

            using (Transaction tr = db.TransactionManager.StartTransaction())
            {
                BlockTable bt = tr.GetObject(db.BlockTableId, OpenMode.ForRead) as BlockTable;
                BlockTableRecord modelSpace = tr.GetObject(bt[BlockTableRecord.ModelSpace], OpenMode.ForRead) as BlockTableRecord;

                // 创建新块定义
                BlockTableRecord newBlockDef = new BlockTableRecord();
                newBlockDef.Name = "CombinedBlock";
                newBlockDef.Origin = Point3d.Origin;

                bt.UpgradeOpen();
                ObjectId newBlockDefId = bt.Add(newBlockDef);
                tr.AddNewlyCreatedDBObject(newBlockDef, true);

                // 1. 处理所有用户自定义块:创建BlockReference插入新块,保留嵌套结构
                foreach (ObjectId btrId in bt)
                {
                    BlockTableRecord btr = tr.GetObject(btrId, OpenMode.ForRead) as BlockTableRecord;
                    // 排除新块、模型空间、布局空间和匿名块
                    if (btrId == newBlockDefId || btr.IsLayout || btr.IsAnonymous)
                        continue;

                    // 创建原块的引用并插入新块
                    BlockReference br = new BlockReference(Point3d.Origin, btrId);
                    newBlockDef.AppendEntity(br);
                    tr.AddNewlyCreatedDBObject(br, true);
                }

                // 2. 处理模型空间中的原始实体:复制并保留所有特性
                foreach (ObjectId entId in modelSpace)
                {
                    Entity ent = tr.GetObject(entId, OpenMode.ForRead) as Entity;
                    // 跳过新块的引用(避免后续重复处理)
                    if (ent is BlockReference br && br.BlockTableRecord == newBlockDefId)
                        continue;

                    // 深克隆实体并完整复制属性
                    Entity entCopy = ent.Clone() as Entity;
                    ent.CopyPropertiesTo(entCopy);
                    entCopy.Color = ent.Color;
                    newBlockDef.AppendEntity(entCopy);
                    tr.AddNewlyCreatedDBObject(entCopy, true);
                }

                // 3. 可选:清空模型空间并插入新块的引用,实现整体嵌套替换
                modelSpace.UpgradeOpen();
                foreach (ObjectId entId in modelSpace)
                {
                    Entity ent = tr.GetObject(entId, OpenMode.ForWrite) as Entity;
                    ent.Erase();
                }
                BlockReference newBlockRef = new BlockReference(Point3d.Origin, newBlockDefId);
                modelSpace.AppendEntity(newBlockRef);
                tr.AddNewlyCreatedDBObject(newBlockRef, true);

                tr.Commit();
            }
        }
    }
}

关键改动说明

  • 保留块嵌套结构:遍历用户自定义块时,创建BlockReference插入到新块中,而非直接复制块内实体,完整保留原块的层级关系
  • 完整保留实体特性:使用CopyPropertiesTo复制实体的所有属性,显式同步颜色值,确保颜色、线型等属性不丢失
  • 过滤无效空间:排除模型空间、布局空间、匿名块和新创建的块,避免冗余操作和错误
  • 整合模型空间实体:将模型空间中的原始实体也纳入新块,并可选清空原空间插入新块引用,实现所有内容的统一嵌套

内容的提问来源于stack exchange,提问作者Guitar123

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.01 04:19:51