b311480e |
1 | // Created on: 1994-09-01 |
2 | // Created by: Christian CAILLET |
3 | // Copyright (c) 1994-1999 Matra Datavision |
4 | // Copyright (c) 1999-2012 OPEN CASCADE SAS |
5 | // |
6 | // The content of this file is subject to the Open CASCADE Technology Public |
7 | // License Version 6.5 (the "License"). You may not use the content of this file |
8 | // except in compliance with the License. Please obtain a copy of the License |
9 | // at http://www.opencascade.org and read it completely before using this file. |
10 | // |
11 | // The Initial Developer of the Original Code is Open CASCADE S.A.S., having its |
12 | // main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France. |
13 | // |
14 | // The Original Code and all software distributed under the License is |
15 | // distributed on an "AS IS" basis, without warranty of any kind, and the |
16 | // Initial Developer hereby disclaims all such warranties, including without |
17 | // limitation, any warranties of merchantability, fitness for a particular |
18 | // purpose or non-infringement. Please see the License for the specific terms |
19 | // and conditions governing the rights and limitations under the License. |
20 | |
7fd59977 |
21 | // modif du 31/01/97 : mjm |
22 | // on commence par les SplineCurves. |
23 | // modif du 17/03/97 : mjm |
24 | // SplineSurfaces. |
25 | //%13 pdn 12.02.99: USA60293 avoid applying transformation twice |
26 | |
27 | #include <IGESConvGeom.ixx> |
28 | |
29 | #include <IGESData_ToolLocation.hxx> |
30 | |
31 | #include <BSplCLib.hxx> |
32 | |
33 | #include <BSplSLib.hxx> |
34 | |
35 | #include <gp_GTrsf.hxx> |
36 | #include <gp_Trsf.hxx> |
37 | #include <GeomConvert_CompCurveToBSplineCurve.hxx> |
38 | #include <PLib.hxx> |
39 | |
40 | #include <TColgp_HArray1OfPnt.hxx> |
41 | #include <TColgp_HArray2OfPnt.hxx> |
b311480e |
42 | |
7fd59977 |
43 | #include <TColStd_Array1OfInteger.hxx> |
44 | #include <TColStd_Array1OfReal.hxx> |
45 | #include <TColStd_HArray1OfReal.hxx> |
46 | |
47 | |
48 | |
49 | //======================================================================= |
50 | //function : IGESConvGeom::SplineCurveFromIGES |
51 | //purpose : |
52 | //======================================================================= |
53 | Standard_Integer IGESConvGeom::SplineCurveFromIGES |
54 | (const Handle(IGESGeom_SplineCurve)& st, |
55 | const Standard_Real /*epscoef*/, const Standard_Real epsgeom, |
56 | Handle(Geom_BSplineCurve)& res) |
57 | { |
58 | Standard_Integer returned = 0; |
59 | |
60 | // on recupere le degre |
61 | Standard_Integer degree = st->SplineType(); |
62 | if (degree > 3) degree = 3; |
63 | |
64 | // on recupere le nombre de segments. |
65 | Standard_Integer nbSegs = st->NbSegments(); |
66 | if (nbSegs < 1) return 5; // FAIL : no segment |
67 | |
68 | Standard_Integer nbKnots = nbSegs+1; |
69 | |
70 | // Array of multiplicities. |
71 | TColStd_Array1OfInteger multi(1, nbKnots); |
72 | multi.Init(degree); |
73 | multi.SetValue(multi.Lower(), degree+1); |
74 | multi.SetValue(multi.Upper(), degree+1); |
75 | |
76 | // Array of knots. |
77 | TColStd_Array1OfReal knots(1, nbKnots); |
78 | TColStd_Array1OfReal delta(1, nbSegs); |
79 | Standard_Integer i; // svv Jan 10 2000 : porting on DEC |
80 | for (i = 1; i<= nbKnots; i++) |
81 | knots.SetValue(i, st->BreakPoint(i)); |
82 | |
83 | for (i = 1; i <= nbSegs; i++) |
84 | delta.SetValue(i, st->BreakPoint(i+1) - st->BreakPoint(i)); |
85 | |
86 | TColgp_Array1OfPnt bspoles(1, nbSegs*degree+1); |
87 | Standard_Integer ibspole = bspoles.Lower()-1; // Bspole Index. |
88 | // il faut reparametrer avant de passer dans PLib. |
89 | // on est entre[0, T(i+1)-T(i)] et on veut [0,1] |
90 | |
91 | for (i = 1; i <= nbSegs; i++) { |
92 | Standard_Real AX,BX,CX,DX,AY,BY,CY,DY,AZ,BZ,CZ,DZ; |
93 | st->XCoordPolynomial(i, AX, BX, CX, DX); |
94 | st->YCoordPolynomial(i, AY, BY, CY, DY); |
95 | st->ZCoordPolynomial(i, AZ, BZ, CZ, DZ); |
96 | if (st->NbDimensions() == 2 ) BZ=0.,CZ=0.,DZ=0.; |
97 | Standard_Real Di = delta(i); |
98 | Standard_Real Di2 = delta(i)*delta(i); |
99 | Standard_Real Di3 = delta(i)*delta(i)*delta(i); |
100 | |
101 | TColgp_Array1OfPnt coeff(0, degree); |
102 | switch (degree) { |
103 | case 3 : |
104 | coeff.SetValue(coeff.Lower()+3, gp_Pnt(DX*Di3, DY*Di3, DZ*Di3)); |
105 | case 2 : |
106 | coeff.SetValue(coeff.Lower()+2, gp_Pnt(CX*Di2, CY*Di2, CZ*Di2)); |
107 | case 1 : |
108 | coeff.SetValue(coeff.Lower()+1, gp_Pnt(BX*Di, BY*Di, BZ*Di)); |
109 | coeff.SetValue(coeff.Lower()+0, gp_Pnt(AX, AY, AZ)); |
110 | break; |
111 | default: |
112 | break; |
113 | } |
114 | |
115 | |
116 | TColgp_Array1OfPnt bzpoles(0, degree); |
117 | PLib::CoefficientsPoles(coeff,PLib::NoWeights(),bzpoles,PLib::NoWeights()); |
118 | |
119 | // C0 test. |
120 | // Not to check the first pole of the first segment. |
121 | if (ibspole > bspoles.Lower()) { |
122 | Standard_Integer bzlow = bzpoles.Lower(); |
123 | if (!(bspoles.Value(ibspole).IsEqual(bzpoles.Value(bzlow), epsgeom))) { |
124 | returned = 1; |
125 | // Medium point computing. |
126 | bspoles.SetValue (ibspole, |
127 | gp_Pnt((bspoles.Value(ibspole).X() + bzpoles.Value(bzlow).X())/2., |
128 | (bspoles.Value(ibspole).Y() + bzpoles.Value(bzlow).Y())/2., |
129 | (bspoles.Value(ibspole).Z() + bzpoles.Value(bzlow).Z())/2.)); |
130 | } |
131 | } |
132 | if (i == 1) bspoles.SetValue(++ibspole, bzpoles.Value(bzpoles.Lower())); |
133 | |
134 | for (Standard_Integer j = bzpoles.Lower()+1; j <= bzpoles.Upper(); j++) |
135 | bspoles.SetValue(++ibspole, bzpoles.Value(j)); |
136 | } |
137 | if (ibspole != bspoles.Upper()) { |
138 | // Just to be sure. |
139 | return 3; // FAIL : Error during creation of control points |
140 | } |
141 | |
142 | // Building result taking into account transformation if any : |
143 | // =========================================================== |
144 | |
145 | //%13 pdn 12.02.99 USA60293 |
146 | // if (st->HasTransf()) { |
147 | // gp_Trsf trsf; |
148 | // Standard_Real epsilon = 1.E-04; |
149 | // if (IGESData_ToolLocation::ConvertLocation |
150 | // (epsilon,st->CompoundLocation(),trsf)) { |
151 | // for (Standard_Integer i = bspoles.Lower(); i <= bspoles.Upper(); i++) |
152 | // bspoles.SetValue(i, bspoles.Value(i).Transformed(trsf)); |
153 | // } |
154 | // else |
155 | // AddFail(st, "Transformation : not a similarity"); |
156 | // } |
157 | res = new Geom_BSplineCurve (bspoles, knots, multi, degree); |
158 | // GeomConvert_CompCurveToBSplineCurve CompCurve = |
159 | // GeomConvert_CompCurveToBSplineCurve(res); |
160 | // res = CompCurve.BSplineCurve(); |
161 | return returned; |
162 | } |
163 | |
164 | |
165 | |
166 | //======================================================================= |
167 | //function : IGESConvGeom::IncreaseCurveContinuity |
168 | //purpose : |
169 | //======================================================================= |
170 | Standard_Integer IGESConvGeom::IncreaseCurveContinuity (const Handle(Geom_BSplineCurve)& res, |
171 | const Standard_Real epsgeom, |
172 | const Standard_Integer continuity) |
173 | { |
174 | if (continuity < 1) return continuity; |
175 | Standard_Boolean isC1 = Standard_True, isC2 = Standard_True; |
176 | Standard_Integer degree = res->Degree(); |
177 | |
178 | |
179 | Standard_Boolean isModified; |
180 | do { |
181 | isModified = Standard_False; |
182 | for (Standard_Integer i = res->FirstUKnotIndex()+1; i < res->LastUKnotIndex(); i++) |
183 | if(degree - res->Multiplicity(i) < continuity) { |
184 | if (continuity >= 2) { |
185 | if (!res->RemoveKnot(i, degree-2, epsgeom)) { |
186 | isC2 = Standard_False; |
187 | Standard_Boolean locOK = res->RemoveKnot(i, degree-1, epsgeom); // is C1 ? |
188 | isC1 &= locOK; |
189 | isModified |= locOK; |
190 | } |
191 | else |
192 | isModified = Standard_True; |
193 | } |
194 | else { |
195 | Standard_Boolean locOK = res->RemoveKnot(i, degree-1, epsgeom); // is C1 ? |
196 | isC1 &= locOK; |
197 | isModified |= locOK; |
198 | } |
199 | } |
200 | } |
201 | while (isModified); |
202 | |
203 | if (!isC1) return 0; |
204 | if (continuity >= 2 && !isC2) return 1; |
205 | return continuity; |
206 | } |
207 | |
208 | //======================================================================= |
209 | //function : IncreaseCurveContinuity |
210 | //purpose : |
211 | //======================================================================= |
212 | |
213 | Standard_Integer IGESConvGeom::IncreaseCurveContinuity (const Handle(Geom2d_BSplineCurve)& res, |
214 | const Standard_Real epsgeom, |
215 | const Standard_Integer continuity) |
216 | { |
217 | if (continuity < 1) return continuity; |
218 | Standard_Boolean isC1 = Standard_True, isC2 = Standard_True; |
219 | Standard_Integer degree = res->Degree(); |
220 | |
221 | Standard_Boolean isModified; |
222 | do { |
223 | isModified = Standard_False; |
224 | for (Standard_Integer i = res->FirstUKnotIndex()+1; i < res->LastUKnotIndex(); i++) |
225 | if(degree - res->Multiplicity(i) < continuity) { |
226 | if (continuity >= 2) { |
227 | if (!res->RemoveKnot(i, degree-2, epsgeom)) { |
228 | isC2 = Standard_False; |
229 | Standard_Boolean locOK = res->RemoveKnot(i, degree-1, epsgeom); // is C1 ? |
230 | isC1 &= locOK; |
231 | isModified |= locOK; |
232 | } |
233 | else |
234 | isModified = Standard_True; |
235 | } |
236 | else { |
237 | Standard_Boolean locOK = res->RemoveKnot(i, degree-1, epsgeom); // is C1 ? |
238 | isC1 &= locOK; |
239 | isModified |= locOK; |
240 | } |
241 | } |
242 | } |
243 | while (isModified); |
244 | |
245 | if (!isC1) return 0; |
246 | if (continuity >= 2 && !isC2) return 1; |
247 | return continuity; |
248 | } |
249 | |
250 | |
251 | //======================================================================= |
252 | //function : IGESConvGeom::SplineSurfaceFromIGES |
253 | //purpose : |
254 | //======================================================================= |
255 | Standard_Integer IGESConvGeom::SplineSurfaceFromIGES |
256 | (const Handle(IGESGeom_SplineSurface)& st, |
257 | const Standard_Real /*epscoef*/, const Standard_Real epsgeom, |
258 | Handle(Geom_BSplineSurface)& res) |
259 | { |
260 | Standard_Integer returned = 0; |
261 | Standard_Integer degree = st->BoundaryType(); |
262 | if (degree > 3) degree = 3; |
263 | Standard_Integer DegreeU = degree; |
264 | Standard_Integer DegreeV = degree; |
265 | |
266 | Standard_Integer NbUSeg = st->NbUSegments(); |
267 | Standard_Integer NbVSeg = st->NbVSegments(); |
268 | |
269 | if ((NbUSeg < 1) || (NbVSeg < 1)) return 5; |
270 | |
271 | // Output BSpline knots & multiplicities arraies for U & V : |
272 | // ========================================================= |
273 | |
274 | TColStd_Array1OfReal UKnot(1,NbUSeg+1); |
275 | TColStd_Array1OfReal VKnot(1,NbVSeg+1); |
276 | TColStd_Array1OfReal deltaU(1,NbUSeg); |
277 | TColStd_Array1OfReal deltaV(1,NbVSeg); |
278 | |
279 | Standard_Integer i; // svv Jan 10 2000 : porting on DEC |
280 | for (i=1; i <= NbUSeg+1; i++) |
281 | UKnot.SetValue(i, st->UBreakPoint(i)); |
282 | |
283 | for (i=1; i <= NbUSeg; i++) |
284 | deltaU.SetValue(i, st->UBreakPoint(i+1)- st->UBreakPoint(i)); |
285 | |
286 | for (i=1; i <= NbVSeg+1; i++) |
287 | VKnot.SetValue(i, st->VBreakPoint(i)); |
288 | |
289 | for (i=1; i <= NbVSeg; i++) |
290 | deltaV.SetValue(i, st->VBreakPoint(i+1)- st->VBreakPoint(i)); |
291 | |
292 | TColStd_Array1OfInteger UMult(1,NbUSeg+1); UMult.Init(DegreeU); |
293 | UMult.SetValue(UMult.Lower(),DegreeU+1); |
294 | UMult.SetValue(UMult.Upper(),DegreeU+1); |
295 | |
296 | TColStd_Array1OfInteger VMult(1,NbVSeg+1); VMult.Init(DegreeV); |
297 | VMult.SetValue(VMult.Lower(),DegreeV+1); |
298 | VMult.SetValue(VMult.Upper(),DegreeV+1); |
299 | |
300 | |
301 | // Poles computing |
302 | // =============== |
303 | |
304 | Standard_Integer NbUPoles = NbUSeg * DegreeU + 1; |
305 | Standard_Integer NbVPoles = NbVSeg * DegreeV + 1; |
306 | |
307 | TColgp_Array2OfPnt BsPole(1, NbUPoles, 1, NbVPoles); |
308 | |
309 | Standard_Integer iBs, jBs, iBz, jBz; |
310 | Standard_Boolean wasC0 = Standard_True; |
311 | |
312 | // Patch (1,1) |
313 | // =========== |
314 | Standard_Integer USeg, VSeg, j; |
315 | USeg = 1; |
316 | VSeg = 1; |
317 | |
318 | Handle(TColStd_HArray1OfReal) XPoly = st->XPolynomial(USeg, VSeg); |
319 | Handle(TColStd_HArray1OfReal) YPoly = st->YPolynomial(USeg, VSeg); |
320 | Handle(TColStd_HArray1OfReal) ZPoly = st->ZPolynomial(USeg, VSeg); |
321 | |
322 | TColgp_Array2OfPnt Coef(1, DegreeU+1, 1, DegreeV+1); |
323 | Standard_Real ParamU, ParamV; |
324 | ParamU = 1.; |
325 | for (i=1; i<=DegreeU+1; i++) { |
326 | ParamV = 1.; |
327 | for (j=1; j<=DegreeV+1; j++) { |
328 | Standard_Integer PolyIndex = i + 4*(j-1); |
329 | gp_Pnt aPoint(XPoly->Value(PolyIndex)*ParamU*ParamV, |
330 | YPoly->Value(PolyIndex)*ParamU*ParamV, |
331 | ZPoly->Value(PolyIndex)*ParamU*ParamV); |
332 | Coef.SetValue(i, j, aPoint); |
333 | ParamV = ParamV *deltaV(VSeg); |
334 | } |
335 | ParamU = ParamU * deltaU(USeg); |
336 | } |
337 | TColgp_Array2OfPnt BzPole(1, DegreeU+1, 1, DegreeV+1); |
338 | PLib::CoefficientsPoles(Coef,PLib::NoWeights2(),BzPole,PLib::NoWeights2()); |
339 | |
340 | iBs = BsPole.LowerRow(); |
341 | jBs = BsPole.LowerCol(); |
342 | |
343 | // Making output BSpline poles array : |
344 | for (iBz=BzPole.LowerRow(); iBz<=BzPole.UpperRow(); iBz++) { |
345 | for (jBz=BzPole.LowerCol(); jBz<=BzPole.UpperCol(); jBz++) |
346 | BsPole.SetValue(iBs, jBs++, BzPole.Value(iBz,jBz)); |
347 | jBs = BsPole.LowerCol(); |
348 | iBs++; |
349 | } |
350 | |
351 | |
352 | // Patches (1<USeg<NbUSeg, 1) |
353 | // ========================== |
354 | |
355 | VSeg = 1; |
356 | for (USeg=2; USeg<=NbUSeg; USeg++) { |
357 | XPoly = st->XPolynomial(USeg, VSeg); |
358 | YPoly = st->YPolynomial(USeg, VSeg); |
359 | ZPoly = st->ZPolynomial(USeg, VSeg); |
360 | Standard_Real ParamU, ParamV; |
361 | ParamU = 1.; |
362 | for (i=Coef.LowerRow(); i<=Coef.UpperRow(); i++) { |
363 | ParamV = 1.; |
364 | for (j=Coef.LowerCol(); j<=Coef.UpperCol(); j++) { |
365 | Standard_Integer PolyIndex = i + 4*(j-1); |
366 | gp_Pnt aPoint; |
367 | aPoint.SetCoord(XPoly->Value(PolyIndex)*ParamU*ParamV, |
368 | YPoly->Value(PolyIndex)*ParamU*ParamV, |
369 | ZPoly->Value(PolyIndex)*ParamU*ParamV); |
370 | Coef.SetValue(i, j, aPoint); |
371 | ParamV = ParamV *deltaV(VSeg); |
372 | } |
373 | ParamU = ParamU * deltaU(USeg); |
374 | } |
375 | PLib::CoefficientsPoles(Coef,PLib::NoWeights2(),BzPole,PLib::NoWeights2()); |
376 | |
377 | // C0 check and correction for poles lying on isoparametrics U=0 & V=0 |
378 | Standard_Integer iBs = BsPole.LowerRow() + (USeg-1)*DegreeU; |
379 | Standard_Integer jBs = BsPole.LowerCol(); |
380 | iBz = BzPole.LowerRow(); |
381 | for (jBz=BzPole.LowerCol(); jBz<=BzPole.UpperCol(); jBz++) { |
382 | if (!BzPole.Value(iBz,jBz).IsEqual(BsPole.Value(iBs,jBs), epsgeom)) { |
383 | wasC0=Standard_False; |
384 | gp_Pnt MidPoint; |
385 | Standard_Real XCoord = |
386 | 0.5 * (BzPole.Value(iBz,jBz).X() + BsPole.Value(iBs,jBs).X()); |
387 | Standard_Real YCoord = |
388 | 0.5 * (BzPole.Value(iBz,jBz).Y() + BsPole.Value(iBs,jBs).Y()); |
389 | Standard_Real ZCoord = |
390 | 0.5 * (BzPole.Value(iBz,jBz).Z() + BsPole.Value(iBs,jBs).Z()); |
391 | MidPoint.SetCoord(XCoord, YCoord, ZCoord); |
392 | BsPole.SetValue(iBs, jBs++, MidPoint); |
393 | } |
394 | else { |
395 | BsPole.SetValue(iBs, jBs++, BzPole.Value(iBz,jBz)); |
396 | } |
397 | } |
398 | |
399 | // Other poles (no check about C0) : |
400 | iBs++; |
401 | jBs = BsPole.LowerCol(); |
402 | for (iBz=BzPole.LowerRow()+1; iBz<=BzPole.UpperRow(); iBz++) { |
403 | for (jBz=BzPole.LowerCol(); jBz<=BzPole.UpperCol(); jBz++) |
404 | BsPole.SetValue(iBs, jBs++, BzPole.Value(iBz,jBz)); |
405 | iBs++; |
406 | jBs = BsPole.LowerCol(); |
407 | } |
408 | } |
409 | |
410 | |
411 | |
412 | // Patches (1, 1<VSeg<NbVSeg) |
413 | // ========================== |
414 | |
415 | USeg = 1; |
416 | for (VSeg=2; VSeg <= NbVSeg; VSeg++) { |
417 | XPoly = st->XPolynomial(USeg, VSeg); |
418 | YPoly = st->YPolynomial(USeg, VSeg); |
419 | ZPoly = st->ZPolynomial(USeg, VSeg); |
420 | Standard_Real ParamU, ParamV; |
421 | ParamU = 1.; |
422 | for (i=Coef.LowerRow(); i<=Coef.UpperRow(); i++) { |
423 | ParamV = 1.; |
424 | for (j=Coef.LowerCol(); j<=Coef.UpperCol(); j++) { |
425 | Standard_Integer PolyIndex = i + 4*(j-1); |
426 | gp_Pnt aPoint; |
427 | aPoint.SetCoord(XPoly->Value(PolyIndex)*ParamU*ParamV, |
428 | YPoly->Value(PolyIndex)*ParamU*ParamV, |
429 | ZPoly->Value(PolyIndex)*ParamU*ParamV); |
430 | Coef.SetValue(i, j, aPoint); |
431 | ParamV = ParamV *deltaV(VSeg); |
432 | } |
433 | ParamU = ParamU * deltaU(USeg); |
434 | } |
435 | PLib::CoefficientsPoles(Coef,PLib::NoWeights2(),BzPole,PLib::NoWeights2()); |
436 | |
437 | // C0 check and correction for poles lying on isoparametrics U=0 & V=0 |
438 | iBs = BsPole.LowerRow(); |
439 | jBs = BsPole.LowerCol() + (VSeg-1)*DegreeV; |
440 | jBz = BzPole.LowerCol(); |
441 | for (iBz=BzPole.LowerRow(); iBz<=BzPole.UpperRow(); iBz++) { |
442 | if (!BzPole.Value(iBz,jBz).IsEqual(BsPole.Value(iBs,jBs), epsgeom)) { |
443 | wasC0=Standard_False; |
444 | gp_Pnt MidPoint; |
445 | Standard_Real XCoord = 0.5 * |
446 | (BzPole.Value(iBz,jBz).X() + BsPole.Value(iBs,jBs).X()); |
447 | Standard_Real YCoord = 0.5 * |
448 | (BzPole.Value(iBz,jBz).Y() + BsPole.Value(iBs,jBs).Y()); |
449 | Standard_Real ZCoord = 0.5 * |
450 | (BzPole.Value(iBz,jBz).Z() + BsPole.Value(iBs,jBs).Z()); |
451 | MidPoint.SetCoord(XCoord, YCoord, ZCoord); |
452 | BsPole.SetValue(iBs++, jBs, MidPoint); |
453 | } |
454 | else{ |
455 | BsPole.SetValue(iBs++, jBs, BzPole.Value(iBz,jBz)); |
456 | } |
457 | } |
458 | |
459 | jBs++; |
460 | iBs = BsPole.LowerRow(); |
461 | for (jBz=BzPole.LowerCol()+1; jBz<=BzPole.UpperCol(); jBz++) { |
462 | for (iBz=BzPole.LowerRow(); iBz<=BzPole.UpperRow(); iBz++) |
463 | BsPole.SetValue(iBs++, jBs, BzPole.Value(iBz,jBz)); |
464 | iBs = BsPole.LowerRow(); |
465 | jBs++; |
466 | } |
467 | } |
468 | |
469 | |
470 | // Patches (1<USeg<NbUSeg, 1<VSeg<NbVSeg) |
471 | // ====================================== |
472 | |
473 | for (VSeg=2; VSeg <= NbVSeg; VSeg++) { |
474 | for (USeg=2; USeg <= NbUSeg; USeg++) { |
475 | XPoly = st->XPolynomial(USeg, VSeg); |
476 | YPoly = st->YPolynomial(USeg, VSeg); |
477 | ZPoly = st->ZPolynomial(USeg, VSeg); |
478 | Standard_Real ParamU, ParamV; |
479 | ParamU = 1.; |
480 | for (i=Coef.LowerRow(); i<=Coef.UpperRow(); i++) { |
481 | ParamV = 1.; |
482 | for (j=Coef.LowerCol(); j<=Coef.UpperCol(); j++) { |
483 | Standard_Integer PolyIndex = i + 4*(j-1); |
484 | gp_Pnt aPoint; |
485 | aPoint.SetCoord(XPoly->Value(PolyIndex)*ParamU*ParamV, |
486 | YPoly->Value(PolyIndex)*ParamU*ParamV, |
487 | ZPoly->Value(PolyIndex)*ParamU*ParamV); |
488 | Coef.SetValue(i, j, aPoint); |
489 | ParamV = ParamV *deltaV(VSeg); |
490 | } |
491 | ParamU = ParamU * deltaU(USeg); |
492 | } |
493 | PLib::CoefficientsPoles(Coef,PLib::NoWeights2(),BzPole,PLib::NoWeights2()); |
494 | |
495 | // C0 check and correction for poles lying on isoparametrics U=0 & V=0 |
496 | iBs = (USeg-1)*DegreeU + BsPole.LowerRow(); |
497 | jBs = (VSeg-1)*DegreeV + BsPole.LowerCol(); |
498 | jBz = BzPole.LowerCol(); |
499 | for (iBz=BzPole.LowerRow(); iBz<=BzPole.UpperRow(); iBz++) { |
500 | if (!BzPole.Value(iBz,jBz).IsEqual(BsPole.Value(iBs,jBs), epsgeom)) { |
501 | wasC0=Standard_False; |
502 | gp_Pnt MidPoint; |
503 | Standard_Real XCoord = 0.5 * |
504 | (BzPole.Value(iBz,jBz).X() + BsPole.Value(iBs,jBs).X()); |
505 | Standard_Real YCoord = 0.5 * |
506 | (BzPole.Value(iBz,jBz).Y() + BsPole.Value(iBs,jBs).Y()); |
507 | Standard_Real ZCoord = 0.5 * |
508 | (BzPole.Value(iBz,jBz).Z() + BsPole.Value(iBs,jBs).Z()); |
509 | MidPoint.SetCoord(XCoord, YCoord, ZCoord); |
510 | BsPole.SetValue(iBs++, jBs, MidPoint); |
511 | } |
512 | else |
513 | BsPole.SetValue(iBs++, jBs, BzPole.Value(iBz,jBz)); |
514 | } |
515 | |
516 | iBs = (USeg-1)*DegreeU + BsPole.LowerRow(); |
517 | iBz = BzPole.LowerRow(); |
518 | for (jBz=BzPole.LowerCol(); jBz<=BzPole.UpperCol(); jBz++) { |
519 | // C0 check and correction for poles lying on isoparametrics U=0 & V=0 |
520 | if (!BzPole.Value(iBz,jBz).IsEqual(BsPole.Value(iBs,jBs), epsgeom)) { |
521 | wasC0=Standard_False; |
522 | gp_Pnt MidPoint; |
523 | Standard_Real XCoord = 0.5 * |
524 | (BzPole.Value(iBz,jBz).X() + BsPole.Value(iBs,jBs).X()); |
525 | Standard_Real YCoord = 0.5 * |
526 | (BzPole.Value(iBz,jBz).Y() + BsPole.Value(iBs,jBs).Y()); |
527 | Standard_Real ZCoord = 0.5 * |
528 | (BzPole.Value(iBz,jBz).Z() + BsPole.Value(iBs,jBs).Z()); |
529 | MidPoint.SetCoord(XCoord, YCoord, ZCoord); |
530 | BsPole.SetValue(iBs, jBs++, MidPoint); |
531 | } |
532 | else |
533 | BsPole.SetValue(iBs, jBs++, BzPole.Value(iBz,jBz)); |
534 | } |
535 | |
536 | iBs = BsPole.LowerRow() + (USeg-1)*DegreeU + 1; |
537 | jBs = BsPole.LowerCol() + (VSeg-1)*DegreeV + 1; |
538 | for (iBz=BzPole.LowerRow()+1; iBz<=BzPole.UpperRow(); iBz++) { |
539 | for (jBz=BzPole.LowerCol()+1; jBz<=BzPole.UpperCol(); jBz++) |
540 | BsPole.SetValue(iBs, jBs++, BzPole.Value(iBz,jBz)); |
541 | jBs = BsPole.LowerCol() + (VSeg-1)*DegreeV + 1; |
542 | iBs++; |
543 | } |
544 | } |
545 | } |
546 | |
547 | // Building result taking into account transformation if any : |
548 | // =========================================================== |
549 | |
550 | if (st->HasTransf()) { |
551 | gp_GTrsf GSplTrsf(st->CompoundLocation()); |
552 | gp_Trsf SplTrsf; |
553 | Standard_Real epsilon = 1.E-04; |
554 | if (IGESData_ToolLocation::ConvertLocation(epsilon,GSplTrsf,SplTrsf)) |
555 | for (iBs=BsPole.LowerRow(); iBs<=BsPole.UpperRow(); iBs++) |
556 | for (jBs=BsPole.LowerCol(); jBs<=BsPole.UpperCol(); jBs++) |
557 | BsPole.SetValue(iBs, jBs, BsPole.Value(iBs,jBs).Transformed(SplTrsf)); |
558 | // else |
559 | // AddWarning(start, "Transformation skipped : Not a similarity"); |
560 | } |
561 | |
562 | res = new Geom_BSplineSurface |
563 | (BsPole, UKnot, VKnot, UMult, VMult, DegreeU, DegreeV); |
564 | if (wasC0) returned += 1; |
565 | return returned; |
566 | } |
567 | |
568 | |
569 | //======================================================================= |
570 | //function : IGESConvGeom::IncreaseSurfaceContinuity |
571 | //purpose : |
572 | //======================================================================= |
573 | Standard_Integer IGESConvGeom::IncreaseSurfaceContinuity (const Handle(Geom_BSplineSurface)& res, |
574 | const Standard_Real epsgeom, |
575 | const Standard_Integer continuity) |
576 | { |
577 | if (continuity < 1) return continuity; |
578 | Standard_Boolean isC1 = Standard_True, isC2 = Standard_True; |
579 | Standard_Integer i,j; |
580 | |
581 | i = res->LastUKnotIndex(); //knots.Upper(); |
582 | j = res->FirstUKnotIndex(); //knots.Lower(); |
583 | Standard_Integer DegreeU = res->UDegree(); |
584 | |
585 | Standard_Boolean isModified; |
586 | do { |
587 | isModified = Standard_False; |
588 | for (i = res->FirstUKnotIndex()+1; i < res->LastUKnotIndex(); i++) |
589 | if(DegreeU - res->UMultiplicity(i) < continuity) { |
590 | if (continuity >= 2) { |
591 | if (!res->RemoveUKnot(i, DegreeU-2, epsgeom)) { |
592 | isC2 = Standard_False; |
593 | Standard_Boolean locOK = res->RemoveUKnot(i, DegreeU-1, epsgeom); // is C1 ? |
594 | isC1 &= locOK; |
595 | isModified |= locOK; |
596 | } |
597 | else |
598 | isModified = Standard_True; |
599 | } |
600 | else { |
601 | Standard_Boolean locOK = res->RemoveUKnot(i, DegreeU-1, epsgeom); // is C1 ? |
602 | isC1 &= locOK; |
603 | isModified |= locOK; |
604 | } |
605 | } |
606 | } |
607 | while (isModified); |
608 | |
609 | Standard_Integer DegreeV = res->VDegree(); |
610 | do { |
611 | isModified = Standard_False; |
612 | for (i = res->FirstVKnotIndex()+1; i < res->LastVKnotIndex(); i++) |
613 | if(DegreeV - res->VMultiplicity(i) < continuity) { |
614 | if (continuity >= 2) { |
615 | if (!res->RemoveVKnot(i, DegreeV-2, epsgeom)) { |
616 | isC2 = Standard_False; |
617 | Standard_Boolean locOK = res->RemoveVKnot(i, DegreeV-1, epsgeom); // is C1 ? |
618 | isC1 &= locOK; |
619 | isModified |= locOK; |
620 | } |
621 | else |
622 | isModified = Standard_True; |
623 | } |
624 | else { |
625 | Standard_Boolean locOK = res->RemoveVKnot(i, DegreeV-1, epsgeom); // is C1 ? |
626 | isC1 &= locOK; |
627 | isModified |= locOK; |
628 | } |
629 | } |
630 | } |
631 | while (isModified); |
632 | |
633 | /* |
634 | while (--i > j) { // from 2 to NbKnots-1 |
635 | if (continuity >= 2) { |
636 | if (!res->RemoveUKnot(i, DegreeU-2, epsgeom)) { // is C2 ? |
637 | isC2 = Standard_False; |
638 | isC1 &= res->RemoveUKnot(i, DegreeU-1, epsgeom); // is C1 ? |
639 | } |
640 | } |
641 | else { |
642 | isC1 &= res->RemoveUKnot(i, DegreeU-1, epsgeom); // is C1 ? |
643 | } |
644 | } |
645 | |
646 | i = res->LastVKnotIndex(); //knots.Upper(); |
647 | j = res->FirstVKnotIndex(); //knots.Lower(); |
648 | Standard_Integer DegreeV = res->VDegree(); |
649 | while (--i > j) { // from 2 to NbKnots-1 |
650 | if (continuity >= 2) { |
651 | if (!res->RemoveVKnot(i, DegreeV-2, epsgeom)) { // is C2 ? |
652 | isC2 = Standard_False; |
653 | isC1 &= res->RemoveVKnot(i, DegreeV-1, epsgeom); // is C1 ? |
654 | } |
655 | } |
656 | else { |
657 | isC1 &= res->RemoveVKnot(i, DegreeV-1, epsgeom); // is C1 ? |
658 | } |
659 | }*/ |
660 | |
661 | |
662 | if (!isC1) return 0; |
663 | if (continuity >= 2 && !isC2) return 1; |
664 | return continuity; |
665 | } |
666 | |