ObjectARX-组字典(Group)
(1)使用ObjectARX创建一个新工程Group.
注册命令AddGroup,提示用户选择实体,将其创建成一个编组,
实现函数为:
static void AAAMyGroupAddGroup() { //提示用户选择多个实体 AcDbObjectIdArray entIds; if (CSelectUtil::PromptSelectEnts(TEXT("\n选择要成组的实体:"), AcDbEntity::desc(), entIds)) { //创建组 AcDbGroup *pGroup = new AcDbGroup(); for (int i = 0; i < entIds.length(); i++) { pGroup->append(entIds[i]); } //将组添加到有名对象字典的组字典中 AcDbDictionary *pGroupDict = NULL; acdbHostApplicationServices()->workingDatabase() ->getGroupDictionary(pGroupDict, AcDb::kForWrite); //如果组名为*,则会创建匿名组 CString groupName = TEXT("*"); AcDbObjectId groupId; pGroupDict->setAt(groupName, pGroup, groupId); pGroupDict->close(); pGroup->close(); } }
其中,函数PromptSelectEnts 的实现:
首先在项目中添加一个普通类 CSelectUtil,
函数 PromptSelectEnts 的声明:
// 提示用户选择多个实体 static bool PromptSelectEnts(const TCHAR* prompt, AcRxClass* classDesc, AcDbObjectIdArray &entIds); static bool PromptSelectEnts(const TCHAR* prompt, const std::vector<AcRxClass*> &classDescs, AcDbObjectIdArray &entIds);函数 PromptSelectEnts 的实现:
bool CSelectUtil::PromptSelectEnts(const TCHAR* prompt, AcRxClass* classDesc, AcDbObjectIdArray &entIds) { std::vector<AcRxClass*> vecClassDesc; vecClassDesc.push_back(classDesc); return PromptSelectEnts(prompt, vecClassDesc, entIds); } bool CSelectUtil::PromptSelectEnts(const TCHAR* prompt, const std::vector<AcRxClass*> &classDescs, AcDbObjectIdArray &entIds) { // 初始化 entIds.setLogicalLength(0); // 提示用户选择实体 ads_name sset; int result = 0; acutPrintf(prompt); result = acedSSGet(NULL, NULL, NULL, NULL, sset); if (result != RTNORM) { return false; } // 取得选择集的长度 long length = 0; acedSSLength(sset, reinterpret_cast<Adesk::Int32*>(&length)); // 遍历选择集 Acad::ErrorStatus es; AcDbEntity* pEnt = NULL; for (long i = 0; i < length; i++) { ads_name ename; acedSSName(sset, i, ename); AcDbObjectId curEntId; es = acdbGetObjectId(curEntId, ename); if (es != Acad::eOk) { continue; } // 打开实体 es = acdbOpenObject(pEnt, curEntId, AcDb::kForRead); if (es != Acad::eOk) { continue; } // 判断当前实体是否是指定的实体类型 for (int j = 0; j < (int)classDescs.size(); j++) { if (pEnt->isKindOf(classDescs[j])) { entIds.append(pEnt->objectId()); break; } } pEnt->close(); // 关闭实体 } acedSSFree(sset); // 释放选择集 return (entIds.length() > 0); }
(2)注册一个命令DeleteGroup,
提示用户选择图形中位于编组内的实体,然后删除这个编组。
实现函数为:
static void AAAMyGroupDeleteGroup() { AcDbObjectIdArray entIds; if (CSelectUtil::PromptSelectEnts(TEXT("\n选择要分解的组中的实体:"), AcDbEntity::desc(), entIds)) { //遍历组字典,判断是否包含了给定的实体 AcDbDictionary *pGroupDict = NULL; acdbHostApplicationServices()->workingDatabase()->getGroupDictionary(pGroupDict, AcDb::kForWrite); AcDbDictionaryIterator *it = pGroupDict->newIterator(); for (; !it->done(); it->next()) { AcDbGroup *pGroup = NULL; if (it->getObject((AcDbObject*&)pGroup, AcDb::kForWrite) == Acad::eOk) { AcDbObjectIdArray groupEntIds; pGroup->allEntityIds(groupEntIds); bool bFound = false; for (int i = 0; i < entIds.length(); i++) { if (groupEntIds.contains(entIds[i])) { bFound = true; break; } } //删除包含选择集中实体的组 if (bFound) { pGroup->erase(); } pGroup->close(); } } pGroupDict->close(); } }
效果:
①运行AutoCAD,加载生成的ARX文件,执行AddGroup命令,
选择若干实体,然后按enter键;
②使用ArxDbg工具来观察:
如果你没有ArxDbg工具,可从这里下载:
https://blog.csdn.net/qq_40416052/article/details/82832475
③执行DelGroup命令,删除编组。
转载请注明出处: 芝麻开花
本文的链接地址: http://www.vmould.cn/?post=165
发表评论 取消回复