54e37688 |
1 | // Created on: 1992-01-20 |
2 | // Created by: Remi GILET |
3 | // Copyright (c) 1992-1999 Matra Datavision |
4 | // Copyright (c) 1999-2014 OPEN CASCADE SAS |
5 | // |
6 | // This file is part of Open CASCADE Technology software library. |
7 | // |
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 |
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. |
13 | // |
14 | // Alternatively, this file may be used under the terms of Open CASCADE |
15 | // commercial license or contractual agreement. |
16 | |
54e37688 |
17 | |
42cf5bc1 |
18 | #include <Geom2dAdaptor_Curve.hxx> |
19 | #include <Geom2dGcc_CurveTool.hxx> |
20 | #include <Geom2dGcc_FunctionTanCirCu.hxx> |
21 | #include <gp_Circ2d.hxx> |
22 | #include <gp_Pnt.hxx> |
54e37688 |
23 | #include <gp_Pnt2d.hxx> |
24 | #include <gp_Vec.hxx> |
42cf5bc1 |
25 | #include <gp_Vec2d.hxx> |
54e37688 |
26 | |
27 | //========================================================================= |
28 | // soit P1 le point sur la courbe Geom2dAdaptor_Curve d abscisse u. + |
29 | // soit C le centre du cercle TheCirc. + |
30 | // Nous recherchons un point P2 appartenant au cercle tel que : + |
31 | // ---> --> + |
32 | // * P1P2 . CP2 = 0 + |
33 | // + |
34 | // * --> 2 2 + |
35 | // ||CP2|| = R + |
36 | // Nous cherchons donc les zeros de la fonction suivante: + |
37 | // --> --> 2 + |
38 | // --> 2 ( CP1 . T ) 2 + |
39 | // ||CP1|| - ----------- - R = F(u) + |
40 | // --> 2 + |
41 | // ||T|| + |
42 | // + |
43 | // La derivee de cette fonction est : + |
44 | // + |
45 | // 2*(CP1.T)(CP1.N) 2*(CP1.T)*(CP1.T)*T.N + |
46 | // f(u) = - ---------------- + --------------------- + |
47 | // T.T (T.T)*(T.T) + |
48 | //========================================================================= |
49 | // + |
50 | // skv: Small addition: The function and the derivative are normalized + |
51 | // by an average square distance between the circle + |
52 | // and the curve. + |
53 | //========================================================================= |
54e37688 |
54 | Geom2dGcc_FunctionTanCirCu:: |
55 | Geom2dGcc_FunctionTanCirCu(const gp_Circ2d& Circ , |
56 | const Geom2dAdaptor_Curve& Curv ) { |
57 | Curve = Curv; |
58 | TheCirc = Circ; |
59 | |
60 | // Modified by Sergey KHROMOV - Thu Apr 5 09:51:21 2001 Begin |
61 | Standard_Integer aNbSamp = Geom2dGcc_CurveTool::NbSamples(Curve); |
62 | Standard_Real aFirst = Geom2dGcc_CurveTool::FirstParameter(Curve); |
63 | Standard_Real aLast = Geom2dGcc_CurveTool::LastParameter(Curve); |
64 | Standard_Real aStep = (aLast - aFirst)/aNbSamp; |
65 | Standard_Real anX = aFirst + aStep/2.; |
66 | Standard_Integer aNbP = 0; |
67 | gp_XY aLoc(0., 0.); |
68 | |
69 | while (anX <= aLast) { |
70 | aLoc += (Geom2dGcc_CurveTool::Value(Curve, anX)).XY(); |
71 | anX += aStep; |
72 | aNbP++; |
73 | } |
74 | myWeight = Max((aLoc - TheCirc.Location().XY()).SquareModulus(), TheCirc.Radius()); |
75 | // Modified by Sergey KHROMOV - Thu Apr 5 09:51:25 2001 End |
76 | } |
77 | |
78 | |
79 | Standard_Boolean Geom2dGcc_FunctionTanCirCu:: |
80 | Value (const Standard_Real X , |
81 | Standard_Real& Fval ) { |
82 | gp_Pnt2d Point; |
83 | gp_Vec2d Vect1; |
84 | Geom2dGcc_CurveTool::D1(Curve,X,Point,Vect1); |
85 | Standard_Real NormeD1 = Vect1.Magnitude(); |
86 | gp_Vec2d TheDirection(TheCirc.Location(),Point); |
87 | Standard_Real squaredir = TheDirection.Dot(TheDirection); |
88 | Standard_Real R = TheCirc.Radius(); |
89 | Fval = squaredir-R*R- |
90 | (TheDirection.Dot(Vect1))*(TheDirection.Dot(Vect1))/(NormeD1*NormeD1); |
91 | // Modified by Sergey KHROMOV - Thu Apr 5 17:38:05 2001 Begin |
92 | Fval /= myWeight; |
93 | // Modified by Sergey KHROMOV - Thu Apr 5 17:38:06 2001 End |
94 | return Standard_True; |
95 | } |
96 | |
97 | Standard_Boolean Geom2dGcc_FunctionTanCirCu:: |
98 | Derivative (const Standard_Real X , |
99 | Standard_Real& Deriv ) { |
100 | gp_Pnt2d Point; |
101 | gp_Vec2d Vect1,Vect2; |
102 | Geom2dGcc_CurveTool::D2(Curve,X,Point,Vect1,Vect2); |
103 | Standard_Real NormeD1 = Vect1.SquareMagnitude(); |
104 | gp_Vec2d TheDirection(TheCirc.Location(),Point); |
105 | Standard_Real cp1dott = TheDirection.Dot(Vect1); |
106 | Deriv = -2.*(cp1dott/NormeD1)* |
107 | ((TheDirection.Dot(Vect2))-cp1dott*Vect1.Dot(Vect2)/NormeD1); |
108 | // Modified by Sergey KHROMOV - Thu Apr 5 17:38:15 2001 Begin |
109 | Deriv /= myWeight; |
110 | // Modified by Sergey KHROMOV - Thu Apr 5 17:38:15 2001 End |
111 | return Standard_True; |
112 | } |
113 | |
114 | Standard_Boolean Geom2dGcc_FunctionTanCirCu:: |
115 | Values (const Standard_Real X , |
116 | Standard_Real& Fval , |
117 | Standard_Real& Deriv ) { |
118 | gp_Pnt2d Point; |
119 | gp_Vec2d Vect1,Vect2; |
120 | Geom2dGcc_CurveTool::D2(Curve,X,Point,Vect1,Vect2); |
121 | Standard_Real NormeD1 = Vect1.SquareMagnitude(); |
122 | gp_Vec2d TheDirection(TheCirc.Location(),Point); |
123 | Standard_Real squaredir = TheDirection.SquareMagnitude(); |
124 | Standard_Real cp1dott = TheDirection.Dot(Vect1); |
125 | Standard_Real R = TheCirc.Radius(); |
126 | |
127 | Fval = squaredir-R*R-cp1dott*cp1dott/NormeD1; |
128 | // Modified by Sergey KHROMOV - Thu Apr 5 17:38:28 2001 Begin |
129 | Fval /= myWeight; |
130 | // Modified by Sergey KHROMOV - Thu Apr 5 17:38:28 2001 End |
131 | |
132 | Deriv = -2.*(cp1dott/NormeD1)* |
133 | ((TheDirection.Dot(Vect2))-cp1dott*Vect1.Dot(Vect2)/NormeD1); |
134 | // Modified by Sergey KHROMOV - Thu Apr 5 17:37:36 2001 Begin |
135 | Deriv /= myWeight; |
136 | // Modified by Sergey KHROMOV - Thu Apr 5 17:37:37 2001 End |
137 | return Standard_True; |
138 | } |