1 |
francois |
1158 |
//####//------------------------------------------------------------ |
2 |
|
|
//####//------------------------------------------------------------ |
3 |
|
|
//####// MAGiC |
4 |
|
|
//####// Jean Christophe Cuilliere et Vincent FRANCOIS |
5 |
|
|
//####// Departement de Genie Mecanique - UQTR |
6 |
|
|
//####//------------------------------------------------------------ |
7 |
|
|
//####// MAGIC est un projet de recherche de l equipe ERICCA |
8 |
|
|
//####// du departement de genie mecanique de l Universite du Quebec a Trois Rivieres |
9 |
|
|
//####// http://www.uqtr.ca/ericca |
10 |
|
|
//####// http://www.uqtr.ca/ |
11 |
|
|
//####//------------------------------------------------------------ |
12 |
|
|
//####//------------------------------------------------------------ |
13 |
|
|
//####// |
14 |
|
|
//####// CAD4FE_PolyCurve.cpp |
15 |
|
|
//####// |
16 |
|
|
//####//------------------------------------------------------------ |
17 |
|
|
//####//------------------------------------------------------------ |
18 |
|
|
//####// COPYRIGHT 2000-2024 |
19 |
|
|
//####// jeu 13 jun 2024 11:58:54 EDT |
20 |
|
|
//####//------------------------------------------------------------ |
21 |
|
|
//####//------------------------------------------------------------ |
22 |
foucault |
27 |
|
23 |
|
|
|
24 |
|
|
#include "gestionversion.h" |
25 |
|
|
#include "mg_geometrie.h" |
26 |
|
|
#include "mg_gestionnaire.h" |
27 |
|
|
#include "mg_arete.h" |
28 |
|
|
#include "lc_point.h" |
29 |
|
|
#include "tpl_fonction.h" |
30 |
|
|
#include "ot_algorithme_geometrique.h" |
31 |
|
|
#include "ot_decalage_parametre.h" |
32 |
foucault |
569 |
#include "CAD4FE_MG_ARETE_ClosestPointOn.h" |
33 |
foucault |
27 |
|
34 |
|
|
|
35 |
|
|
#include <map> |
36 |
|
|
#include <ostream> |
37 |
|
|
#include <string> |
38 |
|
|
#include <vector> |
39 |
|
|
#include <sstream> |
40 |
|
|
|
41 |
|
|
|
42 |
|
|
#pragma hdrstop |
43 |
|
|
|
44 |
foucault |
569 |
#include "CAD4FE_PolyCurve.h" |
45 |
foucault |
27 |
|
46 |
|
|
|
47 |
|
|
#pragma package(smart_init) |
48 |
|
|
|
49 |
|
|
#include <math.h> |
50 |
|
|
|
51 |
|
|
#ifdef __BORLANDC__ |
52 |
foucault |
569 |
#pragma warn -8012 |
53 |
foucault |
27 |
#pragma warn -8037 |
54 |
|
|
#endif |
55 |
|
|
|
56 |
|
|
using namespace CAD4FE; |
57 |
|
|
|
58 |
|
|
PolyCurve::PolyCurve() |
59 |
|
|
{ |
60 |
|
|
|
61 |
|
|
} |
62 |
|
|
|
63 |
|
|
PolyCurve::PolyCurve(MG_ARETE * __edge) |
64 |
|
|
{ |
65 |
foucault |
569 |
t_min = (0); |
66 |
|
|
t_max = (-1); |
67 |
|
|
InsertCurve( __edge ); |
68 |
foucault |
27 |
} |
69 |
|
|
|
70 |
|
|
PolyCurve::PolyCurve(MG_SOMMET * __vertex) |
71 |
|
|
{ |
72 |
|
|
t_min = (0); |
73 |
|
|
t_max = (0); |
74 |
|
|
lst_vertices.push_back(__vertex); |
75 |
|
|
lst_length.push_back(0); |
76 |
foucault |
569 |
} |
77 |
foucault |
27 |
|
78 |
|
|
double |
79 |
|
|
PolyCurve::GetLength(MG_ARETE * __edge) |
80 |
|
|
{ |
81 |
foucault |
569 |
return __edge->get_longueur(__edge->get_tmin(), __edge->get_tmax()); |
82 |
foucault |
27 |
} |
83 |
|
|
|
84 |
|
|
double |
85 |
|
|
PolyCurve::GetLength(unsigned __index) |
86 |
|
|
{ |
87 |
foucault |
569 |
return lst_length[__index]; |
88 |
foucault |
27 |
} |
89 |
foucault |
569 |
|
90 |
foucault |
27 |
double equation_longueur(MG_ARETE & __edge,double t) |
91 |
|
|
{ |
92 |
foucault |
569 |
PolyCurve::VerifyRefEdgeT(&__edge, t); |
93 |
|
|
double dxyz[3]; |
94 |
|
|
__edge.deriver(t,dxyz); |
95 |
|
|
return sqrt(dxyz[0]*dxyz[0]+dxyz[1]*dxyz[1]+dxyz[2]*dxyz[2]); |
96 |
foucault |
27 |
} |
97 |
|
|
|
98 |
|
|
|
99 |
|
|
MG_ARETE * PolyCurve::GetRefEdge(unsigned int __index) |
100 |
|
|
{ |
101 |
|
|
return lst_ref_edges[__index]; |
102 |
|
|
} |
103 |
|
|
|
104 |
|
|
MG_SOMMET * PolyCurve::GetRefVertex(unsigned int __index) |
105 |
|
|
{ |
106 |
|
|
return lst_vertices[__index]; |
107 |
|
|
} |
108 |
|
|
|
109 |
foucault |
569 |
unsigned PolyCurve::GetRefEdgeCount() |
110 |
foucault |
27 |
{ |
111 |
|
|
return lst_ref_edges.size(); |
112 |
|
|
} |
113 |
|
|
|
114 |
foucault |
569 |
unsigned PolyCurve::GetRefVertexCount() |
115 |
foucault |
27 |
{ |
116 |
|
|
return lst_vertices.size(); |
117 |
|
|
} |
118 |
|
|
|
119 |
|
|
|
120 |
|
|
bool PolyCurve::ContainsRefEdge(MG_ARETE * __refEdge) |
121 |
|
|
{ |
122 |
|
|
return ( std::find(lst_ref_edges.begin(),lst_ref_edges.end(),__refEdge) != lst_ref_edges.end()); |
123 |
|
|
} |
124 |
|
|
|
125 |
|
|
bool PolyCurve::ContainsRefVertex(MG_SOMMET * __v) |
126 |
|
|
{ |
127 |
|
|
return ( std::find(lst_vertices.begin(),lst_vertices.end(),__v) != lst_vertices.end()); |
128 |
|
|
} |
129 |
|
|
|
130 |
|
|
bool PolyCurve::Contains(MG_ELEMENT_TOPOLOGIQUE * __topo) |
131 |
|
|
{ |
132 |
|
|
if (__topo->get_dimension() == 0) |
133 |
foucault |
569 |
return ContainsRefVertex((MG_SOMMET *)__topo); |
134 |
foucault |
27 |
if (__topo->get_dimension() == 1) |
135 |
foucault |
569 |
return ContainsRefEdge((MG_ARETE *)__topo); |
136 |
foucault |
27 |
return false; |
137 |
foucault |
569 |
} |
138 |
foucault |
27 |
|
139 |
|
|
void |
140 |
|
|
PolyCurve::VerifyRefEdgeT(MG_ARETE * __edge, double & __t) |
141 |
|
|
{ |
142 |
|
|
double t1 = __edge->get_tmin(); |
143 |
|
|
double t2 = __edge->get_tmax(); |
144 |
|
|
|
145 |
|
|
if ( __edge->get_courbe()->est_periodique() ) |
146 |
|
|
{ |
147 |
foucault |
569 |
if (__t > t2 ) |
148 |
|
|
__t -= __edge->get_courbe()->get_periode(); |
149 |
|
|
if (__t < t1 ) |
150 |
|
|
__t += __edge->get_courbe()->get_periode(); |
151 |
foucault |
27 |
} |
152 |
|
|
else |
153 |
|
|
{ |
154 |
|
|
double tStart=(t1<t2)?t1:t2; |
155 |
|
|
double tEnd=(t1>t2)?t1:t2; |
156 |
foucault |
569 |
if (__t > tEnd ) |
157 |
|
|
__t = tEnd; |
158 |
|
|
if (__t < tStart ) |
159 |
|
|
__t = tStart; |
160 |
foucault |
27 |
} |
161 |
|
|
} |
162 |
|
|
|
163 |
|
|
void |
164 |
|
|
PolyCurve::inverser(double & __t, double __point[3], double precision, bool __curvilinearLength) |
165 |
|
|
{ |
166 |
foucault |
569 |
int j; |
167 |
|
|
double s; |
168 |
foucault |
27 |
|
169 |
foucault |
569 |
double edge_length = t_max; |
170 |
foucault |
27 |
|
171 |
foucault |
569 |
// Test wether the requested point is coincident with a vertex of the polyline |
172 |
|
|
for (std::vector<MG_SOMMET *>::iterator it_vertex = lst_vertices.begin(); |
173 |
|
|
it_vertex != lst_vertices.end(); |
174 |
|
|
it_vertex++) |
175 |
|
|
{ |
176 |
|
|
double vertex_point [3]; |
177 |
|
|
MG_SOMMET * vertex = *it_vertex; |
178 |
|
|
vertex->get_point()->evaluer(vertex_point); |
179 |
foucault |
27 |
|
180 |
foucault |
569 |
for (j = 0; j < 3; j++) |
181 |
|
|
if (fabs(vertex_point[j] - __point[j]) > edge_length*precision) |
182 |
|
|
break; |
183 |
foucault |
27 |
|
184 |
foucault |
569 |
if ( j == 3 ) |
185 |
|
|
{ |
186 |
|
|
unsigned iVertex = std::distance ( lst_vertices.begin(), it_vertex ); |
187 |
|
|
s = 0; |
188 |
|
|
for (unsigned k = 0; k < iVertex; k++) |
189 |
|
|
s += lst_length[k]; |
190 |
foucault |
27 |
|
191 |
foucault |
569 |
__t = s; |
192 |
foucault |
27 |
|
193 |
foucault |
569 |
return; |
194 |
|
|
} |
195 |
foucault |
27 |
} |
196 |
|
|
|
197 |
foucault |
569 |
// If the requested point is not on a vertex |
198 |
|
|
// then test the reference edges |
199 |
|
|
unsigned iClosestEdge; |
200 |
|
|
double tClosestEdge = 0; |
201 |
|
|
double min_distance = 1E99; |
202 |
|
|
MG_ARETE * edge; |
203 |
|
|
for (std::vector <MG_ARETE *>::iterator it_edge = lst_ref_edges.begin(); |
204 |
|
|
it_edge != lst_ref_edges.end(); |
205 |
|
|
it_edge++) |
206 |
foucault |
27 |
{ |
207 |
foucault |
569 |
edge = *it_edge; |
208 |
|
|
double t_edge; |
209 |
|
|
//edge->inverser ( t_edge, __point ); |
210 |
|
|
MG_ARETE_ClosestPointOn func(__point, edge); |
211 |
|
|
t_edge = func.Find(); |
212 |
|
|
double xEdge = (t_edge-edge->get_tmin())/(edge->get_tmax()-edge->get_tmin()); |
213 |
|
|
if (xEdge>1) t_edge = edge->get_tmax(); |
214 |
|
|
if (xEdge<0) t_edge = edge->get_tmin(); |
215 |
|
|
double point[3]; |
216 |
|
|
edge->evaluer (t_edge, point ); |
217 |
|
|
double distance = OT_ALGORITHME_GEOMETRIQUE::VEC3_DISTANCE_VEC3(point, __point); |
218 |
|
|
if (distance < min_distance) |
219 |
|
|
{ |
220 |
|
|
min_distance = distance; |
221 |
|
|
iClosestEdge = std::distance (lst_ref_edges.begin(), it_edge ); |
222 |
|
|
tClosestEdge = t_edge; |
223 |
|
|
} |
224 |
foucault |
27 |
} |
225 |
|
|
|
226 |
foucault |
569 |
Parameter_RefEdgeTToS ( tClosestEdge, lst_ref_edges[iClosestEdge], &s, __curvilinearLength); |
227 |
foucault |
27 |
|
228 |
foucault |
569 |
__t = s; |
229 |
foucault |
27 |
|
230 |
foucault |
569 |
return; |
231 |
foucault |
27 |
} |
232 |
|
|
|
233 |
couturad |
906 |
bool PolyCurve::est_sur_courbe(double* xyz, double precision) |
234 |
|
|
{ |
235 |
|
|
std::cout <<" *** PolyCurve::est_sur_courbe : FONCTION NON IMPLEMENTE ***" << std::endl; |
236 |
francois |
1075 |
return false; |
237 |
couturad |
906 |
} |
238 |
|
|
|
239 |
|
|
|
240 |
foucault |
27 |
void |
241 |
|
|
PolyCurve::VerifyS(double & __s) |
242 |
|
|
{ |
243 |
foucault |
569 |
if ( est_periodique() ) |
244 |
|
|
{ |
245 |
|
|
while (__s > get_tmax() ) |
246 |
|
|
__s -= get_periode(); |
247 |
|
|
} |
248 |
|
|
else |
249 |
|
|
{ |
250 |
|
|
if (__s > get_tmax() ) |
251 |
|
|
__s = get_tmax(); |
252 |
|
|
} |
253 |
foucault |
27 |
} |
254 |
|
|
|
255 |
foucault |
569 |
double |
256 |
foucault |
27 |
PolyCurve::RefVertex_GetS(MG_SOMMET * __refVertex) |
257 |
|
|
{ |
258 |
|
|
int N = RefVertex_GetIndex(__refVertex); |
259 |
|
|
double s; |
260 |
|
|
s=0; |
261 |
|
|
for (int i=0;i<N;i++) |
262 |
|
|
s += GetLength(i); |
263 |
|
|
|
264 |
|
|
return s; |
265 |
|
|
} |
266 |
|
|
|
267 |
|
|
void |
268 |
|
|
PolyCurve::RefEdge_GetT(unsigned __iEdge, |
269 |
foucault |
569 |
double __s, |
270 |
|
|
double *__t, double *__dt, bool __curvilinearLength |
271 |
|
|
) |
272 |
foucault |
27 |
{ |
273 |
foucault |
569 |
double t1,t2; |
274 |
|
|
MG_SOMMET * vertex = lst_vertices[ __iEdge ]; |
275 |
|
|
MG_ARETE * edge = lst_ref_edges[ __iEdge ]; |
276 |
foucault |
27 |
|
277 |
foucault |
569 |
if (vertex == edge->get_cosommet1()->get_sommet()) |
278 |
foucault |
27 |
{ |
279 |
foucault |
569 |
t1=edge->get_tmin(); |
280 |
|
|
t2=edge->get_tmax(); |
281 |
|
|
} |
282 |
|
|
else |
283 |
|
|
{ |
284 |
|
|
t1=edge->get_tmax(); |
285 |
|
|
t2=edge->get_tmin(); |
286 |
|
|
} |
287 |
|
|
|
288 |
|
|
if ( __curvilinearLength == false ) |
289 |
|
|
{ |
290 |
|
|
*__dt = (t2 - t1) / GetLength( __iEdge ); |
291 |
|
|
*__t = t1 + __s * (*__dt); |
292 |
|
|
} |
293 |
|
|
else |
294 |
|
|
{ |
295 |
|
|
TPL_FONCTION1<double,MG_ARETE,double> longueur_bsp(*edge, equation_longueur); |
296 |
|
|
double s = __s; |
297 |
|
|
double increment = s/t_max*(t2-t1)/40; |
298 |
|
|
if (increment < 1E-4 * (t2-t1)) |
299 |
|
|
{ |
300 |
|
|
*__dt = (t2 - t1) / GetLength( __iEdge ); |
301 |
|
|
*__t = t1 + __s * (*__dt); |
302 |
foucault |
27 |
|
303 |
foucault |
569 |
return; |
304 |
|
|
} |
305 |
|
|
longueur_bsp.integrer_jusqua_gauss_2(t1, increment, s, __t); |
306 |
|
|
*__dt = (*__t - t1) / s; |
307 |
foucault |
27 |
} |
308 |
|
|
} |
309 |
|
|
|
310 |
|
|
void |
311 |
|
|
PolyCurve::RefEdge_GetS(unsigned __iEdge, |
312 |
foucault |
569 |
double __t, |
313 |
|
|
double *__s, bool __curvilinearLength |
314 |
|
|
) |
315 |
foucault |
27 |
{ |
316 |
foucault |
569 |
double t1,t2; |
317 |
|
|
MG_SOMMET * vertex = lst_vertices[ __iEdge ]; |
318 |
|
|
MG_ARETE * edge = lst_ref_edges[ __iEdge ]; |
319 |
|
|
double period=edge->get_courbe()->get_periode(); |
320 |
foucault |
27 |
|
321 |
foucault |
569 |
t1=edge->get_tmin(); |
322 |
|
|
t2=edge->get_tmax(); |
323 |
foucault |
27 |
|
324 |
foucault |
569 |
if (edge->get_courbe()->est_periodique()) |
325 |
|
|
{ |
326 |
|
|
if (__t < t1 - period*1E-6) |
327 |
|
|
__t += period; |
328 |
|
|
} |
329 |
foucault |
27 |
|
330 |
foucault |
569 |
if ( __curvilinearLength == false) |
331 |
|
|
{ |
332 |
|
|
if (vertex == edge->get_cosommet1()->get_sommet()) |
333 |
|
|
*__s = lst_length[__iEdge] * (__t-t1)/(t2-t1); |
334 |
|
|
else |
335 |
|
|
*__s = lst_length[__iEdge] * (__t-t2)/(t1-t2); |
336 |
|
|
} |
337 |
foucault |
27 |
else |
338 |
foucault |
569 |
{ |
339 |
|
|
if (vertex == edge->get_cosommet1()->get_sommet()) |
340 |
|
|
*__s = edge->get_longueur(t1,__t); |
341 |
|
|
else |
342 |
|
|
*__s = edge->get_longueur(__t,t2); |
343 |
|
|
} |
344 |
foucault |
27 |
} |
345 |
|
|
|
346 |
|
|
void |
347 |
|
|
PolyCurve::InsertCurve(MG_ARETE *__edge) |
348 |
foucault |
569 |
{ |
349 |
|
|
if (lst_ref_edges.size() == 0) |
350 |
|
|
{ |
351 |
|
|
lst_ref_edges.push_back ( __edge ); |
352 |
|
|
lst_length.push_back ( GetLength(__edge) ); |
353 |
|
|
lst_vertices.push_back ( __edge->get_cosommet1()->get_sommet()); |
354 |
|
|
lst_vertices.push_back ( __edge->get_cosommet2()->get_sommet()); |
355 |
|
|
t_min = 0; |
356 |
|
|
t_max = lst_length[0]; |
357 |
|
|
return; |
358 |
|
|
} |
359 |
|
|
|
360 |
|
|
// Get the two vertices of this edge |
361 |
|
|
MG_SOMMET * V[2]; |
362 |
|
|
int iV[2], // index of V[i] in lst_vertices[] ie. V [ i ] == lst_vertices[ iV[ i ] ] |
363 |
|
|
iiVc=-1, // index < 2 of the common vertex in V[0,1] ie. if (iVc != -1) V [ iiVc ] == lst_vertices[ iV[ iiVc ] ] |
364 |
|
|
iiVo=-1; // index < 2 of the other vertex in V[0,1] ie. if (iVo != -1) V [ iiVo ] == lst_vertices[ iV[ iiVo ] ] |
365 |
|
|
V[0] = __edge->get_cosommet1()->get_sommet(); |
366 |
|
|
V[1] = __edge->get_cosommet2()->get_sommet(); |
367 |
foucault |
27 |
|
368 |
foucault |
569 |
// Verify wether the vertices are already referenced in |
369 |
|
|
// the polycurve |
370 |
|
|
std::vector<MG_SOMMET*>::iterator itV[2]; |
371 |
|
|
for (int i=0; i<2; i++) |
372 |
|
|
{ |
373 |
|
|
itV[i] = std::find (lst_vertices.begin(), lst_vertices.end(), V[i]); |
374 |
|
|
if (itV[i] != lst_vertices.end()) |
375 |
|
|
{ // V[i] is already in a curve of the polycurve |
376 |
|
|
iV[i] = std::distance(lst_vertices.begin(), itV[i]); |
377 |
|
|
if (iiVc == -1) |
378 |
|
|
iiVc = i; |
379 |
|
|
else |
380 |
|
|
{ |
381 |
|
|
if (iV[iiVc] == 0) |
382 |
|
|
{ // case of a periodic polycurve : two vertices are common, the |
383 |
|
|
// common vertex should be the last vertex of this polycurve (iV[iiVc]=N-1), |
384 |
|
|
// and the other vertex the first vertex of this polycurve (iV[iiVo]=0) |
385 |
|
|
iiVo = iiVc; |
386 |
|
|
iiVc = i; |
387 |
|
|
} |
388 |
|
|
else |
389 |
|
|
{ |
390 |
|
|
iiVo = i; |
391 |
|
|
} |
392 |
|
|
} |
393 |
foucault |
27 |
|
394 |
foucault |
569 |
if ( iV[i] != 0 && iV[i]+1 != (int)lst_vertices.size() ) |
395 |
|
|
{ |
396 |
francois |
660 |
printf (" Error in PolyCurve::InsertCurve : can't insert a MG_ARETE (extremities = %lu, %lu) not adjacent to the extremities of this PolyCurve (extremities = %lu, %lu)\n", __edge->get_cosommet1()->get_sommet()->get_id(), __edge->get_cosommet2()->get_sommet()->get_id(), get_sommet1()->get_id(), get_sommet2()->get_id()); |
397 |
foucault |
569 |
return; |
398 |
|
|
} |
399 |
foucault |
27 |
} |
400 |
foucault |
569 |
else // vertex V[i] not found |
401 |
foucault |
27 |
{ |
402 |
foucault |
569 |
iV[i] = -1; |
403 |
|
|
iiVo = i; |
404 |
foucault |
27 |
} |
405 |
foucault |
569 |
} |
406 |
foucault |
27 |
|
407 |
foucault |
569 |
|
408 |
|
|
if (iiVc == -1) |
409 |
|
|
{ |
410 |
|
|
printf (" Error in PolyCurve::InsertCurve : the curve requested to append is not connected to the existing polycurve\n"); |
411 |
foucault |
27 |
return; |
412 |
|
|
} |
413 |
foucault |
569 |
|
414 |
|
|
if ( iV [iiVc] == 0 ) // the inserted curve is adjacent to the first vertex of the polycurve |
415 |
|
|
{ |
416 |
|
|
std::reverse(lst_ref_edges.begin(), lst_ref_edges.end()); |
417 |
|
|
std::reverse(lst_vertices.begin(), lst_vertices.end()); |
418 |
|
|
std::reverse(lst_length.begin(), lst_length.end()); |
419 |
|
|
InsertCurve(__edge); |
420 |
|
|
} |
421 |
|
|
else if ( iV [iiVc]+1 == lst_vertices.size() ) // the inserted curve is adjacent to the last vertex of the polycurve |
422 |
foucault |
27 |
{ |
423 |
foucault |
569 |
lst_vertices.push_back ( V [ iiVo ] ); |
424 |
|
|
lst_ref_edges.push_back ( __edge ); |
425 |
|
|
lst_length.push_back ( GetLength(__edge) ); |
426 |
foucault |
27 |
} |
427 |
foucault |
569 |
else |
428 |
|
|
{ |
429 |
francois |
660 |
printf("PolyCurve::InsertCurve Error : the edge %lu is neither adjacent to end vertex nor to start vertex of polycurve %lu\n", __edge->get_id(), get_id()); |
430 |
|
|
printf("Polycurve Start vertex = %lu, End vertex = %lu\n", get_sommet1()->get_id(),get_sommet2()->get_id()); |
431 |
|
|
printf("Edge Start vertex = %lu, End vertex = %lu\n", V[0]->get_id(), V[1]->get_id()); |
432 |
foucault |
569 |
return; |
433 |
|
|
} |
434 |
foucault |
27 |
|
435 |
foucault |
569 |
// update t_max |
436 |
|
|
t_max = 0; |
437 |
|
|
for (std::vector<double>::const_iterator it_length = lst_length.begin(); |
438 |
|
|
it_length != lst_length.end(); |
439 |
|
|
it_length++) |
440 |
|
|
t_max += (*it_length); |
441 |
foucault |
27 |
|
442 |
|
|
} |
443 |
|
|
|
444 |
|
|
void |
445 |
|
|
PolyCurve::Parameter_SToRefEdgeT (double __s, unsigned * __iEdge, double *__t, double *__dt, bool __curvilinearLength) |
446 |
|
|
{ |
447 |
foucault |
569 |
double s; |
448 |
|
|
unsigned i; |
449 |
foucault |
27 |
|
450 |
foucault |
569 |
VerifyS(__s); |
451 |
foucault |
27 |
|
452 |
foucault |
569 |
i=0; |
453 |
|
|
s=0; |
454 |
|
|
while (s + GetLength(i) < __s && i+1 < lst_ref_edges.size() ) |
455 |
|
|
{ |
456 |
|
|
s += GetLength(i); |
457 |
|
|
i++; |
458 |
|
|
} |
459 |
foucault |
27 |
|
460 |
foucault |
569 |
RefEdge_GetT(i, __s - s, __t, __dt, __curvilinearLength); |
461 |
|
|
*__iEdge = i; |
462 |
foucault |
27 |
} |
463 |
|
|
|
464 |
|
|
void |
465 |
|
|
PolyCurve::Parameter_SToRefEdgeT (double __s, MG_ARETE ** __edge, double *__t, double *__dt, bool __curvilinearLength) |
466 |
|
|
{ |
467 |
|
|
unsigned iEdge; |
468 |
|
|
Parameter_SToRefEdgeT(__s, &iEdge, __t, __dt, __curvilinearLength); |
469 |
|
|
*__edge = GetRefEdge(iEdge); |
470 |
|
|
} |
471 |
|
|
|
472 |
foucault |
569 |
unsigned |
473 |
foucault |
27 |
PolyCurve::RefEdge_GetIndex(MG_ARETE * __edge) |
474 |
|
|
{ |
475 |
|
|
unsigned i = std::distance ( lst_ref_edges.begin(), std::find ( lst_ref_edges.begin(), lst_ref_edges.end(), __edge) ); |
476 |
|
|
return i; |
477 |
|
|
} |
478 |
|
|
|
479 |
foucault |
569 |
unsigned |
480 |
foucault |
27 |
PolyCurve::RefVertex_GetIndex(MG_SOMMET * __vertex) |
481 |
|
|
{ |
482 |
|
|
unsigned i = std::distance ( lst_vertices.begin(), std::find ( lst_vertices.begin(), lst_vertices.end(), __vertex) ); |
483 |
|
|
return i; |
484 |
|
|
} |
485 |
|
|
|
486 |
|
|
void |
487 |
|
|
PolyCurve::Parameter_RefEdgeTToS (double __t, MG_ARETE * __edge, double *__s, bool __curvilinearLength) |
488 |
foucault |
569 |
{ |
489 |
|
|
double s, ds; |
490 |
|
|
unsigned i; |
491 |
foucault |
27 |
|
492 |
foucault |
569 |
i = RefEdge_GetIndex(__edge); |
493 |
foucault |
27 |
|
494 |
foucault |
569 |
s=0; |
495 |
|
|
for ( unsigned k = 0; k < i; k++) |
496 |
|
|
{ |
497 |
|
|
s += GetLength(k); |
498 |
|
|
} |
499 |
|
|
RefEdge_GetS(i, __t, &ds, __curvilinearLength); |
500 |
|
|
s += ds; |
501 |
foucault |
27 |
|
502 |
foucault |
569 |
*__s = s; |
503 |
foucault |
27 |
} |
504 |
foucault |
569 |
|
505 |
foucault |
27 |
void |
506 |
|
|
PolyCurve::evaluer (double __s, double __X[3]) |
507 |
|
|
{ |
508 |
foucault |
569 |
bool curvilinearLength = false; |
509 |
|
|
evaluer(__s, __X, curvilinearLength); |
510 |
foucault |
27 |
} |
511 |
|
|
|
512 |
|
|
void |
513 |
|
|
PolyCurve::evaluer (double __s, double __X[3], bool __curvilinearLength) // curvilinear abcissa |
514 |
|
|
{ |
515 |
foucault |
569 |
if (IsPoint()) |
516 |
|
|
{ |
517 |
|
|
lst_vertices[0]->get_point()->evaluer(__X); |
518 |
|
|
return; |
519 |
|
|
} |
520 |
foucault |
27 |
|
521 |
foucault |
569 |
VerifyS (__s); |
522 |
|
|
unsigned iEdge; |
523 |
|
|
MG_ARETE * edge; |
524 |
|
|
double t, dt; |
525 |
|
|
Parameter_SToRefEdgeT ( __s, & iEdge , &t, &dt, __curvilinearLength ); |
526 |
|
|
edge = lst_ref_edges [ iEdge ]; |
527 |
|
|
PolyCurve::VerifyRefEdgeT(edge, t); |
528 |
|
|
edge->evaluer ( t, __X ); |
529 |
foucault |
27 |
} |
530 |
foucault |
569 |
|
531 |
foucault |
27 |
void |
532 |
|
|
PolyCurve::deriver (double __s, double __X[3]) // curvilinear abcissa |
533 |
|
|
{ |
534 |
foucault |
569 |
bool curvilinearLength = false; |
535 |
|
|
deriver(__s, __X, curvilinearLength); |
536 |
foucault |
27 |
} |
537 |
|
|
|
538 |
|
|
void |
539 |
|
|
PolyCurve::deriver (double __s, double __X[3], bool __curvilinearLength) // curvilinear abcissa |
540 |
foucault |
569 |
{ |
541 |
|
|
if (IsPoint()) |
542 |
|
|
{ |
543 |
|
|
for (int i=0;i<3;i++) __X[i] = 1; |
544 |
|
|
return; |
545 |
|
|
} |
546 |
|
|
|
547 |
|
|
VerifyS (__s); |
548 |
|
|
unsigned iEdge; |
549 |
|
|
MG_ARETE * edge; |
550 |
|
|
double t, dt; |
551 |
|
|
Parameter_SToRefEdgeT ( __s, & iEdge , &t, &dt, __curvilinearLength ); |
552 |
|
|
edge = lst_ref_edges [ iEdge ]; |
553 |
|
|
PolyCurve::VerifyRefEdgeT(edge, t); |
554 |
|
|
edge->deriver ( t, __X ); |
555 |
|
|
|
556 |
|
|
// dC/ds = dC/dt * dt/ds |
557 |
|
|
for (int i = 0; i<3; i++) |
558 |
|
|
__X[i] *= dt; |
559 |
foucault |
27 |
} |
560 |
|
|
|
561 |
foucault |
569 |
|
562 |
foucault |
27 |
void |
563 |
|
|
PolyCurve::deriver_seconde (double __s, double __ddxyz[3], double *__dxyz, double *__xyz) // curvilinear abcissa |
564 |
|
|
{ |
565 |
foucault |
569 |
bool curvilinearLength = false; |
566 |
|
|
deriver_seconde(__s, __ddxyz, __dxyz, __xyz, curvilinearLength); |
567 |
foucault |
27 |
|
568 |
|
|
} |
569 |
|
|
void |
570 |
|
|
PolyCurve::deriver_seconde (double __s, double __ddxyz[3], double *__dxyz, double *__xyz, bool __curvilinearLength) // curvilinear abcissa |
571 |
foucault |
569 |
{ |
572 |
|
|
unsigned iEdge; |
573 |
|
|
MG_ARETE * edge; |
574 |
|
|
double t, dt; |
575 |
|
|
|
576 |
|
|
if (IsPoint()) |
577 |
|
|
{ |
578 |
|
|
if (__ddxyz) for (int i=0;i<3;i++) __ddxyz[i]=1; |
579 |
|
|
if (__dxyz) for (int i=0;i<3;i++) __dxyz[i]=1; |
580 |
|
|
evaluer(0,__xyz); |
581 |
|
|
return; |
582 |
|
|
} |
583 |
foucault |
27 |
|
584 |
foucault |
569 |
VerifyS (__s); |
585 |
foucault |
27 |
|
586 |
foucault |
569 |
Parameter_SToRefEdgeT ( __s, & iEdge , &t, &dt, __curvilinearLength ); |
587 |
|
|
edge = lst_ref_edges [ iEdge ]; |
588 |
foucault |
27 |
|
589 |
foucault |
569 |
for (int i=0; i<3; i++) |
590 |
|
|
__ddxyz[i] = 0; |
591 |
foucault |
27 |
|
592 |
foucault |
569 |
if (__dxyz) |
593 |
|
|
edge->deriver(t, __dxyz); |
594 |
|
|
// dC/ds = dC/dt * dt/ds |
595 |
|
|
for (int i = 0; i<3; i++) |
596 |
|
|
__dxyz[i] *= dt; |
597 |
foucault |
27 |
|
598 |
foucault |
569 |
if (__xyz) |
599 |
|
|
edge->evaluer(t, __xyz); |
600 |
foucault |
27 |
} |
601 |
|
|
|
602 |
|
|
|
603 |
|
|
|
604 |
|
|
void |
605 |
|
|
PolyCurve::Merge( PolyCurve & __polycurve) |
606 |
|
|
{ |
607 |
foucault |
569 |
if (lst_vertices.size() == 0) |
608 |
|
|
{ |
609 |
|
|
for (std::vector < MG_ARETE * >::const_iterator it = __polycurve.lst_ref_edges.begin(); |
610 |
|
|
it != __polycurve.lst_ref_edges.end(); |
611 |
|
|
it++ ) |
612 |
|
|
InsertCurve ( *it ); |
613 |
|
|
} |
614 |
|
|
else if (get_sommet2() == __polycurve.get_sommet2() || get_sommet1() == __polycurve.get_sommet2() ) |
615 |
|
|
{; |
616 |
|
|
for (std::vector < MG_ARETE * >::reverse_iterator it = __polycurve.lst_ref_edges.rbegin(); |
617 |
|
|
it != __polycurve.lst_ref_edges.rend(); |
618 |
|
|
it++) |
619 |
|
|
InsertCurve ( *it ); |
620 |
|
|
} |
621 |
|
|
else if ( get_sommet1() == __polycurve.get_sommet1() || get_sommet2() == __polycurve.get_sommet1() ) |
622 |
|
|
{ |
623 |
|
|
for (std::vector < MG_ARETE * >::const_iterator it = __polycurve.lst_ref_edges.begin(); |
624 |
|
|
it != __polycurve.lst_ref_edges.end(); |
625 |
|
|
it++ ) |
626 |
|
|
InsertCurve ( *it ); |
627 |
|
|
} |
628 |
|
|
else |
629 |
|
|
{ |
630 |
francois |
660 |
printf("PolyCurve::Merge Error : the polycurve %lu is neither adjacent to end vertex nor to start vertex of polycurve %lu\n", __polycurve.get_id(), get_id()); |
631 |
|
|
printf("Polycurve Start vertex = %lu, End vertex = %lu\n", get_sommet1()->get_id(),get_sommet2()->get_id()); |
632 |
|
|
printf("Other __polycurve Start vertex = %lu, End vertex = %lu\n", __polycurve.get_sommet1()->get_id(), __polycurve.get_sommet2()->get_id()); |
633 |
foucault |
569 |
return; |
634 |
foucault |
27 |
|
635 |
foucault |
569 |
} |
636 |
foucault |
27 |
} |
637 |
|
|
|
638 |
|
|
void |
639 |
|
|
PolyCurve::SetPeriodicPoleRefVertex(MG_SOMMET * __v) |
640 |
|
|
{ |
641 |
|
|
if ( est_periodique() == false) |
642 |
|
|
return; |
643 |
foucault |
569 |
|
644 |
foucault |
27 |
std::vector<MG_ARETE*> e; |
645 |
|
|
std::vector<MG_SOMMET*> v; |
646 |
|
|
std::vector<double> l; |
647 |
|
|
unsigned k=RefVertex_GetIndex(__v); |
648 |
|
|
unsigned N=lst_vertices.size(); |
649 |
|
|
for (unsigned i=0; i<N; i++) |
650 |
|
|
{ |
651 |
foucault |
569 |
unsigned m = (i+k)%N; |
652 |
|
|
unsigned n = (i+k+1)%N; |
653 |
foucault |
27 |
MG_SOMMET * tempv = lst_vertices[ m ]; |
654 |
|
|
MG_SOMMET * lastV = (v.size()) ? v[v.size()-1] : 0; |
655 |
|
|
if ( lastV && lastV == tempv ) |
656 |
|
|
tempv = lst_vertices[n]; |
657 |
|
|
v.push_back(tempv); |
658 |
|
|
} |
659 |
|
|
for (unsigned i=0; i+1<N; i++) |
660 |
|
|
e.push_back(lst_ref_edges[ (i+k)%(N-1) ]); |
661 |
|
|
for (unsigned i=0; i+1<N; i++) |
662 |
|
|
l.push_back(lst_length[ (i+k)%(N-1) ]); |
663 |
|
|
lst_vertices = v; |
664 |
|
|
lst_ref_edges = e; |
665 |
|
|
lst_length = l; |
666 |
|
|
} |
667 |
|
|
|
668 |
|
|
double |
669 |
foucault |
569 |
PolyCurve::get_longueur (double __s_min, double __s_max, double precision) |
670 |
foucault |
27 |
{ |
671 |
foucault |
569 |
double result; |
672 |
|
|
if ( __s_min >= 0 && __s_max >= 0 ) |
673 |
|
|
return fabs (__s_min - __s_max); |
674 |
|
|
else |
675 |
|
|
{ |
676 |
|
|
return t_max; |
677 |
|
|
} |
678 |
foucault |
27 |
} |
679 |
|
|
|
680 |
|
|
double PolyCurve::get_tmin() |
681 |
|
|
{ |
682 |
foucault |
569 |
return t_min; |
683 |
foucault |
27 |
} |
684 |
|
|
|
685 |
|
|
double PolyCurve::get_tmax() |
686 |
|
|
{ |
687 |
foucault |
569 |
return t_max; |
688 |
foucault |
27 |
} |
689 |
|
|
|
690 |
|
|
MG_SOMMET * |
691 |
foucault |
569 |
PolyCurve::get_sommet1() |
692 |
foucault |
27 |
{ |
693 |
foucault |
569 |
return lst_vertices[0]; |
694 |
foucault |
27 |
} |
695 |
|
|
|
696 |
|
|
|
697 |
|
|
MG_SOMMET * |
698 |
foucault |
569 |
PolyCurve::get_sommet2() |
699 |
foucault |
27 |
{ |
700 |
foucault |
569 |
return lst_vertices[lst_vertices.size()-1]; |
701 |
foucault |
27 |
} |
702 |
|
|
|
703 |
|
|
double |
704 |
|
|
PolyCurve::get_sommet1_s() |
705 |
|
|
{ |
706 |
foucault |
569 |
return get_tmin(); |
707 |
foucault |
27 |
} |
708 |
|
|
|
709 |
|
|
|
710 |
|
|
double |
711 |
foucault |
569 |
PolyCurve::get_sommet2_s() |
712 |
foucault |
27 |
{ |
713 |
foucault |
569 |
return get_tmax(); |
714 |
foucault |
27 |
} |
715 |
|
|
|
716 |
|
|
void |
717 |
|
|
PolyCurve::inverser(double & __t, double __point[3], double precision) |
718 |
|
|
{ |
719 |
foucault |
569 |
bool curvilinearLength = false; |
720 |
foucault |
27 |
|
721 |
foucault |
569 |
inverser(__t, __point, precision, curvilinearLength); |
722 |
foucault |
27 |
} |
723 |
|
|
|
724 |
|
|
int PolyCurve::est_periodique(void) |
725 |
|
|
{ |
726 |
foucault |
569 |
if ( get_sommet1 () == get_sommet2 () ) |
727 |
|
|
return 1; |
728 |
|
|
else |
729 |
|
|
return 0; |
730 |
foucault |
27 |
} |
731 |
|
|
|
732 |
|
|
double PolyCurve::get_periode(void) |
733 |
|
|
{ |
734 |
|
|
if ( est_periodique() ) |
735 |
|
|
return get_longueur(); |
736 |
|
|
else |
737 |
foucault |
569 |
return 0; |
738 |
foucault |
27 |
} |
739 |
|
|
|
740 |
|
|
|
741 |
|
|
int PolyCurve::get_type_geometrique(TPL_LISTE_ENTITE<double> ¶m) |
742 |
|
|
{ |
743 |
foucault |
569 |
return 4343; // TYPE = Poly curve |
744 |
foucault |
27 |
} |
745 |
|
|
|
746 |
francois |
763 |
void PolyCurve::enregistrer(std::ostream& o,double version) |
747 |
foucault |
27 |
{ |
748 |
|
|
unsigned int i; |
749 |
|
|
|
750 |
|
|
if (IsPoint() == false) |
751 |
foucault |
569 |
{ |
752 |
|
|
o << "%" << get_id() |
753 |
|
|
<< "=CAD4FE_POLYCURVE(" << GetRefEdgeCount() << ",("; |
754 |
|
|
|
755 |
|
|
for (i=0; i < GetRefEdgeCount(); i++) |
756 |
foucault |
27 |
{ |
757 |
foucault |
569 |
if ( i ) o <<","; |
758 |
|
|
o << "$" << GetRefEdge(i)->get_id(); |
759 |
|
|
} |
760 |
foucault |
27 |
|
761 |
foucault |
569 |
o << "));" << std::endl; |
762 |
|
|
} |
763 |
foucault |
27 |
else // The polycurve is a point ! |
764 |
foucault |
569 |
{ |
765 |
|
|
o << "%" << get_id() << "=CAD4FE_POLYCURVE(0,($"<<GetRefVertex(0)->get_id()<<"));"<< std::endl; |
766 |
|
|
} |
767 |
foucault |
27 |
} |
768 |
|
|
|
769 |
foucault |
569 |
std::vector<MG_ARETE*> & |
770 |
|
|
PolyCurve::GetRefEdges() |
771 |
foucault |
27 |
{ |
772 |
foucault |
569 |
return lst_ref_edges; |
773 |
foucault |
27 |
} |
774 |
|
|
|
775 |
|
|
void |
776 |
|
|
CAD4FE::SplitRefEdge(MG_ARETE * __refEdge, MG_SOMMET * __refVertex1, MG_SOMMET * __refVertex2, double __xyz[3], MG_VOLUME * __refBody, MG_GEOMETRIE * __geom, MG_ARETE * edges[2], MG_SOMMET ** __splitVertex) |
777 |
|
|
{ |
778 |
|
|
int i,j; |
779 |
foucault |
569 |
double tSplit; |
780 |
foucault |
27 |
MG_ARETE * splitEdge = __refEdge; |
781 |
|
|
splitEdge->inverser(tSplit, __xyz); |
782 |
|
|
|
783 |
|
|
// Create the split vertex at position xyz |
784 |
|
|
MG_POINT * point = new LC_POINT(__xyz); |
785 |
|
|
__geom->ajouter_mg_point(point); |
786 |
|
|
std::ostringstream idoriginal; |
787 |
|
|
idoriginal << "Vertex of "<< splitEdge->get_idoriginal() <<" split at t="<<tSplit; |
788 |
|
|
MG_SOMMET * splitVertex = new MG_SOMMET(idoriginal.str(), point); |
789 |
|
|
*__splitVertex = splitVertex; |
790 |
|
|
__geom->ajouter_mg_sommet(splitVertex); |
791 |
|
|
|
792 |
|
|
// split the edge in two edges |
793 |
|
|
MG_COURBE * curves[2]; |
794 |
|
|
MG_SOMMET * vertices[2][2]; |
795 |
|
|
MG_COSOMMET * cov[2][2]; |
796 |
foucault |
569 |
|
797 |
foucault |
27 |
vertices[0][0] = splitEdge->get_cosommet1()->get_sommet(); |
798 |
|
|
vertices[0][1] = splitVertex; |
799 |
|
|
vertices[1][0] = splitVertex; |
800 |
|
|
vertices[1][1] = splitEdge->get_cosommet2()->get_sommet(); |
801 |
foucault |
569 |
|
802 |
foucault |
27 |
curves[0] = curves[1] = splitEdge->get_courbe(); |
803 |
|
|
|
804 |
|
|
double verticesT[2][2]; |
805 |
foucault |
569 |
verticesT[0][0] = splitEdge->get_tmin(); |
806 |
foucault |
27 |
verticesT[1][1] = splitEdge->get_tmax(); |
807 |
|
|
verticesT[0][1] = verticesT[1][0] = tSplit; |
808 |
|
|
|
809 |
|
|
// create two edges |
810 |
|
|
for (i=0; i<2; i++) |
811 |
|
|
{ |
812 |
|
|
// orientation |
813 |
foucault |
569 |
int orientation = splitEdge->get_orientation(); |
814 |
foucault |
27 |
// Create an edge using the start vertex and the split vertex |
815 |
|
|
std::ostringstream idoriginal; |
816 |
|
|
idoriginal << __refEdge->get_idoriginal(); |
817 |
|
|
idoriginal << " split with t0 " << verticesT[i][0] << " t1 " << verticesT[i][1]; |
818 |
|
|
edges[i] = new MG_ARETE (idoriginal.str(), 0, curves[i], orientation); |
819 |
|
|
__geom->ajouter_mg_arete (edges[i]); |
820 |
|
|
// create covertices |
821 |
|
|
for (j=0;j<2;j++) |
822 |
|
|
{ |
823 |
|
|
cov[i][j] = __geom->ajouter_mg_cosommet (edges[i], vertices[i][j]); |
824 |
|
|
} |
825 |
|
|
|
826 |
|
|
edges[i]->changer_cosommet1(cov[i][0]); |
827 |
|
|
edges[i]->changer_cosommet2(cov[i][1]); |
828 |
|
|
} |
829 |
|
|
|
830 |
|
|
MG_BOUCLE * split_edge_loops[10]; |
831 |
|
|
int nb_split_edge_loops = 0; |
832 |
|
|
MG_COARETE * split_edge_coedges[10], * coedges[20]; |
833 |
|
|
int nb_split_edge_coedges = 0, nb_coedges = 0; |
834 |
|
|
// create four coedges (in manifold body case) |
835 |
|
|
// replace each coedges belong to initial edge in both loops of the ref faces |
836 |
|
|
// |
837 |
foucault |
569 |
// for each shell of the ref body |
838 |
|
|
unsigned nb_shells = __refBody->get_nb_mg_coquille (); |
839 |
|
|
for (unsigned it_shells = 0; it_shells < nb_shells; it_shells++) |
840 |
|
|
{ |
841 |
|
|
MG_COQUILLE * shell = __refBody->get_mg_coquille(it_shells); |
842 |
francois |
283 |
// for each coface->face F of the shell |
843 |
foucault |
569 |
unsigned nb_coface = shell->get_nb_mg_coface(); |
844 |
|
|
for (unsigned it_coface = 0; it_coface < nb_coface; it_coface++) |
845 |
foucault |
27 |
{ |
846 |
foucault |
569 |
MG_FACE * face = shell->get_mg_coface(it_coface)->get_face(); |
847 |
foucault |
27 |
|
848 |
foucault |
569 |
// for each loop L of this face |
849 |
|
|
unsigned nb_loop = face->get_nb_mg_boucle(); |
850 |
|
|
for (unsigned it_loop = 0; it_loop < nb_loop; it_loop++) |
851 |
foucault |
27 |
{ |
852 |
foucault |
569 |
MG_BOUCLE * loop = face->get_mg_boucle(it_loop); |
853 |
|
|
// for each coedge coe of L |
854 |
|
|
unsigned nb_edge = loop->get_nb_mg_coarete(); |
855 |
|
|
for (unsigned it_edge = 0; it_edge < nb_edge; it_edge++) |
856 |
|
|
{ |
857 |
|
|
MG_COARETE * coedge = loop->get_mg_coarete(it_edge); |
858 |
|
|
MG_ARETE * edge = coedge->get_arete(); |
859 |
|
|
|
860 |
|
|
// if coe contains split_edge |
861 |
|
|
if (edge == splitEdge) |
862 |
|
|
{ |
863 |
|
|
split_edge_loops[ nb_split_edge_loops++ ] = loop; |
864 |
|
|
split_edge_coedges[ nb_split_edge_coedges++ ] = coedge; |
865 |
|
|
// create coe[0] ( edges[0], F, coe->sense ) |
866 |
|
|
// create coe[1] ( edges[1], F, coe->sense ) |
867 |
|
|
// delete coe in L |
868 |
|
|
// add coe[0] in L |
869 |
|
|
// add coe[1] in L |
870 |
|
|
for (i=0; i<2; i++) |
871 |
|
|
{ |
872 |
|
|
coedges[nb_coedges++] = __geom->ajouter_mg_coarete (edges[i], loop, coedge->get_orientation()); |
873 |
|
|
loop->ajouter_mg_coarete(coedges[nb_coedges-1]); |
874 |
|
|
} |
875 |
|
|
|
876 |
|
|
loop->supprimer_mg_coarete(coedge); |
877 |
|
|
__geom->supprimer_mg_coarete(coedge); |
878 |
|
|
} |
879 |
|
|
// fi |
880 |
|
|
} |
881 |
francois |
283 |
} |
882 |
foucault |
27 |
} |
883 |
foucault |
569 |
} |
884 |
foucault |
27 |
|
885 |
|
|
} |
886 |
|
|
|
887 |
|
|
void |
888 |
|
|
CAD4FE::SplitPolyCurve(PolyCurve * __polyCurve, double __xyz[3], MG_VOLUME * __refBody, MG_GEOMETRIE * __geom, PolyCurve * __result[2], MG_ARETE **__origRefEdge, MG_SOMMET ** __splitRefVertex, MG_ARETE * __splitRefEdges[2]) |
889 |
|
|
{ |
890 |
|
|
int i,j; |
891 |
|
|
*__splitRefVertex = NULL; |
892 |
|
|
__splitRefEdges[0]=__splitRefEdges[1]=NULL; |
893 |
|
|
|
894 |
|
|
// get the parameter of __splitVertex |
895 |
|
|
double sSplitVertex; |
896 |
|
|
__polyCurve->inverser(sSplitVertex,__xyz,1E-6); |
897 |
|
|
|
898 |
|
|
unsigned index; // index of the reference edge split |
899 |
|
|
double tEdge, dtEdge; // real parameter of the reference edge split |
900 |
|
|
__polyCurve->Parameter_SToRefEdgeT(sSplitVertex,&index,&tEdge,&dtEdge, false); |
901 |
|
|
*__origRefEdge = __polyCurve->GetRefEdge(index); |
902 |
|
|
MG_SOMMET * v[2]; |
903 |
|
|
v[0] = __polyCurve->GetRefVertex(index); |
904 |
|
|
v[1] = __polyCurve->GetRefVertex(index+1); |
905 |
|
|
|
906 |
|
|
// Test wether __xyz is located on one extremity of the ref edge |
907 |
|
|
for (i=0; i<2; i++) |
908 |
|
|
{ |
909 |
|
|
double v_xyz[3]; |
910 |
|
|
|
911 |
|
|
v[i]->get_point()->evaluer(v_xyz); |
912 |
|
|
|
913 |
|
|
if (OT_ALGORITHME_GEOMETRIQUE::VEC3_DISTANCE_VEC3(__xyz, v_xyz) / __polyCurve->GetLength(index) < 1E-6) |
914 |
|
|
{ |
915 |
|
|
if (index+i == 0 || index+i+1 == __polyCurve->GetRefVertexCount()) |
916 |
|
|
{ |
917 |
francois |
660 |
printf("Can't split a polycurve on vertex ID %lu because its extremities are vertices : %lu and %lu\n", v[i]->get_id(), __polyCurve->GetRefVertex(0)->get_id(), __polyCurve->GetRefVertex(__polyCurve->GetRefVertexCount()-1)->get_id()); |
918 |
foucault |
27 |
return; |
919 |
|
|
} |
920 |
|
|
|
921 |
|
|
*__origRefEdge = NULL; |
922 |
|
|
*__splitRefVertex = v[i]; |
923 |
|
|
__splitRefEdges[0] = __polyCurve->GetRefEdge(index-1+i); |
924 |
|
|
__splitRefEdges[1] = __polyCurve->GetRefEdge(index+i); |
925 |
foucault |
569 |
|
926 |
foucault |
27 |
// create the two polyCurves |
927 |
|
|
for (int k=0; k<2; k++) |
928 |
|
|
{ |
929 |
|
|
// create polycurve |
930 |
|
|
__result[k] = new PolyCurve ( __splitRefEdges[k] ); |
931 |
|
|
__geom->ajouter_mg_courbe(__result[k]); |
932 |
|
|
for (j = (k==0)?index-2+i:index+i+1; j >= 0 && j < __polyCurve->GetRefEdgeCount(); j += -1+2*k) |
933 |
|
|
__result[k]->InsertCurve(__polyCurve->GetRefEdge(j)); |
934 |
|
|
} |
935 |
foucault |
569 |
|
936 |
foucault |
27 |
break; |
937 |
|
|
} |
938 |
|
|
} |
939 |
|
|
if (*__splitRefVertex == NULL) |
940 |
|
|
{ |
941 |
|
|
CAD4FE::SplitRefEdge(*__origRefEdge, v[0], v[1], __xyz, __refBody, __geom, __splitRefEdges, __splitRefVertex); |
942 |
|
|
|
943 |
|
|
if ( __splitRefEdges[0]->get_cosommet1()->get_sommet() != v[0] && __splitRefEdges[0]->get_cosommet2()->get_sommet() != v[0] ) |
944 |
foucault |
569 |
std::swap(__splitRefEdges[0], __splitRefEdges[1] ); |
945 |
foucault |
27 |
|
946 |
|
|
// create the two polyCurves |
947 |
|
|
for (i=0; i<2; i++) |
948 |
|
|
{ |
949 |
|
|
// create polycurve |
950 |
|
|
__result[i] = new PolyCurve ( __splitRefEdges[i] ); |
951 |
|
|
__geom->ajouter_mg_courbe(__result[i]); |
952 |
|
|
for (j = index-1+2*i; j >= 0 && j < __polyCurve->GetRefEdgeCount(); j += -1+2*i) |
953 |
|
|
__result[i]->InsertCurve(__polyCurve->GetRefEdge(j)); |
954 |
|
|
} |
955 |
|
|
} |
956 |
|
|
|
957 |
|
|
if (__result[0]->get_sommet1() !=__result[1]->get_sommet1() &&__result[0]->get_sommet1() !=__result[1]->get_sommet2() && |
958 |
foucault |
569 |
__result[0]->get_sommet2() !=__result[1]->get_sommet1() &&__result[0]->get_sommet2() !=__result[1]->get_sommet2()) |
959 |
foucault |
27 |
printf("Error"); |
960 |
|
|
|
961 |
|
|
} |
962 |
|
|
|
963 |
|
|
bool PolyCurve::IsPoint() const |
964 |
|
|
{ |
965 |
|
|
return lst_vertices.size() == 1 && lst_ref_edges.size() == 0; |
966 |
|
|
} |
967 |
|
|
|
968 |
|
|
void |
969 |
|
|
PolyCurve::get_param_NURBS(int& indx_premier_ptctr,TPL_LISTE_ENTITE<double> ¶m) |
970 |
|
|
{ |
971 |
foucault |
569 |
return; |
972 |
foucault |
27 |
} |
973 |
|
|
|
974 |
|
|
|
975 |
|
|
|