Author Topic: Erase Mtext from 2 or more layouts  (Read 2777 times)

0 Members and 1 Guest are viewing this topic.

teslaxx

  • Guest
Erase Mtext from 2 or more layouts
« on: December 15, 2010, 05:15:05 AM »
My drawing has more than 2 layouts and in every layout, I have the same Mtext (same insert point).

How could I delete EVERY MText object from every layout?

My starting point is: http://docs.autodesk.com/ACD/2010/ENU/AutoCAD%20.NET%20Developer%27s%20Guide/index.html

1. I select the Mtext from Layout1
2. I call the Erase method from that entity
3. But How can I loop the rest of the layouts and delete the rest of the Mtexts, based on the characteristics of the selected Mtext?

Code: [Select]

[CommandMethod("SelectObjectsOnscreen")]
        public static void SelectObjectsOnscreen()
        {

            // Get the current document and database
            Document acDoc = Application.DocumentManager.MdiActiveDocument;
            Database acCurDb = acDoc.Database;

            // Start a transaction
            using (Transaction acTrans = acCurDb.TransactionManager.StartTransaction())
            {
                // Request for objects to be selected in the drawing area
                PromptSelectionResult acSSPrompt = acDoc.Editor.GetSelection();

                // If the prompt status is OK, objects were selected
                if (acSSPrompt.Status == PromptStatus.OK)
                {
                    SelectionSet acSSet = acSSPrompt.Value;

                    // Step through the objects in the selection set
                    DBDictionary databaseDictionary = acCurDb.LayoutDictionaryId.GetObject(OpenMode.ForRead) as DBDictionary;

                    foreach (DBDictionaryEntry dictionaryEntry in databaseDictionary)
                    {
                            foreach (SelectedObject acSSObj in acSSet)
                            {
                                // Check to make sure a valid SelectedObject object was returned
                                if (acSSObj != null)
                                {
                                    // Open the selected object for write
                                    Entity acEnt = acTrans.GetObject(acSSObj.ObjectId,
                                                                     OpenMode.ForWrite) as Entity;
//[color=red][b] Somehow I need to fetch the entities from the rest of the layouts, based on the entities selected from the first layout[/b][/color]
                                    if (acEnt != null)
                                    {
                                       
                                        acEnt.Erase();
                                    }
                                }
                            }
                            // Save the new object to the database
                            acTrans.Commit();
                        }
                    }
                }
                // Dispose of the transaction
            }
« Last Edit: December 15, 2010, 05:19:09 AM by teslaxx »

kaefer

  • Guest
Re: Erase Mtext from 2 or more layouts
« Reply #1 on: December 15, 2010, 05:53:57 AM »
My drawing has more than 2 layouts and in every layout, I have the same Mtext (same insert point).

How could I delete EVERY MText object from every layout?

1. I select the Mtext from Layout1
You might need GetEntity for that.

Quote
2. I call the Erase method from that entity
You might want to wait until your outer loop has finished.

Quote
3. But How can I loop the rest of the layouts and delete the rest of the Mtexts, based on the characteristics of the selected Mtext?
You might want to loop through the BlockTableRecords associated with the Layouts (see Layout.BlockTableRecordId property) and check for MTexts within your specification.

BTW:
Quote
Code: [Select]
                                    // Open the selected object for write
                                    Entity acEnt = acTrans.GetObject(acSSObj.ObjectId,
                                                                     OpenMode.ForWrite) as Entity;
//[b] Somehow I need to fetch the entities from the rest of the layouts, based on the entities selected from the first layout[/b]
                                    if (acEnt != null)
                                    {
                                        acEnt.Erase();
erases Entities, not MTexts. Try the 'as' keyword with the type MText, and if that checks != null, then it is really MTEXT.

Have fun.

Jeff H

  • Needs a day job
  • Posts: 6150
Re: Erase Mtext from 2 or more layouts
« Reply #2 on: December 15, 2010, 06:10:16 AM »
Here is a start

Add ideas that Thorsten(kaefer) mentioned

Unless I am wrong I can not think of a situation where you would call Transaction.Commit() in a for each loop.

Code: [Select]

 [CommandMethod("SelectObjectsOnscreen")]
        public static void SelectObjectsOnscreen()
        {

            // Get the current document and database
            Document acDoc = Application.DocumentManager.MdiActiveDocument;
            Database acCurDb = acDoc.Database;
            string txt = "";
            Point3d mtxtInsertion = Point3d.Origin;
            // Start a transaction
            using (Transaction acTrans = acCurDb.TransactionManager.StartTransaction())
            {
                // Request for objects to be selected in the drawing area
                PromptSelectionResult acSSPrompt = acDoc.Editor.GetSelection();

                // If the prompt status is OK, objects were selected
                if (acSSPrompt.Status == PromptStatus.OK)
                {
                    SelectionSet acSSet = acSSPrompt.Value;

                    // Step through the objects in the selection set
                    DBDictionary databaseDictionary = acCurDb.LayoutDictionaryId.GetObject(OpenMode.ForRead) as DBDictionary;
                    foreach (SelectedObject acSSObj in acSSet)
                    {
                        // Check to make sure a valid SelectedObject object was returned
                       
                        {
                            // Open the selected object for write
                            Entity acEnt = acTrans.GetObject(acSSObj.ObjectId,
                                                             OpenMode.ForWrite) as Entity;
                            //[b] Somehow I need to fetch the entities from the rest of the layouts, based on the entities selected from the first layout[/b]
                            if (acEnt is MText)
                            {
                               
                                MText mtxt = acEnt as MText;
                                txt = mtxt.Contents;
                                mtxtInsertion = mtxt.Location;
                                acEnt.Erase();
                            }
                        }
                    }
                    foreach (DBDictionaryEntry dictionaryEntry in databaseDictionary)
                    {

                        Layout lyt = dictionaryEntry.Value.GetObject(OpenMode.ForRead) as Layout;
                        BlockTableRecord btr = lyt.BlockTableRecordId.GetObject(OpenMode.ForRead) as BlockTableRecord;
                        foreach (ObjectId objId in btr)
                        {
                            Entity ent = objId.GetObject(OpenMode.ForRead) as Entity;
                            if (ent is MText)
                            {
                                MText mtxt = ent as MText;
                                if (mtxt.Contents == txt && mtxt.Location == mtxtInsertion)
                                {
                                    mtxt.UpgradeOpen();
                                    mtxt.Erase();
                                }
                            }
                           
                        }
                    }
                    // Save the new object to the database
                    acTrans.Commit();
                }
            }
            // Dispose of the transaction
        }

teslaxx

  • Guest
Re: Erase Mtext from 2 or more layouts
« Reply #3 on: December 15, 2010, 07:53:01 AM »
Thank you both!

P.S. For who he's trying to use the code of Jeff H, declare txt as string and mtxtInsertion as Point3d.

kaefer

  • Guest
Re: Erase Mtext from 2 or more layouts
« Reply #4 on: December 15, 2010, 04:59:38 PM »
Unless I am wrong I can not think of a situation where you would call Transaction.Commit() in a for each loop.

Everytime you would call TransactionManager.StartTransaction() in a foreach loop? That happens not often, conceded; when going through the Databases of a DocumentCollection, perhaps.

Re: type conversions. I'd have thought the canonical way is (Type) when the target type is known, and the as operator for combined type test and conversion.  Consequently, the is operator is seldom necessary.

Quote
Code: [Select]
                        Layout lyt = dictionaryEntry.Value.GetObject(OpenMode.ForRead) as Layout;
                        BlockTableRecord btr = lyt.BlockTableRecordId.GetObject(OpenMode.ForRead) as BlockTableRecord;
                        foreach (ObjectId objId in btr)
                        {
                            Entity ent = objId.GetObject(OpenMode.ForRead) as Entity;
                            if (ent is MText)
                            {
                                MText mtxt = ent as MText;
                                if (mtxt.Contents == txt && mtxt.Location == mtxtInsertion)
                                {
                                    mtxt.UpgradeOpen();
                                    mtxt.Erase();
                                }
                            }

                        }
should read
Code: [Select]
                        Layout lyt = (Layout)dictionaryEntry.Value.GetObject(OpenMode.ForRead);
                        BlockTableRecord btr = (BlockTableRecord)lyt.BlockTableRecordId.GetObject(OpenMode.ForRead);
                        foreach (ObjectId objId in btr)
                        {
                            MText mtxt = objId.GetObject(OpenMode.ForRead) as MText;
                            if (mtxt != null && mtxt.Contents == txt && mtxt.Location == mtxtInsertion)
                            {
                                mtxt.UpgradeOpen();
                                mtxt.Erase();
                            }
                        }

Regards

LE3

  • Guest
Re: Erase Mtext from 2 or more layouts
« Reply #5 on: December 15, 2010, 09:07:05 PM »
^^^
Here it is a great resource about some .NET little wonders...

http://geekswithblogs.net/BlackRabbitCoder/archive/2010/11/11/c.net-little-wonders---a-presentation.aspx

The As Cast it is on: C#/.NET Five Little Wonders (part 1)