Code:
using Autodesk.AutoCAD.DatabaseServices;
using Autodesk.AutoCAD.EditorInput;
using Autodesk.AutoCAD.Geometry;
using Autodesk.AutoCAD.Runtime;
using static System.Math;
using AcAp = Autodesk.AutoCAD.ApplicationServices.Core.Application;
[assembly: CommandClass(typeof(RectangleJigSample.Commands))]
namespace RectangleJigSample
{
public class Commands
{
double halfWidth = 100.0; // default value
[CommandMethod("CMD")]
public void Cmd()
{
var doc = AcAp.DocumentManager.MdiActiveDocument;
var db = doc.Database;
var ed = doc.Editor;
var pointResult = ed.GetPoint("\nRectangle start point: ");
if (pointResult.Status != PromptStatus.OK) return;
var distOptions = new PromptDistanceOptions("\nRectangle half width: ");
distOptions.AllowNegative = false;
distOptions.AllowZero = false;
distOptions.BasePoint = pointResult.Value;
distOptions.UseBasePoint = true;
distOptions.DefaultValue = halfWidth;
distOptions.UseDefaultValue = true;
var distResult = ed.GetDistance(distOptions);
if (distResult.Status != PromptStatus.OK) return;
var basePt = pointResult.Value.TransformBy(ed.CurrentUserCoordinateSystem);
halfWidth = distResult.Value;
using (var tr = db.TransactionManager.StartTransaction())
using (var pline = new Polyline(4))
{
pline.AddVertexAt(0, Point2d.Origin, 0.0, 0.0, 0.0);
pline.AddVertexAt(1, Point2d.Origin, 0.0, 0.0, 0.0);
pline.AddVertexAt(2, Point2d.Origin, 0.0, 0.0, 0.0);
pline.AddVertexAt(3, Point2d.Origin, 0.0, 0.0, 0.0);
pline.Closed = true;
var jig = new RectangleJig(pline, basePt, halfWidth);
var result = ed.Drag(jig);
if (result.Status == PromptStatus.OK)
{
var curSpace = (BlockTableRecord)tr.GetObject(db.CurrentSpaceId, OpenMode.ForWrite);
curSpace.AppendEntity(pline);
tr.AddNewlyCreatedDBObject(pline, true);
}
tr.Commit();
}
}
}
class RectangleJig : EntityJig
{
Polyline pline;
Point3d basePt, dragPt;
Point2d start;
double halfWidth;
const double HALFPI = 0.5 * PI;
public RectangleJig(Polyline pline, Point3d basePt, double halfWidth) : base(pline)
{
this.pline = pline;
this.basePt = basePt;
this.halfWidth = halfWidth;
start = new Point2d(basePt.X, basePt.Y);
}
protected override SamplerStatus Sampler(JigPrompts prompts)
{
var msg = "\nRectangle end point: ";
var options = new JigPromptPointOptions(msg);
options.UserInputControls =
(UserInputControls.Accept3dCoordinates);
options.BasePoint = basePt;
options.UseBasePoint = true;
options.Cursor = CursorType.RubberBand;
var result = prompts.AcquirePoint(options);
if (dragPt.DistanceTo(result.Value) < Tolerance.Global.EqualPoint)
{
return SamplerStatus.NoChange;
}
else
{
dragPt = result.Value;
}
return SamplerStatus.OK;
}
protected override bool Update()
{
var angle = Vector3d.XAxis.GetAngleTo(basePt.GetVectorTo(dragPt), Vector3d.ZAxis);
var end = new Point2d(dragPt.X, dragPt.Y);
pline.SetPointAt(0, Polar(start, angle - HALFPI, halfWidth));
pline.SetPointAt(1, Polar(end, angle - HALFPI, halfWidth));
pline.SetPointAt(2, Polar(end, angle + HALFPI, halfWidth));
pline.SetPointAt(3, Polar(start, angle + HALFPI, halfWidth));
return true;
}
private Point2d Polar(Point2d pt, double angle, double dist)
{
return new Point2d(pt.X + dist * Cos(angle), pt.Y + dist * Sin(angle));
}
}
}