Through the Interface: Delete all but current Annotation Scales on AutoCAD objects using .NET

May 2015

Sun Mon Tue Wed Thu Fri Sat
          1 2
3 4 5 6 7 8 9
10 11 12 13 14 15 16
17 18 19 20 21 22 23
24 25 26 27 28 29 30


« Using the Microsoft Kinect SDK to capture skeleton data inside AutoCAD | Main | Displaying an AutoCAD ribbon tab contextually using .NET »

October 05, 2011

Delete “all but current” Annotation Scales on AutoCAD objects using .NET

I stumbled across this wishlist request on the forums, the other day, and thought it worth covering in a blog post.

It’s an interesting little piece of code – nothing very startling, but obviously whenever removing data you have to be a bit careful: in fact I would probably add an “are you sure?” question prior to actually removing the various annotation scales, even if the operation participates in the undo mechanism and can therefore be rolled back easily by the user.

Here’s the C# code for the AIOBJECTSCALEREMOVEOTHERS command (yes, I would normally use a slightly more succinct name, myself, such as DABC for “Delete All But Current”, but I decided to make this one more consistent with the AIOBJECTSCALEREMOVE command).

using Autodesk.AutoCAD.ApplicationServices;

using Autodesk.AutoCAD.DatabaseServices;

using Autodesk.AutoCAD.EditorInput;

using Autodesk.AutoCAD.Runtime;


namespace AnnotationScaling


  public class Commands




      (CommandFlags.Modal | CommandFlags.UsePickSet)


    static public void RemoveAllButCurrentScale()


      Document doc =


      Database db = doc.Database;

      Editor ed = doc.Editor;


      // Get the manager object and the list of scales


      ObjectContextManager ocm = db.ObjectContextManager;

      ObjectContextCollection occ =



      // Prompt the user for objects to process (or get them

      // from the pickfirst set)


      PromptSelectionOptions pso = new PromptSelectionOptions();

      pso.MessageForAdding = "\nSelect annotative objects";

      PromptSelectionResult psr = ed.GetSelection(pso);

      if (psr.Status != PromptStatus.OK)



      // Maintain counters of objects modified and scales removed


      int objCount = 0, scaCount = 0;


      // Use a flag to check when we first modify an object


      bool scalesRemovedForObject = false;


      Transaction tr =


      using (tr)


        // If we can't find the current annotation scale in our

        // dictionary, we have a problem


        if (!occ.HasContext(db.Cannoscale.Name))



            "\nCannot find current annotation scale."





        // Get the ObjectContext associated with the current

        // annotation scale


        ObjectContext curCtxt =



        // Check each selected object


        foreach (SelectedObject so in psr.Value)


          // Open it for read


          ObjectId id = so.ObjectId;

          DBObject obj = tr.GetObject(id, OpenMode.ForRead);


          // Check it's annotative and has the current scale


          if (obj.Annotative == AnnotativeStates.True &&




            // Now we get it for write




            // Loop through the various annotation scales in

            // the drawing


            foreach (ObjectContext oc in occ)


              // If it's on the object but not current

              // (for some reason we have to check the name

              // rather than oc == curCtxt)


              if (obj.HasContext(oc) &&

                  oc.Name != db.Cannoscale.Name



                // Remove it and increment our counter/set our

                // flag




                scalesRemovedForObject = true;




            // Increment our counter for objects once per pass

            // and then reset the flag


            if (scalesRemovedForObject)



              scalesRemovedForObject = false;






        // Report the results



          "\n{0} scales removed from {1} objects.",

          scaCount, objCount






For fun, I went ahead and manually added the command via the CUI editor, and added it to the corresponding ribbon panel:

Our new command on the ribbon

If we then launch this command and select some annotative objects, we see that the command reports removing superfluous scales from the selected objects:


Select annotative objects: Specify opposite corner: 4 found

Select annotative objects:

12 scales removed from 4 objects.

It should be noted that – while it’s unlikely a command this long is going to be entered at the command-line – this command does make use of the implied (aka pickfirst) selection set, should you prefer to prefer working in the noun-verb style. The ribbon item clears the pickfirst selection when launching the command, but it does work if launched via the command-line, in case.

blog comments powered by Disqus


10 Random Posts