是否存在对应AutoLisp中vlax-ldata-put的.NET API版本?
实现AutoLISP vlax-ldata-put等效功能的C#方案
可以实现该需求,vlax-ldata系列函数存储的数据本质是存储在命名对象字典(NOD)的VL_LISP_DATA固定子字典下,只要存储结构符合AutoLISP可识别的resbuf规范,就可以直接用vlax-ldata-get读取。
前置依赖
需要先在C#项目中引用AutoCAD .NET API的核心程序集,引入以下命名空间:
Autodesk.AutoCAD.ApplicationServicesAutodesk.AutoCAD.DatabaseServicesAutodesk.AutoCAD.Runtime
代码实现
/// <summary> /// 等效于AutoLISP (vlax-ldata-put appName key data) 功能 /// </summary> /// <param name="appName">应用标识名,和vlax-ldata-get调用的参数保持一致</param> /// <param name="key">存储键名</param> /// <param name="data">要存储的数据,支持字符串、数值、布尔等AutoLISP兼容类型</param> /// <returns>存储成功返回true,失败返回false</returns> public static bool LispDataPut(string appName, string key, object data) { Document doc = Application.DocumentManager.MdiActiveDocument; Database db = doc.Database; using (Transaction tr = db.TransactionManager.StartTransaction()) { // 获取根命名对象字典 DBDictionary nod = tr.GetObject(db.NamedObjectsDictionaryId, OpenMode.ForWrite) as DBDictionary; // 获取或创建VLISP专用存储字典VL_LISP_DATA DBDictionary lispDataDict; if (nod.Contains("VL_LISP_DATA")) { lispDataDict = tr.GetObject(nod.GetAt("VL_LISP_DATA"), OpenMode.ForWrite) as DBDictionary; } else { lispDataDict = new DBDictionary(); nod.SetAt("VL_LISP_DATA", lispDataDict); tr.AddNewlyCreatedDBObject(lispDataDict, true); } // 获取或创建当前应用对应的子字典 DBDictionary appDict; if (lispDataDict.Contains(appName)) { appDict = tr.GetObject(lispDataDict.GetAt(appName), OpenMode.ForWrite) as DBDictionary; } else { appDict = new DBDictionary(); lispDataDict.SetAt(appName, appDict); tr.AddNewlyCreatedDBObject(appDict, true); } // 将C#数据转换为AutoLISP可识别的ResultBuffer结构 using (ResultBuffer rb = new ResultBuffer()) { switch (data) { case string strVal: rb.Add(new TypedValue((int)LispDataType.Text, strVal)); break; case int intVal: rb.Add(new TypedValue((int)LispDataType.Int32, intVal)); break; case double doubleVal: rb.Add(new TypedValue((int)LispDataType.Double, doubleVal)); break; case bool boolVal: rb.Add(new TypedValue((int)LispDataType.Boolean, boolVal ? 1 : 0)); break; // 可扩展支持列表、点坐标等复合类型,按Lisp嵌套顺序添加TypedValue即可 default: return false; } // 存入对应键的Xrecord if (appDict.Contains(key)) { Xrecord xrec = tr.GetObject(appDict.GetAt(key), OpenMode.ForWrite) as Xrecord; xrec.Data = rb; } else { Xrecord xrec = new Xrecord { Data = rb }; appDict.SetAt(key, xrec); tr.AddNewlyCreatedDBObject(xrec, true); } } tr.Commit(); return true; } }
调用验证
- C#侧调用存储数据:
LispDataPut("MY_PROJECT", "PROJECT_ID", 2024001); - AutoLISP侧读取数据,在命令行输入:
(vlax-ldata-get "MY_PROJECT" "PROJECT_ID")
即可读到返回值2024001。
注意事项
appName和key的大小写要和vlax-ldata-get调用时保持一致,命名对象字典的键名区分大小写,建议统一用大写避免匹配失败- 存储复合类型(如点坐标、列表)时,需要按AutoLISP的嵌套顺序组织
ResultBuffer的TypedValue条目 - 不要修改
VL_LISP_DATA字典下非自定义应用的条目,避免破坏AutoLISP自身存储的ldata数据
内容的提问来源于stack exchange,提问作者OGP99
相关产品推荐
相关产品推荐

