Functions | |
template<class OUTPUTTYPE> | |
unsigned int | SolveQuadraticEquation (const double a, const double b, const double c, OUTPUTTYPE out) |
Solve the quadratic equation: a*x*x + b*x + c = 0;. | |
template<class OUTPUTTYPE, class aPoint, class aVector> | |
unsigned int | LineIntersectsTheSphere (const aPoint &point, const aVector &vect, const double radius, OUTPUTTYPE out) |
find intersection ticks for the line parametrized as Point + Vector * Tick with sphere of radius Radius | |
template<class OUTPUTTYPE, class aPoint, class aVector> | |
unsigned int | LineIntersectsTheSphere2 (const aPoint &point, const aVector &vect, const double r2, OUTPUTTYPE out) |
find intersection ticks for the line parametrized as Point + Vector * Tick with sphere of radius Radius | |
template<class OUTPUTTYPE, class aPoint, class aVector> | |
unsigned int | LineIntersectsTheCylinder (const aPoint &point, const aVector &vect, const double radius, OUTPUTTYPE out) |
find intersection ticks for the line parametrized as Point + Vector * Tick with cylinder of radius Radius | |
template<class OUTPUTTYPE, class aPoint, class aVector> | |
unsigned int | LineIntersectsTheX (const aPoint &point, const aVector &vect, const double X, OUTPUTTYPE out) |
find intersection ticks for the line parametrized as Point + Vector * Tick with x-plane x=X | |
template<class OUTPUTTYPE, class aPoint, class aVector> | |
unsigned int | LineIntersectsTheY (const aPoint &point, const aVector &vect, const double Y, OUTPUTTYPE out) |
find intersection ticks for the line parametrized as Point + Vector * Tick with y-plane y=Y | |
template<class OUTPUTTYPE, class aPoint, class aVector> | |
unsigned int | LineIntersectsTheZ (const aPoint &point, const aVector &vect, const double Z, OUTPUTTYPE out) |
find intersection ticks for the line parametrized as Point + Vector * Tick with z-plane z=Z | |
template<class OUTPUTTYPE, class aPoint, class aVector> | |
unsigned int | LineIntersectsThePhi (const aPoint &point, const aVector &vect, const double Phi, OUTPUTTYPE out) |
find intersection ticks for the line parametrized as Point + Vector * Tick with half-plane phi=Phi | |
template<class OUTPUTTYPE, class aPoint, class aVector> | |
unsigned int | LineIntersectsTheTheta (const aPoint &point, const aVector &vect, const double Theta, OUTPUTTYPE out) |
find intersection ticks for the line parametrized as Point + Vector * Tick with cone theta=Theta | |
template<class OUTPUTTYPE, class aPoint, class aVector> | |
unsigned int | LineIntersectsTheCone (const aPoint &point, const aVector &vect, const double r1, const double r2, const double z1, const double z2, OUTPUTTYPE out) |
find intersection ticks for the line parametrized as Point + Vector * Tick with conical surface | |
template<class SOLID, class aPoint, class aVector> | |
unsigned int | RemoveAdjancent (ISolid::Ticks &ticks, const aPoint &point, const aVector &vect, const SOLID &solid) |
Remove all adjancent ticks. | |
template<class SOLID, class aPoint, class aVector> | |
unsigned int | RemoveAdjancentTicks (ISolid::Ticks &ticks, const aPoint &point, const aVector &vect, const SOLID &solid) |
Sort Ticks, eliminate duplicates and remove all adjancent ticks. | |
template<class SOLID, class aPoint, class aVector> | |
unsigned int | RemoveAdjancentTicks (ISolid::Ticks &ticks, const aPoint &point, const aVector &vect, const ISolid::Tick &tickMin, const ISolid::Tick &tickMax, const SOLID &solid) |
Eliminate duplicates and remove all adjancent ticks, Assume that "ticks" are already sorted and all adjancent ticks are removed! | |
template<class SOLID, class aPoint, class aVector, class TickContainer> | |
unsigned int | RemoveAdjacentTicksFast (TickContainer &ticks, const aPoint &point, const aVector &vect, const SOLID &solid) |
Eliminate duplicate ticks. | |
template<class TickContainer> | |
unsigned int | adjustToTickRange (TickContainer &ticks, const ISolid::Tick &tickMin, const ISolid::Tick &tickMax) |
Remove or adjust intervals such that they overlap with tick range Assume that "ticks" are already sorted, come in pairs and that adjancent ticks are removed. |
SolidTicks - a collection of technical methods for manipulation of ISolid::Tick ans ISolid::Ticks. Also some additional mathematical utilities are supplied.
unsigned int SolidTicks::SolveQuadraticEquation | ( | const double | a, | |
const double | b, | |||
const double | c, | |||
OUTPUTTYPE | out | |||
) | [inline] |
Solve the quadratic equation: a*x*x + b*x + c = 0;.
a | equation parameter | |
b | equation parameter | |
c | equation parameter | |
out | output iterator |
Definition at line 75 of file SolidMath.h.
00079 { 00080 if( 0 == a ) // it is indeed a linear equation: b*x + c = 0 00081 { 00082 // no solution! 00083 if( b == 0 ) { return 0 ; } // RETURN !!! 00084 // 1 solution! 00085 *out++ = -1.0 * c / b ; 00086 *out++ = -1.0 * c / b ; // double the solutions 00087 return 1; // RETURN !!! 00088 } 00089 double d = b * b - 4.0 * a * c ; 00090 // no solutions 00091 if( d < 0 ) { return 0; } // RETURN !!! 00092 // 1 or 2 solution 00093 d = sqrt( d ) ; 00094 *out++ = 0.5 * ( -b - d ) / a ; 00095 *out++ = 0.5 * ( -b + d ) / a ; 00096 // return number of solutions; 00097 return 0 == d ? 1 : 2 ; // RETURN !!! 00098 };
unsigned int SolidTicks::LineIntersectsTheSphere | ( | const aPoint & | point, | |
const aVector & | vect, | |||
const double | radius, | |||
OUTPUTTYPE | out | |||
) | [inline] |
find intersection ticks for the line parametrized as Point + Vector * Tick with sphere of radius Radius
point | point for line parametrisation | |
vect | vector along the line | |
radius | sphere radius | |
out | output iterator |
It is equivalent to the equation ( Point + Vector * Tick )^2 = R^2 it is quadratic equation! a*x^2+b*x+c=0
Definition at line 113 of file SolidMath.h.
00117 { 00118 // sphere with non-positive radius is not able to intersect the line! 00119 if( radius <= 0 ) { return 0 ; } 00120 // line with null direction vector does not intersect the sphere! 00121 double v2 = vect.mag2(); 00122 if( v2 <= 0 ) { return 0 ; } 00123 double p2 = point.mag2() ; 00124 double pv = point.Dot(vect) ; 00129 const double a = v2 ; 00130 const double b = 2.0*pv ; 00131 const double c = p2 - radius * radius ; 00132 // solve the equation! 00133 return SolidTicks::SolveQuadraticEquation( a , b , c , out ); 00134 };
unsigned int SolidTicks::LineIntersectsTheSphere2 | ( | const aPoint & | point, | |
const aVector & | vect, | |||
const double | r2, | |||
OUTPUTTYPE | out | |||
) | [inline] |
find intersection ticks for the line parametrized as Point + Vector * Tick with sphere of radius Radius
point | point for line parametrisation | |
vect | vector along the line | |
r2 | sphere radius squared | |
out | output iterator |
It is equivalent to the equation ( Point + Vector * Tick )^2 = R^2 it is quadratic equation! a*x^2+b*x+c=0
Definition at line 149 of file SolidMath.h.
00153 { 00154 // sphere with non-positive radius is not able to intersect the line! 00155 if( r2 <= 0 ) { return 0 ; } 00156 // line with null direction vector does not intersect the sphere! 00157 double v2 = vect.mag2(); 00158 if( v2 <= 0 ) { return 0 ; } 00159 double p2 = point.mag2() ; 00160 double pv = point.Dot(vect) ; 00165 const double a = v2 ; 00166 const double b = 2.0*pv ; 00167 const double c = p2 - r2 ; 00168 // solve the equation! 00169 return SolidTicks::SolveQuadraticEquation( a , b , c , out ); 00170 };
unsigned int SolidTicks::LineIntersectsTheCylinder | ( | const aPoint & | point, | |
const aVector & | vect, | |||
const double | radius, | |||
OUTPUTTYPE | out | |||
) | [inline] |
find intersection ticks for the line parametrized as Point + Vector * Tick with cylinder of radius Radius
point | point for line parametrisation | |
vect | vector along the line | |
radius | cylinder radius | |
out | output iterator |
It is equivalent to the equation ( Point + Vector * Tick )^2 = R^2 it is quadratic equation! a*x^2+b*x+c=0
Definition at line 185 of file SolidMath.h.
00190 { 00191 // Cylinder with non-positive radius is not able to intersect the line! 00192 if( radius <= 0 ) { return 0 ; } 00193 // line with null direction vector is not able to intersect the cylinder! 00194 const double v2 = vect.x()*vect.x() + vect.y()*vect.y() ; 00195 if( v2 <= 0 ) { return 0 ; } 00196 // 00197 const double p2 = point.x() * point.x() + point.y() * point.y() ; 00198 const double pv = point.x() * vect.x() + point.y() * vect.y() ; 00203 const double a = v2 ; 00204 const double b = 2.0*pv ; 00205 const double c = p2 - radius * radius ; 00206 // solve the equation! 00207 return SolidTicks::SolveQuadraticEquation( a , b , c , out ); 00208 };
unsigned int SolidTicks::LineIntersectsTheX | ( | const aPoint & | point, | |
const aVector & | vect, | |||
const double | X, | |||
OUTPUTTYPE | out | |||
) | [inline] |
find intersection ticks for the line parametrized as Point + Vector * Tick with x-plane x=X
point | point for line parametrisation | |
vect | vector along the line | |
X | x-parameter | |
out | output iterator |
line with null vector in X-direction is not able to intersect the x-plane!
Definition at line 223 of file SolidMath.h.
00228 { 00232 if( 0 == vect.x() ) { return 0; } 00233 *out++ = ( X - point.x() ) / vect.x() ; 00234 return 1; 00235 };
unsigned int SolidTicks::LineIntersectsTheY | ( | const aPoint & | point, | |
const aVector & | vect, | |||
const double | Y, | |||
OUTPUTTYPE | out | |||
) | [inline] |
find intersection ticks for the line parametrized as Point + Vector * Tick with y-plane y=Y
point | point for line parametrisation | |
vect | vector along the line | |
Y | y-parameter | |
out | output iterator |
line with null vector in Y-direction is not able to intersect the y-plane!
Definition at line 250 of file SolidMath.h.
00255 { 00259 if( 0 == vect.y() ) { return 0; } 00260 *out++ = ( Y - point.y() ) / vect.y() ; 00261 return 1; 00262 };
unsigned int SolidTicks::LineIntersectsTheZ | ( | const aPoint & | point, | |
const aVector & | vect, | |||
const double | Z, | |||
OUTPUTTYPE | out | |||
) | [inline] |
find intersection ticks for the line parametrized as Point + Vector * Tick with z-plane z=Z
point | point for line parametrisation | |
vect | vector along the line | |
Z | z-parameter | |
out | output iterator |
line with null vector in Z-direction is not able to intersect the z-plane!
Definition at line 277 of file SolidMath.h.
00282 { 00286 if( 0 == vect.z() ) { return 0; } 00287 *out++ = ( Z - point.z() ) / vect.z() ; 00288 return 1; 00289 };
unsigned int SolidTicks::LineIntersectsThePhi | ( | const aPoint & | point, | |
const aVector & | vect, | |||
const double | Phi, | |||
OUTPUTTYPE | out | |||
) | [inline] |
find intersection ticks for the line parametrized as Point + Vector * Tick with half-plane phi=Phi
point | point for line parametrisation | |
vect | vector along the line | |
Phi | phi-parameter | |
out | output iterator |
Definition at line 304 of file SolidMath.h.
00309 { 00310 const double sinphi = sin( Phi ) ; 00311 const double cosphi = cos( Phi ) ; 00312 const double d = vect.x() * sinphi - vect.y() * cosphi ; 00313 if( 0 == d ) { return 0; } 00314 // only accept half the phi plane ! 00315 const double e = vect.y() * point.x() - vect.x() * point.y() ; 00316 if( e * d > 0 ) { return 0 ; } 00317 *out++ = ( point.y() * cosphi - point.x() * sinphi ) / d ; 00318 return 1; 00319 };
unsigned int SolidTicks::LineIntersectsTheTheta | ( | const aPoint & | point, | |
const aVector & | vect, | |||
const double | Theta, | |||
OUTPUTTYPE | out | |||
) | [inline] |
find intersection ticks for the line parametrized as Point + Vector * Tick with cone theta=Theta
point | point for line parametrisation | |
vect | vector along the line | |
Theta | Theta-parameter | |
out | output iterator |
it is equivalent to solve the equation cos^2(x^2+y^2)=sin^2*z^2
Definition at line 334 of file SolidMath.h.
00339 { 00343 const double sinthe = sin( Theta ) ; 00344 const double costhe = cos( Theta ) ; 00345 00346 const double c2 = costhe * costhe ; 00347 const double s2 = sinthe * sinthe ; 00348 00349 const double a = 00350 c2 * vect.x() * vect.x() + 00351 c2 * vect.y() * vect.y() - 00352 s2 * vect.z() * vect.z() ; 00353 double b = 00354 c2 * vect.x() * point.x() + 00355 c2 * vect.y() * point.y() - 00356 s2 * vect.z() * point.z() ; 00357 const double c = 00358 c2 * point.x() * point.x() + 00359 c2 * point.y() * point.y() - 00360 s2 * point.z() * point.z() ; 00361 00362 b *= 2.0; 00363 00364 // return the result 00365 return SolidTicks::SolveQuadraticEquation( a , b, c, out ); 00366 };
unsigned int SolidTicks::LineIntersectsTheCone | ( | const aPoint & | point, | |
const aVector & | vect, | |||
const double | r1, | |||
const double | r2, | |||
const double | z1, | |||
const double | z2, | |||
OUTPUTTYPE | out | |||
) | [inline] |
find intersection ticks for the line parametrized as Point + Vector * Tick with conical surface
point | point for line parametrisation | |
vect | vector along the line | |
r1 | cone-parameter | |
r2 | cone-parameter | |
z1 | cone-parameter | |
z2 | cone-parameter | |
out | output iterator |
it is equivalent to the equation (x^2+y^2)=(r(z))^2
r(z) = r1 + (z-z1)*(r2-r1)/(z2-z1) = = r1 + (z-z1)*(drdz) = = r1 - z1*drdz + drdz*(pz+vz*t) = = r1 - z1*drdz + drdz*pz + drdz*vz*t = = p1 + p2*t ;
Definition at line 387 of file SolidMath.h.
00395 { 00405 const double drdz = (r2-r1)/(z2-z1) ; 00406 const double p1 = r1 - z1*drdz + drdz*point.z() ; 00407 const double p2 = drdz * vect.z() ; 00408 00409 double a = vect.x () * vect.x () + vect.y () * vect.y () ; 00410 a -= p2*p2 ; 00411 double b = vect.x () * point.x() + vect.y () * point.y() ; 00412 b -= p2*p1 ; 00413 b *= 2.0 ; 00414 double c = point.x() * point.x() + point.y() * point.y() ; 00415 c -= p1*p1 ; 00416 00417 // return result 00418 return SolidTicks::SolveQuadraticEquation( a , b, c, out ); 00419 };
unsigned int SolidTicks::RemoveAdjancent | ( | ISolid::Ticks & | ticks, | |
const aPoint & | point, | |||
const aVector & | vect, | |||
const SOLID & | solid | |||
) | [inline] |
Remove all adjancent ticks.
ticks | container of "ticks" (sorted!) | |
point | point for line perametrisation | |
vect | vector along the line | |
solid | reference to SOLID |
to write the last tick it is enought to have the previous interval "inside"
to write the first tick it is enought to have the first interval "inside"
to write the "regular" tick, it should separate 2 different zones!
Definition at line 52 of file SolidTicks.h.
00056 { 00057 // local typedefs 00058 typedef std::vector<size_t> Indexes ; 00059 typedef ISolid::Tick Tick ; 00060 typedef ISolid::Ticks::iterator iterator ; 00061 // no abjancent ? 00062 if ( ticks.size() < 2 ) { ticks.clear() ; return 0 ; } // RETURN 00063 else if( ticks.size() == 2 ) 00064 { 00065 Tick tick1 = ticks.front () ; // first tick 00066 Tick tick2 = ticks.back () ; // last tick 00067 Tick tick = 0.5 * ( tick1 + tick2 ) ; // middle tick 00068 if( solid.isInside( point + vect * tick ) ) { return 2 ; } // RETURN 00069 else { ticks.clear() ; return 0 ; } // RETURN 00070 } 00071 // perform removing of adjancent ticks 00072 Indexes tmp ; 00073 Tick tickNext = 0.0 ; 00074 Tick tickPrev = 0.0 ; 00075 bool boolPrev = true ; 00076 bool boolNext = true ; 00077 for ( iterator it = ticks.begin() ; it != ticks.end() ; ++it ) 00078 { 00079 // the last point is to be treated in a specific way 00080 if ( ticks.end () != it + 1 ) 00081 { tickNext = 0.5 * ( (*it) + *(it+1) ) ; 00082 boolNext = solid.isInside( point + vect * tickNext ); } 00083 // get the index 00084 unsigned int index = it - ticks.begin(); 00088 if ( ticks.end () == it + 1 ) 00089 { if( !boolPrev ) { tmp.push_back( index ) ; } } 00093 else if ( ticks.begin() == it ) 00094 { if( !boolNext ) { tmp.push_back( index ) ; } } 00098 else 00099 { if( boolPrev == boolNext ) { tmp.push_back( index ) ; } } 00101 boolPrev = boolNext; 00102 tickPrev = tickNext; 00103 } 00104 // remove ticks (from the end!) 00105 Indexes::reverse_iterator cri = tmp.rbegin(); 00106 while( cri != tmp.rend() ) { ticks.erase( ticks.begin() + *cri++ ); } 00107 // get the final answer 00108 return ticks.size(); 00109 };
unsigned int SolidTicks::RemoveAdjancentTicks | ( | ISolid::Ticks & | ticks, | |
const aPoint & | point, | |||
const aVector & | vect, | |||
const SOLID & | solid | |||
) | [inline] |
Sort Ticks, eliminate duplicates and remove all adjancent ticks.
ticks | container of "ticks" (unsorted!) | |
point | point for line perametrisation | |
vect | vector along the line | |
solid | reference to SOLID |
Definition at line 124 of file SolidTicks.h.
00128 { 00129 // useful local typedefs 00130 typedef ISolid::Tick Tick ; 00131 typedef ISolid::Ticks::iterator iterator ; 00132 // (1) sort container 00133 std::sort( ticks.begin() , ticks.end() ) ; 00134 // (2) eliminate duplicates and (3) shrink container 00135 ticks.erase( std::unique( ticks.begin() , ticks.end() ) , ticks.end() ); 00136 // remove adjancent 00137 return RemoveAdjancent( ticks , point , vect , solid ); 00138 };
unsigned int SolidTicks::RemoveAdjancentTicks | ( | ISolid::Ticks & | ticks, | |
const aPoint & | point, | |||
const aVector & | vect, | |||
const ISolid::Tick & | tickMin, | |||
const ISolid::Tick & | tickMax, | |||
const SOLID & | solid | |||
) | [inline] |
Eliminate duplicates and remove all adjancent ticks, Assume that "ticks" are already sorted and all adjancent ticks are removed!
ticks | container of "ticks" (sorted!) | |
point | point for line perametrisation | |
vect | vector along the line | |
tickMin | minimal value of tick | |
tickMax | maximal value of tick | |
solid | reference to SOLID |
Definition at line 158 of file SolidTicks.h.
00164 { 00165 // useful local typedefs 00166 typedef ISolid::Tick Tick ; 00167 typedef ISolid::Ticks::iterator iterator ; 00168 // valid arguments? 00169 if( tickMin >= tickMax ) { ticks.clear(); return 0 ; } // RETURN 00170 // remove all garbage what is less than 'tickMin' 00171 iterator itMin = 00172 std::remove_if( ticks.begin () , 00173 ticks.end () , 00174 std::bind2nd( std::less<Tick> () , tickMin ) ); 00175 // remove all garbage what is larger than 'tickMax' 00176 iterator itMax = 00177 std::remove_if( ticks.begin () , 00178 itMin , 00179 std::bind2nd( std::greater<Tick> () , tickMax ) ); 00180 ticks.erase ( itMax , ticks.end() ) ; 00181 00182 // empty ticks! 00183 if( ticks.empty() ) 00184 { 00185 const Tick middle = 0.5 * ( tickMin + tickMax ) ; 00186 if( solid.isInside( point + middle * vect ) ) 00187 { 00188 ticks.push_back( tickMin ) ; 00189 ticks.push_back( tickMax ) ; 00190 } 00191 return ticks.size() ; 00192 } 00193 00194 // first tick 00195 if( ticks.front () != tickMin ) 00196 { 00197 const Tick middle = 0.5 * ( tickMin + ticks.front() ) ; 00198 if( solid.isInside ( point + middle * vect ) ) 00199 { ticks.insert ( ticks.begin() , tickMin ) ; } 00200 } 00201 00202 // last tick 00203 if( ticks.back () != tickMax ) 00204 { 00205 const Tick middle = 0.5 * ( ticks.back() + tickMax ) ; 00206 if( solid.isInside ( point + middle * vect ) ) 00207 { ticks.push_back ( tickMax ) ; } 00208 } 00209 // adjancent are already removed 00210 return ticks.size () ; 00211 };
unsigned int SolidTicks::RemoveAdjacentTicksFast | ( | TickContainer & | ticks, | |
const aPoint & | point, | |||
const aVector & | vect, | |||
const SOLID & | solid | |||
) | [inline] |
Eliminate duplicate ticks.
Not as safe as the original, but a bit more efficient: it will not call the 'isInside' stuff unless it has reason to belief there is actually something wrong with this vector of ticks. It decides that there is something wrong if there are an odd number of ticks or if there are 'double' ticks.
ticks | container of "ticks" (sorted!) | |
point | point for line perametrisation | |
vect | vector along the line | |
solid | reference to SOLID |
Definition at line 229 of file SolidTicks.h.
00233 { 00234 // only call the expensive method if we find that something is wrong: 00235 typename TickContainer::iterator newend = std::unique( ticks.begin() , ticks.end() ) ; 00236 if( newend != ticks.end() || ticks.size()%2 != 0 ) { 00237 ticks.erase( newend, ticks.end()) ; 00238 RemoveAdjancent( ticks , point , vect , solid ); 00239 } 00240 return ticks.size() ; 00241 } ;
unsigned int SolidTicks::adjustToTickRange | ( | TickContainer & | ticks, | |
const ISolid::Tick & | tickMin, | |||
const ISolid::Tick & | tickMax | |||
) |
Remove or adjust intervals such that they overlap with tick range Assume that "ticks" are already sorted, come in pairs and that adjancent ticks are removed.
ticks | container of "ticks" (sorted and in pairs) | |
tickMin | minimal value of tick | |
tickMax | maximal value of tick |
Definition at line 255 of file SolidTicks.h.
00256 { 00257 // useful local typedefs 00258 typedef ISolid::Tick Tick ; 00259 typedef ISolid::Ticks::iterator iterator ; 00260 if( !ticks.empty() ) { 00261 static ISolid::Ticks validticks ; validticks.clear() ; 00262 // explicitely use that ticks come in pairs 00263 for( typename TickContainer::const_iterator it = ticks.begin() ; it+1 < ticks.end(); it +=2) 00264 if( *it <= tickMax && *(it+1) >= tickMin ) { 00265 validticks.push_back( std::max( tickMin, *it) ) ; 00266 validticks.push_back( std::min( tickMax, *(it+1)) ) ; 00267 } 00268 ticks.swap(validticks) ; 00269 } 00270 return ticks.size () ; 00271 };