/********************************************************************/ /* Copyright (c) 2017 System fugen G.K. and Yuzi Mizuno */ /* All rights reserved. */ /********************************************************************/ #include "MGCLStdAfx.h" #include "topo/Edge.h" #include "topo/Face.h" #include "topo/Loop.h" #include "mg/Curve.h" #include "mg/Surface.h" #include "mg/Pvector.h" #include "mg/Straight.h" #include "mg/CCisect_list.h" #include "mg/CParam_list.h" #include "mg/Tolerance.h" #if defined(_DEBUG) #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif using namespace std; //ボックス枠に囲まれる交点を持つUV曲線を生成する void MGFace::getTrimCrv( double uerror, double verror,//u and v parameter error. const MGBox& box, //parameter (u,v) box of the surface. MGPvector& vecCrv //paremter curves will be output ) const{ double u0=box[0].low_point(), u1=box[0].high_point(); double v0=box[1].low_point(), v1=box[1].high_point(); // if(u0>159. && v0>-1. && u1<223. && v1<102.) // u0=u0; const int n = number_of_boundaries(); for(int i = 0; i < n; i++){ const MGLoop& lpi = *(loop(i)); if(!lpi.active()) continue; const int m = lpi.number_of_edges(); for(int j = 0; j < m; j++){ const MGEdge& ei = *(lpi.edge(j)); //if(ei.on_surface_perimeter())continue; //ペリメータ以外のバウンダリの処理 MGBox boxEdge(ei.box()); if((boxEdge&box).empty()) continue;//共通ボックスなし std::unique_ptr atpCrv(ei.curve_limitted()); //エッジが与えられたボックスに含まれるときの処理 if(box >> boxEdge){ //When boxEdge is included in box. //std::cout<<(*atpCrv);///////// vecCrv.push_back(atpCrv.release()); continue; } MGCParam_list isectParamList(atpCrv.get()); isectParamList.append(atpCrv->param_s()); isectParamList.append(atpCrv->param_e()); double dPreWcTol = MGTolerance::set_wc_zero(uerror); isectParamList.append(atpCrv->isect_1D(u0,0)); MGTolerance::set_wc_zero(verror); isectParamList.append(atpCrv->isect_1D(v0,1)); isectParamList.append(atpCrv->isect_1D(v1,1)); MGTolerance::set_wc_zero(dPreWcTol); isectParamList.sort();//std::cout<eval(tmid);//面上パラメータ if(box >> UVPos) vecCrv.push_back(atpCrv->part(t0,t1)); //std::cout<> int MGFace::offset(double distance, MGPvector& vecOfsFace)const{ vecOfsFace.clear(); const MGSurface *psrf = surface(); int err; MGPvector vecOfsSrf = psrf->offset(distance, err); if(err < 0) return err; if(vecOfsSrf.size()==1){ //境界線を取り出す const std::vector& bounds = boundaries(); //Faceを生成する MGFace* f=new MGFace(vecOfsSrf.release(0), bounds);//std::cout<::const_iterator i=vecOfsSrf.begin(), ie=vecOfsSrf.end(); for(; i!=ie; i++){ const MGSurface& srfi=**i; MGPvector uvcurves; getTrimCrv(uerror, verror, srfi.box_param(), uvcurves); int n=(int)uvcurves.size(); if(!n){//If no trim curves. if(in_range(srfi.center_param())) vecOfsFace.push_back(new MGFace(srfi)); continue; } //If there were trim curves. int pnum,l; vector::const_iterator j; j=uvcurves.begin(); int oldpnum=-1; for(l=0;ltrim(**j); vecOfsFace.push_back(pOfsFace); //std::cout<<(*pOfsFace);////// } } return 0; } //Offset. //distance is plus value if the direction is toward normal vector of the //face. Minus if against the normal vector. //エラーコード 0:成功 -1:面におれがある -2:曲率半径以上のオフセット不可 -3:面生成コンストラクタエラー MGFace MGFace::offset(double distance, int& error)const { //Faceの面をオフセットする const MGSurface *srf = surface(); std::unique_ptr pofsSrf = srf->offset_c1(distance, error); if(error < 0){ if(error==-1){ //Recover the surface of multiplicity order()-1 //by remove_knot(). MGSurface* srf2=srf->copy_surface(); srf2->remove_knot(); pofsSrf = std::unique_ptr(srf2->offset_c1(distance, error)); delete srf2; if(error) return MGFace(); }else return MGFace(); } //境界線を取り出す const std::vector& bounds = boundaries(); //Faceを生成する MGFace f2(pofsSrf.release(), bounds);//std::cout<& vecOfsFSurface)const{ MGPvector faces; int error=offset(distance,faces); if(error) return error; int n=(int)faces.size(); for(int i=0; i