FreeFOAM The Cross-Platform CFD Toolkit
Hosted by SourceForge:
Get FreeFOAM at SourceForge.net.
            Fast, secure and Free Open Source software downloads

treeBoundBoxI.H

Go to the documentation of this file.
00001 /*---------------------------------------------------------------------------*\
00002   =========                 |
00003   \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
00004    \\    /   O peration     |
00005     \\  /    A nd           | Copyright (C) 1991-2010 OpenCFD Ltd.
00006      \\/     M anipulation  |
00007 -------------------------------------------------------------------------------
00008 License
00009     This file is part of OpenFOAM.
00010 
00011     OpenFOAM is free software: you can redistribute it and/or modify it
00012     under the terms of the GNU General Public License as published by
00013     the Free Software Foundation, either version 3 of the License, or
00014     (at your option) any later version.
00015 
00016     OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
00017     ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
00018     FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
00019     for more details.
00020 
00021     You should have received a copy of the GNU General Public License
00022     along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
00023 
00024 \*---------------------------------------------------------------------------*/
00025 
00026 #include "treeBoundBox.H"
00027 #include <OpenFOAM/Random.H>
00028 
00029 // * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
00030 
00031 inline Foam::treeBoundBox::treeBoundBox()
00032 :
00033     boundBox()
00034 {}
00035 
00036 
00037 inline Foam::treeBoundBox::treeBoundBox(const point& min, const point& max)
00038 :
00039     boundBox(min, max)
00040 {}
00041 
00042 
00043 inline Foam::treeBoundBox::treeBoundBox(const boundBox& bb)
00044 :
00045     boundBox(bb)
00046 {}
00047 
00048 
00049 // * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
00050 
00051 inline Foam::scalar Foam::treeBoundBox::typDim() const
00052 {
00053     return avgDim();
00054 }
00055 
00056 
00057 inline Foam::point Foam::treeBoundBox::corner(const direction octant) const
00058 {
00059     return point
00060     (
00061         (octant & RIGHTHALF) ? max().x() : min().x(),
00062         (octant & TOPHALF)   ? max().y() : min().y(),
00063         (octant & FRONTHALF) ? max().z() : min().z()
00064     );
00065 }
00066 
00067 
00068 // Returns octant in which point resides. Reverse of subBbox.
00069 inline Foam::direction Foam::treeBoundBox::subOctant(const point& pt) const
00070 {
00071     return subOctant(midpoint(), pt);
00072 }
00073 
00074 
00075 // Returns octant in which point resides. Reverse of subBbox.
00076 // Precalculated midpoint
00077 inline Foam::direction Foam::treeBoundBox::subOctant
00078 (
00079     const point& mid,
00080     const point& pt
00081 )
00082 {
00083     direction octant = 0;
00084 
00085     if (pt.x() > mid.x())
00086     {
00087         octant |= treeBoundBox::RIGHTHALF;
00088     }
00089 
00090     if (pt.y() > mid.y())
00091     {
00092         octant |= treeBoundBox::TOPHALF;
00093     }
00094 
00095     if (pt.z() > mid.z())
00096     {
00097         octant |= treeBoundBox::FRONTHALF;
00098     }
00099 
00100     return octant;
00101 }
00102 
00103 
00104 // Returns octant in which point resides. Reverse of subBbox.
00105 // Flags point exactly on edge.
00106 inline Foam::direction Foam::treeBoundBox::subOctant
00107 (
00108     const point& pt,
00109     bool& onEdge
00110 ) const
00111 {
00112     return subOctant(midpoint(), pt, onEdge);
00113 }
00114 
00115 
00116 // Returns octant in which point resides. Reverse of subBbox.
00117 // Precalculated midpoint
00118 inline Foam::direction Foam::treeBoundBox::subOctant
00119 (
00120     const point& mid,
00121     const point& pt,
00122     bool& onEdge
00123 )
00124 {
00125     direction octant = 0;
00126     onEdge = false;
00127 
00128     if (pt.x() > mid.x())
00129     {
00130         octant |= treeBoundBox::RIGHTHALF;
00131     }
00132     else if (pt.x() == mid.x())
00133     {
00134         onEdge = true;
00135     }
00136 
00137     if (pt.y() > mid.y())
00138     {
00139         octant |= treeBoundBox::TOPHALF;
00140     }
00141     else if (pt.y() == mid.y())
00142     {
00143         onEdge = true;
00144     }
00145 
00146     if (pt.z() > mid.z())
00147     {
00148         octant |= treeBoundBox::FRONTHALF;
00149     }
00150     else if (pt.z() == mid.z())
00151     {
00152         onEdge = true;
00153     }
00154 
00155     return octant;
00156 }
00157 
00158 
00159 // Returns octant in which intersection resides.
00160 // Precalculated midpoint. If the point is on the dividing line between
00161 // the octants the direction vector determines which octant to use
00162 // (i.e. in which octant the point would be if it were moved along dir)
00163 inline Foam::direction Foam::treeBoundBox::subOctant
00164 (
00165     const point& mid,
00166     const vector& dir,
00167     const point& pt,
00168     bool& onEdge
00169 )
00170 {
00171     direction octant = 0;
00172     onEdge = false;
00173 
00174     if (pt.x() > mid.x())
00175     {
00176         octant |= treeBoundBox::RIGHTHALF;
00177     }
00178     else if (pt.x() == mid.x())
00179     {
00180         onEdge = true;
00181         if (dir.x() > 0)
00182         {
00183             octant |= treeBoundBox::RIGHTHALF;
00184         }
00185     }
00186 
00187     if (pt.y() > mid.y())
00188     {
00189         octant |= treeBoundBox::TOPHALF;
00190     }
00191     else if (pt.y() == mid.y())
00192     {
00193         onEdge = true;
00194         if (dir.y() > 0)
00195         {
00196             octant |= treeBoundBox::TOPHALF;
00197         }
00198     }
00199 
00200     if (pt.z() > mid.z())
00201     {
00202         octant |= treeBoundBox::FRONTHALF;
00203     }
00204     else if (pt.z() == mid.z())
00205     {
00206         onEdge = true;
00207         if (dir.z() > 0)
00208         {
00209             octant |= treeBoundBox::FRONTHALF;
00210         }
00211     }
00212 
00213     return octant;
00214 }
00215 
00216 
00217 // Returns reference to octantOrder which defines the
00218 // order to do the search.
00219 inline void Foam::treeBoundBox::searchOrder
00220 (
00221     const point& pt,
00222     FixedList<direction,8>& octantOrder
00223 ) const
00224 {
00225     vector dist = midpoint() - pt;
00226 
00227     direction octant = 0;
00228 
00229     if (dist.x() < 0)
00230     {
00231         octant |= treeBoundBox::RIGHTHALF;
00232         dist.x() *= -1;
00233     }
00234 
00235     if (dist.y() < 0)
00236     {
00237         octant |= treeBoundBox::TOPHALF;
00238         dist.y() *= -1;
00239     }
00240 
00241     if (dist.z() < 0)
00242     {
00243         octant |= treeBoundBox::FRONTHALF;
00244     dist.z() *= -1;
00245     }
00246 
00247     direction min = 0;
00248     direction mid = 0;
00249     direction max = 0;
00250 
00251     if (dist.x() < dist.y())
00252     {
00253         if (dist.y() < dist.z())
00254     {
00255         min = treeBoundBox::RIGHTHALF;
00256         mid = treeBoundBox::TOPHALF;
00257         max = treeBoundBox::FRONTHALF;
00258     }
00259     else if (dist.z() < dist.x())
00260     {
00261         min = treeBoundBox::FRONTHALF;
00262             mid = treeBoundBox::RIGHTHALF;
00263         max = treeBoundBox::TOPHALF;
00264     }
00265     else
00266     {
00267         min = treeBoundBox::RIGHTHALF;
00268         mid = treeBoundBox::FRONTHALF;
00269         max = treeBoundBox::TOPHALF;
00270     }
00271     }
00272     else
00273     {
00274         if (dist.z() < dist.y())
00275     {
00276         min = treeBoundBox::FRONTHALF;
00277         mid = treeBoundBox::TOPHALF;
00278         max = treeBoundBox::RIGHTHALF;
00279     }
00280     else if (dist.x() < dist.z())
00281     {
00282         min = treeBoundBox::TOPHALF;
00283         mid = treeBoundBox::RIGHTHALF;
00284         max = treeBoundBox::FRONTHALF;
00285     }
00286     else
00287     {
00288         min = treeBoundBox::TOPHALF;
00289         mid = treeBoundBox::FRONTHALF;
00290         max = treeBoundBox::RIGHTHALF;
00291     }
00292     }
00293 
00294     // Primary subOctant
00295     octantOrder[0] = octant;
00296     // subOctants joined to the primary by faces.
00297     octantOrder[1] = octant ^ min;
00298     octantOrder[2] = octant ^ mid;
00299     octantOrder[3] = octant ^ max;
00300     // subOctants joined to the primary by edges.
00301     octantOrder[4] = octantOrder[1] ^ mid;
00302     octantOrder[5] = octantOrder[1] ^ max;
00303     octantOrder[6] = octantOrder[2] ^ max;
00304     // subOctants joined to the primary by corner.
00305     octantOrder[7] = octantOrder[4] ^ max;
00306 }
00307 
00308 
00309 // true if bb's intersect or overlap.
00310 // Note: <= to make sure we catch all.
00311 inline bool Foam::treeBoundBox::overlaps(const treeBoundBox& bb) const
00312 {
00313     return boundBox::overlaps(bb);
00314 }
00315 
00316 
00317 inline bool Foam::treeBoundBox::contains(const point& pt) const
00318 {
00319     return boundBox::contains(pt);
00320 }
00321 
00322 
00323 //- Return slightly wider bounding box
00324 inline Foam::treeBoundBox Foam::treeBoundBox::extend
00325 (
00326     Random& rndGen,
00327     const scalar s
00328 ) const
00329 {
00330     treeBoundBox bb(*this);
00331 
00332     vector newSpan = bb.span();
00333 
00334     // Make 3D
00335     scalar minSpan = s * Foam::mag(newSpan);
00336 
00337     for (direction dir = 0; dir < vector::nComponents; dir++)
00338     {
00339         newSpan[dir] = Foam::max(newSpan[dir], minSpan);
00340     }
00341 
00342     bb.min() -= cmptMultiply(s * rndGen.vector01(), newSpan);
00343     bb.max() += cmptMultiply(s * rndGen.vector01(), newSpan);
00344 
00345     return bb;
00346 }
00347 
00348 
00349 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
00350 
00351 // ************************ vim: set sw=4 sts=4 et: ************************ //
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines