【发布时间】:2016-09-16 12:22:38
【问题描述】:
我刚开始为 AutoCAD 2016 开发应用程序。我想将我的 DLL 加载到单独的 AppDomain 中,这样我就不必一直重新启动 ACAD。
经过大量研究和尝试,我最终得到了一个管道解决方案 使用 System.Addin 和 System.Addin.Contract。
我只使用 Views Contract 和 Adapters 的接口和标准类,就像这个例子中的 here。
这是我的插件,其中包含一种将 Hello 写入 Acad 编辑器的方法和第二种绘制线条的方法。
using System.AddIn;
using CADAddinView;
using Autodesk.AutoCAD.EditorInput;
using Autodesk.AutoCAD.ApplicationServices;
using Autodesk.AutoCAD.DatabaseServices;
using Autodesk.AutoCAD.Geometry;
namespace CADAddIn
{
[AddIn("cadAddIn", Version = "1.0.0.0")]
public class CADAddIn : ICADAddinView
{
public void drawLine()
{
Document acDoc = Autodesk.AutoCAD.ApplicationServices.Core.Application.DocumentManager.MdiActiveDocument;
Database acCurDb = acDoc.Database;
using (DocumentLock acLckDoc = acDoc.LockDocument())
{
using (Transaction acTrans = acCurDb.TransactionManager.StartTransaction())
{
DBObject blkTbl = acTrans.GetObject(acCurDb.BlockTableId, OpenMode.ForRead);
BlockTable acBlkTbl = blkTbl as BlockTable;
BlockTableRecord acBlkTblRec = (BlockTableRecord)acTrans.GetObject(acBlkTbl[BlockTableRecord.ModelSpace], OpenMode.ForWrite);
Polyline acPoly = new Polyline();
acPoly.SetDatabaseDefaults();
acPoly.AddVertexAt(0, new Point2d(0, 0), 0, 0, 0);
acPoly.AddVertexAt(0, new Point2d(100, 100), 0, 0, 0);
acBlkTblRec.AppendEntity(acPoly);
acTrans.AddNewlyCreatedDBObject(acPoly, true);
acTrans.Commit();
}
}
}
public void sayHello()
{
Editor ed = Autodesk.AutoCAD.ApplicationServices.Core.Application.DocumentManager.MdiActiveDocument.Editor;
ed.WriteMessage("Hello");
}
}
}
这是我的主机应用程序:
using System.AddIn.Hosting;
using System.Windows.Forms;
using CADHostView;
using System;
using System.Collections.ObjectModel;
using Autodesk.AutoCAD.Runtime;
namespace CADHost
{
public class CADHost
{
[CommandMethod("sayHello")]
public static void sayHello()
{
string addInPath = Environment.CurrentDirectory + "\\Pipeline";
string[] warnings = AddInStore.Update(addInPath);
foreach (string warning in warnings)
{
MessageBox.Show(warning);
}
Collection<AddInToken> tokens = AddInStore.FindAddIns(typeof(ICADHostView), addInPath);
if (tokens.Count == 0)
{
MessageBox.Show("No AddIn found.");
}
else
{
AddInToken cadToken = tokens[0];
ICADHostView cadApp = cadToken.Activate<ICADHostView>(AddInSecurityLevel.Host);
cadApp.sayHello();
}
}
[CommandMethod("drawLine")]
public static void drawLine()
{
string addInPath = Environment.CurrentDirectory + "\\Pipeline";
string[] warnings = AddInStore.Update(addInPath);
foreach (string warning in warnings)
{
MessageBox.Show(warning);
}
Collection<AddInToken> tokens = AddInStore.FindAddIns(typeof(ICADHostView), addInPath);
if (tokens.Count == 0)
{
MessageBox.Show("No AddIn found.");
}
else
{
AddInToken cadToken = tokens[0];
ICADHostView cadApp = cadToken.Activate<ICADHostView>(AddInSecurityLevel.Host);
cadApp.drawLine();
}
}
}
}
这两个应用程序都引用了来自 Acad 的三个标准 Dll: accremgd.dll、acdbmgd.dll、acmgd.dll。
在这两个项目中,这些 dll 都具有选项 local copy false。 如果我开始然后我得到一个异常,程序找不到文件“accoremgd.dll”并且Acad崩溃。
所以我尝试为插件设置选项本地副本为真。 现在它适用于“sayHello”-Methode。
但是当 acBlkTbl 被初始化时,我得到了一个无效转换异常。
如果有人能帮我完成这项工作,那就太好了。 同样很棒的是不能使用 Addinsystem 制作一个工作示例 我只想让这项工作不要一直重新启动 acad^^
感谢您的帮助 马蒂亚斯
【问题讨论】:
-
如果有人感兴趣,我也可以通过邮件发送孔项目进行测试。