.NET

Reply
Valued Contributor
swaywood
Posts: 91
Registered: ‎08-22-2013
Message 1 of 8 (309 Views)
Accepted Solution

How to draw a revcloud?

309 Views, 7 Replies
03-18-2014 01:37 AM

now i have the polyline object id, but i don't know how to create a revcloud by select a object by code, and generate a revcloud entity.

        public static void drawRevCloudLine(ObjectId polyId, double scale)
        {
            //最小弧长
            string smallArc = Math.Ceiling(2.0 / scale).ToString();
            //最大弧长
            string largeArc = Math.Ceiling(6.0 / scale).ToString();
            //运行命令
            ResultBuffer rb = new ResultBuffer();
            rb.Add(new TypedValue(5005, "_revcloud"));
            rb.Add(new TypedValue(5005, "_a"));
            rb.Add(new TypedValue(5005, smallArc));
            rb.Add(new TypedValue(5005, largeArc));
            rb.Add(new TypedValue(5006, polyId));
            rb.Add(new TypedValue(5005, "_n"));

            try
            {
                acedCmd(rb.UnmanagedObject);
                Document doc = Application.DocumentManager.MdiActiveDocument;
                Editor editor = doc.Editor;
                Polyline rev=new Polyline();
                editor.Command("_revcloud", "_a", smallArc, largeArc, polyId, "_n");
            }
            catch (System.Exception ex)
            {
                AcadApp.ShowAlertDialog(ex.StackTrace + "\n" + ex.Message);
            }
            finally
            {
                rb.Dispose();
            }
        }

 the following is the support code

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Linq.Expressions;
using System.Reflection;
using Autodesk.AutoCAD.ApplicationServices;

namespace Autodesk.AutoCAD.EditorInput
{
    public static class EditorInputExtensionMethods
    {
        public static PromptStatus Command(this Editor editor, params object[] args)
        {
            if (editor == null)
                throw new ArgumentNullException("editor");
            return runCommand(editor, args);
        }

        static Func<Editor, object[], PromptStatus> runCommand = GenerateRunCommand();

        static Func<Editor, object[], PromptStatus> GenerateRunCommand()
        {
            MethodInfo method = typeof(Editor).GetMethod("RunCommand",
               BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public);
            var instance = Expression.Parameter(typeof(Editor), "instance");
            var args = Expression.Parameter(typeof(object[]), "args");
            return Expression.Lambda<Func<Editor, object[], PromptStatus>>(
               Expression.Call(instance, method, args), instance, args)
                  .Compile();
        }
    }
}

 

 

 

Have a try with the posted solution.

It defines two commands: CLOUD1 using RunCommand and CLOUD2 using acedCmd.

Both work as expected on my AutoCAD 2013.

*Expert Elite*
_gile
Posts: 2,087
Registered: ‎04-29-2006
Message 2 of 8 (296 Views)

Re : How to draw a revcloud?

03-18-2014 03:32 AM in reply to: swaywood

It seems you're confusing.

Use acedCmd or runCommand but not both

 

P/Invoking acedCmd

        private void drawRevCloudLine(ObjectId polyId, double scale)
        {
            ResultBuffer args = new ResultBuffer(
                new TypedValue((int)LispDataType.Text, "_revcloud"),
                new TypedValue((int)LispDataType.Text, "_arc"),
                new TypedValue((int)LispDataType.Double, 2.0 / scale),
                new TypedValue((int)LispDataType.Double, 2.0 / scale),
                new TypedValue((int)LispDataType.Text, "_object"),
                new TypedValue((int)LispDataType.ObjectId, polyId),
                new TypedValue((int)LispDataType.Text, "_no"));
            Command(args);
        }

 

Using runCommand wrapper

        private void drawRevCloudLine(ObjectId polyId, double scale)
        {
            Editor ed = Application.DocumentManager.MdiActiveDocument.Editor;
            ed.Command("_revcloud", "_arc", 2.0 / scale, 6.0 / scale, "_object", polyId, "_no");
        }

 

Gilles Chanteau
Valued Contributor
swaywood
Posts: 91
Registered: ‎08-22-2013
Message 3 of 8 (273 Views)

Re: How to draw a revcloud?

03-18-2014 07:51 AM in reply to: swaywood

Hi,Gilles:

    I tried several times, but not joy. So i made an entire sample, please check for me, and point out where the code is wrong.

    autocad2013+framwork4.0+vs2010

regards

swaywood

*Expert Elite*
_gile
Posts: 2,087
Registered: ‎04-29-2006
Message 4 of 8 (261 Views)

Re: How to draw a revcloud?

03-18-2014 01:15 PM in reply to: swaywood

Your code does not work beacause you try to add to the current space and the transaction the polyligne created by the revcloud command.

You don't have to matter for this while you're calling AutoCAD commands, AutoCAD will do all this stuff for you.

 

Here's a way using the runCommand route and some other extension methods.

 

using System;
using System.Linq.Expressions;
using System.Reflection;
using Autodesk.AutoCAD.ApplicationServices;
using Autodesk.AutoCAD.DatabaseServices;
using Autodesk.AutoCAD.EditorInput;
using Autodesk.AutoCAD.Geometry;
using Autodesk.AutoCAD.Runtime;
using AcAp = Autodesk.AutoCAD.ApplicationServices.Application;

namespace Acad2013CsTemplate
{
    public class Commands
    {
        [CommandMethod("CLOUD")]
        public void Cloud()
        {
            Document doc = AcAp.DocumentManager.MdiActiveDocument;
            Database db = doc.Database;
            Editor ed = doc.Editor;

            PromptPointResult ppr = ed.GetPoint("\nSpecify the first corner: ");
            if (ppr.Status != PromptStatus.OK) return;
            Point3d pt1 = ppr.Value;

            ppr = ed.GetCorner("\nSpecify the opposite corner: ", pt1);
            if (ppr.Status != PromptStatus.OK) return;
            Point3d pt2 = ppr.Value;

            ObjectId id;
            using (Transaction tr = db.TransactionManager.StartTransaction())
            using (Polyline pline = new Polyline(4))
            {
                pline.AddVertexAt(0, new Point2d(pt1.X, pt1.Y), 0.0, 0.0, 0.0);
                pline.AddVertexAt(1, new Point2d(pt2.X, pt1.Y), 0.0, 0.0, 0.0);
                pline.AddVertexAt(2, new Point2d(pt2.X, pt2.Y), 0.0, 0.0, 0.0);
                pline.AddVertexAt(3, new Point2d(pt1.X, pt2.Y), 0.0, 0.0, 0.0);
                pline.Closed = true;
                id = db.GetCurrentSpace(OpenMode.ForWrite).Add(pline);
                tr.Commit();
            }
            ed.Command("_revcloud", "_arc", 2.0, 6.0, "_object", id, "_no");
        }
    }

    public static class Extension
    {
        public static PromptStatus Command(this Editor ed, params object[] args)
        {
            if (ed == null)
                throw new ArgumentNullException("ed");
            return runCommand(ed, args);
        }

        static Func<Editor, object[], PromptStatus> runCommand = GenerateRunCommand();

        static Func<Editor, object[], PromptStatus> GenerateRunCommand()
        {
            MethodInfo method = typeof(Editor).GetMethod(
                "RunCommand", BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public);
            ParameterExpression instance = Expression.Parameter(typeof(Editor), "ed");
            ParameterExpression args = Expression.Parameter(typeof(object[]), "args");
            return Expression.Lambda<Func<Editor, object[], PromptStatus>>(
               Expression.Call(instance, method, args), instance, args)
                  .Compile();
        }

        public static T GetObject<T>(this ObjectId id, OpenMode mode)
            where T : DBObject
        {
            return (T)id.GetObject(mode);
        }

        public static BlockTableRecord GetCurrentSpace(this Database db, OpenMode mode)
        {
            return db.CurrentSpaceId.GetObject<BlockTableRecord>(mode);
        }

        public static ObjectId Add(this BlockTableRecord owner, Entity ent)
        {
            ObjectId id = owner.AppendEntity(ent);
            owner.Database.TransactionManager.AddNewlyCreatedDBObject(ent, true);
            return id;
        }
    }
}

 

Gilles Chanteau
Valued Contributor
swaywood
Posts: 91
Registered: ‎08-22-2013
Message 5 of 8 (250 Views)

Re: How to draw a revcloud?

03-18-2014 06:37 PM in reply to: swaywood

Hi Gilles:

Unfortunatelly, I failed again.

Is there any systemvalue shall be set in AutoCAD?

I only got the Rectangle again.

And when I test by step, I found when run to line

'id = db.GetCurrentSpace(OpenMode.ForWrite).Add(pline);'

the code swith to func GenerateRunCommand.

And when the code run to line 'ed.Command("_revcloud", "_arc", 2.0, 6.0, "_object", id, "_no");'

It can run to 'return RunCommand(ed, args);'

but can not run into 'func GenerateRunCommand'

at last quit step by step.

Were you got the 'RevCloud' successfully?

PS:I found some 'runCommand', I changed it to 'RunCommand', but it seems no influence.

thanks

swaywood

*Expert Elite*
_gile
Posts: 2,087
Registered: ‎04-29-2006
Message 6 of 8 (240 Views)

Re: How to draw a revcloud?

03-19-2014 01:28 AM in reply to: swaywood

Have a try with the posted solution.

It defines two commands: CLOUD1 using RunCommand and CLOUD2 using acedCmd.

Both work as expected on my AutoCAD 2013.

Gilles Chanteau
Valued Contributor
swaywood
Posts: 91
Registered: ‎08-22-2013
Message 7 of 8 (234 Views)

Re: How to draw a revcloud?

03-19-2014 02:46 AM in reply to: _gile

Hi Gilles:

    I found the problem where was, in autocad2013 there is a systemvalue 'nextfiberworld', I changed it to '0' before, so all the methods can not works fine, After change the value to 1, I got it both.

    now i can draw the revsion cloud, but i do not know why the 'nextfiberworld' can control the both mthods?

thanks so much!

swaywood

*Expert Elite*
Hallex
Posts: 1,569
Registered: ‎10-08-2008
Message 8 of 8 (198 Views)

Re: How to draw a revcloud?

03-21-2014 01:23 PM in reply to: swaywood

Here is another one using command way:

        //ads_queueexpr
        [DllImport("accore.dll", CharSet = CharSet.Unicode,
CallingConvention = CallingConvention.Cdecl,
EntryPoint = "ads_queueexpr")]
        extern static private int ads_queueexpr(byte[] command);

         public void CurveCloud(string hdl){
         UnicodeEncoding uEncode = new UnicodeEncoding();
         string hand=  string.Format("(handent  \"{0}\")",hdl);
         ads_queueexpr(uEncode.GetBytes("(command \"_.revcloud\" \"_arc\" \"2.54\" \"7.62\" \"_Ob\" " +  hand  + " \"N\"" + ")"));
        }

        [CommandMethod("revc")]
        public void MakeRevCloud()
         {
             var doc = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument;
            var ed = doc.Editor;
            using (var tr = doc.TransactionManager.StartTransaction())
            {
                ObjectId id = ed.GetEntity("\nSelect Closed curve").ObjectId;
                if (id != ObjectId.Null)
                {
                    DBObject obj = tr.GetObject(id, OpenMode.ForRead);
                    
                    string hdl = obj.Handle.ToString();
                    obj.UpgradeOpen();
                    CurveCloud(hdl);
                    tr.Commit();
                }
            }
        }

 

_____________________________________
C6309D9E0751D165D0934D0621DFF27919
Need installation help?

Start with some of our most frequented solutions or visit the Installation and Licensing Forum to get help installing your software.