Author Topic: Layout creation tool  (Read 16693 times)

0 Members and 1 Guest are viewing this topic.

vegbruiser

  • Guest
Layout creation tool
« on: July 23, 2008, 04:22:40 AM »
In VBA I have created a routine that allows the user to create a series of layouts based on the position, rotation, scale and user-input-values (attributes for the resultant viewport scale etc.) of a particular "viewport" block in Modelspace and I was wondering about the best way to convert it to .NET.

Can anyone give me some pointers on where I should start?

(or should I just go for it and post the results here?)

sinc

  • Guest
Re: Layout creation tool
« Reply #1 on: July 23, 2008, 10:46:43 AM »
Go for it, and if you have specific questions about how to perform certain tasks in .NET, ask those.

.NET is a pretty big topic, so it's a lot easier to answer specific questions.

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #2 on: July 31, 2008, 01:34:03 PM »
Well, I finally got stuck into making this thing. Here's what I've got so far: -
(this is my first attempt at a program in C# - hence the cobbled-together nature of what I've done here - also, thanks to the guys whose code I've borrowed. - I did this whilst at work today, so the link I got the original .zip file from I'll have to dig out tomorrow. )

One thing that bugs me about this code is that when I tried it earlier (with my boss watching) it didn't work the first time. Yet, when I ran it again, it did exactly what it should. Any ideas?

Also I've uploaded the viewport-block.dwg file so you C# gurus can properly test it (assuming you might want to)

Quote
Damnit, I'll upload the entire solution - the code is too many characters. :|

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #3 on: August 06, 2008, 12:33:55 PM »
Here's what I've got today: -

It inserts the block no problem, and, up until I borrowed the attribute support code (from Kean) it was inserting the second block no problem too. Could someone take a look and tell me why it's not working?

I've debugged it right the way through and it gets as far as the following function.

Code: [Select]
public void InsertBlock(ObjectId Blockid, int ISPOSP) // Point3d BlockPos, Double BlockScale, RotationAngle BlockAngle,int ISPOSP)
        {
            //this assumes that because the viewport block has been copied to the drawing, the other necessary blocks will have been too.
            // Blockid = the id of the block we inserted using the jig.
            // BlockPos = the position of the above block.
            // Blockscale = the scale of the above block.
            // BlockAngle = the rotation angle of the above block.
            Database db = HostApplicationServices.WorkingDatabase;
            Document dwg = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument;
            Editor ed = dwg.Editor;
            BlockTable bt = null;
            BlockTableRecord btr = null;
            Point3d BlockPos = new Point3d(0, 0, 0);
            Scale3d BlockScale = new Scale3d(1);
            Double BlockAngle = 0;
            BlockReference blkref = null;
            BlockReference frameref = null;
            PromptStringOptions prso = null;
            PromptKeywordOptions prko = null;
            PromptResult res = null;
 
            // this next section adds the ISPviewport-frame block on top of the already-inserted ISPViewport block.
#region InsertISPViewportframe
            if (ISPOSP == 0) // Viewport = ISP
            {
                using (Transaction tr = db.TransactionManager.StartTransaction())
                {
                    bt = tr.GetObject(db.BlockTableId, OpenMode.ForRead, false) as BlockTable;
                    foreach (ObjectId btrid in bt)
                    {
                        if (btrid == Blockid)
                        // we found the correct block?
                        {
                            btr = tr.GetObject(btrid, OpenMode.ForRead, false) as BlockTableRecord;
                            // normally we could filter out layouts, xrefs etc. but since we already know the objectid of the block
                            // we're looking for we don't need to bother.
                            if (btr.IsLayout || btr.IsFromExternalReference || !btr.IsDynamicBlock || btr.IsFromOverlayReference || !btr.HasAttributeDefinitions)
                            {
                                continue;
                            }
                            ObjectIdCollection blkrefIds = btr.GetBlockReferenceIds(true, false);
                            if (blkrefIds == null || blkrefIds.Count == 0) // this is where the code now stops. If you comment out the attribute support code, it works no problem??
                                break;
                            //int counter = 0;
                            foreach (ObjectId blkrefid in blkrefIds)
                            {
                                blkref = tr.GetObject(blkrefid, OpenMode.ForRead, false) as BlockReference;
                                BlockPos = blkref.Position;
                                BlockScale = blkref.ScaleFactors;
                                BlockAngle = blkref.Rotation;
                               
                                blkref = tr.GetObject(blkrefid, OpenMode.ForRead, false) as BlockReference;
                                AttributeCollection attrefids = blkref.AttributeCollection;
                                foreach (ObjectId attrefid in attrefids)
                                {
                                    AttributeReference attref = tr.GetObject(attrefid, OpenMode.ForWrite, false) as AttributeReference;
                                    switch (attref.Tag)
                                    {
                                        case "VIEWNO":
                                            prso = new PromptStringOptions("\nWhat view number is this?");
                                            res = ed.GetString(prso);
                                            if (res.Status == PromptStatus.OK)
                                            {
                                                attref.UpgradeOpen();
                                                string update = res.StringResult;
                                                attref.TextString = update;
                                                attref.DowngradeOpen();
                                            }
                                            break;
                                        case "FULLORPARTIAL":
                                            prko = new PromptKeywordOptions("\nWhat floor does this view depict?");
                                            prko.Keywords.Add("FULL");
                                            prko.Keywords.Add("PARTIAL");
                                            prko.Keywords.Add("DC");
                                            prko.Keywords.Add("ELEVATION");
                                            res = ed.GetKeywords(prko);
                                            if (res.Status == PromptStatus.OK)
                                            {
                                                attref.UpgradeOpen();
                                                string update = res.StringResult;
                                                attref.TextString = update;
                                                attref.DowngradeOpen();
                                            }
                                            break;
                                        case "FLOOR":
                                            prko = new PromptKeywordOptions("\nWhat floor does this view depict?");
                                            prko.Keywords.Add("GROUND");
                                            prko.Keywords.Add("FIRST");
                                            prko.Keywords.Add("SECOND");
                                            prko.Keywords.Add("THIRD");
                                            prko.Keywords.Add("FOURTH");
                                            prko.Keywords.Add("OTHER");
                                            PromptResult getWhichFloorResult = ed.GetKeywords(prko);
                                            if (getWhichFloorResult.StringResult == "OTHER")
                                            {
                                                res = ed.GetString("\nEnter another floor that's not listed.");
                                            }
                                            else
                                            {
                                                res = ed.GetKeywords(prko);
                                            }
                                            if (res.Status == PromptStatus.OK)
                                            {
                                                attref.UpgradeOpen();
                                                string update = res.StringResult;
                                                attref.TextString = update;
                                                attref.DowngradeOpen();
                                            }
                                            break;
                                    }
                                }
                                btr = tr.GetObject(bt[BlockTableRecord.ModelSpace], OpenMode.ForWrite) as BlockTableRecord;
                                frameref = new BlockReference(BlockPos, bt["ISPVIEWPORT-FRAME"]);
                                frameref.ScaleFactors = BlockScale;
                                frameref.Rotation = BlockAngle;
                                btr.AppendEntity(frameref);
                                tr.AddNewlyCreatedDBObject(frameref, true);
                            }
                        }
                    }
                    tr.Commit();
                }
#endregion //InsertISPViewportframe
            }
        }
In case people are wondering, the attribute support code looks like this: -

Code: [Select]
        public void StartInsert(String JigBlockName,int ISPOSP)
        {
            Editor ed = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument.Editor;
            Database db = HostApplicationServices.WorkingDatabase; // Application.DocumentManager.MdiActiveDocument.Database;
            try
            {
                Vector3d Normal = db.Ucsxdir.CrossProduct(db.Ucsydir);
                PromptResult res; // = ed.GetString(opts);
                if (JigBlockName != string.Empty)
                {
                    ObjectId block = GetBlockId(db, JigBlockName);
                    block = GetBlockId(db, JigBlockName);
                    if (block.IsNull)
                    {
                        ed.WriteMessage("\nBlock {0} not found.", JigBlockName);
                        return;
                    }
 
                    InsertJig jig = new InsertJig(block, Point3d.Origin, Normal.GetNormal());
 
                    //blockRotation 
                    if (vRotationUse == true)
                    {
                        jig.RotationAngleUse = true;
                        jig.RotationAngleValue = vRotationVal;
                    }
                    else
                    {
                        jig.RotationAngleUse = false;
                    }
               
                    jig.ScaleValue = vScaleVal;
                    jig.JigPromptCounter = 0; // Start with insertpoint
 
                    using (DocumentLock docLock = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument.LockDocument())
                    {
                        res = ed.Drag(jig); // First Jig option..[Insertpoint]
 
                        // Should it accept a rightclick as the 0-point of the drawing?
                        // or does that cancel the operation...?
                        if (res.Status == PromptStatus.OK)
                        {
                            jig.UpdateBlockRef(); // Check if it returns True!!!
                            // Here also the Rotation-Jig should Start...
                            // if Rotation was fixed this should have been set at first...
                            // Should Accept rightclick as 0-rotation
                            if (vRotationUse == true)
                            {
                                // Ready...end the Jig
                            }
                            else
                            {
                                // Start a new Jig for the rotation..
                                jig.JigPromptCounter = 1;
                                res = ed.Drag(jig);
                                if (res.Status == PromptStatus.OK)
                                {
                                    jig.UpdateBlockRef();
                                    //Set a bite to check if it should continue...(esc => no block placed!!)
                                }
                            }
 
                            // if jig.RotationAngleUse = false then do it...
                            // jig.RotationAngleValue = 1; // Or skip this altogether if it's a given rotation...
                            // No checking to be done by Jig(ger)..??
 
                            Autodesk.AutoCAD.DatabaseServices.TransactionManager tm = db.TransactionManager;
 
 
                            if (res.Status == PromptStatus.OK) // Second check needed if there was a rotation Jig..
                            {
                                using (Transaction tr = tm.StartTransaction())
                                {
 
                                    BlockTableRecord btr = (BlockTableRecord)tr.GetObject(db.CurrentSpaceId, OpenMode.ForWrite, false);
                                    btr.AppendEntity(jig.BlockReference);
                                    tr.AddNewlyCreatedDBObject(jig.BlockReference, true);
                                    // Start attribute support code
                                    BlockTable bt = (BlockTable)tr.GetObject(db.BlockTableId,OpenMode.ForRead);
 
                                    ObjectId bdId = bt[JigBlockName];
                                    btr = (BlockTableRecord)tr.GetObject(bdId,OpenMode.ForRead);
                                    // Add the attributes
                                    foreach (ObjectId attId in btr)
                                    {
                                        Entity ent =(Entity)tr.GetObject(attId,OpenMode.ForRead);
                                        if (ent is AttributeDefinition)
                                        {
                                            AttributeDefinition ad =(AttributeDefinition)ent;
                                            AttributeReference ar =new AttributeReference();
                                            ar.SetAttributeFromBlock(ad, jig.BlockReference.BlockTransform);
                                            jig.BlockReference.AttributeCollection.AppendAttribute(ar);
                                            tr.AddNewlyCreatedDBObject(ar, true);
                                        }
                                    }
                                    // End attribute support code
 
                                    // Call a function to make the graphics display
                                    // (otherwise it will only do so when we Commit)
                                    tm.QueueForGraphicsFlush();
                                    tr.Commit();
                                }
                            }
                        }
                    }
                    // Insert the viewportframe block (if ISP) here and update the attributes in the Viewport block.
                    InsertBlock(block, ISPOSP);
                }
               
 
            }
            catch (Autodesk.AutoCAD.Runtime.Exception ex)
            {
                ed.WriteMessage("\nThe Error was: " + ex.Message);
                //return false;
            }
            db.Dispose();
        }

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #4 on: August 11, 2008, 07:23:00 AM »
Right, after not looking at this for a couple of days, I have fixed the attribute not inserting issue.

My insertblock command now looks like this: -

Code: [Select]
public void InsertBlock(ObjectId Blockid, int ISPOSP)
        {
            //this assumes that because the viewport block has been copied to the drawing, the other necessary blocks will have been too.
            // Blockid = the id of the block we inserted using the jig.
            // BlockPos = the position of the above block.
            // Blockscale = the scale of the above block.
            // BlockAngle = the rotation angle of the above block.
            Database db = HostApplicationServices.WorkingDatabase;
            Document dwg = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument;
            Editor ed = dwg.Editor;
            BlockTable bt = null;
            BlockTableRecord btr = null;
            Point3d BlockPos = new Point3d(0, 0, 0);
            Scale3d BlockScale = new Scale3d(1);
            Double BlockAngle = 0;
            BlockReference blkref = null;
            BlockReference frameref = null;
            PromptStringOptions prso = null;
            PromptKeywordOptions prko = null;
            PromptResult res = null;
 
            // this next section adds the ISPviewport-frame block on top of the already-inserted ISPViewport block.
#region InsertISPViewportframe
            if (ISPOSP == 0) // Viewport = ISP
            {
                using (Transaction tr = db.TransactionManager.StartTransaction())
                {
                    bt = tr.GetObject(db.BlockTableId, OpenMode.ForRead, false) as BlockTable;
                    foreach (ObjectId btrid in bt)
                    {
                        if (btrid == Blockid)
                        // we found the correct block?
                        {
                            btr = tr.GetObject(btrid, OpenMode.ForRead, false) as BlockTableRecord;
                            // normally we could filter out layouts, xrefs etc. but since we already know the objectid of the block
                            // we're looking for we don't need to bother.
                            if (btr.IsLayout || btr.IsFromExternalReference || !btr.IsDynamicBlock || btr.IsFromOverlayReference || !btr.HasAttributeDefinitions)
                            {
                                continue;
                            }
                            ObjectIdCollection blkrefIds = btr.GetBlockReferenceIds(true, false);
                            if (blkrefIds == null || blkrefIds.Count == 0)
                                break;
                            //int counter = 0;
                            foreach (ObjectId blkrefid in blkrefIds)
                            {
                                blkref = tr.GetObject(blkrefid, OpenMode.ForWrite, false) as BlockReference;
                                BlockPos = blkref.Position;
                                BlockScale = blkref.ScaleFactors;
                                BlockAngle = blkref.Rotation;
                                //Start newly placed attribute start code.
                                BlockTable newbt = (BlockTable)tr.GetObject(db.BlockTableId, OpenMode.ForRead);
                                ObjectId bdid = bt[blkref.Name];
                                BlockTableRecord newbtr = (BlockTableRecord)tr.GetObject(bdid, OpenMode.ForRead);
                                //Add the attributes to the block definition otherwise we won't be able to edit them in blkref?
                                if (newbtr.HasAttributeDefinitions)
                                {
                                    foreach (ObjectId attid in newbtr)
                                    {
                                        AttributeDefinition attdef = tr.GetObject(attid, OpenMode.ForRead) as AttributeDefinition;
                                        if (attdef != null)
                                        {
                                            AttributeReference ar = new AttributeReference();
                                            ar.SetAttributeFromBlock(attdef, blkref.BlockTransform);
                                            blkref.AttributeCollection.AppendAttribute(ar);
                                            tr.AddNewlyCreatedDBObject(ar, true);
                                        }
                                    }
                                }
                                blkref = tr.GetObject(blkrefid, OpenMode.ForRead, false) as BlockReference;
                                AttributeCollection attrefids = blkref.AttributeCollection;
                                foreach (ObjectId attrefid in attrefids)
                                {
                                    AttributeReference attref = tr.GetObject(attrefid, OpenMode.ForWrite, false) as AttributeReference;
                                    switch (attref.Tag)
                                    {
                                        case "VIEWNO":
                                            prso = new PromptStringOptions("\nWhat view number is this?");
                                            res = ed.GetString(prso);
                                            if (res.Status == PromptStatus.OK)
                                            {
                                                attref.UpgradeOpen();
                                                string update = res.StringResult;
                                                attref.TextString = update;
                                                attref.DowngradeOpen();
                                            }
                                            break;
                                        case "FULLORPARTIAL":
                                            prko = new PromptKeywordOptions("\nWhat floor does this view depict?");
                                            prko.Keywords.Add("FULL");
                                            prko.Keywords.Add("PARTIAL");
                                            prko.Keywords.Add("DC");
                                            prko.Keywords.Add("ELEVATION");
                                            res = ed.GetKeywords(prko);
                                            if (res.Status == PromptStatus.OK)
                                            {
                                                attref.UpgradeOpen();
                                                string update = res.StringResult;
                                                attref.TextString = update;
                                                attref.DowngradeOpen();
                                            }
                                            break;
                                        case "FLOOR":
                                            prko = new PromptKeywordOptions("\nWhat floor does this view depict?");
                                            prko.Keywords.Add("GROUND");
                                            prko.Keywords.Add("FIRST");
                                            prko.Keywords.Add("SECOND");
                                            prko.Keywords.Add("THIRD");
                                            prko.Keywords.Add("FOURTH");
                                            prko.Keywords.Add("OTHER");
                                            PromptResult getWhichFloorResult = ed.GetKeywords(prko);
                                            if (getWhichFloorResult.StringResult == "OTHER")
                                            {
                                                res = ed.GetString("\nEnter another floor that's not listed.");
                                            }
                                            else
                                            {
                                                res = ed.GetKeywords(prko);
                                            }
                                            if (res.Status == PromptStatus.OK)
                                            {
                                                attref.UpgradeOpen();
                                                string update = res.StringResult;
                                                attref.TextString = update;
                                                attref.DowngradeOpen();
                                            }
                                            break;
                                    }
                                }
                                btr = tr.GetObject(bt[BlockTableRecord.ModelSpace], OpenMode.ForWrite) as BlockTableRecord;
                                frameref = new BlockReference(BlockPos, bt["ISPVIEWPORT-FRAME"]);
                                frameref.ScaleFactors = BlockScale;
                                frameref.Rotation = BlockAngle;
                                btr.AppendEntity(frameref);
                                tr.AddNewlyCreatedDBObject(frameref, true);
                            }
                        }
                    }
                    tr.Commit();
                }
#endregion //InsertISPViewportframe
            }
        }

It's Alive!

  • Retired
  • Needs a day job
  • Posts: 8706
  • AKA Daniel
Re: Layout creation tool
« Reply #5 on: August 11, 2008, 09:50:11 AM »
I noticed you are reusing the variable btr, I don’t know if that might cause any problems

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #6 on: August 11, 2008, 10:23:19 AM »
I noticed you are reusing the variable btr, I don’t know if that might cause any problems
Indeed I am :| . I'll call the two BlockTableRecords something else.

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #7 on: August 12, 2008, 12:10:19 PM »
Another day, another problem.

Code: [Select]
public void InsertBlock(ObjectId Blockid, int ISPOSP)
        {
            //this assumes that because the viewport block has been copied to the drawing, the other necessary blocks will have been too.
            // Blockid = the id of the block we inserted using the jig.
            // BlockPos = the position of the above block.
            // Blockscale = the scale of the above block.
            // BlockAngle = the rotation angle of the above block.
            Database db = HostApplicationServices.WorkingDatabase;
            Document dwg = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument;
            Editor ed = dwg.Editor;
            BlockTable bt = null;
            BlockTableRecord btr = null;
            Point3d BlockPos = new Point3d(0, 0, 0);
            Scale3d BlockScale = new Scale3d(1);
            Double BlockAngle = 0;
            BlockReference blkref = null;
            BlockReference frameref = null;
            PromptStringOptions prso = null;
            PromptKeywordOptions prko = null;
            PromptResult res = null;
 
            // this next section adds the ISPviewport-frame block on top of the already-inserted ISPViewport block.
            #region InsertISPViewportframe
            if (ISPOSP == 0) // Viewport = ISP
            {
                using (Transaction tr = db.TransactionManager.StartTransaction())
                {
                    bt = tr.GetObject(db.BlockTableId, OpenMode.ForRead, false) as BlockTable;
                    foreach (ObjectId btrid in bt)
                    {
                        if (btrid == Blockid)
                        // we found the correct block?
                        {
                            btr = tr.GetObject(btrid, OpenMode.ForRead, false) as BlockTableRecord;
                            // normally we could filter out layouts, xrefs etc. but since we already know the objectid of the block
                            // we're looking for we don't need to bother.
                            if (btr.IsLayout || btr.IsFromExternalReference || !btr.IsDynamicBlock || btr.IsFromOverlayReference || !btr.HasAttributeDefinitions)
                            {
                                continue;
                            }
                            ObjectIdCollection blkrefIds = btr.GetBlockReferenceIds(true, false);
                            if (blkrefIds == null || blkrefIds.Count == 0)
                                break;
                            //int counter = 0;
                            foreach (ObjectId blkrefid in blkrefIds)
                            {
                                blkref = tr.GetObject(blkrefid, OpenMode.ForWrite, false) as BlockReference;
                                BlockPos = blkref.Position;
                                BlockScale = blkref.ScaleFactors;
                                BlockAngle = blkref.Rotation;
                                // Code should skip the next part if the block has already been inserted and has a blockref.AttributeCollection.Count greater than zero.                               
                                if (blkref.AttributeCollection.Count == 0)
                                {
                                    //Start newly placed attribute start code.
                                    //Maybe need to filter so this only runs once.
                                    BlockTable newbt = (BlockTable)tr.GetObject(db.BlockTableId, OpenMode.ForRead);
                                    ObjectId bdid = bt[blkref.Name];
                                    BlockTableRecord newbtr = (BlockTableRecord)tr.GetObject(bdid, OpenMode.ForRead);
                                    //Add the attributes to the block definition otherwise we won't be able to edit them in blkref?
                                    if (newbtr.HasAttributeDefinitions)
                                    {
                                        foreach (ObjectId attid in newbtr)
                                        {
                                            AttributeDefinition attdef = tr.GetObject(attid, OpenMode.ForRead) as AttributeDefinition;
                                            if (attdef != null)
                                            {
                                                AttributeReference ar = new AttributeReference();
                                                ar.SetAttributeFromBlock(attdef, blkref.BlockTransform);
                                                blkref.AttributeCollection.AppendAttribute(ar);
                                                tr.AddNewlyCreatedDBObject(ar, true);
                                            }
                                        }
                                    }
                                    OldBlockPos = BlockPos;
                                }
                                blkref = tr.GetObject(blkrefid, OpenMode.ForRead, false) as BlockReference;
                                AttributeCollection attrefids = blkref.AttributeCollection;
                                foreach (ObjectId attrefid in attrefids)
                                {
                                    AttributeReference attref = tr.GetObject(attrefid, OpenMode.ForWrite, false) as AttributeReference;
                                    switch (attref.Tag)
                                    {
                                        case "VIEWNO_NONVIS":
                                            prso = new PromptStringOptions("\nWhat view number is this?");
                                            res = ed.GetString(prso);
                                            if (res.Status == PromptStatus.OK)
                                            {
                                                attref.UpgradeOpen();
                                                string update = res.StringResult;
                                                attref.TextString = update;
                                                attref.DowngradeOpen();
                                            }
                                            break;
                                        case "FULLORPARTIAL":
                                            prko = new PromptKeywordOptions("\nWhat floor does this view depict?");
                                            prko.Keywords.Add("FULL");
                                            prko.Keywords.Add("PARTIAL");
                                            prko.Keywords.Add("DC");
                                            prko.Keywords.Add("ELEVATION");
                                            res = ed.GetKeywords(prko);
                                            if (res.Status == PromptStatus.OK)
                                            {
                                                attref.UpgradeOpen();
                                                string update = res.StringResult;
                                                attref.TextString = update;
                                                attref.DowngradeOpen();
                                                if (res.StringResult == "PARTIAL")
                                                {
                                                    btr = tr.GetObject(bt[BlockTableRecord.ModelSpace], OpenMode.ForWrite) as BlockTableRecord;
                                                    frameref = new BlockReference(BlockPos, bt["ISPVIEWPORT-FRAME"]);
                                                    frameref.ScaleFactors = BlockScale;
                                                    frameref.Rotation = BlockAngle;
                                                    btr.AppendEntity(frameref);
                                                    tr.AddNewlyCreatedDBObject(frameref, true);
                                                }
                                            }
                                            break;
                                        case "FLOOR":
                                            prko = new PromptKeywordOptions("\nWhat floor does this view depict?");
                                            prko.Keywords.Add("GROUND");
                                            prko.Keywords.Add("FIRST");
                                            prko.Keywords.Add("SECOND");
                                            prko.Keywords.Add("THIRD");
                                            prko.Keywords.Add("FOURTH");
                                            prko.Keywords.Add("OTHER");
                                            PromptResult getWhichFloorResult = ed.GetKeywords(prko);
                                            if (getWhichFloorResult.StringResult == "OTHER")
                                            {
                                                res = ed.GetString("\nEnter another floor that's not listed.");
                                            }
                                            else
                                            {
                                                res = getWhichFloorResult;
                                            }
                                            if (res.Status == PromptStatus.OK)
                                            {
                                                attref.UpgradeOpen();
                                                string update = res.StringResult;
                                                attref.TextString = update;
                                                attref.DowngradeOpen();
                                            }
                                            break;
                                    }
                                }
                            }
                        }
                    }
                    tr.Commit();
                }
            #endregion //InsertISPViewportframe
            }
        }

The above code allows me to insert the block(s) I require but for some reason it seems to go back into the previous inserted blocks and add the attributes again.

The line that isn't working as expected is: -

 if (blkref.AttributeCollection.Count == 0)

After the first block is inserted, and the attributes filled out, it shouldn't then have an AttributeCollection count of 0, but for reasons that escape me it does.  I can't for the life of me work out another check I could do to prevent the attributes being added again (short of moving the attribute editing part of this code into its' own function).

Any ideas?

(Incidentally, if I was doing this exact same thing in VBA I'd insert the block, then sendcommand "ATTSYNC" to sychronize the attributereferences with the blockdefinition.)
« Last Edit: August 12, 2008, 12:24:43 PM by vegbruiser »

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #8 on: August 16, 2008, 06:01:49 PM »
Right, after a few more days spent reading through sample code (for dynamic blocks this time), this is what I've got: -
(see attached)

This code allows you to insert a Viewport block at any 2d location/angle you like, then pick what resultant sheet size you'd like: A0/A1/A2/A3 and what scale you want the viewport to be.

(The size/shape of the Viewport block is directly proportional to the available space in the template we use at any given scale - so if you were to choose A3 & a scale of 1:100 the final view will fit exactly on an A3 sheet :) .)

Next you input what sheet number this view is. (I plan on implementing the same counting facility I used in the VBA version of this code next week).

Then you have to decide what type of view it is - for my purposes the choices are Full/Partial/Data Closet/Elevation - but these can easily be changed to suit.

And that's it for now.

The next thing for me to do is put each new Viewport block onto a specific (in some cases unique) layer depending on the choice of view type - this then allows me to properly create the keyplans that are necessary for our designs.

After that my next step is to add a new named UCS for each of the new Viewport blocks - hence the as yet unused UCS Class. - This will then allow me to align the main Viewport in each resultant page to the new UCS.

Last but by no means least it's simply a matter of sorting an array of the Viewport numbers (because they'd have to be taken from each block in turn?) and starting to create the new layouts.

(if it doesn't drive me :loco: first that is) - that said, I am learning a lot though.

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #9 on: August 20, 2008, 06:14:42 AM »
And for my next question: -

In VBA if I want to align a PaperSpace Viewport to a named UCS, I used to use the PLAN command - is there an equivalent function in .NET?

(I guess I will need to use XDATA stored in the viewport?)

EDIT: Actually, this might be what I need: -
(from here)
Code: [Select]
Editor ed = AcadApp.DocumentManager.MdiActiveDocument.Editor;

ViewTableRecord viewRec = ed.GetCurrentView();
Vector3d viewDirection = viewRec.ViewDirection;

Vector3d xVec = viewDirection.GetPerpendicularVector();
Vector3d yVec = xVec.CrossProduct(viewDirection.Negate());

Matrix3d mat = Matrix3d.AlignCoordinateSystem(
Point3d.Origin, Vector3d.XAxis, Vector3d.YAxis, Vector3d.ZAxis,
viewRec.Target, xVec, yVec, viewDirection.Negate());

//ed.CurrentUserCoordinateSystem = Matrix3d.Identity;
ed.CurrentUserCoordinateSystem = mat;
ed.UpdateScreen();
« Last Edit: August 20, 2008, 08:24:46 AM by vegbruiser »

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #10 on: August 22, 2008, 10:57:55 AM »
One of the steps required by my Layout creation tool is the ability to store the layer properties that are present prior to running the code, and then restoring them afterwards.

The reason for this is that we have large drawings which, when the code was in vba would grind to a halt switching between layouts with all layers turned on/thawed. By freezing them/turning them off and then creating the layouts, I got around this problem. I would then simply reverse the changes with the exception of any newly created layers.

My problem now is that I'm a bit puzzled as to the best way to store the properties: -

Do I use an ArrayList, or an Array, or a Collection?

(I've searched TheSwamp and the Autodesk discussion groups archive I have on my (Non-Internet) machine but maybe I'm not looking for the right search string - the way I figure it I can't be the first person to want to store layer properties and subsequently restore them.)

Can anyone help?

Glenn R

  • Guest
Re: Layout creation tool
« Reply #11 on: August 22, 2008, 12:33:10 PM »
Can you explain further? Are you wanting to store WHILST the routine does it's creation thing, then restore the previous properties at the end or something else?

Also, when you said it ground to halt when switching layouts, what was your LAYOUTREGENCTL (fairly sure that's the variable name) setting?

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #12 on: August 22, 2008, 04:12:18 PM »
Can you explain further? Are you wanting to store WHILST the routine does it's creation thing, then restore the previous properties at the end or something else?

Also, when you said it ground to halt when switching layouts, what was your LAYOUTREGENCTL (fairly sure that's the variable name) setting?
I would like to be able to store the layer settings of existing layers, then freeze everything except a specific few layers, run the creation tool, then finally restore the previously saved properties.

As for the LAYOUTREGENCTL variable, I have no idea. (The last time I had the problem it was using Autocad 2006 - I've not experienced it with AC2009.)

Glenn R

  • Guest
Re: Layout creation tool
« Reply #13 on: August 22, 2008, 04:35:22 PM »
From the AutoCAD 2006 help:

Code: [Select]
Type:  Integer
Saved in:  Registry
Initial value:  2


Specifies how the display list is updated in the Model tab and layout tabs. For each tab, the display list is updated either by regenerating the drawing when you switch to that tab or by saving the display list to memory and regenerating only the modified objects when you switch to that tab. Changing the LAYOUTREGENCTL setting can improve performance.

0
 The drawing is regenerated each time you switch tabs.
 
1
 For the Model tab and the last layout made current, the display list is saved to memory and regenerations are suppressed when you switch between the two tabs. For all other layouts, regenerations still occur when you switch to those tabs.
 
2
 The drawing is regenerated the first time you switch to each tab. For the remainder of the drawing session, the display list is saved to memory and regenerations are suppressed when you switch to those tabs.
 

The performance gain achieved by changing the LAYOUTREGENCTL setting is dependent on several factors, including the drawing size and type, the objects contained in the drawing, the amount of available memory, and the effect of other open drawings or applications. When LAYOUTREGENCTL is set to 1 or 2, the amount of additional memory used is the size of the Model tab’s display list multiplied by the number of viewports in each layout for which the display list is saved.

If LAYOUTREGENCTL is set to 1 or 2 and performance seems slow in general or when you switch between tabs for which the display list is saved, consider changing to a setting of 0 or 1 to find the optimal balance for your work environment. For additional information about performance settings, see System tab (in the Options dialog box).

Regardless of the LAYOUTREGENCTL setting, if you redefine a block or undo a tab switch, the drawing is regenerated the first time you switch to any tab that contains saved viewports.


You've already mentioned the drg's are complex/large - how many layout tabs are generally in each drawing?

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #14 on: August 22, 2008, 04:45:13 PM »
It really depends on the drawing. That sounds obvious, but for some jobs there will likely be a maximum of three, but for more complex jobs we sometimes have over 100.

One thing that badly affects layout switching is the number of Viewports present on each layout. On a typical (standard) drawing we'll have no more than 7 viewports. So, on a large (100 layout) drawing that makes 700 Viewports.

Glenn R

  • Guest
Re: Layout creation tool
« Reply #15 on: August 22, 2008, 04:52:17 PM »
Damn! Run, right now, to any lisp startup script you have and add this:

Code: [Select]
(setvar "LAYOUTREGENCTL" 0)

In friends' experiments and mine own, very roughly, 20mb of RAM is used to cache each layout when the above variable is set to 2...start multiplying that by your figures above and I'm not surprised it was slow.

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #16 on: August 22, 2008, 04:56:44 PM »
Cheers Glenn, I'll try that out. :)

EDIT: One problem down, Now I just have to figure out the best way to store the layer properties...?

T.Willey

  • Needs a day job
  • Posts: 5251
Re: Layout creation tool
« Reply #17 on: August 22, 2008, 06:21:38 PM »
EDIT: One problem down, Now I just have to figure out the best way to store the layer properties...?

Maybe a dictionary.  You can store it by the layer name, and then have a list of all the properties.  Since you are the one putting in the information, then you will know what to do with it, since you would have to put it in as an object because it will be different types; strings ints ... etc.
Tim

I don't want to ' end-up ', I want to ' become '. - Me

Please think about donating if this post helped you.

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #18 on: August 26, 2008, 06:26:45 AM »
EDIT: One problem down, Now I just have to figure out the best way to store the layer properties...?

Maybe a dictionary.  You can store it by the layer name, and then have a list of all the properties.  Since you are the one putting in the information, then you will know what to do with it, since you would have to put it in as an object because it will be different types; strings ints ... etc.
Thanks Tim, did you mean a DbDictionary (Autocad-specific) or the more generic System.Collections.Generic.Dictionary type?


Kerry

  • Mesozoic relic
  • Seagull
  • Posts: 11654
  • class keyThumper<T>:ILazy<T>
Re: Layout creation tool
« Reply #19 on: August 26, 2008, 06:28:31 AM »
He would have meant DbDictionary.
kdub, kdub_nz in other timelines.
Perfection is not optional.
Everything will work just as you expect it to, unless your expectations are incorrect.
Discipline: None at all.

Glenn R

  • Guest
Re: Layout creation tool
« Reply #20 on: August 26, 2008, 06:35:05 AM »
Kerry, I would have thought Dictionary<> myself, but I could be wrong.

Personally, I'd be saving and restoring a LayerState :)

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #21 on: August 26, 2008, 07:28:16 AM »
Kerry, I would have thought Dictionary<> myself, but I could be wrong.

Personally, I'd be saving and restoring a LayerState :)
Thanks Glenn, I think I'll go with your suggestion - I don't want to reinvent the wheel after all.

:)

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #22 on: August 26, 2008, 08:12:30 AM »
Kerry, I would have thought Dictionary<> myself, but I could be wrong.

Personally, I'd be saving and restoring a LayerState :)
I was about to ask for help in figuring out what the deal was with LayerStates, but after a bit of searching the Autodesk forums I came up with the following: -

(At the moment the two commands are called by the "savelayers" and "restorelayers" commands respectively.)

Code: [Select]
public class LayerCommands
   {
       [CommandMethod ("SaveLayers")]
       public static void SaveLayerstate()
       {
           Document doc = AcadApp.DocumentManager.MdiActiveDocument;
           Editor ed = doc.Editor;
           DocumentLock doclock = doc.LockDocument();
           Database db = doc.Database;
           LayerStateManager lsm = db.LayerStateManager;
           string dwgname = "test";
           lsm.SaveLayerState(dwgname, LayerStateMasks.Frozen |
LayerStateMasks.Locked | LayerStateMasks.On, ObjectId.Null);
       }
       [CommandMethod("RestoreLayers")]
       public static void RestoreLayerstate()
       {
           Document doc = AcadApp.DocumentManager.MdiActiveDocument;
           Editor ed = doc.Editor;
           DocumentLock doclock = doc.LockDocument();
           Database db = doc.Database;
           LayerStateManager lsm = db.LayerStateManager;
           string dwgname = "test";
           lsm.RestoreLayerState(dwgname, ObjectId.Null, 0,
LayerStateMasks.Frozen | LayerStateMasks.Locked | LayerStateMasks.On);
       }
   }
For once that was quite easy.  :lol:

You can test that this works by running first the savelayers command in a drawing with a few layers. Then change some of the properties of those layers, and run the restorelayers command. You should then see that the properties you changed have been restored.

For my purposes (I think) I'm only storing the Frozen, Locked and On settings, but you can add more as you see fit.

Glenn R

  • Guest
Re: Layout creation tool
« Reply #23 on: August 26, 2008, 08:16:09 AM »
I was waiting for the questions to start popping about LayerStates ;)

Why are you locking the document btw?

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #24 on: August 26, 2008, 08:19:19 AM »
I was waiting for the questions to start popping about LayerStates ;)

Why are you locking the document btw?
Ah, that's because of the ol' "Copy+Paste" chestnut. My bad.

Glenn R

  • Guest
Re: Layout creation tool
« Reply #25 on: August 26, 2008, 08:19:53 AM »
Also, if you are going to lock the document, make sure you unlock it when you're finished or nasty things can happen. One way to do this is to wrap it in a 'using' block.

Glenn R

  • Guest
Re: Layout creation tool
« Reply #26 on: August 26, 2008, 08:20:48 AM »
I was waiting for the questions to start popping about LayerStates ;)

Why are you locking the document btw?
Ah, that's because of the ol' "Copy+Paste" chestnut. My bad.

Ah...no worries then.

T.Willey

  • Needs a day job
  • Posts: 5251
Re: Layout creation tool
« Reply #27 on: August 26, 2008, 11:11:52 AM »
EDIT: One problem down, Now I just have to figure out the best way to store the layer properties...?

Maybe a dictionary.  You can store it by the layer name, and then have a list of all the properties.  Since you are the one putting in the information, then you will know what to do with it, since you would have to put it in as an object because it will be different types; strings ints ... etc.
Thanks Tim, did you mean a DbDictionary (Autocad-specific) or the more generic System.Collections.Generic.Dictionary type?

Just to sum it up; I did mean the system Dictionary class.  Not like it matters now, as you have found a way that works.
Tim

I don't want to ' end-up ', I want to ' become '. - Me

Please think about donating if this post helped you.

Glenn R

  • Guest
Re: Layout creation tool
« Reply #28 on: August 27, 2008, 12:44:51 PM »
Speaking of LayerStates, have you seen Xref States?

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #29 on: August 27, 2008, 02:46:59 PM »
Interesting, I shall look at that in more detail tomorrow (when I'm being paid to do so) :)

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #30 on: August 28, 2008, 04:53:39 AM »
For my next trick, I've been trying to get to grips with groups.

As part of the process of creating the new layouts, my method for creating what we call a "Keyplan" involved, (In VBA at least) creating a group and then zooming to that group. (The same way I would do it if I were doing so manually.)

I've been wondering this morning whether I need to bother doing that any more. given the following code (originally from Kean): -

// (the usual "usings" are required in order to make this work: -

using Autodesk.AutoCAD.ApplicationServices;
using Autodesk.AutoCAD.DatabaseServices;
using Autodesk.AutoCAD.EditorInput;
using Autodesk.AutoCAD.Geometry;
using Autodesk.AutoCAD.Runtime;
// This is a special one:
using AcadApp = Autodesk.AutoCAD.ApplicationServices.Application;

[CommandMethod ("ZE")]
public static void ZoomToEntity(ObjectId GroupId)
{
  Document doc = AcadApp.DocumentManager.MdiActiveDocument;
  Database db = doc.Database;
  Editor ed = doc.Editor;
 
  //Extract the extents of the "group"
 
  Extents3d ext;
  Transaction tr = db.TransactionManager.StartTransaction();
  using (tr)
  {
    Entity ent = (Entity)tr.GetObject(GroupId, OpenMode.ForRead);
    ext = ent.GeometricExtents;
    tr.Commit();
  }

  ext.TransformBy(ed.CurrentUserCoordinateSystem.Inverse());
 
  // Call our helper function
 
  private static void ZoomWin(Editor ed, Point3d min, Point3d max)
  {

      Point2d min2d = new Point2d(min.X, min.Y);
      Point2d max2d = new Point2d(max.X, max.Y);
      ViewTableRecord view =  new ViewTableRecord();
      view.CenterPoint =  min2d + ((max2d - min2d) / 2.0);
      view.Height = max2d.Y - min2d.Y;
      view.Width = max2d.X - min2d.X;
      ed.SetCurrentView(view);
  }

I guess I would just need to create an object (in my case a user-defined rectangle) and then store the ObjectId of said Object for when it's time to create the viewports.  :|

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #31 on: September 01, 2008, 05:05:54 AM »
Right, I seem to have fudged the look/layout of my creation tool: -

I'm pretty sure I haven't broken anything in AutoCAD but whereas when I started writing this tool I'd get the options appearing next to the cursor, (when I prompt the user for input using either a PromptPointOptions, PrompStringOptions, or Prompt now, all I get is the command-line prompt. Can anyone offer an explanation as to how to fix this?

(Code attached for testing purposes)

Glenn R

  • Guest
Re: Layout creation tool
« Reply #32 on: September 01, 2008, 02:12:20 PM »
You've probably switched Dynamic Input off - it's the 'DYN' button (from memory) on the application status bar at the bottom of AutoCAD's main window.

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #33 on: September 01, 2008, 03:48:58 PM »
You've probably switched Dynamic Input off - it's the 'DYN' button (from memory) on the application status bar at the bottom of AutoCAD's main window.
That's strange - I don't remember turning that feature off. I shall take a look tomorrow morning. Cheers Glenn. :)

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #34 on: September 02, 2008, 04:22:50 AM »
You've probably switched Dynamic Input off - it's the 'DYN' button (from memory) on the application status bar at the bottom of AutoCAD's main window.
That was the problem mate, cheers. :) A typical case of RTFM :-o

Glenn R

  • Guest
Re: Layout creation tool
« Reply #35 on: September 02, 2008, 04:54:01 AM »
:D

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #36 on: September 03, 2008, 05:09:55 PM »
Right, I seem to have reached a bit of an impasse.

In my VBA implementation of this solution, the next stage of the process involved populating an array with several pieces of information in order to then create the new viewports that will be required: -

(Below are just some of the information that needs to be captured.)

Block location (Double Values) (which would I guess translate to Position3d values in C#)
specific Attribute location (In order to locate the centre of a new viewport) (Double Values) (again these would now be Position3d values)
Scale values (String Value)
Ucs to align to (String value)

(It's just dawned on me that rather than re-traversing the modelspace blocktable I should collate this information when the blocks are being inserted. After all, I'm already editing attributes that I would otherwise revisit at this stage.)

I'm a bit puzzled as to how I should proceed from here. Can anyone point in the right direction?

Glenn R

  • Guest
Re: Layout creation tool
« Reply #37 on: September 03, 2008, 05:13:45 PM »
Claaaaassss.

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #38 on: September 03, 2008, 05:15:22 PM »

Glenn R

  • Guest
Re: Layout creation tool
« Reply #39 on: September 03, 2008, 05:26:52 PM »
Without seeing more of the current and previous VBA implentation, as well as not having a good mental picture of what you're trying to accomplish (ie not being close to the idea/development), I would create a class object with all the properties you need, toss this into a List<YourClassNameHere> and use that..............or you might use a generic Dictionary.........

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #40 on: September 08, 2008, 07:35:03 AM »
Without seeing more of the current and previous VBA implentation, as well as not having a good mental picture of what you're trying to accomplish (ie not being close to the idea/development), I would create a class object with all the properties you need, toss this into a List<YourClassNameHere> and use that..............or you might use a generic Dictionary.........
Right, having spent a couple of days doing other things, (Mowing the lawn amongst them) I think I've almost got a working Viewport class sorted out. (at least, it contains the properties I want to store for use later on) I am however having trouble figuring out what you meant by "List<YourClassNameHere>"??

Maybe I'm googling the wrong thing...?

EDIT:
Code: [Select]
using System;
using System.Collections.Generic;

class Program
{
    static void Main()
    {
        List<String> names = new List<String>();
        names.Add("Bruce");
        names.Add("Alfred");
        names.Add("Tim");
        names.Add("Richard");

        // Display the contents of the List out using the "Print" delegate.
        names.ForEach(Print);

        // The following demonstrates the Anonymous Delegate feature of C#
        // to display the contents of the List to the console.
        names.ForEach(delegate(String name)
        {
            Console.WriteLine(name);
        });
    }

    private static void Print(string s)
    {
        Console.WriteLine(s);
    }
}
/* This code will produce output similar to the following:
 * Bruce
 * Alfred
 * Tim
 * Richard
 * Bruce
 * Alfred
 * Tim
 * Richard
 */

Is the above (from here) similar to what you meant?


Glenn R

  • Guest
Re: Layout creation tool
« Reply #41 on: September 08, 2008, 07:40:09 AM »
WRT the List container bit - yes. That's essentially what I meant.

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #42 on: September 10, 2008, 10:39:46 AM »
Right, I've managed to store in a list the properties I need to create the viewports/layouts using Glenn's post here as a reference.

Here's my Vports class: -

Code: [Select]
public class Vports
{
 public string vpName { get; set; }
 public string vpScale { get; set; }
 public Point3d vpPSCentrePoint { get; set; }
 public Point3d vpMSCentrePoint { get; set; }
 public string FullorPartial { get; set; }
 public vpVisProp { get; set; }
 public vpHeight {get; set; }
 public vpWidth {get; set; }
 public PageSize { get; set; }
}

My next step is to pass this information to my LayoutCommands class and use it to create the new required layouts.

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #43 on: January 04, 2010, 06:16:29 AM »
I realise it's been some time since I updated this thread, but I recently found some time to continue my work on this tool:

If the user has already inserted some blocks, but doesn't add any new ones (if say for instance the user is updating the drawing with a view they missed) I've been struggling with how to collect the necessary information from the existing blocks. I hoped to be able to simply add the ObjectId for each existing block to a custom dictionary for later retrieval but am yet to understand how to do this without parsing through the block table at this level.

Thinking about it now, I think parsing the block table at this stage would be easier/simpler than passing dictionaries/lists up/down through my procedure?

(I hope that all makes sense :-o )

PS. I've also found a neat way of visualising the stages in my procedure (see attached)

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #44 on: November 16, 2010, 09:33:43 AM »
Hi folks,

It's me and my zombie thread again.  :lol:

I've managed to pick this up yet again in an attempt to finally finish it off - I can't believe I never did after all this time!

Anywho, I've hit upon an interesting (and annoying!) problem I hope you can help me with.

The attached code runs all the way through without error on 2 different machines - assuming you copy Viewport-blocks.dwg to C:\

The first machine is running AutoCAD 2009 and the code will run all the way through without throwing an error. The block(s) are inserted, and the attributes are filled out correctly- everybody’s happy.

The second machine is running AutoCAD 2011 and the code will also run through without an error. However, when it gets to the following section, blkrefIds.Count is always zero.

Code: [Select]
btr = tr.GetObject(btrid, OpenMode.ForRead, false) as BlockTableRecord;
if (btr.IsLayout || btr.IsFromExternalReference || !btr.IsDynamicBlock || btr.IsFromOverlayReference || !btr.HasAttributeDefinitions)
{
continue;
}
ObjectIdCollection blkrefIds = GetBlockReferenceIds(btr.ObjectId);
if (blkrefIds == null || blkrefIds.Count == 0)
break;

I originally copied portions of this code from TTIF back in 2008, can you shed any immediate thoughts on my problem before I turn to the Autodesk Forums for assistance?

In case it was just me, I tried this code on a third machine running AutoCAD 2010 and the result is the same as with 2011 - the initial blocks are inserted, but blkrefIds.Count is always zero. What am I missing?

Thanks again,

Alex.


kaefer

  • Guest
Re: Layout creation tool
« Reply #45 on: November 16, 2010, 12:59:56 PM »
Hi folks,

It's me and my zombie thread again.  :lol:

Hi Alex,

can't help you there(1) - anyway, was your January visualization by any chance from http://www.graphviz.org ?  I've found that with saveas in SVG format and (mis-)using Visio to convert the output to an acceptable DWG it's a pretty cool tool.

(1)Your static GetBlockReferenceIds replacement method seems pretty innocent, are you sure that you are always avoiding the pitfalls of BlockTableRecord.GetBlockReferenceIds? I.e. it may return ObjectIds where IsEffectivelyErased == true, or calling it with directonly != true so that parent objects of nested blocks are included?

vegbruiser

  • Guest
Re: Layout creation tool
« Reply #46 on: November 17, 2010, 11:28:58 AM »
Hi folks,

It's me and my zombie thread again.  :lol:

Hi Alex,

can't help you there(1) - anyway, was your January visualization by any chance from http://www.graphviz.org ?  I've found that with saveas in SVG format and (mis-)using Visio to convert the output to an acceptable DWG it's a pretty cool tool.

(1)Your static GetBlockReferenceIds replacement method seems pretty innocent, are you sure that you are always avoiding the pitfalls of BlockTableRecord.GetBlockReferenceIds? I.e. it may return ObjectIds where IsEffectivelyErased == true, or calling it with directonly != true so that parent objects of nested blocks are included?

:?

It seems the problem stems from my having AutoCAD Mechanical installed. If I run the code from within VS, it automatically starts AutoCAD Mechanical - which means the code fails.

If I run the code from regular AutoCAD, i.e. not within the Dev. environment, it runs as designed.

Does anybody know how to force AutoCAD to start normally without the Mechanical crap - I talked to Kean Walmsley about it and he said to copy the command-line switches from the AutoCAD shortcut to the Debug page, but when I look at  the shortcut for AutoCAD there are none, yet the Mechanical shortcut has "  /p <<ACADMPP>>"

EDIT: Perhaps I could just use "/p"?? You can indeed use "/p" in the Command Line Arguments box on the Debug page.

And yes, the visualization was from Graphviz - it's pretty cool.  :lol:
« Last Edit: November 17, 2010, 11:32:37 AM by vegbruiser »