#include "DbSection.h"
static Acad::ErrorStatus appendWithColor(AcArray<AcDbEntity *> Ents, AcDbBlockTableRecord *btr, Adesk::UInt16 col)
{
Acad::ErrorStatus esBad = Acad::eOk, es;
for(int i=0;i<Ents.length();++i)
{
AcDbEntity *ent = Ents.at(i);
es = btr->appendAcDbEntity(ent);
if (es)
{
delete ent;
ent = nullptr;
}
else
{
esBad = es;
ent->setColorIndex(col);
ent->close();
}
}
return esBad;
}
static void ClearCollection(AcArray<AcDbEntity *> &Ents)
{
for(int i=0;i<Ents.length();++i)
{
AcDbEntity *ent = Ents.at(i);
if (ent)
{
if (ent->database())
{
if (ent->isReadEnabled())
ent->close();
}
else
delete ent;
}
}
Ents.setLogicalLength(0);
}
static Acad::ErrorStatus drawSilhouette(AcArray<AcDbEntity *> objIds)
{
Acad::ErrorStatus es;
AcDbDatabase *db = acdbHostApplicationServices()->workingDatabase();
AcDbObjectId entId;
//TB: You must NOT append the entities to the modelspace! So the follwing isn't required.
//AcDbBlockTable *pBlkTbl = NULL;
//db->getBlockTable(pBlkTbl, AcDb::kForRead);
//AcDbBlockTableRecord *pBlkTblRcd = NULL;
//pBlkTbl->getAt(ACDB_MODEL_SPACE, pBlkTblRcd, AcDb::kForWrite);
//pBlkTbl->close();
//AcTransaction *pTrans = actrTransactionManager->startTransaction(); //TB: Not required
AcDbExtents exts;
int len = objIds.length();
for (int i = 0; i < len; i++)
{
AcDbExtents extents;
if (Acad::eOk != objIds.at(i)->getGeomExtents(extents)) continue;
exts.addPoint(extents.minPoint());
exts.addPoint(extents.maxPoint());
//pBlkTblRcd->appendAcDbEntity(entId, objIds.at(i)); //TB NO! These entities are already in the modelspace!
}
//actrTransactionManager->endTransaction(); //TB: not required
//pBlkTblRcd->close();
AcDbExtents extents;
extents = exts;
auto minX = extents.minPoint().x;
auto minY = extents.minPoint().y;
auto z = extents.maxPoint().z;
auto maxX = extents.maxPoint().x;
auto maxY = extents.maxPoint().y;
//DbSection.h
AcDbSection *pSection = new AcDbSection;
pSection->setDatabaseDefaults(db);
AcDbSection §ion = *pSection;
section.setState(AcDbSection::kPlane);
section.addVertex(0, AcGePoint3d(minX, minY, z));
section.addVertex(1, AcGePoint3d(maxX, minY, z));
section.setViewingDirection(AcGeVector3d::kZAxis);
section.setVerticalDirection(AcGeVector3d::kYAxis);
AcArray<AcDbEntity *> intBoundaryEnts;
AcArray<AcDbEntity *> intFillEnts;
AcArray<AcDbEntity *> backgroundEnts;
AcArray<AcDbEntity *> foregroundEnts;
AcArray<AcDbEntity *> curveTangencyEnts;
es = section.generateSectionGeometry(objIds, intBoundaryEnts, intFillEnts, backgroundEnts, foregroundEnts, curveTangencyEnts);
if (es == Acad::eOk)
{
AcGeMatrix3d mat;
mat.setToTranslation(AcGeVector3d(1000, 0, 0));
AcDbObjectId idModelSpace = acdbSymUtil()->blockModelSpaceId(db);
AcDbBlockTableRecord *modelspace;
es = acdbOpenObject(modelspace, idModelSpace, AcDb::kForWrite);
if (!es)
{
es = modelspace->appendAcDbEntity(pSection);
if (!es)
pSection->close();
else
delete pSection;
appendWithColor(intBoundaryEnts, modelspace, 1);
appendWithColor(intFillEnts, modelspace, 2);
appendWithColor(backgroundEnts, modelspace, 3);
appendWithColor(foregroundEnts, modelspace, 4);
appendWithColor(curveTangencyEnts, modelspace, 5);
modelspace->close();
}
}
ClearCollection(intBoundaryEnts);
ClearCollection(intFillEnts);
ClearCollection(backgroundEnts);
ClearCollection(foregroundEnts);
ClearCollection(curveTangencyEnts);
return es;
}
// static void AddIdsToSelection(AcDbObjectIdArray &ids, AcArray<AcDbEntity *> entset)
//TB
// 1.) AcDbObjectIdArray &ids is unused
// 2.) You must pass entset as reference (&entset) to return the selected entities to the caller!
static void AddIdsToSelection(AcArray<AcDbEntity *> &entset)
{
Acad::ErrorStatus es;
ads_name selectSet;
AcDbObjectId idSolid;
acedSSGet(NULL, NULL, NULL, NULL, selectSet);
Adesk::Int32 len = 0; //TB type changed from long
acedSSLength(selectSet, &len);
for (int i = 0; i < len; ++i)
{
ads_name en_SS;
acedSSName(selectSet, i, en_SS);
AcDb3dSolid *solid = nullptr;
es = acdbGetObjectId(idSolid, en_SS);
if (!es) {
es = acdbOpenObject(solid, idSolid, AcDb::kForRead); //TB kForRead es enough
if (!es) {
entset.append(solid);
//solid->close(); //TB No! keep it open
}
}
}
acedSSFree(selectSet);
}
//Registered as command SOSI/SS
void MyGroupMyCommand2() {
AcDb3dSolid *solid = nullptr;
AcArray<AcDbEntity *> entset;
//AcDbObjectIdArray ids; // unused
AddIdsToSelection(/*ids, unused*/ entset);
drawSilhouette(entset);
}
参考:https://forums.autodesk.com/t5/objectarx/acdbsection-to-create-a-2d-outline-of-a-solid/td-p/11410996
文章评论