Files
envi-code/SourceCode/Code2026/CoreLibrary/BrepOper.cpp
T
2026-09-28 15:28:50 +08:00

1796 lines
47 KiB
C++

#include "stdafx.h"
#include "dbobjptr.h "
#include "CoreTools.h"
#include "acedsubsel.h"
#pragma region brep-include
#include "acutads.h"
#include "acedads.h"
#include "string.h"
#include "adscodes.h"
#include "brent.h"
#include "brbrep.h"
#include "dbmain.h"
#include "geextc3d.h"
#include "brface.h"
#include "brvtx.h"
#include "dbents.h"
#include "geassign.h"
#include "geextc2d.h"
#include "gexbndsf.h"
#include "aced.h"
#include "acestext.h"
#include "actrans.h"
#include "adeskabb.h"
#include "brbctrav.h"
#include "brbvtrav.h"
#include "bredge.h"
#include "brfltrav.h"
#include "brgbl.h"
#include "brletrav.h"
#include "brlvtrav.h"
#include "dbsol3d.h"
#include "dbsymtb.h"
#include "gelnsg3d.h"
#include "gemat3d.h"
#include "genurb3d.h"
#include "genurbsf.h"
#include "geray3d.h"
#include "ol_errno.h"
#include "adesk.h"
#include "adslib.h"
#include "brbetrav.h"
#include "brbftrav.h"
#include "brbstrav.h"
#include "brcstrav.h"
#include "brelem2d.h"
#include "breltrav.h"
#include "brentrav.h"
#include "brhit.h"
#include "brloop.h"
#include "brmetrav.h"
#include "brprops.h"
#include "brm2dctl.h"
#include "brmesh2d.h"
#include "brnode.h"
#pragma endregion
#include "BrepOper.h"
#include "KTCADUtilityEx.h"
#include "KTCADUtility.h"
#pragma region sh-entity
#include "AecDbBDPipeBase.h"
#include "AecDbWall.h"
#include "AecDbSlab.h"
#include "AecDbColumn.h"
#include "AecDbBeam.h"
#include "AecDbEwEquipment.h"
#pragma endregion
namespace
{
const double kPi = 3.14159265358979323846;
const double kTwoPi = 6.28318530717958647692;
const double kHalfPi = 1.57079632679489661923;
void errorReport(AcBr::ErrorStatus errorCode)
{
switch (errorCode) {
case(AcBr::eBrepChanged):
acutPrintf(ACRX_T(" Brep Changed\n"));
break;
case(AcBr::eUnsuitableTopology):
acutPrintf(ACRX_T(" Unsuitable Topology\n"));
break;
case(AcBr::eDegenerateTopology):
acutPrintf(ACRX_T(" Degenerate Topology\n"));
break;
case(AcBr::eUninitialisedObject):
acutPrintf(ACRX_T(" Uninitialised Object\n"));
break;
default:
acutPrintf(ACRX_T(" AutoCAD Error Code: %d\n"), errorCode);
acadErrorStatusText((Acad::ErrorStatus)errorCode);
break;
}
return;
}
// Add the given entity to the current Database
Acad::ErrorStatus addToDatabase(AcDbEntity* pEnt, AcDbObjectId& objId)
{
Acad::ErrorStatus acadReturnValue = Acad::eOk;
AcDbBlockTable* pBlockTable;
AcDbBlockTableRecord* pSpaceRecord;
AcDbDatabase *pCurDwg = acdbHostApplicationServices()->workingDatabase();
if (pCurDwg==NULL)
return Acad::eNoDatabase;
if ((acadReturnValue = pCurDwg->getBlockTable(pBlockTable,
AcDb::kForRead)) != Acad::eOk) {
acutPrintf(ACRX_T("\n acdbCurDwg()->getBlockTable() failed"));
return acadReturnValue;
}
if ((acadReturnValue = pBlockTable->getAt(ACDB_MODEL_SPACE,
pSpaceRecord, AcDb::kForWrite)) != Acad::eOk) {
acutPrintf(ACRX_T("\n AcDbBlockTable::getAt() failed"));
return acadReturnValue;
}
// close the block table object
if ((acadReturnValue = pBlockTable->close()) != Acad::eOk) {
acutPrintf(ACRX_T("\n AcDbBlockTable::close() failed"));
return acadReturnValue;
}
// append the entity to the display list
if ((acadReturnValue = pSpaceRecord->appendAcDbEntity(objId, pEnt))
!= Acad::eOk) {
acutPrintf(ACRX_T("\n AcDbBlockTableRecord::appendAcDbEntity() failed"));
return acadReturnValue;
}
// close the block table record object
if ((acadReturnValue = pSpaceRecord->close()) != Acad::eOk) {
acutPrintf(ACRX_T("\n AcDbBlockTableRecord::close() failed"));
return acadReturnValue;
}
return acadReturnValue;
}
Acad::ErrorStatus dbOpenTransaction(Adesk::Boolean& ownTransaction)
{
Acad::ErrorStatus acadReturnValue = Acad::eOk;
// Open a new transaction only when there is not an existing one.
if (actrTransactionManager->numActiveTransactions() == 0) {
if (actrTransactionManager->startTransaction() == NULL) {
return Acad::eNoActiveTransactions;
} else ownTransaction = kTrue;
} else ownTransaction = kFalse;
return acadReturnValue;
}
// Note: This function conditionally closes a transaction.
Acad::ErrorStatus dbCloseTransaction(Adesk::Boolean& ownTransaction)
{
Acad::ErrorStatus acadReturnValue = Acad::eOk;
// Close only in the case where we own the transaction.
if (ownTransaction)
acadReturnValue = actrTransactionManager->endTransaction();
return acadReturnValue;
}
// Note: This function conditionally aborts a transaction, which invokes UNDO.
Acad::ErrorStatus dbAbortTransaction(Adesk::Boolean& ownTransaction)
{
Acad::ErrorStatus acadReturnValue = Acad::eOk;
// Abort only in the case where we own the transaction.
if (ownTransaction)
acadReturnValue = actrTransactionManager->abortTransaction();
return acadReturnValue;
}
void objIds2SubPath(const AcDbObjectIdArray &objIdList,
const AcDb::SubentType &subType,
const AcDbFullSubentPath *subentIds,
AcDbFullSubentPath &subPath)
{
if (subType != AcDb::kNullSubentType)
{
// Make a subent path for a face or an edge using the
// picked subentity (retrieved from the GS markers)
subPath = subentIds[0];
subPath.objectIds() = objIdList;
}
else
{
// Make a subent path for a brep object (object ID array
// with null subentity ID)
subPath = kNullSubent;
subPath.objectIds() = objIdList;
}
return;
}
Acad::ErrorStatus makeSubentPath(const AcDbObject *pObj,
const AcDbObjectIdArray &objIdList,
const AcDb::SubentType &subType,
const short &marker,
const AcGePoint3d &pickpnt,
AcDbFullSubentPath &subPath)
{
Acad::ErrorStatus acadReturnValue = Acad::eOk;
AcGeMatrix3d xform(AcGeMatrix3d::kIdentity);
int numIds = 0L;
AcDbFullSubentPath* subentIds = NULL;
// Check to see if entity is a supported solid, surface, region or body
AcDb3dSolid* pSolid(NULL);
AcDbSurface* pSurface(NULL);
AcDbRegion* pRegion(NULL);
AcDbBody* pBody(NULL);
AecDbBDPipeBase *pSH(NULL);
if ((pSolid = AcDb3dSolid::cast(pObj)) != NULL)
{
if (subType != AcDb::kNullSubentType)
acadReturnValue = pSolid->getSubentPathsAtGsMarker( subType, marker, pickpnt, xform, numIds, subentIds);
if (subentIds != NULL)
objIds2SubPath(objIdList, subType, subentIds, subPath);
}
else if ((pSurface = AcDbSurface::cast(pObj)) != NULL)
{
if (subType != AcDb::kNullSubentType)
acadReturnValue = pSurface->getSubentPathsAtGsMarker( subType, marker, pickpnt, xform, numIds, subentIds);
if (subentIds != NULL)
objIds2SubPath(objIdList, subType, subentIds, subPath);
}
else if ((pRegion = AcDbRegion::cast(pObj)) != NULL)
{
if (subType != AcDb::kNullSubentType)
acadReturnValue = pRegion->getSubentPathsAtGsMarker( subType, marker, pickpnt, xform, numIds, subentIds);
if (subentIds != NULL)
objIds2SubPath(objIdList, subType, subentIds, subPath);
}
else if ((pBody = AcDbBody::cast(pObj)) != NULL)
{
if (subType != AcDb::kNullSubentType)
acadReturnValue = pBody->getSubentPathsAtGsMarker( subType, marker, pickpnt, xform, numIds, subentIds);
if (subentIds != NULL)
objIds2SubPath(objIdList, subType, subentIds, subPath);
}
else if ((pSH = AecDbBDPipeBase::cast(pObj)) != NULL)
{
if (subType != AcDb::kNullSubentType)
acadReturnValue = pSH->getSubentPathsAtGsMarker(subType, marker, pickpnt, xform, numIds, subentIds);
if (subentIds != NULL)
objIds2SubPath(objIdList, subType, subentIds, subPath);
}
else
{
acutPrintf(ACRX_T("\n Selected object not a brep object\n"));
return Acad::eWrongObjectType;
}
if (subentIds == NULL) acadReturnValue = Acad::ePointNotOnEntity;
if (acadReturnValue != Acad::eOk)
{
acutPrintf(ACRX_T("\n getSubentPathsAtGsMarker failed\n"));
errorReport((AcBr::ErrorStatus)acadReturnValue);
return acadReturnValue;
}
return acadReturnValue;
}
Acad::ErrorStatus extractSolidFromBlock(ads_name ename,
const AcDb::SubentType &subType,
const short &marker,
const AcGePoint3d &pickpnt,
AcDbFullSubentPath &subPath)
{
Acad::ErrorStatus acadReturnValue = Acad::eOk;
struct resbuf* insertStack;
ads_matrix adsMatrix;
int errStat = RTERROR;
errStat = acedNEntSelP(NULL, ename, asDblArray(pickpnt), Adesk::kTrue,
adsMatrix, &insertStack);
if (errStat != RTNORM)
{
acutPrintf(ACRX_T("\n %d nentselp failed\n"), errStat);
return acadReturnValue;
}
// ename should be the solid
AcDbObjectId objId;
acadReturnValue = acdbGetObjectId(objId, ename);
if (acadReturnValue != Acad::eOk)
{
acutPrintf(ACRX_T("\n acdbGetObjectId failed\n"));
errorReport((AcBr::ErrorStatus)acadReturnValue);
return acadReturnValue;
}
// Use an existing transaction if there is one;
// else open a new one
Adesk::Boolean ownTransaction = Adesk::kFalse;
acadReturnValue = dbOpenTransaction(ownTransaction);
if (acadReturnValue != Acad::eOk)
{
acutPrintf(ACRX_T("\n Error in dbOpenTransaction:"));
errorReport((AcBr::ErrorStatus)acadReturnValue);
return acadReturnValue;
}
// Open the object for read-only
AcDbObject* pObj = NULL;
acadReturnValue = actrTransactionManager->getObject(
pObj, objId, AcDb::kForRead);
if (acadReturnValue != Acad::eOk)
{
dbAbortTransaction(ownTransaction);
acutPrintf(ACRX_T("\n Error in getPath:"));
errorReport((AcBr::ErrorStatus)acadReturnValue);
return acadReturnValue;
}
int count = 0;
AcDbObjectId* idArray = new AcDbObjectId[100];
idArray[count++] = objId;
while (insertStack != NULL)
{
ename[0] = insertStack->resval.rlname[0];
ename[1] = insertStack->resval.rlname[1];
acadReturnValue = acdbGetObjectId(objId, ename);
if (acadReturnValue != Acad::eOk) {
acutPrintf(ACRX_T("\n acdbGetObjectId failed\n"));
errorReport((AcBr::ErrorStatus)acadReturnValue);
dbCloseTransaction(ownTransaction);
return acadReturnValue;
}
idArray[count++] = objId;
insertStack = insertStack->rbnext;
}
// Invert the list
AcDbObjectIdArray objIdList;
for (int j=(count-1); j>=0; j--) objIdList.append(idArray[j]);
acadReturnValue = makeSubentPath(pObj, objIdList, subType, marker, pickpnt, subPath);
if (acadReturnValue != Acad::eOk)
{
acutPrintf(ACRX_T("\n makeSubentPath failed\n"));
dbCloseTransaction(ownTransaction);
return acadReturnValue;
}
// Close the transaction
dbCloseTransaction(ownTransaction);
return acadReturnValue;
}
Acad::ErrorStatus selectEntity(const AcDb::SubentType &subType, AcDbFullSubentPath &subPath, const AcGePoint3d &pickPnt)
{
Acad::ErrorStatus acadReturnValue = Acad::eOk;
int errStat = RTERROR;
ads_name sset;
//AcGePoint3d pickPnt;
struct resbuf org_osnap;
acedGetVar(ACRX_T("OSMODE"), &org_osnap);
struct resbuf new_osnap = org_osnap;
new_osnap.resval.rint = 0;
acedSetVar(ACRX_T("OSMODE"), &new_osnap);
//while ((errStat != RTNORM) && (errStat != RTCAN) && (errStat != RTREJ) && (errStat != RTNONE))
//{
// ads_name ent_name;
// switch (subType)
// {
// case AcDb::kNullSubentType:
// errStat = acedEntSel(ACRX_T("\n Pick a solid\n"), ent_name, asDblArray(pickPnt));
// break;
// case AcDb::kFaceSubentType:
// errStat = acedEntSel(ACRX_T("\n Çëʰȡһ¸öÃæ£º\n"), ent_name, asDblArray(pickPnt));
// break;
// case AcDb::kEdgeSubentType:
// errStat = acedEntSel(ACRX_T("\n Pick an edge\n"), ent_name, asDblArray(pickPnt));
// break;
// default:
// acutPrintf(ACRX_T("\n getPath: unsupported subentity type: %d\n"), subType);
// return Acad::eInvalidInput;
// }
// if (errStat == RTERROR)
// {
// struct resbuf buf_errno;
// acedGetVar(ACRX_T("ERRNO"), &buf_errno);
// if (buf_errno.resval.rint == OL_ENTSELNULL) errStat = RTNONE;
// }
//}
//if (errStat == RTNORM)
//{
errStat = acedSSGet(NULL, asDblArray(pickPnt), NULL, NULL, sset);
//}
acedSetVar(ACRX_T("OSMODE"), &org_osnap);
if (errStat != RTNORM) return Acad::eAmbiguousInput;
// Get the entity name
struct resbuf* rb;
errStat = acedSSNameX(&rb, sset, 0L);
if (errStat != RTNORM)
{
acedSSFree(sset);
return Acad::eAmbiguousInput;
}
// Free the selection set
acedSSFree(sset);
// The selected entity is the final entry in the resbuf
int i;
struct resbuf* pTemp;
for (i = 1, pTemp = rb; i < 3; i++, pTemp = pTemp->rbnext)
;
ads_name ename;
ads_name_set(pTemp->resval.rlname, ename);
// Get the GsMarker
pTemp = pTemp->rbnext;
short marker = pTemp->resval.rint;
// Free the rb resbuf entity
acutRelRb(rb);
// Get the object ID of the selected entity
AcDbObjectId objId;
acadReturnValue = acdbGetObjectId(objId, ename);
if (acadReturnValue != Acad::eOk)
{
acutPrintf(ACRX_T("\n acdbGetObjectId failed\n"));
return acadReturnValue;
}
// Use an existing transaction if there is one;
// else open a new one
Adesk::Boolean ownTransaction = Adesk::kFalse;
acadReturnValue = dbOpenTransaction(ownTransaction);
if (acadReturnValue != Acad::eOk)
{
acutPrintf(ACRX_T("\n Error in dbOpenTransaction:"));
errorReport((AcBr::ErrorStatus)acadReturnValue);
return acadReturnValue;
}
// Open the object for read-only
AcDbObject* pObj = NULL;
acadReturnValue = actrTransactionManager->getObject( pObj, objId, AcDb::kForRead);
if (acadReturnValue != Acad::eOk)
{
dbAbortTransaction(ownTransaction);
acutPrintf(ACRX_T("\n Error in getPath:"));
errorReport((AcBr::ErrorStatus)acadReturnValue);
return acadReturnValue;
}
if (AcDbBlockReference::cast(pObj) != NULL)
{
acadReturnValue = extractSolidFromBlock(ename, subType, marker, pickPnt, subPath);
if (acadReturnValue != Acad::eOk)
{
dbCloseTransaction(ownTransaction);
acutPrintf(ACRX_T("\n extractSolidFromBlock failed\n"));
return acadReturnValue;
}
}
else
{
AcDbObjectIdArray objIdList;
objIdList.append(objId);
acadReturnValue = makeSubentPath(pObj, objIdList, subType, marker, pickPnt, subPath);
if (acadReturnValue != Acad::eOk)
{
dbCloseTransaction(ownTransaction);
acutPrintf(ACRX_T("\n makeSubentPath failed\n"));
return acadReturnValue;
}
}
// Close the transaction
dbCloseTransaction(ownTransaction);
return acadReturnValue;
}
AcBr::ErrorStatus selectEntityByType(AcBrEntity*& pEnt
, const AcDb::SubentType &subType
, const AcBr::ValidationLevel &vlevel
, const AcGePoint3d &pickPnt )
{
Acad::ErrorStatus acadReturnValue = Acad::eOk;
AcBr::ErrorStatus returnValue = AcBr::eOk;
// Query the subentity by AutoCAD pick and get the subentity path
AcDbFullSubentPath subPath(kNullSubent);
acadReturnValue = selectEntity(subType, subPath, pickPnt);
if (acadReturnValue != Acad::eOk)
{
acutPrintf(ACRX_T("\n Error in selectEntity: %d"), acadReturnValue);
return (AcBr::ErrorStatus)acadReturnValue;
}
// Call the appropriate subentity constructor
switch (subType)
{
case AcDb::kNullSubentType:
pEnt = new AcBrBrep();
break;
case AcDb::kFaceSubentType:
pEnt = new AcBrFace();
break;
case AcDb::kEdgeSubentType:
pEnt = new AcBrEdge();
break;
default:
acutPrintf(ACRX_T("\n selectEntityByType: unsupported subentity type: %d\n"), subType);
returnValue = (AcBr::ErrorStatus)Acad::eWrongSubentityType;
return returnValue;
}
if (pEnt == NULL) {
acutPrintf(ACRX_T("\n selectEntityByType: unable to allocate memory\n"));
returnValue = (AcBr::ErrorStatus)Acad::eOutOfMemory;
return returnValue;
}
returnValue = pEnt->set(subPath);
if (returnValue != AcBr::eOk)
{
acutPrintf(ACRX_T("\n Error in AcBrEntity::set:"));
errorReport(returnValue);
return returnValue;
}
returnValue = pEnt->setValidationLevel(vlevel);
if (returnValue != AcBr::eOk)
{
acutPrintf(ACRX_T("\n Error in AcBrEntity::setValidationLevel:"));
errorReport(returnValue);
return returnValue;
}
return returnValue;
}
AcBr::ErrorStatus getNativeSurface(const AcBrFace& faceEntity,
AcGeSurface *&surfaceGeometry,
AcGeSurface *&nativeGeometry)
{
AcBr::ErrorStatus returnValue = faceEntity.getSurface(surfaceGeometry);
if (returnValue != AcBr::eOk) {
acutPrintf(ACRX_T("\n Error in AcBrFace::getSurface:"));
errorReport(returnValue);
return returnValue;
}
if (surfaceGeometry == NULL) {
acutPrintf(ACRX_T("\n getNativeSurface: external bounded surface is undefined\n"));
returnValue = AcBr::eMissingGeometry;
return returnValue;
}
if (surfaceGeometry->type() != kExternalBoundedSurface) {
acutPrintf(ACRX_T("\n getNativeSurface: surface is not an external bounded surface\n"));
returnValue = AcBr::eMissingGeometry;
return returnValue;
}
AcGeExternalSurface baseGeometry;
((AcGeExternalBoundedSurface*)surfaceGeometry)->getBaseSurface(baseGeometry);
if (!baseGeometry.isDefined()) {
acutPrintf(ACRX_T("\n getNativeSurface: external surface is undefined\n"));
returnValue = AcBr::eMissingGeometry;
return returnValue;
}
if (!baseGeometry.isNativeSurface(nativeGeometry)
|| (nativeGeometry == NULL)) {
acutPrintf(ACRX_T("\n getNativeSurface: native surface is undefined\n"));
returnValue = AcBr::eMissingGeometry;
return returnValue;
}
return returnValue;
}
AcBr::ErrorStatus getNativeCurve(const AcBrEdge& edgeEntity,
AcGeCurve3d*& curveGeometry,
AcGeCurve3d*& nativeGeometry)
{
AcBr::ErrorStatus returnValue = edgeEntity.getCurve(curveGeometry);
if (returnValue != AcBr::eOk) {
acutPrintf(ACRX_T("\n Error in AcBrEdge::getCurve:"));
errorReport(returnValue);
return returnValue;
}
if (curveGeometry == NULL) {
acutPrintf(ACRX_T("\n getNativeCurve: external 3d curve is undefined\n"));
returnValue = AcBr::eMissingGeometry;
return returnValue;
}
if (curveGeometry->type() != kExternalCurve3d) {
acutPrintf(ACRX_T("\n getNativeCurve: curve is not an external 3d curve\n"));
returnValue = AcBr::eMissingGeometry;
return returnValue;
}
if (!((AcGeExternalCurve3d*)curveGeometry)->isDefined()) {
acutPrintf(ACRX_T("\n getNativeCurve: external 3d curve is undefined\n"));
returnValue = AcBr::eMissingGeometry;
return returnValue;
}
if (!((AcGeExternalCurve3d*)curveGeometry)->isNativeCurve(nativeGeometry)
|| (nativeGeometry == NULL)) {
acutPrintf(ACRX_T("\n getNativeCurve: native 3d curve is undefined\n"));
returnValue = AcBr::eMissingGeometry;
return returnValue;
}
return returnValue;
}
AcBr::ErrorStatus edgeDump(const AcBrEdge& edgeEntity, AcGeCurve3d *&pCurve, AcGe::EntityId &type)
{
AcBr::ErrorStatus returnValue = AcBr::eOk;
if (edgeEntity.isA() == NULL)
{
acutPrintf(ACRX_T("\n edgeDump: AcBrEntity::isA() failed\n"));
return returnValue;
}
if (!edgeEntity.isKindOf(AcBrEdge::desc()))
{
acutPrintf(ACRX_T("\n edgeDump: AcBrEntity::isKindOf() failed\n"));
return returnValue;
}
AcBrEntity* entClass = (AcBrEntity*)&edgeEntity;
AcBrFace* pFace = AcBrFace::cast(entClass);
if (pFace != NULL)
{
acutPrintf(ACRX_T("\n edgeDump: AcBrEntity::cast() failed\n"));
return (AcBr::ErrorStatus)Acad::eNotThatKindOfClass;
}
// validate the brep "owner" of the edge
AcBrBrep brepOwner;
returnValue = edgeEntity.getBrep(brepOwner);
if (returnValue != AcBr::eOk)
{
acutPrintf(ACRX_T("\n Error in AcBrEdge::getBrep:"));
errorReport(returnValue);
return returnValue;
}
returnValue = edgeEntity.getCurveType(type);
if (returnValue != AcBr::eOk)
{
acutPrintf(ACRX_T("\n Error in AcBrEdge::getCurveType:"));
errorReport(returnValue);
return returnValue;
}
AcGeCurve3d* curveGeometry = NULL;
returnValue = getNativeCurve(edgeEntity, curveGeometry, pCurve);
if (returnValue != AcBr::eOk)
{
acutPrintf(ACRX_T("\n Error in getNativeCurve:"));
errorReport(returnValue);
delete curveGeometry;
delete pCurve;
return returnValue;
}
delete curveGeometry;
Adesk::Boolean oriented;
returnValue = edgeEntity.getOrientToCurve(oriented);
if (returnValue != AcBr::eOk) {
acutPrintf(ACRX_T("\n Error in AcBrEdge::getOrientToCurve:"));
errorReport(returnValue);
return returnValue;
}
return returnValue;
}
AcDbCurve* geCurve2dbCurve(AcGeCurve3d *pGe, const AcGe::EntityId &type)
{
switch (type)
{
case(kLine3d):
{
AcGeLine3d* lineGeometry = (AcGeLine3d*)pGe;
AcGePoint3d pt1, pt2;
if (lineGeometry->hasStartPoint(pt1) && lineGeometry->hasEndPoint(pt2))
return new AcDbLine(pt1, pt2);
return NULL;
}
case(kRay3d):
{
AcGeRay3d* rayGeometry = (AcGeRay3d*)pGe;
AcGePoint3d pt = rayGeometry->pointOnLine();
AcGeVector3d dir = rayGeometry->direction();
AcGePoint3d pt1;
if (rayGeometry->hasStartPoint(pt1))
{
AcDbRay *pRay = new AcDbRay();
pRay->setBasePoint(pt1);
pRay->setUnitDir(dir);
return pRay;
}
return NULL;
}
case(kLineSeg3d):
{
AcGeLineSeg3d* segGeometry = (AcGeLineSeg3d*)pGe;
AcGePoint3d pt1, pt2;
if (segGeometry->hasStartPoint(pt1) && segGeometry->hasEndPoint(pt2))
return new AcDbLine(pt1, pt2);
return NULL;
}
case(kEllipArc3d):
{
AcGeEllipArc3d* ellipGeometry = (AcGeEllipArc3d*)pGe;
AcGePoint3d centre = ellipGeometry->center();
AcDbEllipse *p = new AcDbEllipse(ellipGeometry->center()
, ellipGeometry->normal()
, ellipGeometry->majorAxis() * ellipGeometry->majorRadius()
, ellipGeometry->minorRadius() / ellipGeometry->majorRadius()
, ellipGeometry->startAng()
, ellipGeometry->endAng());
return p;
}
case(kCircArc3d):
{
AcGeCircArc3d* circGeometry = (AcGeCircArc3d*)pGe;
AcGePoint3d centre = circGeometry->center();
AcGePoint3d start = circGeometry->startPoint();
AcGePoint3d end = circGeometry->endPoint();
double sa = circGeometry->startAng();
double ea = circGeometry->endAng();
if (sa < .0001 && ea - 2 * PI < .0001) // circle
{
return new AcDbCircle(circGeometry->center()
, circGeometry->normal()
, circGeometry->radius());
}
else // arc
{
return new AcDbArc(circGeometry->center()
, circGeometry->normal()
, circGeometry->radius()
, circGeometry->startAng()
, circGeometry->endAng() );
}
break;
}
case(kNurbCurve3d):
{
AcGeNurbCurve3d* nurbGeometry = (AcGeNurbCurve3d*)pGe;
int count = nurbGeometry->numControlPoints();
AcGePoint3dArray ctrlPts;
for (int i = 0; i < count; ++i)
ctrlPts.append(nurbGeometry->controlPointAt(i));
count = nurbGeometry->numKnots();
AcGeDoubleArray Knots;
for (int i = 0; i < count; ++i)
Knots.append(nurbGeometry->knotAt(i));
count = nurbGeometry->numWeights();
AcGeDoubleArray Weights;
for (int i = 0; i < count; ++i)
Weights.append(nurbGeometry->weightAt(i));
return new AcDbSpline(nurbGeometry->degree()
, nurbGeometry->isRational()
, nurbGeometry->isClosed()
, false
, ctrlPts
, Knots
, Weights);
}
default:
acutPrintf(ACRX_T("\nCurve Type: Unexpected Non Curve\n"));
return NULL;
}
return NULL;
}
AcBr::ErrorStatus faceDump(const AcBrFace& faceEntity
, AcGe::EntityId &geType
, AcGeSurface *&nativeGeometry
, int &orient )
{
AcBr::ErrorStatus returnValue = AcBr::eOk;
if (faceEntity.isA() == NULL) {
acutPrintf(ACRX_T("\n faceDump: AcBrEntity::isA() failed\n"));
return returnValue;
}
if (!faceEntity.isKindOf(AcBrFace::desc())) {
acutPrintf(ACRX_T("\n faceDump: AcBrEntity::isKindOf() failed\n"));
return returnValue;
}
AcBrEntity* entClass = (AcBrEntity*)&faceEntity;
AcBrEdge* pEdge = AcBrEdge::cast(entClass);
if (pEdge != NULL) {
acutPrintf(ACRX_T("\n faceDump: AcBrEntity::cast() failed\n"));
return (AcBr::ErrorStatus)Acad::eNotThatKindOfClass;
}
AcGe::EntityId entId;
returnValue = faceEntity.getSurfaceType(entId);
if (returnValue != AcBr::eOk) {
acutPrintf(ACRX_T("\n Error in AcBrFace::getSurfaceType:"));
errorReport(returnValue);
return returnValue;
}
geType = entId;
AcGeSurface* surfaceGeometry = NULL;
returnValue = getNativeSurface(faceEntity, surfaceGeometry, nativeGeometry);
if ((returnValue != AcBr::eOk) && (returnValue != (AcBr::ErrorStatus)Acad::eInvalidInput))
{
acutPrintf(ACRX_T("\n Error in getNativeSurface:"));
errorReport(returnValue);
delete surfaceGeometry;
delete nativeGeometry;
return returnValue;
}
delete surfaceGeometry;
Adesk::Boolean oriented;
returnValue = faceEntity.getOrientToSurface(oriented);
if (returnValue != AcBr::eOk) {
acutPrintf(ACRX_T("\n Error in AcBrFace::getOrientToSurface:"));
errorReport(returnValue);
return returnValue;
}
oriented ? acutPrintf(ACRX_T("\nSurface Orientation is Positive\n"))
: acutPrintf(ACRX_T("\nSurface Orientation is Negative\n"));
orient = oriented ? 1 : -1;
return returnValue;
}
AcBrFace* selectBrFace(const AcGePoint3d &pickPnt)
{
AcBrEntity *pBrEnt(NULL);
if (selectEntityByType(pBrEnt, AcDb::kFaceSubentType, AcBr::kFullValidation, pickPnt) != AcBr::eOk) return NULL;
return (AcBrFace*)pBrEnt;
}
AcBrEdge* selectBrEdge(const AcGePoint3d &pickPnt)
{
AcBrEntity *pBrEnt(NULL);
if (selectEntityByType(pBrEnt, AcDb::kEdgeSubentType, AcBr::kFullValidation, pickPnt) != AcBr::eOk) return NULL;
return (AcBrEdge*)pBrEnt;
}
bool getPlaneByBrFace(const AcBrFace *pFace, AcGePlane &plan)
{
if (!pFace) return false;
AcGeSurface *pSurface(NULL);
AcGe::EntityId geType;
int orient;
AcBr::ErrorStatus es = faceDump(*pFace, geType, pSurface, orient);
if (es != AcBr::eOk || !pSurface)
{
DELETE_PTR(pSurface);
return false;
}
bool bRel(true);
if (pSurface->isKindOf(AcGe::kPlane))
{
plan = (*(AcGePlane*)pSurface);
}
else if (pSurface->isKindOf(AcGe::kSphere))
{
AcGeSphere *sphereGeometry = (AcGeSphere*)pSurface;
plan.set(sphereGeometry->center(), sphereGeometry->northAxis());
}
else if (pSurface->isKindOf(AcGe::kTorus))
{
AcGeTorus *torusGeometry = (AcGeTorus*)pSurface;
plan.set(torusGeometry->center(), torusGeometry->axisOfSymmetry());
}
else if (pSurface->isKindOf(AcGe::kCylinder))
{
AcGeCylinder *cylinderGeometry = (AcGeCylinder*)pSurface;
AcGeVector3d refAxis = cylinderGeometry->refAxis();
plan.set(cylinderGeometry->origin() + refAxis * cylinderGeometry->radius(), refAxis);
}
else if (pSurface->isKindOf(AcGe::kCone))
{
AcGeCone *coneGeometry = (AcGeCone*)pSurface;
AcGeVector3d refAxis = coneGeometry->refAxis();
plan.set(coneGeometry->baseCenter() + refAxis * coneGeometry->baseRadius(), refAxis);
}
//else if (pSurface->isKindOf(AcGe::kNurbSurface))
//{
// AcGeNurbSurface *nurbGeometry = (AcGeNurbSurface*)pSurface;
// acutPrintf(_T("\nÔݲ»Ö§³Ö´ËÀàÇúÃæ£¡"));
//}
else
{
acutPrintf(_T("\nÔݲ»Ö§³Ö´ËÀàÇúÃæ£¡"));
bRel = false;
}
DELETE_PTR(pSurface);
if (bRel)
{
if (orient < 0)
plan.reverseNormal();
}
return bRel;
}
void setColorForSolid(AcDbObjectId solidId)
{
AcCmColor specialColor;
AcDb3dSolid* pSolid;
if (Acad::eOk == acdbOpenObject(pSolid, solidId, AcDb::kForRead))
{
AcDbFullSubentPath path(solidId, AcDbSubentId());
AcBrBrep brep;
AcBr::ErrorStatus bs = brep.setSubentPath(path);
if (bs != AcBr::eOk)
return;
//Initialize the BrepFace traverser
AcBrBrepFaceTraverser bft;
bs = bft.setBrep(brep);
if (bs != AcBr::eOk)
return;
AcArray<AcDbSubentId> arrSubentId;
// Traverse all faces
for (;!bft.done();bft.next())
{
AcBrFace face;
bs = bft.getFace(face);
if (bs != Acad::eOk)
{
acutPrintf(L"\ngetFace failed");
break;
}
AcDbFullSubentPath Path(kNullSubent);
AcDbSubentId subentId;
AcBr::ErrorStatus bss = face.getSubentPath(Path);
subentId = Path.subentId();
arrSubentId.append(subentId);
}
pSolid->upgradeOpen();
for (int i = 0; i < arrSubentId.length(); i++)
{
specialColor.setColorIndex(i);
pSolid->setSubentColor(arrSubentId[i],specialColor);
}
pSolid->downgradeOpen();
}
pSolid->close();
}
void getProfileByFace(AcBrFace *pFace, AcDbVoidPtrArray &curves)
{
if (!pFace) return;
AcBrFaceLoopTraverser faLoTrav;
AcGe::EntityId type;
for (faLoTrav.setFace(*pFace); !faLoTrav.done(); faLoTrav.next())
{
AcBrLoopEdgeTraverser loEdTrav;
if (loEdTrav.setLoop(faLoTrav) == AcBr::eOk)
{
for( ; !loEdTrav.done(); loEdTrav.next())
{
AcBrEdge edge;
loEdTrav.getEdge(edge);
AcGeCurve3d *pGe(NULL);
if (AcBr::eOk == edgeDump(edge, pGe, type) && pGe)
{
AcDbCurve *pCrv = geCurve2dbCurve(pGe, type);
if (pCrv)
curves.append(pCrv);
DELETE_PTR(pGe);
}
}
}
}
}
void getProfileByFace2(AcBrFace *pFace, AcDbVoidPtrArray &curvesOut, AcDbVoidPtrArray&curvesIn)
{
if (!pFace) return;
AcBrFaceLoopTraverser faLoTrav;
AcGe::EntityId type;
for (faLoTrav.setFace(*pFace); !faLoTrav.done(); faLoTrav.next())
{
AcBrLoopEdgeTraverser loEdTrav;
if (loEdTrav.setLoop(faLoTrav) == AcBr::eOk)
{
for (; !loEdTrav.done(); loEdTrav.next())
{
AcBrEdge edge;
loEdTrav.getEdge(edge);
AcBrLoop brLoop;
loEdTrav.getLoop(brLoop);
AcBr::LoopType ltype = AcBr::kUnclassified;
brLoop.getType(ltype);
AcGeCurve3d *pGe(NULL);
if (AcBr::eOk == edgeDump(edge, pGe, type) && pGe)
{
AcDbCurve *pCrv = geCurve2dbCurve(pGe, type);
if (pCrv)
{
(ltype == AcBr::kInterior) ? curvesIn.append(pCrv) : curvesOut.append(pCrv);
}
DELETE_PTR(pGe);
}
}
}
}
}
void impget3DSolidToPolyMesh()
{
ads_name en; ads_point p;
if (acedEntSel(_T("\nSelect 3DSolid:"), en, p) != RTNORM)
return;
AcDbObjectId eid;
if (acdbGetObjectId(eid, en) != Acad::eOk)
return;
AcDbObjectPointer<AcDb3dSolid> p3DSolid(eid, AcDb::kForRead);
if (p3DSolid.openStatus() == Acad::eWrongObjectType) {
acutPrintf(_T("\nEnt is not a 3dsolid!"));
return;
}
AcDbExtents ext; p3DSolid->getGeomExtents(ext);
double length = ext.minPoint().distanceTo(ext.maxPoint());
AcBrBrep brp;
AcBr::ErrorStatus ebr;
ebr = brp.set(*p3DSolid);
if (ebr != AcBr::eOk)
{
acutPrintf(_T("\nerror br.set(*p3DSolid) = %d"), ebr);
return;
}
AcBrMesh2dControl mc;
// mc.setMaxNodeSpacing( length / 100.0);
// mc.setMaxSubdivisions(100000);
mc.setDistTol(length / 100.0);
mc.setElementShape(AcBr::kAllTriangles);
AcBrMesh2dFilter mf;
const AcBrEntity *meshEnt = (AcBrEntity *)&brp;
mf.insert(make_pair(meshEnt, mc));
AcBrMesh2d brepMesh;
if ((ebr = brepMesh.generate(mf)) != AcBr::eOk)
{
acutPrintf(_T("\nerror AcBrMesh2d::generate %d"), ebr);
return;
}
AcDbObjectPointer<AcDbPolyFaceMesh> pMesh; pMesh.create();
pMesh->setDatabaseDefaults();
pMesh->setColorIndex(2);
AcDbBlockTableRecordPointer pBtr(acdbCurDwg()->currentSpaceId(), AcDb::kForWrite);
if (pBtr.openStatus() != Acad::eOk)
return;
pBtr->appendAcDbEntity(pMesh);
int v0 = 0, v1 = 0, v2 = 0, v3 = 0;
int iter = 0;
AcGePoint3dArray vertexLookup;
vertexLookup.setPhysicalLength(10000);
vertexLookup.append(AcGePoint3d::kOrigin);
AcBrMesh2dElement2dTraverser meshElemTrav;
for (ebr = meshElemTrav.setMesh(brepMesh); !meshElemTrav.done(); ebr = meshElemTrav.next())
{
if (ebr != AcBr::eOk) return;
AcBrElement2d e; ebr = meshElemTrav.getElement(e);
AcBrElement2dNodeTraverser elemNodeTrav;
for (ebr = elemNodeTrav.setElement(e); !elemNodeTrav.done(); elemNodeTrav.next())
{
AcBrNode brn;
ebr = elemNodeTrav.getNode(brn);
AcGePoint3d p; brn.getPoint(p);
if (!vertexLookup.contains(p)) {
AcDbObjectPointer<AcDbPolyFaceMeshVertex> pMeshVert; pMeshVert.create();
pMeshVert->setPosition(p);
pMesh->appendVertex(pMeshVert);
vertexLookup.append(p);
}
}
}
for (ebr = meshElemTrav.setMesh(brepMesh); !meshElemTrav.done(); ebr = meshElemTrav.next())
{
if (ebr != AcBr::eOk) return;
AcBrElement2d e; ebr = meshElemTrav.getElement(e);
AcBrElement2dNodeTraverser elemNodeTrav;
AcGePoint3dArray pts;
for (ebr = elemNodeTrav.setElement(e); !elemNodeTrav.done(); ebr = elemNodeTrav.next())
{
if (ebr != AcBr::eOk) return;
AcBrNode brn;
ebr = elemNodeTrav.getNode(brn);
AcGePoint3d p; brn.getPoint(p);
pts.append(p);
}
v0 = v1 = v2 = v3 = 0;
vertexLookup.find(pts[0], v0);
vertexLookup.find(pts[1], v1);
vertexLookup.find(pts[2], v2);
if (pts.length() == 4) {
vertexLookup.find(pts[3], v3);
}
AcDbFaceRecord *pFaceRecord = new AcDbFaceRecord(v0, v1, v2, v3);
pMesh->appendFaceRecord(pFaceRecord);
pFaceRecord->close();
}
}
bool impget3DSolidToPolyMesh(AcDb3dSolid* p3DSolid, CString& sVertices, CString& sIndices)
{
CString sPt,sInd;
AcDbExtents ext;
p3DSolid->getGeomExtents(ext);
double length = ext.minPoint().distanceTo(ext.maxPoint());
AcBrBrep brp;
AcBr::ErrorStatus ebr;
ebr = brp.set(*p3DSolid);
if (ebr != AcBr::eOk)
{
acutPrintf(_T("\nerror br.set(*p3DSolid) = %d"), ebr);
return false;
}
AcBrMesh2dControl mc;
// mc.setMaxNodeSpacing( length / 100.0);
// mc.setMaxSubdivisions(100000);
mc.setDistTol(length / 100.0);
mc.setElementShape(AcBr::kAllTriangles);
AcBrMesh2dFilter mf;
const AcBrEntity *meshEnt = (AcBrEntity *)&brp;
mf.insert(make_pair(meshEnt, mc));
AcBrMesh2d brepMesh;
if ((ebr = brepMesh.generate(mf)) != AcBr::eOk)
{
acutPrintf(_T("\nerror AcBrMesh2d::generate %d"), ebr);
return false;
}
//AcDbObjectPointer<AcDbPolyFaceMesh> pMesh;
//pMesh.create();
//pMesh->setDatabaseDefaults();
//pMesh->setColorIndex(2);
//AcDbBlockTableRecordPointer pBtr(acdbCurDwg()->currentSpaceId(), AcDb::kForWrite);
//if (pBtr.openStatus() != Acad::eOk)
// return;
//pBtr->appendAcDbEntity(pMesh);
int v0 = 0, v1 = 0, v2 = 0, v3 = 0;
int iter = 0;
AcGePoint3dArray vertexLookup;
vertexLookup.setPhysicalLength(10000);
vertexLookup.append(AcGePoint3d::kOrigin);
AcBrMesh2dElement2dTraverser meshElemTrav;
for (ebr = meshElemTrav.setMesh(brepMesh); !meshElemTrav.done(); ebr = meshElemTrav.next())
{
if (ebr != AcBr::eOk) return false;
AcBrElement2d e; ebr = meshElemTrav.getElement(e);
AcBrElement2dNodeTraverser elemNodeTrav;
for (ebr = elemNodeTrav.setElement(e); !elemNodeTrav.done(); elemNodeTrav.next())
{
AcBrNode brn;
ebr = elemNodeTrav.getNode(brn);
AcGePoint3d p; brn.getPoint(p);
if (!vertexLookup.contains(p)) {
AcDbObjectPointer<AcDbPolyFaceMeshVertex> pMeshVert; pMeshVert.create();
pMeshVert->setPosition(p);
//pMesh->appendVertex(pMeshVert);
sPt.Format(_T("%.3f,%.3f,%.3f,"),p.x,p.y,p.z);
sVertices += sPt;
vertexLookup.append(p);
}
}
}
sVertices.TrimRight(_T(','));
for (ebr = meshElemTrav.setMesh(brepMesh); !meshElemTrav.done(); ebr = meshElemTrav.next())
{
if (ebr != AcBr::eOk) return false;
AcBrElement2d e; ebr = meshElemTrav.getElement(e);
AcBrElement2dNodeTraverser elemNodeTrav;
AcGePoint3dArray pts;
for (ebr = elemNodeTrav.setElement(e); !elemNodeTrav.done(); ebr = elemNodeTrav.next())
{
if (ebr != AcBr::eOk) return false;
AcBrNode brn;
ebr = elemNodeTrav.getNode(brn);
AcGePoint3d p; brn.getPoint(p);
pts.append(p);
}
v0 = v1 = v2 = v3 = 0;
vertexLookup.find(pts[0], v0);
vertexLookup.find(pts[1], v1);
vertexLookup.find(pts[2], v2);
if (pts.length() == 4)
{
vertexLookup.find(pts[3], v3);
sInd.Format(_T("%d,%d,%d,"), v0, v1, v2);
sIndices += sInd;
sInd.Format(_T("%d,%d,%d,"), v0, v2, v3);
sIndices += sInd;
}
else
{
sInd.Format(_T("%d,%d,%d,"),v0,v1,v2);
sIndices += sInd;
}
//AcDbFaceRecord *pFaceRecord = new AcDbFaceRecord(v0, v1, v2, v3);
//pMesh->appendFaceRecord(pFaceRecord);
//pFaceRecord->close();
}
sIndices.TrimRight(_T(','));
return true;
}
}
void BrepOper::setUCS(AcGePlane &plan, bool bPlan)
{
AcGePoint3d pt;
AcGeVector3d vtNormal(plan.normal()), vt1, vt2;
plan.getCoordSystem(pt, vt1, vt2);
AcGeMatrix3d mat;
AcGeVector3d vt(vt1.crossProduct(vt2));
if (vt.negate().isCodirectionalTo(vtNormal))
mat.setCoordSystem(pt, vt2, vt1, vtNormal);
else
mat.setCoordSystem(pt, vt1, vt2, vtNormal);
acedSetCurrentUCS(mat);
if (bPlan)
SHacedCommand(RTSTR, _T("PLAN"), RTSTR, _T(""), RTNONE);
}
bool BrepOper::setUCSByFace(AcBrFace *pFace, bool bPlan)
{
AcGePlane plane;
if (getPlaneByBrepFace(pFace, plane))
{
BrepOper::setUCS(plane, bPlan);
return true;
}
return false;
}
bool BrepOper::setUCSBySubentPath(AcDbFullSubentPath &path, bool bPlan)
{
if (path.subentId().type() != AcDb::kFaceSubentType) return false;
AcBrFace face;
if (face.set(path) != AcBr::eOk) return false;
return setUCSByFace(&face, bPlan);
}
void BrepOper::getSubPathBySolid(AcDbObjectId & solidId, AcArray<AcDbSubentId>& subs, AcArray<AcGePlane> &plans)
{
AcDbFullSubentPath path(solidId, AcDbSubentId());
AcBrBrep brep;
AcBr::ErrorStatus bs = brep.setSubentPath(path);
if (bs != AcBr::eOk) return;
AcBrBrepFaceTraverser bft;
bs = bft.setBrep(brep);
if (bs != AcBr::eOk) return;
AcDbFullSubentPath Path(kNullSubent);
AcGeSurface *pSu(NULL);
for (;!bft.done();bft.next())
{
AcBrFace face;
bs = bft.getFace(face);
if (bs != Acad::eOk)
{
acutPrintf(L"\ngetFace failed");
break;
}
AcGePlane plan;
if (face.getSubentPath(Path) == AcBr::eOk && getPlaneByBrFace(&face, plan))
{
subs.append(Path.subentId());
plans.append(plan);
}
}
}
AcDb3dSolid* BrepOper::get3DSolidBySH(AcDbObjectId &idSH)
{
AcDbVoidPtrArray ar3d;
OPENOBJ_BEGIN(idSH, AcDb::kForRead, AecDbEntityBase, pEw)
if (pEw) pEw->GetDraw3dables(ar3d);
OPENOBJ_END()
OPENOBJ_BEGIN(idSH, AcDb::kForRead, AecDbCurveBase, pEw)
if (pEw) pEw->GetDraw3dables(ar3d);
OPENOBJ_END()
if (ar3d.isEmpty()) return NULL;
std::vector<AcDb3dSolid*> solids;
AcDb3dSolid *pSolid(NULL);
for (int i = 0; i < ar3d.length(); ++i)
{
pSolid = AcDb3dSolid::cast((AcDbEntity*)ar3d[i]);
if (pSolid)
solids.push_back((AcDb3dSolid*)pSolid->clone());
}
if (solids.empty()) return NULL;
AcDb3dSolid *pSolidAll(solids[0]);
for (size_t i = 1; i < solids.size(); ++i)
{
if (pSolidAll->booleanOper(AcDb::kBoolUnite, solids[i]) != Acad::eOk)
DELETE_PTR(solids[i]);
}
return pSolidAll;
}
bool BrepOper::setUcsByPickFace(AcDbObjectId &idSH, const AcGePoint3d &pickPnt, AcDbVoidPtrArray *pAr)
{
AcDbFullSubentPathArray arPaths;
AcDb3dSolid *pSolidAll = get3DSolidBySH(idSH);
if (!pSolidAll) return false;
AcDbObjectId idSolid;
CoreTools::AddToModelSpace(pSolidAll, NULL, true, &idSolid);
SHacedCommand(RTSTR, _T("regen"), RTNONE);
OPENOBJ_BEGIN(idSH, AcDb::kForWrite, AcDbEntity, pEw)
if (pEw) pEw->setVisibility(AcDb::kInvisible);
OPENOBJ_END()
selectSubentPaths(_T("3DSOLID"), asDblArray(pickPnt), AcDb::kFaceSubentType, arPaths);
bool bRel(false);
if (!arPaths.isEmpty())
{
bRel = setUCSBySubentPath(arPaths.first(), false);
if (pAr && bRel)
{
AcBrFace face;
if (face.set(arPaths.first()) == AcBr::eOk)
getProfileByFace(&face, *pAr);
}
}
OPENOBJ_BEGIN(idSolid, AcDb::kForWrite, AcDb3dSolid, pEnt)
if (pEnt) pEnt->erase();
OPENOBJ_END()
OPENOBJ_BEGIN(idSH, AcDb::kForWrite, AcDbEntity, pEw)
if (pEw) pEw->setVisibility(AcDb::kVisible);
OPENOBJ_END()
return bRel;
}
void BrepOper::copyEdgeByFace(AcDbObjectId &idSH, const AcGePoint3d &pickPnt, AcDbCurve *&pEdge)
{
AcDb3dSolid *pSolidAll = get3DSolidBySH(idSH);
if (!pSolidAll) return;
AcDbObjectId idSolid;
CoreTools::AddToModelSpace(pSolidAll, NULL, true, &idSolid);
SHacedCommand(RTSTR, _T("regen"), RTNONE);
OPENOBJ_BEGIN(idSH, AcDb::kForWrite, AecDbEwPipeBase, pEw)
if (pEw) pEw->setVisibility(AcDb::kInvisible);
OPENOBJ_END()
AcDbFullSubentPathArray arPaths;
selectSubentPaths(_T("3DSOLID"), asDblArray(pickPnt), AcDb::kEdgeSubentType, arPaths);
if (!arPaths.isEmpty())
{
AcDbFullSubentPath &path(arPaths.first());
AcBrEdge edge;
if (edge.set(path) == AcBr::eOk)
{
AcGe::EntityId type;
AcGeCurve3d *pGe(NULL);
if (AcBr::eOk == edgeDump(edge, pGe, type) && pGe)
{
pEdge = geCurve2dbCurve(pGe, type);
DELETE_PTR(pGe);
}
}
}
OPENOBJ_BEGIN(idSolid, AcDb::kForWrite, AcDb3dSolid, pEnt)
if (pEnt) pEnt->erase();
OPENOBJ_END()
OPENOBJ_BEGIN(idSH, AcDb::kForWrite, AecDbEwPipeBase, pEw)
if (pEw) pEw->setVisibility(AcDb::kVisible);
OPENOBJ_END()
}
bool BrepOper::getPlaneByBrepFace(const AcBrFace *pFace, AcGePlane &plan)
{
AcGe::EntityId suType;
AcBr::ErrorStatus es;
if ((es = pFace->getSurfaceType(suType)) != AcBr::eOk)
{
acutPrintf(_T("\ngetSurfaceType err%d"), es);
return false;
}
if (suType != AcGe::kPlane)
{
acutPrintf(_T("\nËùÑ¡Ãæ±ØÐëÊÇÆ½Ã棡"));
return false;
}
Adesk::Boolean bOrient(false);
if ((es = pFace->getOrientToSurface(bOrient)) != AcBr::eOk)
{
acutPrintf(_T("\ngetOrientToSurface err:%d"), es);
return false;
}
AcGeSurface *pSurface(NULL), *pNative(NULL);
if ((es = pFace->getSurface(pSurface)) != AcBr::eOk)
{
acutPrintf(_T("\ngetSurface err:%d"), es);
return false;
}
if (pSurface->type() != kExternalBoundedSurface)
{
acutPrintf(_T("\nSurface is not kExternalBoundedSurface"), es);
return false;
}
AcGeExternalBoundedSurface *pSur = (AcGeExternalBoundedSurface *)pSurface;
AcGeExternalSurface baseGeometry;
pSur->getBaseSurface(baseGeometry);
if (!baseGeometry.isDefined())
{
acutPrintf(_T("\nbaseGeometry is undefined!"));
DELETE_PTR(pSurface);
return false;
}
if (baseGeometry.isNativeSurface(pNative) && pNative)
{
plan = *(AcGePlane*)pNative;
if (!bOrient)
plan.reverseNormal();
DELETE_PTR(pNative);
return true;
}
else
{
acutPrintf(_T("\nNative surface is undefined!"));
}
return false;
}
bool BrepOper::selectSubentPaths(LPCTSTR filter
, ads_point adsPt
, const AcDb::SubentType &subType
, AcDbFullSubentPathArray &paths)
{
ads_name ss;
AcArray<AcDb::SubentType> subTypes;
subTypes.append(subType);
acedSSSetSubentTypes(subTypes);
struct resbuf *pRb(NULL);
if (filter)
pRb = acutBuildList(RTDXF0, filter, 0);
#ifndef ZWCAD
int nRet = acedSSGet(_T("_:V:S"), adsPt, NULL, pRb, ss);
#else
CString str;
if (subType == AcDb::kFaceSubentType)
str = _T("\nÖÐÍûÓû§ÇëÔÙÑ¡ÔñÒ»´ÎÃæ:");
else if (subType == AcDb::kEdgeSubentType)
str = _T("\nÖÐÍûÓû§ÇëÔÙÑ¡ÔñÒ»´Î±ß:");
LPCTSTR prompts[] = { str, _T("") };
int nRet = acedSSGet(_T("_:V:S:$"), prompts, NULL, pRb, ss);
#endif
if (pRb) acutRelRb(pRb);
if (nRet != RTNORM) return false;
Adesk::Int32 nEnts = 0, nSubs = 0;
acedSSLength(ss, &nEnts);
AcDbFullSubentPath path;
for (int i = 0; i < nEnts; i++)
{
acedSSSubentLength(ss, i, &nSubs);
for (int j = 0; j < nSubs; j++)
{
acedSSSubentName(ss, i, j, path);
paths.append(path);
}
}
acedSSFree(ss);
return !paths.isEmpty();
}
bool BrepOper::getProfileByPickFace(AcDbObjectId &idSH
, const AcGePoint3d &pickPnt
, AcDbVoidPtrArray &ptrs)
{
AcDbFullSubentPathArray arPaths;
AcDb3dSolid *pSolidAll = get3DSolidBySH(idSH);
if (!pSolidAll) return false;
AcDbObjectId idSolid;
CoreTools::AddToModelSpace(pSolidAll, NULL, true, &idSolid);
SHacedCommand(RTSTR, _T("regen"), RTNONE);
OPENOBJ_BEGIN(idSH, AcDb::kForWrite, AcDbEntity, pEw)
if (pEw) pEw->setVisibility(AcDb::kInvisible);
OPENOBJ_END()
selectSubentPaths(_T("3DSOLID"), asDblArray(pickPnt), AcDb::kFaceSubentType, arPaths);
if (!arPaths.isEmpty())
{
AcBrFace face;
if (face.set(arPaths.first()) == AcBr::eOk)
getProfileByFace(&face, ptrs);
}
OPENOBJ_BEGIN(idSolid, AcDb::kForWrite, AcDb3dSolid, pEnt)
if (pEnt) pEnt->erase();
OPENOBJ_END()
OPENOBJ_BEGIN(idSH, AcDb::kForWrite, AcDbEntity, pEw)
if (pEw) pEw->setVisibility(AcDb::kVisible);
OPENOBJ_END()
return !ptrs.isEmpty();
}
bool BrepOper::getProfileByPickFace2(AcDbObjectId &idSH
, const AcGePoint3d &pickPnt
, AcDbVoidPtrArray &ptrsOut
, AcDbVoidPtrArray &ptrsIn)
{
AcDbFullSubentPathArray arPaths;
AcDb3dSolid *pSolidAll = get3DSolidBySH(idSH);
if (!pSolidAll) return false;
AcDbObjectId idSolid;
CoreTools::AddToModelSpace(pSolidAll, NULL, true, &idSolid);
SHacedCommand(RTSTR, _T("regen"), RTNONE);
OPENOBJ_BEGIN(idSH, AcDb::kForWrite, AcDbEntity, pEw)
if (pEw) pEw->setVisibility(AcDb::kInvisible);
OPENOBJ_END()
selectSubentPaths(_T("3DSOLID"), asDblArray(pickPnt), AcDb::kFaceSubentType, arPaths);
if (!arPaths.isEmpty())
{
AcBrFace face;
if (face.set(arPaths.first()) == AcBr::eOk)
getProfileByFace2(&face, ptrsOut,ptrsIn);
}
OPENOBJ_BEGIN(idSolid, AcDb::kForWrite, AcDb3dSolid, pEnt)
if (pEnt) pEnt->erase();
OPENOBJ_END()
OPENOBJ_BEGIN(idSH, AcDb::kForWrite, AcDbEntity, pEw)
if (pEw) pEw->setVisibility(AcDb::kVisible);
OPENOBJ_END()
return !ptrsOut.isEmpty() || !ptrsIn.isEmpty();
}
bool BrepOper::getProfileByPickFace3(AcDbObjectId &idSH
, const AcGePoint3d &pickPnt
, AcDbVoidPtrArray &ptrsOut
, AcDbVoidPtrArray &ptrsIn
, void*& pFaceSolid)//
{
AcDbFullSubentPathArray arPaths;
AcDb3dSolid *pSolidAll = get3DSolidBySH(idSH);
if (!pSolidAll) return false;
AcDbObjectId idSolid;
CoreTools::AddToModelSpace(pSolidAll, NULL, true, &idSolid);
SHacedCommand(RTSTR, _T("regen"), RTNONE);
OPENOBJ_BEGIN(idSH, AcDb::kForWrite, AcDbEntity, pEw)
if (pEw) pEw->setVisibility(AcDb::kInvisible);
OPENOBJ_END()
selectSubentPaths(_T("3DSOLID"), asDblArray(pickPnt), AcDb::kFaceSubentType, arPaths);
if (!arPaths.isEmpty())
{
AcBrFace face;
if (face.set(arPaths.first()) == AcBr::eOk)
getProfileByFace2(&face, ptrsOut, ptrsIn);
AcDbEntity *pEntT = NULL;
AcDbFullSubentPath& path = arPaths.first();
pSolidAll->copyFace(path.subentId(), pEntT);
pFaceSolid = pEntT;
}
OPENOBJ_BEGIN(idSolid, AcDb::kForWrite, AcDb3dSolid, pEnt)
if (pEnt) pEnt->erase();
OPENOBJ_END()
OPENOBJ_BEGIN(idSH, AcDb::kForWrite, AcDbEntity, pEw)
if (pEw) pEw->setVisibility(AcDb::kVisible);
OPENOBJ_END()
return !ptrsOut.isEmpty() || !ptrsIn.isEmpty();
}
AcDbSubentId BrepOper::Acad2Zcad(const AcDbSubentId &idCad)
{
#ifdef ZWCAD
AcDb::SubentType subType = idCad.type();
Adesk::GsMarker subIndex = idCad.index() + 1;
return AcDbSubentId (subType, subIndex * 4 + subType);
#else
return idCad;
#endif
}
namespace
{
void pickFaceForSolid()
{
#ifdef ZWCAD
SHacedCommand(RTSTR, _T("_SHADEMODE"), RTSTR, _T("_G"), RTNONE);
#else
SHacedCommand(RTSTR, _T("_vscurrent"), RTSTR, _T("c"), RTNONE);
#endif
ads_name ent, ss;
ads_point adsPt;
LPCTSTR pszMsg[] = { _T("\nÑ¡ÔñÒ»¸öÈýάʵÌå:"), _T("")};
struct resbuf *pRb = acutBuildList(RTDXF0, _T("3DSOLID"), 0);
#ifdef ZWCAD
int nRes = acedSSGet(_T("_:V:S:$"), pszMsg, NULL, pRb, ss);
#else
int nRes = acedSSGet(_T("_:S:$"), pszMsg, NULL, pRb, ss);
#endif
acutRelRb(pRb);
if (nRes != RTNORM) return;
nRes = acedSSNameX(&pRb, ss, 0L);
acedSSFree(ss);
if (nRes != RTNORM) return;
struct resbuf *pTemp = pRb;
pTemp = pTemp->rbnext;
pTemp = pTemp->rbnext;
ads_name_set(pTemp->resval.rlname, ent);
pTemp = pTemp->rbnext;
int gsMarker = pTemp->resval.rint;
acutRelRb(pRb);
acutPrintf(_T("\nGS:%d"), gsMarker);
}
void setColorForSolid()
{
ads_name ent, ss;
ads_point adsPt;
LPCTSTR pszMsg[] = { _T("\nÑ¡ÔñÒ»¸ö3dPolyline:"), _T("") };
//struct resbuf *pRb = acutBuildList(RTDXF0, _T("3DSOLID"), 0);
int nRes = acedEntSel(NULL, ent, adsPt);
if (nRes != RTNORM) return;
OPENOBJ_BEGIN(ent, AcDb::kForWrite, AcDbCurve, pPl);
if (pPl)
{
AcDbCurve *pNew = (AcDbCurve*)pPl->clone();
AecDbEntityBase::CopyObject(*pPl, *pNew);
AcGePoint3d ptStart(AcGePoint3d::kOrigin);
Acad::ErrorStatus es = pNew->getStartPoint(ptStart);
acutPrintf(_T("err:%d"), es);
DELETE_PTR(pNew);
}
OPENOBJ_END();
}
}
void BrepOper::test()
{
//pickFaceForSolid();
setColorForSolid();
}
void BrepOper::get3DSolidToPolyMesh()
{
impget3DSolidToPolyMesh();
}
bool BrepOper::PolyhedronGeometry(AcDb3dSolid* p3d, CString& sVertices, CString& sIndices)
{
sVertices = _T("");
sIndices = _T("");
return impget3DSolidToPolyMesh(p3d, sVertices, sIndices);
}