void FaceCutting(BSPNode *n,std::vector<Face*> &faces) { if(n->isleaf==OVER) { return; } if(n->isleaf==UNDER) { for(auto &f : faces) { delete f; } faces.clear(); return; } std::vector<Face*> faces_over; std::vector<Face*> faces_under; std::vector<Face*> faces_coplanar; while (faces.size()) { Face *f; f= Pop(faces); int s = FaceSplitTest(f, n->plane()); if(s==COPLANAR) faces_coplanar.push_back(f); else if(s==UNDER) faces_under.push_back(f); else if(s==OVER) faces_over.push_back(f); else { assert(s==SPLIT); Face *ovr = FaceDup(f); FaceClip(f,(*n)); FaceClip(ovr, float4(-n->xyz(), -n->w)); faces_under.push_back(f); faces_over.push_back(ovr); } } FaceCutting(n->under,faces_under); FaceCutting(n->over,faces_over); for(unsigned int i=0;i<faces_under.size();i++) faces.push_back(faces_under[i]); for (unsigned int i = 0; i<faces_over.size(); i++) faces.push_back(faces_over[i]); for (unsigned int i = 0; i<faces_coplanar.size(); i++) faces.push_back(faces_coplanar[i]); }
std::unique_ptr<BSPNode> BSPUnion(std::unique_ptr<BSPNode> a, std::unique_ptr<BSPNode> b) { if(!a || b->isleaf == UNDER || a->isleaf==OVER) { if(a && b->isleaf==UNDER) { FaceCutting(a.get(), b->brep); } return b; } if(a->isleaf == UNDER || b->isleaf==OVER) { return a; } std::unique_ptr<BSPNode> aover; std::unique_ptr<BSPNode> aunder; // its like "b" is the master, so a should be the little object and b is the area's shell assert(!a->isleaf); BSPPartition(move(a), float4(b->xyz(), b->w), aunder, aover); assert(aunder || aover); b->under = BSPUnion(move(aunder), move(b->under)); b->over = BSPUnion(move(aover), move(b->over)); /* if(fusenodes) { if(b->over->isleaf == UNDER) { DeriveCells(b->under,b->cell); return b->under; } if(b->under->isleaf == OVER) { DeriveCells(b->over,b->cell); return b->over; } } */ return b; }
BSPNode *BSPUnion(BSPNode *a,BSPNode *b) { if(!a || b->isleaf == UNDER || a->isleaf==OVER) { if(a && b->isleaf==UNDER) { FaceCutting(a,b->brep); } return b; } if(a->isleaf == UNDER || b->isleaf==OVER) { return a; } BSPNode *aover; BSPNode *aunder; // its like "b" is the master, so a should be the little object and b is the area's shell assert(!a->isleaf); BSPPartition(a, float4(b->xyz(), b->w), aunder, aover); assert(aunder || aover); b->under = BSPUnion(aunder,b->under); b->over = BSPUnion(aover ,b->over ); /* if(fusenodes) { if(b->over->isleaf == UNDER) { DeriveCells(b->under,b->cell); return b->under; } if(b->under->isleaf == OVER) { DeriveCells(b->over,b->cell); return b->over; } } */ return b; }
void FaceCutting(BSPNode *n, std::vector<Face> & faces) { if(n->isleaf==OVER) { return; } if(n->isleaf==UNDER) { faces.clear(); return; } std::vector<Face> faces_over; std::vector<Face> faces_under; std::vector<Face> faces_coplanar; while (faces.size()) { Face f = Pop(faces); int s = FaceSplitTest(f, n->plane()); if(s==COPLANAR) faces_coplanar.push_back(std::move(f)); else if(s==UNDER) faces_under.push_back(std::move(f)); else if(s==OVER) faces_over.push_back(std::move(f)); else { assert(s==SPLIT); faces_under.push_back(FaceClip(f, n->plane())); faces_over.push_back(FaceClip(std::move(f), -n->plane())); } } FaceCutting(n->under.get(),faces_under); FaceCutting(n->over.get(),faces_over); for(unsigned int i=0;i<faces_under.size();i++) faces.push_back(faces_under[i]); for (unsigned int i = 0; i<faces_over.size(); i++) faces.push_back(faces_over[i]); for (unsigned int i = 0; i<faces_coplanar.size(); i++) faces.push_back(faces_coplanar[i]); }