Commit | Line | Data |
---|---|---|
b311480e | 1 | // Created on: 1991-10-07 |
2 | // Created by: Remi GILET | |
3 | // Copyright (c) 1991-1999 Matra Datavision | |
973c2be1 | 4 | // Copyright (c) 1999-2014 OPEN CASCADE SAS |
b311480e | 5 | // |
973c2be1 | 6 | // This file is part of Open CASCADE Technology software library. |
b311480e | 7 | // |
d5f74e42 | 8 | // This library is free software; you can redistribute it and/or modify it under |
9 | // the terms of the GNU Lesser General Public License version 2.1 as published | |
973c2be1 | 10 | // by the Free Software Foundation, with special exception defined in the file |
11 | // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT | |
12 | // distribution for complete text of the license and disclaimer of any warranty. | |
b311480e | 13 | // |
973c2be1 | 14 | // Alternatively, this file may be used under the terms of Open CASCADE |
15 | // commercial license or contractual agreement. | |
7fd59977 | 16 | |
17 | //========================================================================= | |
0d969553 | 18 | // CREATION of the BISSECTICE between two CIRCLES. + |
7fd59977 | 19 | //========================================================================= |
20 | ||
42cf5bc1 | 21 | #include <GccAna_Circ2dBisec.hxx> |
22 | #include <GccEnt_BadQualifier.hxx> | |
23 | #include <GccInt_BCirc.hxx> | |
24 | #include <GccInt_BElips.hxx> | |
25 | #include <GccInt_BHyper.hxx> | |
26 | #include <GccInt_Bisec.hxx> | |
27 | #include <GccInt_BLine.hxx> | |
28 | #include <GccInt_BParab.hxx> | |
29 | #include <gp.hxx> | |
7fd59977 | 30 | #include <gp_Circ2d.hxx> |
42cf5bc1 | 31 | #include <gp_Dir2d.hxx> |
7fd59977 | 32 | #include <gp_Hypr2d.hxx> |
42cf5bc1 | 33 | #include <gp_Vec2d.hxx> |
34 | #include <gp_XY.hxx> | |
35 | #include <IntAna2d_AnaIntersection.hxx> | |
36 | #include <Precision.hxx> | |
7fd59977 | 37 | #include <Standard_ConstructionError.hxx> |
38 | #include <Standard_OutOfRange.hxx> | |
7fd59977 | 39 | #include <StdFail_NotDone.hxx> |
7fd59977 | 40 | |
42cf5bc1 | 41 | //========================================================================= |
7fd59977 | 42 | GccAna_Circ2dBisec:: |
43 | GccAna_Circ2dBisec (const gp_Circ2d& Circ1 , | |
44 | const gp_Circ2d& Circ2 ) { | |
45 | ||
46 | //========================================================================= | |
0d969553 Y |
47 | // Initialization of fields : + |
48 | // - circle1 (Circle : first argument.) + | |
49 | // - circle2 (Line : second argument.) + | |
50 | // - intersection (Integer showing the smallest position + | |
51 | // of two circles correspondingly to each other.) + | |
52 | // - sameradius (Booleen showing if the two circles have + | |
53 | // the same radius or not.) + | |
54 | // - NbrSol (Integer showing the number of solutions.) + | |
55 | // - WellDone (Boolean showing succes or failure of the algo.). + | |
7fd59977 | 56 | //========================================================================= |
57 | ||
58 | WellDone = Standard_False; | |
59 | Standard_Real Tol=Precision::Confusion(); | |
60 | ||
61 | Standard_Real R1 = Circ1.Radius(); | |
62 | Standard_Real R2 = Circ2.Radius(); | |
63 | if (Abs(R1-R2) <= Tol) { sameradius = Standard_True; } | |
64 | else { sameradius = Standard_False; } | |
65 | if (R1 < R2) { | |
66 | circle1 = gp_Circ2d(Circ2); | |
67 | circle2 = gp_Circ2d(Circ1); | |
68 | R1 = circle1.Radius(); | |
69 | R2 = circle2.Radius(); | |
70 | } | |
71 | else { | |
72 | circle1 = gp_Circ2d(Circ1); | |
73 | circle2 = gp_Circ2d(Circ2); | |
74 | } | |
75 | Standard_Real dist = circle2.Location().Distance(circle1.Location()); | |
76 | if (R1-dist-R2 > Tol) { | |
77 | intersection = 0; | |
78 | NbrSol = 2; | |
79 | WellDone = Standard_True; | |
80 | } | |
81 | else if (Abs(R1-dist-R2) <= Tol) { | |
82 | intersection = 1; | |
83 | if (sameradius) { | |
84 | NbrSol = 0; | |
85 | WellDone = Standard_True; | |
86 | } | |
87 | else { | |
88 | NbrSol = 2; | |
89 | WellDone = Standard_True; | |
90 | } | |
91 | } | |
92 | else if ((dist+R2-R1 > Tol) && (R1-dist+R2 > Tol)) { | |
93 | intersection = 2; | |
94 | if (sameradius) { | |
95 | NbrSol = 2; | |
96 | WellDone = Standard_True; | |
97 | } | |
98 | else { | |
99 | NbrSol = 3; | |
100 | WellDone = Standard_True; | |
101 | } | |
102 | } | |
103 | else if (Abs(R1-dist+R2) <= Tol) { | |
104 | intersection = 3; | |
105 | if (sameradius) { | |
106 | NbrSol = 2; | |
107 | WellDone = Standard_True; | |
108 | } | |
109 | else { | |
110 | NbrSol = 3; | |
111 | WellDone = Standard_True; | |
112 | } | |
113 | } | |
114 | else { | |
115 | intersection = 4; | |
116 | if (sameradius) { | |
117 | NbrSol = 3; | |
118 | WellDone = Standard_True; | |
119 | } | |
120 | else { | |
121 | NbrSol = 4; | |
122 | WellDone = Standard_True; | |
123 | } | |
124 | } | |
125 | } | |
126 | ||
127 | //========================================================================= | |
0d969553 Y |
128 | // Processing. + |
129 | // Return the coordinates of centers of circles circle1 and circle2 + | |
7fd59977 | 130 | // (xcencir1, ycencir1, xcencir2, ycencir2). + |
0d969553 | 131 | // Also return the radiuses of two circles R1 and R2. + |
7fd59977 | 132 | //========================================================================= |
133 | ||
134 | Handle(GccInt_Bisec) GccAna_Circ2dBisec:: | |
135 | ThisSolution (const Standard_Integer Index) const { | |
136 | ||
137 | Standard_Real Tol = 1.e-14; | |
138 | Handle(GccInt_Bisec) bissol; | |
139 | ||
9775fa61 | 140 | if (!WellDone) { throw StdFail_NotDone(); } |
141 | else if (Index <= 0 || Index > NbrSol) { throw Standard_OutOfRange(); } | |
7fd59977 | 142 | else { |
143 | Standard_Real xcencir1 = circle1.Location().X(); | |
144 | Standard_Real ycencir1 = circle1.Location().Y(); | |
145 | Standard_Real xcencir2 = circle2.Location().X(); | |
146 | Standard_Real ycencir2 = circle2.Location().Y(); | |
147 | Standard_Real dist = circle1.Location().Distance(circle2.Location()); | |
148 | ||
149 | gp_Pnt2d pcen((xcencir1+xcencir2)/2.0,(ycencir1+ycencir2)/2.0); | |
150 | gp_Dir2d dircen,medcen; | |
151 | if (dist > Tol) { | |
152 | dircen.SetCoord(xcencir2-xcencir1,ycencir2-ycencir1); | |
153 | medcen.SetCoord(ycencir2-ycencir1,xcencir1-xcencir2); | |
154 | } | |
155 | gp_Dir2d dirx(1.0,0.0); | |
156 | gp_Ax2d acenx(pcen,dirx); | |
157 | gp_Ax2d acencen(pcen,dircen); | |
158 | ||
159 | Standard_Real R1 = circle1.Radius(); | |
160 | Standard_Real R2 = circle2.Radius(); | |
161 | ||
162 | if ((NbrSol == 1) && (intersection == 0)) { | |
163 | Standard_Real R; | |
164 | if (Index == 1) | |
165 | R = (R1+R2)/2.0; | |
166 | else | |
167 | R = (R1-R2)/2.0; | |
168 | gp_Circ2d C(acenx,R); | |
169 | bissol = new GccInt_BCirc(C); | |
170 | // ============================= | |
171 | } | |
172 | else if ((NbrSol == 2) && (intersection == 1)) { | |
173 | if (Index == 1) { | |
174 | gp_Elips2d E(acencen, | |
175 | (R1+R2)/2.0,Sqrt((R1*R1+R2*R2-dist*dist)/4.+R1*R2/2.)); | |
176 | bissol = new GccInt_BElips(E); | |
177 | // ============================= | |
178 | } | |
179 | else if (Index == 2) { | |
180 | gp_Lin2d L(circle1.Location(), | |
181 | dircen); | |
182 | bissol = new GccInt_BLine(L); | |
183 | // ============================= | |
184 | } | |
185 | } | |
186 | else if ((NbrSol == 2) && (intersection == 0)) { | |
187 | if (Index == 1) { | |
188 | if (Abs(xcencir2-xcencir1)<Tol && Abs(ycencir2-ycencir1)< Tol) { | |
189 | gp_Circ2d C(acenx,(R1+R2)/2.0); | |
190 | bissol = new GccInt_BCirc(C); | |
191 | // ============================= | |
192 | } | |
193 | else { | |
194 | gp_Elips2d E(acencen, | |
195 | (R1+R2)/2.0,Sqrt((R1*R1+R2*R2-dist*dist)/4.+R1*R2/2.)); | |
196 | bissol = new GccInt_BElips(E); | |
197 | // ============================== | |
198 | } | |
199 | } | |
200 | else if (Index == 2) { | |
201 | if (Abs(xcencir2-xcencir1)< Tol && Abs(ycencir2-ycencir1)< Tol) { | |
202 | gp_Circ2d C(acencen,(R1-R2)/2.); | |
203 | bissol = new GccInt_BCirc(C); | |
204 | // ============================= | |
205 | } | |
206 | else { | |
207 | gp_Elips2d E(acencen, | |
208 | (R1-R2)/2.0,Sqrt((R1*R1+R2*R2-dist*dist)/4.-R1*R2/2.)); | |
209 | bissol = new GccInt_BElips(E); | |
210 | // ============================== | |
211 | } | |
212 | } | |
213 | } | |
214 | else if (intersection == 2) { | |
215 | if (sameradius) { | |
216 | if (Index == 1) { | |
217 | gp_Lin2d L(pcen,medcen); | |
218 | bissol = new GccInt_BLine(L); | |
219 | // ============================= | |
220 | } | |
221 | else if (Index == 2) { | |
222 | gp_Elips2d E(acencen, | |
223 | R1,Sqrt(R1*R1-dist*dist/4.0)); | |
224 | bissol = new GccInt_BElips(E); | |
225 | // ============================== | |
226 | } | |
227 | } | |
228 | else { | |
229 | if (Index == 1) { | |
230 | gp_Hypr2d H1; | |
231 | H1 = gp_Hypr2d(acencen, | |
232 | (R1-R2)/2.0,Sqrt(dist*dist-(R1-R2)*(R1-R2))/2.0); | |
233 | bissol = new GccInt_BHyper(H1); | |
234 | // =============================== | |
235 | } | |
236 | else if (Index == 2) { | |
237 | gp_Hypr2d H1(acencen, | |
238 | (R1-R2)/2.0,Sqrt(dist*dist-(R1-R2)*(R1-R2))/2.0); | |
239 | bissol = new GccInt_BHyper(H1.OtherBranch()); | |
240 | // =============================== | |
241 | } | |
242 | else if (Index == 3) { | |
243 | gp_Elips2d E(acencen, | |
244 | (R1+R2)/2.0,Sqrt((R1*R1+R2*R2-dist*dist)/4.+R1*R2/2.)); | |
245 | bissol = new GccInt_BElips(E); | |
246 | // ============================== | |
247 | } | |
248 | } | |
249 | } | |
250 | else if (intersection == 3) { | |
251 | if (sameradius) { | |
252 | if (Index == 1) { | |
253 | gp_Lin2d L(pcen, dircen); | |
254 | bissol = new GccInt_BLine(L); | |
255 | // ============================= | |
256 | } | |
257 | else if (Index == 2) { | |
258 | gp_Lin2d L(pcen, medcen); | |
259 | bissol = new GccInt_BLine(L); | |
260 | // ============================= | |
261 | } | |
262 | } | |
263 | else { | |
264 | if (Index == 1) { | |
265 | gp_Lin2d L(pcen, dircen); | |
266 | bissol = new GccInt_BLine(L); | |
267 | // ============================= | |
268 | } | |
269 | else if (Index == 2) { | |
270 | gp_Hypr2d H1(acencen, | |
271 | (R1-R2)/2.0,Sqrt(dist*dist-(R1-R2)*(R1-R2))/2.0); | |
272 | bissol = new GccInt_BHyper(H1); | |
273 | // =============================== | |
274 | } | |
275 | else if (Index == 3) { | |
276 | gp_Hypr2d H1(acencen, | |
277 | (R1-R2)/2.0,Sqrt(dist*dist-(R1-R2)*(R1-R2))/2.0); | |
278 | bissol = new GccInt_BHyper(H1.OtherBranch()); | |
279 | // =============================== | |
280 | } | |
281 | } | |
282 | } | |
283 | else if (intersection == 4) { | |
284 | if (sameradius) { | |
285 | if (Index == 1) { | |
286 | gp_Lin2d L(pcen,medcen); | |
287 | bissol = new GccInt_BLine(L); | |
288 | // ============================= | |
289 | } | |
290 | else if (Index == 2) { | |
291 | gp_Hypr2d H1(acencen,R1,Sqrt(dist*dist-4*R1*R1)/2.0); | |
292 | bissol = new GccInt_BHyper(H1); | |
293 | // =============================== | |
294 | } | |
295 | else if (Index == 3) { | |
296 | gp_Hypr2d H1(acencen,R1,Sqrt(dist*dist-4*R1*R1)/2.0); | |
297 | bissol = new GccInt_BHyper(H1.OtherBranch()); | |
298 | // =============================== | |
299 | } | |
300 | } | |
301 | else { | |
302 | if (Index == 1) { | |
303 | gp_Hypr2d H1(acencen, | |
304 | (R1-R2)/2.0,Sqrt(dist*dist-(R1-R2)*(R1-R2))/2.0); | |
305 | bissol = new GccInt_BHyper(H1); | |
306 | // =============================== | |
307 | } | |
308 | else if (Index == 2) { | |
309 | gp_Hypr2d H1(acencen, | |
310 | (R1-R2)/2.0,Sqrt(dist*dist-(R1-R2)*(R1-R2))/2.0); | |
311 | bissol = new GccInt_BHyper(H1.OtherBranch()); | |
312 | // =============================== | |
313 | } | |
314 | else if (Index == 3) { | |
315 | gp_Hypr2d H1(acencen, | |
316 | (R1+R2)/2.0,Sqrt(dist*dist-(R1+R2)*(R1+R2))/2.0); | |
317 | bissol = new GccInt_BHyper(H1); | |
318 | // =============================== | |
319 | } | |
320 | else if (Index == 4) { | |
321 | gp_Hypr2d H1(acencen, | |
322 | (R1+R2)/2.0,Sqrt(dist*dist-(R1+R2)*(R1+R2))/2.0); | |
323 | bissol = new GccInt_BHyper(H1.OtherBranch()); | |
324 | // =============================== | |
325 | } | |
326 | } | |
327 | } | |
328 | } | |
329 | return bissol; | |
330 | } | |
331 | ||
332 | //========================================================================= | |
333 | ||
334 | Standard_Boolean GccAna_Circ2dBisec:: | |
335 | IsDone () const { return WellDone; } | |
336 | ||
337 | Standard_Integer GccAna_Circ2dBisec::NbSolutions () const | |
338 | { | |
9775fa61 | 339 | if (!WellDone) throw StdFail_NotDone(); |
7fd59977 | 340 | |
341 | return NbrSol; | |
342 | } |