ObjectARX的扩展数据和扩展记录的定义及应用不再赘述,下面着重介绍如何将结果缓冲区作为参数传递给自定义读写函数。见代码:
1. 先创建一个测试命令,用于测试将扩展记录和扩展数据附加到一个实体。此处省略了如何将实体推入数据库的过程,即代码中的 AppendEntityToBlock()函数。
// 本例创建一个圆实体,并附加扩展数据和扩展记录
void Test()
{
AcDbCircle* pCir = new AcDbCircle(AcGePoint3d(10, 10, 0), AcGeVector3d::kZAxis, 5.0);
AcDbObjectId objId = AppendEntityToBlock(pCir);
// 设置扩展记录
struct resbuf* pRb1 = acutBuildList(AcDb::kDxfText, _RXST("演示1"), RTNONE);
if (SetXRecord(objId, pRb1)) acutPrintf(_T("\n--- 添加扩展记录 成功 ---"));
// 读取扩展记录
struct resbuf* pRb2 = NULL;
if (GetXRecord(objId, &pRb2))
{
if (pRb2)
{
acutPrintf(_T("\n--- 读取扩展记录:%s ---"), pRb2->resval.rstring);
acutRelRb(pRb2);
}
}
// 设置扩展数据
// resbuf 的 restype 字段中只接受有效的 xdata 组代码(1000--1071),
// 这就以为着类型码的前缀只能是 AcDb::kDxfXd,AcDb::kDxfRegAppName 除外,否则添加不能成功
struct resbuf* pRb3 = acutBuildList(AcDb::kDxfRegAppName, _RXST("WjcStudio_ObjectARX"), AcDb::kDxfXdAsciiString, _RXST("演示2"), RTNONE);
if (SetXData(objId, pRb3))
acutPrintf(_T("\n--- 添加扩展数据 成功 ---"));
// 读取扩展数据
struct resbuf* pRb4 = NULL;
if (GetXData(objId, &pRb4))
{
if (pRb4)
{
acutPrintf(_T("\n--- 读取扩展数据:%s ---"), pRb4->rbnext->resval.rstring);
acutRelRb(pRb4);
}
}
}
2. 设置扩展记录
//-----------------------------------------------------------------------------
// 为 AcDbObject 类对象添加扩展记录
// destObjId:AcDbObject 类的 ID -----------------------<input>
// *pSrcRb:结果缓冲区链表指针, 包含全部扩展记录的数据 ----<input>
// appName:应用程序名称,默认为 “WjcStudio_ObjectARX” ---<input>
// 返回:true-成功,false-失败
static bool SetXRecord(const AcDbObjectId& destObjId, struct resbuf* pSrcRb,
AcString appName = _RXST("WjcStudio_ObjectARX"))
{
Acad::ErrorStatus es;
AcDbObject* pObject = NULL;
es = acdbOpenObject(pObject, destObjId, AcDb::kForWrite);
if (es != Acad::eOk)
{
if (pSrcRb) acutRelRb(pSrcRb);//释放结果缓冲区
return false;
}
es = pObject->createExtensionDictionary();//新建对象扩展字典
if (es != Acad::eOk && es != Acad::eAlreadyInDb)
{
pObject->close();
if (pSrcRb) acutRelRb(pSrcRb);
return false;
}
AcDbObjectId dictId = NULL;
AcDbDictionary* pDict = NULL;
dictId = pObject->extensionDictionary();
pObject->close();
if (dictId.isNull())
{
if (pSrcRb) acutRelRb(pSrcRb);
return false;
}
//创建扩展记录实体
AcDbXrecord* pXRecord = new AcDbXrecord();
//向扩展字典中添加一条记录
AcDbObjectId xRecordId = NULL;
if (Acad::eOk == acdbOpenObject(pDict, dictId, AcDb::kForWrite))
{
es = pDict->setAt(appName, pXRecord, xRecordId);
pDict->close();
}
if (Acad::eOk != es)
{
delete pXRecord;
if (pSrcRb) acutRelRb(pSrcRb);
return false;
} //设置扩展记录的内容
es = pXRecord->setFromRbChain(*pSrcRb);
pXRecord->close();
if (pSrcRb) acutRelRb(pSrcRb);//释放结果缓冲区
if (es != Acad::eOk) return false;
return true;
}
3. 读取扩展记录
//-----------------------------------------------------------------------------
// 读取AcDbObject类对象的扩展记录
// destObjId:AcDbObject 类的 ID ----------------------------<input>
// **pSrcRb:结果缓冲区链表指针的指针, 包含全部扩展记录的数据 ---<output>
// appName: 应用程序名称,默认为 “WjcStudio_ObjectARX” --------<input>
// 返回:true-成功,false-失败
static bool GetXRecord(const AcDbObjectId& destObjId, struct resbuf** pRtnRb,
AcString appName = _RXST("WjcStudio_ObjectARX"))
{
Acad::ErrorStatus es;
AcDbObject* pObject = NULL;
AcDbXrecord* pXRecord = NULL;
AcDbDictionary* pDict = NULL;
if (*pRtnRb) acutRelRb(*pRtnRb);
*pRtnRb = NULL;
// 打开对象
es = acdbOpenObject(pObject, destObjId, AcDb::kForRead);
if (es != Acad::eOk) return false;
// 获取对象的扩展字典
AcDbObjectId dictId = pObject->extensionDictionary();
pObject->close();
if (dictId.isNull()) return false;
// 打开字典
es = acdbOpenObject(pDict, dictId, AcDb::kForRead);
if (Acad::eOk != es) return false;
// 获取指定应用程序的扩展记录
es = pDict->getAt(appName, pXRecord, AcDb::kForRead);
pDict->close();
if (Acad::eOk != es) return false;
// 扩展记录数据读入结果缓冲区
es = pXRecord->rbChain(pRtnRb);
pXRecord->close();
if (Acad::eOk != es) return false;
return true;
}
4. 设置扩展数据
//-----------------------------------------------------------------------------
// 为AcDbObject类对象添加扩展数据
// destObjId:AcDbObject 类的 ID -----------------------<input>
// *pRtnRb: 结果缓冲区链表指针, 包含全部扩展数据的数据 ----<input>
// appName: 应用程序名称,默认为 “WjcStudio_ObjectARX” ---<input>
// 返回:true-成功,false-失败
static bool SetXData(const AcDbObjectId& objectId, struct resbuf* pRtnRb,
AcString appName = _RXST("WjcStudio_ObjectARX"))
{
AcDbObject* pObject = NULL;
if (Acad::eOk != acdbOpenObject(pObject, objectId, AcDb::kForWrite)) return false;
int rtnRegApp = acdbRegApp(appName);
if (rtnRegApp == RTNORM || rtnRegApp == RTERROR)
pObject->setXData(pRtnRb);//新建或覆盖扩展数据
pObject->close();
if (pRtnRb) acutRelRb(pRtnRb); // 删除链表
return true;
}
5. 读取扩展数据
//-----------------------------------------------------------------------------
// 读取AcDbObject类对象的扩展数据
// destObjId:AcDbObject 类的 ID ----------------------------<input>
// **pRtnRb:结果缓冲区链表指针的指针, 包含全部扩展数据的数据 ---<output>
// appName:应用程序名称,默认为 “WjcStudio_ObjectARX” --------<input>
// 返回:true-成功,false-失败
static bool GetXData(const AcDbObjectId& destObjId, struct resbuf** pRtnRb,
AcString appName = _T("WjcStudio_ObjectARX"))
{
if (*pRtnRb) acutRelRb(*pRtnRb);
*pRtnRb = NULL;
AcDbEntity* pObject = NULL;
if (Acad::eOk != acdbOpenObject(pObject, destObjId, AcDb::kForRead)) return false;
*pRtnRb = pObject->xData(appName);
pObject->close();
if ((*pRtnRb)) return true;
return false;
}