1 // Copyright (C) 2007-2008 CEA/DEN, EDF R&D
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License.
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 // Lesser General Public License for more details.
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
20 #include "InterpKernelException.hxx"
21 #include "EdgeArcCircle.hxx"
24 using namespace INTERP_KERNEL;
26 const double& Bounds::operator[](int i) const
39 throw Exception("internal error occurs !");
42 double &Bounds::operator[](int i)
55 throw Exception("internal error occurs !");
58 double Bounds::getDiagonal() const
60 double a=_x_max-_x_min;
61 double b=_y_max-_y_min;
66 * See Node::applySimilarity to see signification of params.
68 void Bounds::applySimilarity(double xBary, double yBary, double dimChar)
70 _x_min=(_x_min-xBary)/dimChar;
71 _x_max=(_x_max-xBary)/dimChar;
72 _y_min=(_y_min-yBary)/dimChar;
73 _y_max=(_y_max-yBary)/dimChar;
76 void Bounds::getBarycenter(double& xBary, double& yBary) const
78 xBary=(_x_min+_x_max)/2.;
79 yBary=(_y_max+_y_min)/2.;
82 void Bounds::prepareForAggregation()
84 _x_min=1e200; _x_max=-1e200; _y_min=1e200; _y_max=-1e200;
88 * Given an arc defined by 'center', 'radius' and 'intrcptArcDelta' in radian, returns (by outputs intrcptArcAngle0 and intrcptArcDelta)
89 * the intercepted angle of 'this' from 'center' point of view.
90 * If diagonal of 'this' is the same order of 2*radius, intrcptArcAngle0 and intrcptArcDelta remains unchanged.
91 * @param center IN parameter.
92 * @param radius IN parameter.
93 * @param intrcptArcAngle0 OUT parameter.
94 * @param intrcptArcDelta IN/OUT parameter.
96 void Bounds::getInterceptedArc(const double *center, double radius, double& intrcptArcAngle0, double& intrcptArcDelta) const
98 double diag=getDiagonal();
101 double v1[2],v2[2],w1[2],w2[2];
102 v1[0]=_x_min-center[0]; v1[1]=_y_max-center[1]; v2[0]=_x_max-center[0]; v2[1]=_y_min-center[1];
103 w1[0]=v1[0]; w1[1]=_y_min-center[1]; w2[0]=v2[0]; w2[1]=_y_max-center[1];
104 double delta1=EdgeArcCircle::safeAsin(v1[0]*v2[1]-v1[1]*v2[0]);
105 double delta2=EdgeArcCircle::safeAsin(w1[0]*w2[1]-w1[1]*w2[0]);
107 if(fabs(delta1)>fabs(delta2))
109 intrcptArcDelta=delta1;
110 intrcptArcAngle0=EdgeArcCircle::getAbsoluteAngle(v1,tmp);
114 intrcptArcDelta=delta2;
115 intrcptArcAngle0=EdgeArcCircle::getAbsoluteAngle(w1,tmp);
120 double Bounds::fitXForXFigD(double val, int res) const
122 double delta=std::max(_x_max-_x_min,_y_max-_y_min)/2.;
123 double ret=val-(_x_max+_x_min)/2.+delta;
124 delta=11.1375*res/(2.*delta);
128 double Bounds::fitYForXFigD(double val, int res) const
130 double delta=std::max(_x_max-_x_min,_y_max-_y_min)/2.;
131 double ret=val-(_y_max+_y_min)/2.+delta;
132 delta=11.1375*res/(2.*delta);
136 Bounds *Bounds::nearlyAmIIntersectingWith(const Bounds& other) const
138 if( (other._x_min > _x_max+QUADRATIC_PLANAR::_precision) || (other._x_max < _x_min-QUADRATIC_PLANAR::_precision) || (other._y_min > _y_max+QUADRATIC_PLANAR::_precision)
139 || (other._y_max < _y_min-QUADRATIC_PLANAR::_precision) )
141 if( (other._x_min >= _x_max ) || (other._x_max <= _x_min) || (other._y_min >= _y_max) || (other._y_max <= _y_min) )
142 return new Bounds(std::max(_x_min-QUADRATIC_PLANAR::_precision,other._x_min),
143 std::min(_x_max+QUADRATIC_PLANAR::_precision,other._x_max),
144 std::max(_y_min-QUADRATIC_PLANAR::_precision,other._y_min),
145 std::min(_y_max+QUADRATIC_PLANAR::_precision,other._y_max));//In approx cases.
147 return new Bounds(std::max(_x_min,other._x_min),std::min(_x_max,other._x_max),std::max(_y_min,other._y_min),std::min(_y_max,other._y_max));
150 Bounds *Bounds::amIIntersectingWith(const Bounds& other) const
152 if( (other._x_min > _x_max) || (other._x_max < _x_min) || (other._y_min > _y_max) || (other._y_max < _y_min) )
154 return new Bounds(std::max(_x_min,other._x_min),std::min(_x_max,other._x_max),std::max(_y_min,other._y_min),std::min(_y_max,other._y_max));
157 Position Bounds::where(double x, double y) const
159 if((x>=_x_min && x<=_x_max) && (y>=_y_min && y<=_y_max))
165 Position Bounds::nearlyWhere(double x, double y) const
167 bool thinX=Node::areDoubleEquals(_x_min,_x_max);
168 bool thinY=Node::areDoubleEquals(_y_min,_y_max);
171 if(Node::areDoubleEquals(x,_x_min) || Node::areDoubleEquals(x,_x_max) && (y<_y_max+QUADRATIC_PLANAR::_precision) && (y>_y_min-QUADRATIC_PLANAR::_precision))
172 return ON_BOUNDARY_POS;
175 if(!Node::areDoubleEquals(_x_min,x) && !Node::areDoubleEquals(_x_max,x))
179 if(Node::areDoubleEquals(y,_y_min) || Node::areDoubleEquals(y,_y_max) && (x<_x_max+QUADRATIC_PLANAR::_precision) && (x>_x_min-QUADRATIC_PLANAR::_precision))
180 return ON_BOUNDARY_POS;
183 if(!Node::areDoubleEquals(_y_min,y) && !Node::areDoubleEquals(_y_max,y))
186 return ON_BOUNDARY_POS;
187 if((x>=_x_min && x<=_x_max) && (y>=_y_min && y<=_y_max))
193 void Bounds::aggregate(const Bounds& other)
195 _x_min=std::min(_x_min,other._x_min); _x_max=std::max(_x_max,other._x_max);
196 _y_min=std::min(_y_min,other._y_min); _y_max=std::max(_y_max,other._y_max);