Hatch cannot be updated automatically after dynamic block attributes are modified

Hatch cannot be updated automatically after dynamic block attributes are modified

zzx2
Explorer Explorer
727 Views
1 Reply
Message 1 of 2

Hatch cannot be updated automatically after dynamic block attributes are modified

zzx2
Explorer
Explorer

The version I am using is CAD2020. I encountered the same problem in CAD2018 and CAD2019.
Scenario: I use the code to copy the block file I need from my block storage drawing to my target drawing project, and then modify the dynamic length and width attributes after inserting. The problem is that the in-block filling cannot be updated automatically. You need to manually open the block file, and then click to save the changes when closing. All blocks will be updated automatically.

zzx2_0-1678255647582.jpeg

zzx2_1-1678255653887.jpeg

 

zzx2_2-1678255666115.jpeg

 

    public class TestCmd
    {
        [CommandMethod("TestCmd")]
        public void Test()
        {
            try
            {
                HatchInDynamicBlock();
            }
            catch (System.Exception ex)
            {
                Trace.WriteLine(ex.Message + ex.StackTrace);
            }
        }

        public void HatchInDynamicBlock()
        {
            Document doc = Autodesk.AutoCAD.ApplicationServices.Core.Application.DocumentManager.MdiActiveDocument;
            Database db = doc.Database;
            ObjectId result = ObjectId.Null;
            Point3d originPoint = new Point3d(0, 0, 0);
            double resultWidth = 1.1;
            double resultHeight = 2.2;
            string blockName = "块状测试图案";
            string blockDWGPath = @"C:\Users\Acer\Desktop\块测试图纸路径\块图纸.dwg";
            ObjectId blockId = ObjectId.Null;
            #region 拿到块的id
            //开启事务处理
            using (Transaction trans = db.TransactionManager.StartTransaction())
            {
                try
                {
                    BlockTable bt = trans.GetObject(db.BlockTableId, OpenMode.ForRead) as BlockTable;
                    if (!bt.Has(blockName))
                    {
                        using (Database tempDB = new Database(false, false))
                        {
                            tempDB.ReadDwgFile(blockDWGPath, FileOpenMode.OpenForReadAndReadShare, true, null);//读取外部DWG到临时数据库
                            tempDB.CloseInput(true);
                            ObjectIdCollection ids = new ObjectIdCollection();//存放块OjbectId的集合
                            using (Transaction trans2 = tempDB.TransactionManager.StartTransaction())
                            {
                                BlockTable bt2 = trans2.GetObject(tempDB.BlockTableId, OpenMode.ForRead) as BlockTable;
                                ObjectId targetID = bt2[blockName];
                                ids.Add(targetID);
                            }
                            ////复制临时数据库中的块到当前数据库的块表中
                            tempDB.WblockCloneObjects(ids, db.BlockTableId, new IdMapping(), DuplicateRecordCloning.Ignore, false);
                        }
                    }
                    blockId = bt[blockName];
                }
                catch (System.Exception ex)
                {
                    Trace.WriteLine(ex.Message);
                }
                trans.Commit();
            }
            #endregion

            #region 插入块
            using(Transaction createTrans = doc.TransactionManager.StartTransaction())
            {
                //插入图块
                BlockTable bt = createTrans.GetObject(db.BlockTableId, OpenMode.ForRead) as BlockTable;
                BlockTableRecord curBtr = createTrans.GetObject(bt[BlockTableRecord.ModelSpace], OpenMode.ForWrite) as BlockTableRecord;
                //Trace.WriteLine(blockId.ToString());
                db.TransactionManager.QueueForGraphicsFlush();
                using (BlockReference blockRef = new BlockReference(originPoint, blockId))
                {
                    db.Regenmode = true;
                    result = curBtr.AppendEntity(blockRef);
                    createTrans.AddNewlyCreatedDBObject(blockRef, true);
                }
                createTrans.Commit();
            }
            #endregion

            #region 修改动态快属性
            using (Transaction trans2 = doc.TransactionManager.StartTransaction())
            {
                try
                {
                    doc.TransactionManager.QueueForGraphicsFlush();
                    BlockReference blockRef = trans2.GetObject(result, OpenMode.ForWrite, true, true) as BlockReference;
                    BlockTableRecord btr = trans2.GetObject(blockRef.BlockTableRecord, OpenMode.ForWrite) as BlockTableRecord;
                    var blockDynamicProperty = blockRef.DynamicBlockReferencePropertyCollection;
                    List<DynamicBlockReferenceProperty> blockPropertyList = blockDynamicProperty.OfType<DynamicBlockReferenceProperty>().ToList();
                    blockPropertyList.FirstOrDefault(x => x.PropertyName.Equals("长度")).Value = resultHeight;
                    blockPropertyList.FirstOrDefault(x => x.PropertyName.Equals("宽度")).Value = resultWidth;
                    btr.UpdateAnonymousBlocks();
                }
                catch (System.Exception ex)
                {

                    Trace.WriteLine(ex.Message);
                }
                trans2.Commit();
            }
            #endregion

        }
    }

Where Path is replaced by the downloaded block drawing file path。

I also provide the block drawing file I use to test, and I will occasionally encounter this kind of thing, especially when it comes to batch generation, I hope I can get your help

 

0 Likes
728 Views
1 Reply
Reply (1)
Message 2 of 2

Ed__Jobe
Mentor
Mentor

Your code could use some cleaning up, but the main problem is that you need to update the properties of the block reference, not the block table record. See this post for a sample. Note the section below. It uses a method called SetDynProps to set the properties of the BlockReference. Note that you don't need multiple transactions. You do it in the same transaction, where you already have a reference to the BlockReference.

 using (var tr = db.TransactionManager.StartTransaction())
            {
                // insert the block reference and set its dynamic properties
                var curSpace = (BlockTableRecord)tr.GetObject(db.CurrentSpaceId, OpenMode.ForWrite);
                var br = new BlockReference(Point3d.Origin, btrId);
                curSpace.AppendEntity(br);
                tr.AddNewlyCreatedDBObject(br, true);
                SetDynProps(br, dynPropValues);

                // create the solid 3d
                CreateSweptSolid(ed, startPoint, endPoint, tr, curSpace, br);
                tr.Commit();
            }

 

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