.NET

.NET

Reply
Active Member
7 Posts
1 Kudo
Registered: ‎09-22-2012
Post 1 of 2

Empty blocktablerecord when inserting from and to database

95 Views, 1 Replies
03-24-2014 11:52 PM

I've recently been porting a batch processing application to work directly on the database instead of the Document so all processing can be done in the background.

 

As a part of this port I rewrote my generic block insert snippet to cope with just a database instead of a document and added 'forwarding methods' to maintain backwards compatibility:

 

Spoiler

 

        public static ObjectId insertBlock(Document acDoc, Transaction acTrans, string blocknaam, DefaultBlock defBlock = DefaultBlock.None)
        {
            return InsertBlock(acDoc, acTrans, blocknaam, false, defBlock);
        }

        public static ObjectId InsertBlock(Document acDoc, Transaction acTrans, string blocknaam, bool overrideExisting = false, DefaultBlock defBlock = DefaultBlock.None)
        {
            return InsertBlock(acDoc.Database, acTrans, blocknaam, overrideExisting, defBlock);
        }
        public static ObjectId InsertBlock(Database db, Transaction acTrans, string blockName, bool overrideExisting = false, DefaultBlock defBlock = DefaultBlock.None)
        {
            ObjectId blkid = ObjectId.Null;
            BlockTable blktbl = acTrans.GetObject(db.BlockTableId, OpenMode.ForRead) as BlockTable;

            if ((blockName != BlockTableRecord.ModelSpace) && (!blktbl.Has(blockName) || overrideExisting)) {
                string fileName = null;
                //Insert the block
                try {
                    fileName = HostApplicationServices.Current.FindFile(blockName + ".dwg", db, FindFileHint.Default);
                }
                catch {
                    //Block hasn't been found. For now just return ObjectId.Null
                    //return CreateBlock(db, acTrans, defBlock);
                    return ObjectId.Null;
                }
                if (!string.IsNullOrEmpty(fileName)) {
                    Database dbNew = new Database(false, false);
                    dbNew.ReadDwgFile(fileName, System.IO.FileShare.Read, false, null);
                    blkid = db.Insert(blockName, db, false);
                    dbNew.Dispose();
                }
            }
            else {
                blkid = blktbl[blockName];
            }
            return blkid;
        }
    }
    internal enum DefaultBlock
    {
        None = -1,
        Point = 0,
        Cross = 1,
        Circle = 2,
    }

 

 

 

The old main block was as following (apologies for the few dutch terms)

 

 

Spoiler

 

		public static ObjectId insertBlock(Document acDoc, Transaction acTrans, string blocknaam, DefaultBlock defBlock = DefaultBlock.None)
		{
			ObjectId blkid = ObjectId.Null;
			BlockTable blktbl = acTrans.GetObject(acDoc.Database.BlockTableId, OpenMode.ForRead) as BlockTable;

			if ((blocknaam != BlockTableRecord.ModelSpace) && (!blktbl.Has(blocknaam))) {
				string fileName = null;
				//We moeten inserten
				try {
					fileName = HostApplicationServices.Current.FindFile(blocknaam + ".dwg", acDoc.Database, FindFileHint.Default);
#if DEBUG
                    acDoc.Editor.WriteMessage("\nBlock {0} inserted from {1}", blocknaam, fileName);
#endif
				}
				catch {
					//Block niet gevonden. Afhankelijk van instellingen moeten we 'm gaan maken
					return CreateBlock(acDoc, acTrans, defBlock, blocknaam);
				}
				if (!string.IsNullOrEmpty(fileName)) {
					Database db = new Database(false, false);
					db.ReadDwgFile(fileName, System.IO.FileShare.Read, false, null);
					blkid = acDoc.Database.Insert(blocknaam, db, false);
					db.Dispose();
				}
			}
			else {
				blkid = blktbl[blocknaam];
			}
			return blkid;
		}

 

 

 

The old code worked, and stills works, just fine. The new code however returns a valid ObjectId for the BlockTableRecord, but when a block with this blkid is inserted, the block is empty. When edited with the block editor, the BlockTableRecord seems to be empty too.

 

The bug seems to be in the following code:

        public static ObjectId InsertBlock(Database db, Transaction acTrans, string blockName, bool overrideExisting = false, DefaultBlock defBlock = DefaultBlock.None)
        {
            if (!string.IsNullOrEmpty(fileName)) {
                Database dbNew = new Database(false, false);
                dbNew.ReadDwgFile(fileName, System.IO.FileShare.Read, false, null);
                blkid = db.Insert(blockName, db, false);
                dbNew.Dispose();
            }
        }

  

Any ideas on how to solve this?

*Expert Elite*
2,142 Posts
255 Kudos
Registered: ‎04-29-2006
Post 2 of 2

Re : Empty blocktablerecord when inserting from and to database

03-25-2014 01:36 AM in reply to: vinkd

Hi,

 

This works for me:

 

        public ObjectId ImportBlock(Database targetDb, string fileName, string blockName, bool overrideExisting)
        {
            if (targetDb == null)
                throw new ArgumentNullException("targetDb");

            if (string.IsNullOrEmpty(fileName))
                throw new ArgumentNullException("fileName");

            if (!File.Exists(fileName))
                throw new FileNotFoundException("File not found", fileName);

            using (Transaction tr = targetDb.TransactionManager.StartOpenCloseTransaction())
            {
                BlockTable bt = (BlockTable)tr.GetObject(targetDb.BlockTableId, OpenMode.ForRead);
                if (bt.Has(blockName) && !overrideExisting)
                    return bt[blockName];
            }

            using (Database sourceDb = new Database())
            {
                sourceDb.ReadDwgFile(fileName, FileShare.Read, false, null);
                return targetDb.Insert(blockName, sourceDb, true);
            }
        }

 

Gilles Chanteau
Post to the Community

Have questions about Autodesk products? Ask the community.

New Post
Announcements
Are you interested in helping shape the future of the Autodesk Community? To participate in this brief usability study, please click here. Your time and input is greatly appreciated!