0022312: Translation of french commentaries in OCCT files
[occt.git] / src / GccAna / GccAna_Lin2dTanPer.cxx
1 // File GccAna_Lin2dTanPer.cxx, REG 08/07/91
2
3 //=========================================================================
4 //   CREATION of a STRAIGHT LINE TANGENT to a CIRCLE or PASSING by a POINT   +
5 //                      and ORTHOGONAL to a STRAIGHT LINE.                      +
6 //=========================================================================
7
8 #include <GccAna_Lin2dTanPer.ixx>
9
10 #include <ElCLib.hxx>
11 #include <StdFail_NotDone.hxx>
12 #include <gp_XY.hxx>
13 #include <gp_Dir2d.hxx>
14 #include <gp_Vec2d.hxx>
15 #include <gp_Circ2d.hxx>
16 #include <Standard_OutOfRange.hxx>
17 #include <GccEnt_BadQualifier.hxx>
18 #include <IntAna2d_AnaIntersection.hxx>
19 #include <IntAna2d_IntPoint.hxx>
20
21 //=========================================================================
22 //   Straight line passing by point  : ThePoint and                       +
23 //       orthogonal to straight line : TheLin.                            +
24 //   Create the straight line of origin     : ThePoint                           +
25 //                  and direction  : TheLin.Direction() turned by 90   +
26 //=========================================================================
27
28 GccAna_Lin2dTanPer::
29    GccAna_Lin2dTanPer (const gp_Pnt2d& ThePnt    ,
30                        const gp_Lin2d& TheLin    ):
31    linsol(1,1),
32    qualifier1(1,1) ,
33    pnttg1sol(1,1),
34    pntint2sol(1,1),
35    par1sol(1,1),
36    par2sol(1,1),
37    pararg1(1,1),
38    pararg2(1,1)
39 {
40
41    linsol(1) = gp_Lin2d(ThePnt,gp_Dir2d(-(TheLin.Direction().Y()),
42 // ===============================================================
43                                         TheLin.Direction().X()));
44 //                                      ========================
45    pnttg1sol(1) = ThePnt;
46    IntAna2d_AnaIntersection Intp(linsol(1),TheLin);
47    if (Intp.IsDone()) {
48      if (!Intp.IsEmpty()) {
49        for (Standard_Integer i = 1 ; i <= Intp.NbPoints() ; i++) {
50          pntint2sol(1) = Intp.Point(i).Value();
51        }
52      }
53    }
54    par1sol(1) = ElCLib::Parameter(linsol(1),pnttg1sol(1));
55    par2sol(1) = ElCLib::Parameter(linsol(1),pntint2sol(1));
56    pararg1(1) = 0.;
57    pararg2(1) = ElCLib::Parameter(TheLin,pntint2sol(1));
58    NbrSol = 1;
59    WellDone = Standard_True;
60  }
61
62 //=========================================================================
63 //   Straight line passing by point      : ThePnt                             +
64 //       and orthogonal to circle        : TheCircle.                         +
65 //   Create the straight line of origin  : ThePoint                           +
66 //                  and direction        : (TheCircle.Location(),ThePnt).     +
67 //=========================================================================
68
69 GccAna_Lin2dTanPer::
70    GccAna_Lin2dTanPer (const gp_Pnt2d&  ThePnt    ,
71                        const gp_Circ2d& TheCircle ):
72    linsol(1,1),
73    qualifier1(1,1) ,
74    pnttg1sol(1,1),
75    pntint2sol(1,1),
76    par1sol(1,1),
77    par2sol(1,1),
78    pararg1(1,1),
79    pararg2(1,1)
80 {
81
82    linsol(1) = gp_Lin2d(ThePnt,
83 // ============================
84                         gp_Dir2d(TheCircle.Location().XY()-ThePnt.XY()));
85 //                      ================================================
86    pnttg1sol(1) = ThePnt;
87    IntAna2d_AnaIntersection Intp(linsol(1),TheCircle);
88    if (Intp.IsDone()) {
89      if (!Intp.IsEmpty()) {
90        Standard_Real maxdist = RealLast();
91        for (Standard_Integer i = 1 ; i <= Intp.NbPoints() ; i++) {
92          if (Intp.Point(i).Value().Distance(ThePnt) < maxdist) {
93            pntint2sol(1) = Intp.Point(i).Value();
94          }
95        }
96      }
97    }
98    par1sol(1) = ElCLib::Parameter(linsol(1),pnttg1sol(1));
99    par2sol(1) = ElCLib::Parameter(linsol(1),pntint2sol(1));
100    pararg1(1) = 0.;
101    pararg2(1) = ElCLib::Parameter(TheCircle,pntint2sol(1));
102    NbrSol = 1;
103    WellDone = Standard_True;
104  }
105
106 //=========================================================================
107 //   Straight line tangent to circle     : Qualified1 (C1)                    +
108 //   and orthogonal to straight line     : TheLin.                            +
109 //   Create straight line of origin      : P1 (on C1)                         +
110 //                  and direction        : TheLin.Direction() turned by 90`   +
111 //=========================================================================
112
113 GccAna_Lin2dTanPer::
114    GccAna_Lin2dTanPer (const GccEnt_QualifiedCirc& Qualified1,
115                        const gp_Lin2d&             TheLin    ):
116    linsol(1,2),
117    qualifier1(1,2) ,
118    pnttg1sol(1,2),
119    pntint2sol(1,2),
120    par1sol(1,2),
121    par2sol(1,2),
122    pararg1(1,2),
123    pararg2(1,2)
124 {
125
126    WellDone = Standard_False;
127    Standard_Integer nbsol = 0;
128    Standard_Integer signe = 0;
129    NbrSol = 0;
130    gp_Circ2d C1 = Qualified1.Qualified();
131
132    if (Qualified1.IsEnclosed()) {
133 // ============================
134      GccEnt_BadQualifier::Raise();
135    }
136    else if (Qualified1.IsEnclosing()) {
137 // ==================================
138      nbsol = 1;
139      signe = -1;
140    }
141    else if (Qualified1.IsOutside()) {
142 // ================================
143      nbsol = 1;
144      signe = 1;
145    }
146    else {
147      nbsol = 2;
148      signe = -1;
149    }
150    gp_XY xy(C1.Radius()*TheLin.Direction().XY());
151    for (Standard_Integer j = 1 ; j <= nbsol ; j++) {
152      signe = -signe;
153      NbrSol++;
154      linsol(NbrSol)=gp_Lin2d(gp_Pnt2d((C1.Location().XY()).Added(signe*xy)),
155 //   =======================================================================
156                              gp_Dir2d(-TheLin.Direction().Y(),
157 //                           =================================
158                                       TheLin.Direction().X()));
159 //                                    ========================
160      pnttg1sol(NbrSol) = gp_Pnt2d((C1.Location().XY()).Added(signe*xy));
161      IntAna2d_AnaIntersection Intp(linsol(NbrSol),TheLin);
162      if (Intp.IsDone()) {
163        if (!Intp.IsEmpty()) {
164          for (Standard_Integer i = 1 ; i <= Intp.NbPoints() ; i++) {
165            pntint2sol(NbrSol) = Intp.Point(i).Value();
166          }
167        }
168      }
169      par1sol(NbrSol) = ElCLib::Parameter(linsol(NbrSol),pnttg1sol(NbrSol));
170      par2sol(NbrSol) = ElCLib::Parameter(linsol(NbrSol),pntint2sol(NbrSol));
171      pararg1(NbrSol) = ElCLib::Parameter(C1,pnttg1sol(NbrSol));
172      pararg2(NbrSol) = ElCLib::Parameter(TheLin,pntint2sol(NbrSol));
173      WellDone = Standard_True;
174    }
175  }
176
177 //=========================================================================
178 //   Straight line tangent to circle     : Qualified1 (C1)                    +
179 //       and orthogonal to circle        : TheCircle.                         +
180 //   Create straight line of origin      : P1 (on C1)                         +
181 //                  and direction        : TheLin.Direction() turned by 90`   +
182 //=========================================================================
183
184 GccAna_Lin2dTanPer::
185    GccAna_Lin2dTanPer (const GccEnt_QualifiedCirc& Qualified1,
186                        const gp_Circ2d&            TheCircle ):
187    linsol(1,2),
188    qualifier1(1,2) ,
189    pnttg1sol(1,2),
190    pntint2sol(1,2),
191    par1sol(1,2),
192    par2sol(1,2),
193    pararg1(1,2),
194    pararg2(1,2)
195 {
196
197    WellDone = Standard_False;
198    NbrSol = 0;
199    Standard_Integer nbsol = 0;
200    Standard_Integer signe = 0;
201    gp_Circ2d C1 = Qualified1.Qualified();
202
203    if (Qualified1.IsEnclosed()) {
204 // ============================
205      GccEnt_BadQualifier::Raise();
206    }
207    else if (Qualified1.IsEnclosing()) {
208 // ==================================
209      nbsol = 1;
210      signe = -1;
211      qualifier1(1) = GccEnt_enclosing;
212    }
213    else if (Qualified1.IsOutside()) {
214 // ================================
215      nbsol = 1;
216      signe = 1;
217      qualifier1(1) = GccEnt_outside;
218    }
219    else if (Qualified1.IsUnqualified()) {
220 // ====================================
221      nbsol = 2;
222      signe = -1;
223      qualifier1(1) = GccEnt_enclosing;
224      qualifier1(2) = GccEnt_outside;
225    }
226    for (Standard_Integer j = 1 ; j <= 2 ; j++) {
227      NbrSol++;
228      signe = -signe;
229      gp_Dir2d D1(TheCircle.Location().XY()-C1.Location().XY());
230      linsol(NbrSol) = gp_Lin2d(gp_Pnt2d((C1.Location().XY())+
231 //   ===================================================
232                        signe*(D1.XY()*C1.Radius())),gp_Dir2d(-D1.Y(),D1.X()));
233 //                     ======================================================
234      pnttg1sol(NbrSol) = gp_Pnt2d((C1.Location().XY())+
235                                   signe*(D1.XY()*C1.Radius()));
236      IntAna2d_AnaIntersection Intp(linsol(NbrSol),TheCircle);
237      if (Intp.IsDone()) {
238        if (!Intp.IsEmpty()) {
239          Standard_Real maxdist = RealLast();
240          for (Standard_Integer i = 1 ; i <= Intp.NbPoints() ; i++) {
241            if (Intp.Point(i).Value().Distance(pnttg1sol(NbrSol)) < maxdist) {
242              pntint2sol(NbrSol) = Intp.Point(i).Value();
243            }
244          }
245        }
246      }
247      par1sol(NbrSol) = ElCLib::Parameter(linsol(NbrSol),pnttg1sol(NbrSol));
248      par2sol(NbrSol) = ElCLib::Parameter(linsol(NbrSol),pntint2sol(NbrSol));
249      pararg1(NbrSol) = ElCLib::Parameter(C1,pnttg1sol(NbrSol));
250      pararg2(NbrSol) = ElCLib::Parameter(TheCircle,pntint2sol(NbrSol));
251      WellDone = Standard_True;
252    }
253  }
254
255 Standard_Boolean GccAna_Lin2dTanPer::
256    IsDone () const { return WellDone; }
257
258 Standard_Integer GccAna_Lin2dTanPer::
259    NbSolutions () const 
260 {
261   if (!WellDone) { StdFail_NotDone::Raise(); } 
262   return NbrSol;
263 }
264
265 gp_Lin2d GccAna_Lin2dTanPer::
266    ThisSolution (const Standard_Integer Index) const 
267 {
268   if (!WellDone) { StdFail_NotDone::Raise(); } 
269   if (Index <= 0 || Index > NbrSol) { Standard_RangeError::Raise(); }
270   return linsol(Index);
271 }
272
273 void GccAna_Lin2dTanPer::
274   WhichQualifier(const Standard_Integer Index   ,
275                        GccEnt_Position& Qualif1 ) const
276 {
277   if (!WellDone) { StdFail_NotDone::Raise(); }
278   if (Index <= 0 ||Index > NbrSol) { Standard_OutOfRange::Raise(); }
279   else {
280     Qualif1 = qualifier1(Index);
281   }
282 }
283
284 void GccAna_Lin2dTanPer::
285    Tangency1 (const Standard_Integer Index,
286               Standard_Real& ParSol,
287               Standard_Real& ParArg,
288               gp_Pnt2d& Pnt) const{
289    if (!WellDone) { StdFail_NotDone::Raise(); }
290    else if (Index <= 0 ||Index > NbrSol) { Standard_OutOfRange::Raise(); }
291    else {
292      ParSol = par1sol(Index);
293      ParArg = pararg1(Index);
294      Pnt    = gp_Pnt2d(pnttg1sol(Index));
295    }
296  }
297
298 void GccAna_Lin2dTanPer::
299    Intersection2 (const Standard_Integer Index,
300                   Standard_Real& ParSol,
301                   Standard_Real& ParArg,
302                   gp_Pnt2d& PntSol) const {
303    if (!WellDone) { StdFail_NotDone::Raise(); }
304    else if (Index <= 0 ||Index > NbrSol) { Standard_OutOfRange::Raise(); }
305    else {
306      ParSol = par2sol(Index);
307      ParArg = pararg2(Index);
308      PntSol = gp_Pnt2d(pntint2sol(Index));
309    }
310  }
311