1) Is it possible to extract data from dwf file in autocad 2012?
2)I need to extract blockNames from dwg file but i dont know how to extract blackNames because text in dwg file may change but pattern will remain same.
I am using Visual studio 2010 and Autocad 2012
Solved! Go to Solution.
Solved by Hallex. Go to Solution.
1. See www.autodesk.com/developdwf.
2. You'll find some related code here that shows how to find a block name - http://adndevblog.typepad.com/autocad/2012/05/identifying-block-name-from-the-block-reference.html. Probably not exactly what you want. If you're new to AutoCAD .NET development, visit www.autodesk.com/developautocad.
thanks for reply,
I have a blockName " UserName" and i want to fetch this and insert into sql server
can any one tell be how to extract this blockname properties using .Net api in c#?
Try this code for selecting your blocks,
change list of tags in there
[CommandMethod("ibsql", CommandFlags.Modal | CommandFlags.Session | CommandFlags.Transparent)] public void ImportDataTableToSQL() { Document doc = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument; Database db = doc.Database; Editor ed = doc.Editor; string ctab = Autodesk.AutoCAD.ApplicationServices.Application.GetSystemVariable("ctab").ToString(); System.Data.DataTable dt = new System.Data.DataTable(); List<string> tags = new List<string>() { "TAG1", "TAG2", "TAG3", "TAG4" }; using ( DocumentLock docklock = ed.Document.LockDocument()) { using (Transaction tr = db.TransactionManager.StartTransaction()) { try { BlockTable tb = tr.GetObject(db.BlockTableId, OpenMode.ForRead) as BlockTable; BlockTableRecord tbr = tr.GetObject(db.CurrentSpaceId, OpenMode.ForWrite) as BlockTableRecord; dt.TableName = "MyBlockTable"; dt.Columns.Add("BlockName", typeof(string)); dt.Columns.Add("Handle", typeof(string)); dt.Columns.Add("X_Coordinate", typeof(double)); dt.Columns.Add("Y_Coordinate", typeof(double)); dt.Columns.Add("Z_Coordinate", typeof(double)); // add columns for attributes foreach (string tag in tags) dt.Columns.Add(tag, typeof(string)); TypedValue[] values = { new TypedValue(0, "INSERT"), new TypedValue(66, 1), new TypedValue(410, ctab), new TypedValue(2, "UserName, `*U*") }; SelectionFilter filter = new SelectionFilter(values); PromptSelectionResult res = ed.SelectAll(filter); if (res.Status != PromptStatus.OK) return; SelectionSet sset = res.Value; foreach (SelectedObject selobj in sset) { DBObject obj = (DBObject)tr.GetObject(selobj.ObjectId, OpenMode.ForRead); BlockReference blk = obj as BlockReference; string bname = string.Empty; // get real block name if (blk.IsDynamicBlock) { BlockTableRecord btrec = (BlockTableRecord)tr.GetObject(blk.DynamicBlockTableRecord, OpenMode.ForRead); bname = btrec.Name; } else { BlockTableRecord btrec = (BlockTableRecord)tr.GetObject(blk.BlockTableRecord, OpenMode.ForRead); bname = btrec.Name; } string hdl = blk.Handle.Value.ToString(); Point3d pt = blk.Position; double xp = pt.X; double yp = pt.Y; double zp = pt.Z; System.Data.DataRow dr = dt.NewRow(); dr[0] = bname; dr[1] = hdl; dr[2] = xp; dr[3] = yp; dr[4] = zp; AttributeCollection attribs = blk.AttributeCollection; int k = 5; foreach (ObjectId attid in attribs) { AttributeReference attref = (AttributeReference)tr.GetObject(attid, OpenMode.ForRead); dr[k] = attref.TextString; k += 1; } dt.Rows.Add(dr); } //Autodesk.AutoCAD.ApplicationServices.Application.ShowAlertDialog("At this point you can load this table on SQL Server"); // for debug only: for (int i = 0; i < dt.Rows.Count; i++) { System.Data.DataRow dr = dt.Rows[i]; object[] rowarr = dr.ItemArray; for (int j = 0; j < dt.Columns.Count; j++) { ed.WriteMessage("\n{0}\n",rowarr[j]); } } tr.Commit(); } catch (System.Exception ex) { ed.WriteMessage("\n{0}\n{1}\n",ex.Message,ex.StackTrace); } finally { Autodesk.AutoCAD.ApplicationServices.Application.ShowAlertDialog("At this point you can load this table on SQL Server"); dt.Dispose(); } } } }
~'J'~
Thanks for reply, i used your code but its displaying the Alert message and even there is nothing in dt
can you look into my code? is it right?
[CommandMethod("ibsql", CommandFlags.Modal | CommandFlags.Session | CommandFlags.Transparent)]
public void ImportDataTableToSQL()
{
Document doc = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument;
Database db = doc.Database;
Editor ed = doc.Editor;
string ctab = Autodesk.AutoCAD.ApplicationServices.Application.GetSystemVariable("ctab").ToString();
System.Data.DataTable dt = new System.Data.DataTable();
List<string> tags = new List<string>() { "TAG1", "TAG2", "TAG3", "TAG4" };
using (DocumentLock docklock = ed.Document.LockDocument())
{
using (Transaction tr = db.TransactionManager.StartTransaction())
{
try
{
BlockTable tb = tr.GetObject(db.BlockTableId, OpenMode.ForRead) as BlockTable;
BlockTableRecord tbr = tr.GetObject(db.CurrentSpaceId, OpenMode.ForWrite) as BlockTableRecord;
dt.TableName = "MyBlockTable";
dt.Columns.Add("BlockName", typeof(string));
dt.Columns.Add("Handle", typeof(string));
dt.Columns.Add("X_Coordinate", typeof(double));
dt.Columns.Add("Y_Coordinate", typeof(double));
dt.Columns.Add("Z_Coordinate", typeof(double));
// add columns for attributes
foreach (string tag in tags)
dt.Columns.Add(tag, typeof(string));
TypedValue[] values = { new TypedValue(0, "INSERT"),
new TypedValue(66, 1),
new TypedValue(410, ctab),
new TypedValue(2, "UserName, `*U*") };
SelectionFilter filter = new SelectionFilter(values);
PromptSelectionResult res = ed.SelectAll(filter);
if (res.Status != PromptStatus.OK) return;
SelectionSet sset = res.Value;
foreach (SelectedObject selobj in sset)
{
DBObject obj = (DBObject)tr.GetObject(selobj.ObjectId, OpenMode.ForRead);
BlockReference blk = obj as BlockReference;
string bname = string.Empty;
// get real block name
if (blk.IsDynamicBlock)
{
BlockTableRecord btrec = (BlockTableRecord)tr.GetObject(blk.DynamicBlockTableRecord, OpenMode.ForRead);
bname = btrec.Name;
}
else
{
BlockTableRecord btrec = (BlockTableRecord)tr.GetObject(blk.BlockTableRecord, OpenMode.ForRead);
bname = btrec.Name;
}
string hdl = blk.Handle.Value.ToString();
Point3d pt = blk.Position;
double xp = pt.X;
double yp = pt.Y;
double zp = pt.Z;
System.Data.DataRow dr = dt.NewRow();
dr[0] = bname;
dr[1] = hdl;
dr[2] = xp;
dr[3] = yp;
dr[4] = zp;
Autodesk.AutoCAD.DatabaseServices.AttributeCollection attribs = blk.AttributeCollection;
int k = 5;
foreach (ObjectId attid in attribs)
{
AttributeReference attref = (AttributeReference)tr.GetObject(attid, OpenMode.ForRead);
dr[k] = attref.TextString;
k += 1;
}
dt.Rows.Add(dr);
}
//Autodesk.AutoCAD.ApplicationServices.Application.ShowAlertDialog("At this point you can load this table on SQL Server");
// for debug only:
for (int i = 0; i < dt.Rows.Count; i++)
{
System.Data.DataRow dr = dt.Rows[i];
object[] rowarr = dr.ItemArray;
for (int j = 0; j < dt.Columns.Count; j++)
{
ed.WriteMessage("\n{0}\n", rowarr[j]);
}
}
tr.Commit();
}
catch (System.Exception ex)
{
ed.WriteMessage("\n{0}\n{1}\n", ex.Message, ex.StackTrace);
}
finally
{
//Here i am trying to display the record in datagridview but its NUll
dataGridView1.DataSource = dt.DefaultView;
Form1 form = new Form1();
form.Show();
Autodesk.AutoCAD.ApplicationServices.Application.ShowAlertDialog("At this point you can load this table on SQL Server");
dt.Dispose();
}
}
}
}
And also can you help to list all blockNames with text ? show that i can filter this later...
Hi
As you have block name as “UserName”, can you please try with below filter?
TypedValue[] values = { new TypedValue(0, "INSERT"), new TypedValue(410, ctab), new TypedValue(2, "UserName") };
You have to declare Datatable in Form class as public:
public System.Data.DataTable dt = new System.Data.DataTable();
then add button to do your work AutoCAD
then on Form Initializing do your job with DatagridView, e.g. add columns etc,
then click button to go to AutoCAD,
hide form before,
then after the selection would be executed,
show Form,
display result in DataGridView,
somerhing along this way...
~'J'~
Can't find what you're looking for? Ask the community or share your knowledge.