- 积分
- 237
- 明经币
- 个
- 注册时间
- 2003-3-4
- 在线时间
- 小时
- 威望
-
- 金钱
- 个
- 贡献
-
- 激情
-
|
我现在在用ARX做程序!!现在遇到了这样的问题!!在brep例程中给出了如何遍历3dSolid实体的所有面,也给出了如何把一个面划分网格的程序!!可现在我把循环访问实体的所有面,然后在小网格上显示颜色,于是就想把上面两段程序连起来,这就时循环调用面的划分网格程序!!执行中,程序划分了第一个面,在划分第2个面的时候,就不能在划分网格了!!请问怎么解决!!!非常急急急急!!!!!!!!!!!
下面是我给的程序代码:
static void test()
{
AcBr::ErrorStatus returnValue=AcBr::eOk;
Acad::ErrorStatus acadReturnValue = Acad::eOk;
AcDb3dSolid *pEnt;
AcGePoint3d pickPnt;
ads_name ent;
AcDbObjectId objId;
AcBrBrep brepEntity;
AcBrBrepFaceTraverser brepFaceTrav;
int faceCount;
AcBrFace brepFace;
acedEntSel("\n Pick a solid\n", ent, asDblArray(pickPnt));
acadReturnValue=acdbGetObjectId(objId,ent);
if(acadReturnValue!= Acad::eOk)
{
acutPrintf("\n Error in getting AcDbObjecyId:");
return ;
}
acadReturnValue=acdbOpenObject(pEnt,objId,AcDb::kForRead);
if(acadReturnValue!= Acad::eOk)
{
acutPrintf("\n Error in opening AcDbEntity:");
return ;
}
returnValue=brepEntity.set((const AcDbEntity&)*pEnt);
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in AcBrBrep::set:");
return ;
}
returnValue=brepFaceTrav.setBrep(brepEntity);
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in AcBrBrepFaceTraverser::setBrep:");
return ;
}
faceCount=0;
while (!brepFaceTrav.done() && (returnValue == AcBr::eOk))
{
returnValue=brepFaceTrav.getFace(brepFace);
if(returnValue!=AcBr::eOk)
{
acutPrintf("\n Error in AcBrBrepFaceTraverser::getFace:");
return ;
}
returnValue = faceMesh(brepFace);
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in faceMesh:");
return ;
}
faceCount++;
returnValue = brepFaceTrav.next();
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in AcBrBrepFaceTraverser::next:");
return ;
}
}
pEnt->close();
acutPrintf("\n ***brep has %d faces.\n",faceCount);
}
static AcBr::ErrorStatus
faceMesh(const AcBrFace& faceEntity)
{
AcBr::ErrorStatus returnValue = AcBr::eOk;
// Verify that AcBr was explicitly and not implicitly loaded,
// by testing ObjectARX functions (which are unavailable unless
// explicitly loaded)
if (faceEntity.isA() == NULL)
{
acutPrintf("\n faceMesh: AcBrEntity::isA() failed\n");
return returnValue;
}
if (!faceEntity.isKindOf(AcBrFace::desc()))
{
acutPrintf("\n faceMesh: AcBrEntity::isKindOf() failed\n");
return returnValue;
}
AcBrEntity* entClass = (AcBrEntity*)&faceEntity;
AcBrEdge* pEdge = AcBrEdge::cast(entClass);
if (pEdge != NULL)
{
acutPrintf("\n faceMesh: AcBrEntity::cast() failed\n");
return (AcBr::ErrorStatus)eNotThatKindOfClass;
}
AcGe::EntityId entId;
returnValue = faceEntity.getSurfaceType(entId);
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in AcBrFace::getSurfaceType:");
return returnValue;
}
AcGeSurface* surfaceGeometry = NULL;
AcGeSurface* nativeGeometry = NULL;
// NOTE: ignore unsupported geometry types for now, since we already know
// that elliptic cylinders and elliptic cones are rejected by AcGe, but we
// can still perform useful evaluations on the external bounded surface.
returnValue = getNativeSurface(faceEntity, surfaceGeometry, nativeGeometry);
if ((returnValue != AcBr::eOk) && (returnValue != (AcBr::ErrorStatus)Acad::eInvalidInput))
{
acutPrintf("\n Error in getNativeSurface:");
delete surfaceGeometry;
delete nativeGeometry;
return returnValue;
}
// conditionally set the mesh controls based on surface type
AcBrMesh2dControl meshCtrl;
switch (entId)
{
case(kPlane):
acutPrintf("\nSurface Type: Plane\n");
if ((returnValue = meshCtrl.setMinSubdivisionsInU()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMinSubdivisionsInV()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxSubdivisions()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxNodeSpacing(kMaxNodeSpacing)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setAngTol(90.0 * kDeg2Rad)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setDistTol(kDistTol)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxAspectRatio(kMaxAspectRatio)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setElementShape(AcBr::kAllQuadrilaterals)) != eOk)
return returnValue;
break;
case(kSphere):
acutPrintf("\nSurface Type: Sphere\n");
if ((returnValue = meshCtrl.setMinSubdivisionsInU(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMinSubdivisionsInV(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxSubdivisions()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxNodeSpacing(kMaxNodeSpacing)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setAngTol()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setDistTol(kDistTol)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxAspectRatio(kMaxAspectRatio)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setElementShape(AcBr::kAllQuadrilaterals)) != eOk)
return returnValue;
break;
case(kTorus):
acutPrintf("\nSurface Type: Torus\n");
if ((returnValue = meshCtrl.setMinSubdivisionsInU(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMinSubdivisionsInV(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxSubdivisions()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxNodeSpacing(kMaxNodeSpacing)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setAngTol()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setDistTol(kDistTol)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxAspectRatio(kMaxAspectRatio)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setElementShape(AcBr::kAllQuadrilaterals)) != eOk)
return returnValue;
break;
case(kCylinder):
acutPrintf("\nSurface Type: Circular Cylinder\n");
if ((returnValue = meshCtrl.setMinSubdivisionsInU(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMinSubdivisionsInV(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxSubdivisions()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxNodeSpacing(kMaxNodeSpacing)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setAngTol()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setDistTol(kDistTol)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxAspectRatio(kMaxAspectRatio)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setElementShape(AcBr::kAllQuadrilaterals)) != eOk)
return returnValue;
break;
case(kCone):
acutPrintf("\nSurface Type: Circular Cone\n");
if ((returnValue = meshCtrl.setMinSubdivisionsInU(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMinSubdivisionsInV(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxSubdivisions()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxNodeSpacing(kMaxNodeSpacing)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setAngTol()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setDistTol(kDistTol)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxAspectRatio(kMaxAspectRatio)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setElementShape(AcBr::kAllQuadrilaterals)) != eOk)
return returnValue;
break;
case(kNurbSurface):
acutPrintf("\nSurface Type: NURB Surface\n");
if ((returnValue = meshCtrl.setMinSubdivisionsInU(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMinSubdivisionsInV(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxSubdivisions()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxNodeSpacing(kMaxNodeSpacing)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setAngTol(30.0 * kDeg2Rad)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setDistTol(kDistTol)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxAspectRatio(kMaxAspectRatio)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setElementShape(AcBr::kAllQuadrilaterals)) != eOk)
return returnValue;
break;
// NOTE: This surface is not yet supported in AcGe, so we infer the definition
// data by analysing evaluated data on the external bounded surface.
case(kEllipCylinder):
acutPrintf("\nSurface Type: Elliptic Cylinder\n");
if ((returnValue = meshCtrl.setMinSubdivisionsInU(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMinSubdivisionsInV(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxSubdivisions()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxNodeSpacing(kMaxNodeSpacing)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setAngTol()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setDistTol(kDistTol)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxAspectRatio(kMaxAspectRatio)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setElementShape(AcBr::kAllQuadrilaterals)) != eOk)
return returnValue;
break;
// NOTE: This surface is not yet supported in AcGe, so we infer the definition
// data by analysing evaluated data on the external bounded surface.
case(kEllipCone):
acutPrintf("\nSurface Type: Elliptic Cone\n");
if ((returnValue = meshCtrl.setMinSubdivisionsInU(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMinSubdivisionsInV(2L)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxSubdivisions()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxNodeSpacing(kMaxNodeSpacing)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setAngTol()) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setDistTol(kDistTol)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setMaxAspectRatio(kMaxAspectRatio)) != eOk)
return returnValue;
if ((returnValue = meshCtrl.setElementShape(AcBr::kAllQuadrilaterals)) != eOk)
return returnValue;
break;
default:
acutPrintf("\nSurface Type: Unexpected Non Surface\n");
return (AcBr::ErrorStatus)Acad::eInvalidInput;
} // end switch(entId)
delete nativeGeometry;
// make the mesh filter from the topology entity and the mesh controls
AcBrEntity* meshEnt = (AcBrEntity*)&faceEntity;
AcBrMesh2dFilter meshFilter;
meshFilter.insert(make_pair(meshEnt, (const AcBrMesh2dControl)meshCtrl));
// generate the mesh, display any errors and attempt to dump all
// generated elements (most errors are not fatal so we want to do
// the best we can with whatever subset of the face was meshed).
AcBrMesh2d faceMesh;
if ((returnValue = faceMesh.generate(meshFilter)) != eOk)
{
acutPrintf("\n Error in AcBrMesh2d::generate:");
return returnValue;
}
// check to see if the mesh owner is the face we used in the filter
AcBrEntity* meshOwner = NULL;
if ((returnValue = faceMesh.getEntityAssociated(meshOwner)) != eOk)
{
acutPrintf("\n Error in AcBrMesh2d::getEntityAssociate:");
return returnValue;
}
if (!meshEnt->isEqualTo(meshOwner))
{
acutPrintf("\nMesh owner is not the face we asked to mesh!");
}
// dump or display the elements (regardless of incomplete mesh)
returnValue = meshDisplay(faceMesh);
return returnValue;
}
static AcBr::ErrorStatus
meshDisplay(const AcBrMesh2d& mesh)
{
AcBr::ErrorStatus returnValue = AcBr::eOk;
// make a global element traverser
AcBrMesh2dElement2dTraverser meshElemTrav;
returnValue = meshElemTrav.setMesh(mesh);
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in AcBrMesh2dElement2dTraverser::setMesh:");
return returnValue;
}
// display the elements
while (!meshElemTrav.done() && (returnValue == AcBr::eOk) && !acedUsrBrk())
{
// convert the nodes into a 3d point array for AcDbPolyline
AcGePoint3dArray pts;
AcBrElement2dNodeTraverser elemNodeTrav;
returnValue = elemNodeTrav.setElement(meshElemTrav);
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in AcBrElement2dNodeTraverser::setElement:");
return returnValue;
}
while (!elemNodeTrav.done() && (returnValue == AcBr::eOk))
{
AcBrNode node;
returnValue = elemNodeTrav.getNode(node);
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in AcBrElement2dNodeTraverser::getNode:");
return returnValue;
}
// add the node geometry data to the lightweight polyline point array
returnValue = nodeDisplay(node, pts);
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in nodeDisplay:");
return returnValue;
}
returnValue = elemNodeTrav.next();
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in AcBrElement2dNodeTraverser::next:");
return returnValue;
}
} // end element while
// create a simple, closed polygon from the element node list
AcDbFace* pFace;
if(pts.logicalLength()==4)
{
pFace = new AcDbFace(pts[0], pts[1], pts[2], pts[3], Adesk::kTrue,
Adesk::kTrue, Adesk::kTrue, Adesk::kTrue);
if (pFace == NULL)
{
returnValue = (AcBr::ErrorStatus)Acad::eOutOfMemory;
acutPrintf("\n Unable to allocate memory for face");
return returnValue;
}
}
else if(pts.logicalLength()==3)
{
pFace = new AcDbFace(pts[0], pts[1], pts[2], Adesk::kTrue,
Adesk::kTrue, Adesk::kTrue, Adesk::kTrue);
if (pFace == NULL)
{
returnValue = (AcBr::ErrorStatus)Acad::eOutOfMemory;
acutPrintf("\n Unable to allocate memory for face");
return returnValue;
}
}
else
{
delete pFace;
return (AcBr::ErrorStatus)Acad::eOutOfMemory;
}
pFace->setColorIndex(2);
// post the polyline to the database (this should display the element)
AcDbObjectId objId;
if (addToDatabase(pFace, objId) != AcBr::eOk)
{
acutPrintf("\n addToDatabase failed");
return returnValue;
}
// close the database object
if (pFace->close() != AcBr::eOk)
{
acutPrintf("\n AcDb3dPolyline::close() failed");
return returnValue;
}
returnValue = meshElemTrav.next();
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in AcBrMesh2dElement2dTraverser::next:");
return returnValue;
}
} // end mesh while
return returnValue;
}
static AcBr::ErrorStatus
getNativeSurface(const AcBrFace& faceEntity,
AcGeSurface*& surfaceGeometry,
AcGeSurface*& nativeGeometry)
{
AcBr::ErrorStatus returnValue = faceEntity.getSurface(surfaceGeometry);
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in AcBrFace::getSurface:");
return returnValue;
}
if (surfaceGeometry == NULL)
{
acutPrintf("\n getNativeSurface: external bounded surface is undefined\n");
returnValue = AcBr::eMissingGeometry;
return returnValue;
}
if (surfaceGeometry->type() != kExternalBoundedSurface)
{
acutPrintf("\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("\n getNativeSurface: external surface is undefined\n");
returnValue = AcBr::eMissingGeometry;
return returnValue;
}
if (!baseGeometry.isNativeSurface(nativeGeometry) || (nativeGeometry == NULL))
{
acutPrintf("\n getNativeSurface: native surface is undefined\n");
returnValue = AcBr::eMissingGeometry;
return returnValue;
}
return returnValue;
}
static AcBr::ErrorStatus
nodeDisplay(const AcBrNode& node, AcGePoint3dArray& pts)
{
AcBr::ErrorStatus returnValue = AcBr::eOk;
AcGePoint3d nodePoint;
returnValue = node.getPoint(nodePoint);
if (returnValue != AcBr::eOk)
{
acutPrintf("\n Error in AcBrNode::getPoint:");
return returnValue;
}
pts.append((const AcGePoint3d&)nodePoint);
return returnValue;
}
static 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("\n acdbCurDwg()->getBlockTable() failed");
return acadReturnValue;
}
if ((acadReturnValue = pBlockTable->getAt(ACDB_MODEL_SPACE,
pSpaceRecord, AcDb::kForWrite)) != Acad::eOk)
{
acutPrintf("\n AcDbBlockTable::getAt() failed");
return acadReturnValue;
}
// close the block table object
if ((acadReturnValue = pBlockTable->close()) != Acad::eOk)
{
acutPrintf("\n AcDbBlockTable::close() failed");
return acadReturnValue;
}
// append the entity to the display list
if ((acadReturnValue = pSpaceRecord->appendAcDbEntity(objId, pEnt)) != Acad::eOk)
{
acutPrintf("\n AcDbBlockTableRecord::appendAcDbEntity() failed");
return acadReturnValue;
}
// close the block table record object
if ((acadReturnValue = pSpaceRecord->close()) != Acad::eOk)
{
acutPrintf("\n AcDbBlockTableRecord::close() failed");
return acadReturnValue;
}
return acadReturnValue;
} |
|