Thursday, August 23, 2007
Auto Increment Numbering Macro for AutoCAD LT
*^c^c_text;\;;$M=$(+,$(getvar,USERR1),$(getvar,USERR2));setvar;USERR1;$M=$(+,$(getvar,USERR1),$(getvar,USERR2));
Configure the macro in a button (or wherever you are comfortable). Click on the button once and click on the required locations continuously to keep the incremented numbers. use USERR1 system variable to set the starting number and USERR2 for the increment. For example, suppose you need to start numbering from 1.001 and continue like 1.002,1.003,1.004........, set USERR1 to 1 and USERR2 to .001. This will enable you to do the numbering as stated before.
The above macro is restricted to work only when the text height in the current text style is 0. If you have the habit of assigning specific text height to a text style, then you should better use the following macro.
Quote:
*^c^c_text;\;$M=$(+,$(getvar,USERR1),$(getvar,USERR2));setvar;USERR1;$M=$(+,$(getvar,USERR1),$(getvar,USERR2));
I just removed only one semicolumn from the second macro after the 'Text' command. It's becuase the 'Text' command skips one step (Text height) if the current text style has already got text height assigned. Hope AutoCAD LT people find this tip very useful. Needless to say, it will give you the same result in AutoCAD full version.
*EDIT*
Thanks to a very good suggestion from Russ for adding a prefix, I ended up adding both prefix and suffix to the numbers.
*^c^c_text;\;;$M=$(getvar,USERS1)$M=$(+,$(getvar,USERR1),$(getvar,USERR2))$M=$(getvar,USERS2);setvar;USERR1;$M=$(+,$(getvar,USERR1),$(getvar,USERR2));
The macro uses USERS1 system variable to hold the prefix and USERS2 for the suffix. Thanks to comments from an anonymous visitor, I realised that USERSx system variables are not supported in AutoCAD LT. So I replaced the macro with a new one using (getenv,variable) function in place of (getvar,USERSx).
*^c^c_text;\;;$M=$(getenv,StrPrefix)$M=$(+,$(getvar,USERR1),$(getvar,USERR2))$M=$(getenv,StrSuffix);setvar;USERR1;$M=$(+,$(getvar,USERR1),$(getvar,USERR2));
You need to set two environment variables (I used StrPreifx for prefix and StrSuffix for suffix) using SETENV command which, I beleive, is available in AutoCAD LT. Don't forget to respect the text height of the current text style as mentioned eariler. Again, I don't have AutoCAD LT to test this macro. I would be really thankful if somebody could test it on LT and post a feedback on it.
*EDIT*
Sunday, August 19, 2007
Putting Everything Together - An Enhanced Line Command
using Autodesk.AutoCAD.ApplicationServices;
using Autodesk.AutoCAD.Runtime;
using Autodesk.AutoCAD.EditorInput;
using Autodesk.AutoCAD.DatabaseServices;
using Autodesk.AutoCAD.Geometry;
namespace AcadNetSamples
{
public class Commands
{
/// <summary>
/// Enhanced Line Command.
/// Allows user to change current layer and
/// linetype from within the command.
/// </summary>
[CommandMethod("ELINE")]
public static void DrawEnhancedLine()
{
Document doc = Application.DocumentManager.MdiActiveDocument;
Database db = doc.Database;
Editor ed = doc.Editor;
PromptPointOptions prPO = new PromptPointOptions("\nPick start point of line : ");
prPO.AllowNone = true;
prPO.UseBasePoint = false;
PromptPointResult ppr;
ppr = ed.GetPoint(prPO);
//Get start point
Point3d SPoint = ppr.Value;
//Remeber it for the CLOSE option
Point3d CPoint = SPoint;
prPO.Keywords.Add("LAyer");
prPO.Keywords.Add("LType");
prPO.Keywords.Add("Close");
// Continue line command until the user interrupts
while (ppr.Status == PromptStatus.OK ppr.Status ==
PromptStatus.Keyword)
{
prPO.UseBasePoint = true;
//Use the previously picked point as the base point for new line
prPO.BasePoint = SPoint;
prPO.Message = "\nPick next point or ";
ppr = ed.GetPoint(prPO);
Point3d NPoint = ppr.Value;
if (ppr.Status == PromptStatus.OK ppr.Status ==
PromptStatus.Keyword)
{
//Exit command on enter key
if (ppr.Status == PromptStatus.None) break;
//Declare ObjectId variable for common use
ObjectId objID;
// Check to see whether any keyword is choosen
if (ppr.Status == PromptStatus.Keyword)
{
PromptResult prs;
switch (ppr.StringResult)
{
case "LAyer":
prs = ed.GetString("\nEnter a layer name to make it current: ");
if (prs.Status == PromptStatus.OK)
{
//Loop back on Enter
if (prs.StringResult == "")
continue ;
try
{
objID =
SetCurrentLayer(prs.StringResult);
//Check whether the operation was successful
if (objID != ObjectId.Null)
ed.WriteMessage("\nCurrent layer is '"
+ prs.StringResult+"'");
else
ed.WriteMessage("\nThe layer '" +
prs.StringResult + "' was not found.");
continue;
}
catch
{
ed.WriteMessage("\nUnable to change current
layer. An error occured...!!");
continue;
}
}
return ;
case "LType":
prs = ed.GetString("\nEnter a linetype name to make it current: ");
if (prs.Status == PromptStatus.OK)
{
//Loop back on Enter
if (prs.StringResult == "")
continue;
try
{
objID =
SetCurrentLType(prs.StringResult);
//Check whether the operation was successful
if (objID != ObjectId.Null)
ed.WriteMessage("\nCurrent linetype is "
+ prs.StringResult +"'");
else
ed.WriteMessage("\nThe linetype '"
+ prs.StringResult + "' was not found.");
continue;
}
catch
{
ed.WriteMessage("\nUnable to change current linetype. An error occured...!!");
continue;
}
}
return ;
case "Close":
try
{
objID =
CreateLine(SPoint, CPoint);
if (objID != ObjectId.Null)
return;
break;
}
catch {}
return;
}
}
try
{
objID = CreateLine(SPoint, NPoint);
//The last end point will serve as the next base point
if (objID != ObjectId.Null) SPoint = NPoint;
}
catch { return; }
}
}
}
private static ObjectId SetCurrentLayer(string LayerName)
{
ObjectId layerId=ObjectId.Null ;
Document doc = Application.DocumentManager.MdiActiveDocument;
Database db = doc.Database;
Editor ed = doc.Editor;
Autodesk.AutoCAD.DatabaseServices.TransactionManager tm = db.TransactionManager;
using (Transaction tr = tm.StartTransaction())
{
LayerTable lt = (LayerTable)tm.GetObject(db.LayerTableId, OpenMode.ForRead, false);
if (lt.Has(LayerName))
{
layerId = lt[LayerName];
db.Clayer = layerId;
}
tr.Commit();
}
return layerId;
}
private static ObjectId SetCurrentLType(string LineTypeName)
{
ObjectId ltypeId = ObjectId.Null;
Document doc = Application.DocumentManager.MdiActiveDocument;
Database db = doc.Database;
Editor ed = doc.Editor;
Autodesk.AutoCAD.DatabaseServices.TransactionManager tm = db.TransactionManager;
using (Transaction tr = tm.StartTransaction())
{
LinetypeTable ltt = (LinetypeTable)tm.GetObject(db.LinetypeTableId, OpenMode.ForRead, false);
if (ltt.Has(LineTypeName))
{
ltypeId = ltt[LineTypeName];
db.Celtype = ltypeId;
}
tr.Commit();
}
return ltypeId;
}
private static ObjectId CreateLine(Point3d SPoint,Point3d EPoint)
{
ObjectId lineId = ObjectId.Null;
Document doc = Application.DocumentManager.MdiActiveDocument;
Database db = doc.Database;
Editor ed = doc.Editor;
Line oLine = new Line(SPoint, EPoint);
Autodesk.AutoCAD.DatabaseServices.TransactionManager tm = db.TransactionManager;
using (Transaction tr = tm.StartTransaction())
{
BlockTable bt = (BlockTable)tm.GetObject(db.BlockTableId, OpenMode.ForRead, false);
BlockTableRecord btr = (BlockTableRecord)tm.GetObject(bt[BlockTableRecord.ModelSpace], OpenMode.ForWrite, false);
using (oLine)
{
lineId = btr.AppendEntity(oLine);
tm.AddNewlyCreatedDBObject(oLine, true);
}
tr.Commit();
}
return lineId;
}
}
}
Tuesday, August 14, 2007
Creating AutoCAD Geometry
I think it's time to get into AutoCAD geometry. So, in this session, we are going to create a line command . We will also see using prompt options in this sample code. The command name used here is DRAWLINE.
using Autodesk.AutoCAD.ApplicationServices;
using Autodesk.AutoCAD.Runtime;
using Autodesk.AutoCAD.EditorInput;
using Autodesk.AutoCAD.DatabaseServices;
using Autodesk.AutoCAD.Geometry;
namespace AcadNetSamples
{
public class Commands
{
[CommandMethod("DrawLine")]
public static void DrawLine()
{
Document doc = Application.DocumentManager.MdiActiveDocument;
Database db = doc.Database;
Editor ed = doc.Editor;
PromptPointOptions prPO = new PromptPointOptions("\nPick start point of line: ");
prPO.AllowNone = false;
prPO.UseBasePoint = false;
PromptPointResult ppr1 = ed.GetPoint(prPO);
if (ppr1.Status == PromptStatus.OK)
{
prPO.UseBasePoint = true;
prPO.BasePoint = ppr1.Value;
prPO.Message = "\nPick end point: ";
PromptPointResult ppr2 = ed.GetPoint(prPO);
if (ppr2.Status == PromptStatus.OK)
{
Point3d SPoint = ppr1.Value;
Point3d EPoint = ppr2.Value;
Line oLine = new Line(SPoint, EPoint);
Autodesk.AutoCAD.DatabaseServices.TransactionManager tm = db.TransactionManager;
Autodesk.AutoCAD.DatabaseServices.Transaction tr = tm.StartTransaction();
using
(tr)
{
BlockTable bt = (BlockTable)tm.GetObject(db.BlockTableId, OpenMode.ForRead, false);
BlockTableRecord btr = (BlockTableRecord)tm.GetObject(bt[BlockTableRecord.ModelSpace], OpenMode.ForWrite, false);
using
(oLine)
{
btr.AppendEntity(oLine);
tm.AddNewlyCreatedDBObject(oLine, true);
}
tr.Commit();
}
}
}
}
}
}
I don't want to confine this blog to learning AutoCAD.Net only. I have got some Tips & Tricks to share with you. You may encounter these in between the dotnet posts (If you see one, just understand that I didn't get enough time to learn next dotnet topic :-).
Saturday, August 11, 2007
AutoCAD Prompts & Error Handling
using Autodesk.AutoCAD.ApplicationServices;
using Autodesk.AutoCAD.Runtime;
using Autodesk.AutoCAD.EditorInput;
namespace AcadNetSamples
{
public class Commands
{
[CommandMethod("OPENDWG")]
public static void OpenDrawing()
{
Document doc = Application.DocumentManager.MdiActiveDocument;
Editor ed = doc.Editor;
PromptResult res = ed.GetString("\nEnter a drawing path: ");
if (res.Status == PromptStatus.OK)
{
try
{
Application.DocumentManager.Open(res.StringResult,false);
}
catch
{
ed.WriteMessage("\nUnable to open drawing file.");
return;
}
finally
{
ed.WriteMessage("\nThis is an AutoCAD.Net sample command.");
}
}
}
[CommandMethod("DISPOINT")]
public void DisplayPoint()
{
Editor ed = Application.DocumentManager.MdiActiveDocument.Editor;
PromptPointOptions prPO = new PromptPointOptions("Select a point: ");
PromptPointResult prPR = ed.GetPoint(prPO);
if (prPR.Status != PromptStatus.OK)
{
ed.WriteMessage("An error occured...!");
}
else
}
[CommandMethod("GETDIST")]
public void GetDistance()
{
Editor ed = Application.DocumentManager.MdiActiveDocument.Editor;
PromptDistanceOptions prDO = new PromptDistanceOptions("Select first point: ");
PromptDoubleResult prDR = ed.GetDistance(prDO);
if (prDR.Status != PromptStatus.OK)
{
ed.WriteMessage("An error occured...!");
}
else
ed.WriteMessage("Distance: " + prDR.Value.ToString());
}
}
}
Sunday, August 5, 2007
Iterations in C#
using Autodesk.AutoCAD.ApplicationServices;
using Autodesk.AutoCAD.Runtime;
using Autodesk.AutoCAD.EditorInput;
namespace AcadNetSamples
{
public class Commands
{
[CommandMethod("LOOPS")]
public static void LoopOperations()
{
Document doc = Application.DocumentManager.MdiActiveDocument;
Editor ed = doc.Editor;
string[] strs = new string[10];
int i;
for (i = 0; i < 10; i++)
{
strs[i] = "String No. " + (i + 1).ToString();
}
ed.WriteMessage("\n\nUsing 'foreach' Loop\n");
foreach (string str in strs)
{
ed.WriteMessage("\n\t\t" + str);
}
ed.WriteMessage("\n\nUsing 'While' Loop\n");
i = 0;
while (i < 10)
{
ed.WriteMessage("\n\t\tString No. " + (i + 1).ToString());
i++;
}
ed.WriteMessage("\n\nUsing 'Do While' Loop\n");
i = 0;
do
{
ed.WriteMessage("\n\t\tString No. "+ (i + 1).ToString());
i++;
} while (i < 10);
}
}
}
Wednesday, August 1, 2007
Conditions forever
using Autodesk.AutoCAD.ApplicationServices;
using Autodesk.AutoCAD.Runtime;
using Autodesk.AutoCAD.EditorInput;
namespace AcadNetSamples
{
public class Commands
{
[CommandMethod("CONDITIONS")]
public static void ConditionalOperations()
{
Document doc = Application.DocumentManager.MdiActiveDocument;
Editor ed = doc.Editor;
int x = 1; int y = 2; int z = 3;
if ((x + y) == z) ed.WriteMessage("\n{0}+{1} is equal to {2}",x,y,z);
if ((z - y) != x)
{
ed.WriteMessage("\n{0}+{1} is not equal to {2}", z, y, x);
}
else
{
ed.WriteMessage("\n{0}-{1} is equal to {2}", z, y, x);
}
switch (x + y + z)
{
case 3:
ed.WriteMessage("\n{0}+{1}+{2}=3", x, y, z);
break;
case 4:
ed.WriteMessage("\n{0}+{1}+{2}=4", x, y, z);
break;
case 5:
ed.WriteMessage("\n{0}+{1}+{2}=5", x, y, z);
break;
default:
ed.WriteMessage("\n{0}+{1}+{2}={3}", x, y, z, (x + y + z));
break;
}
}
}
}
Try to experiment with the above code using different conditions. Also try to work with common logical operators like AND, OR etc. in your code.