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

isoSurface.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 Class
00025     Foam::isoSurface
00026 
00027 Description
00028     A surface formed by the iso value.
00029     After "Regularised Marching Tetrahedra: improved iso-surface extraction",
00030     G.M. Treece, R.W. Prager and A.H. Gee.
00031 
00032     Note:
00033     - does tets without using cell centres/cell values. Not tested.
00034     - regularisation can create duplicate triangles/non-manifold surfaces.
00035     Current handling of those is bit ad-hoc for now and not perfect.
00036     - regularisation does not do boundary points so as to preserve the
00037       boundary perfectly.
00038     - uses geometric merge with fraction of bounding box as distance.
00039     - triangles can be between two cell centres so constant sampling
00040       does not make sense.
00041     - on empty patches behaves like zero gradient.
00042     - does not do 2D correctly, creates non-flat iso surface.
00043     - on processor boundaries might two overlapping (identical) triangles
00044       (one from either side)
00045 
00046     The handling on coupled patches is a bit complex. All fields
00047     (values and coordinates) get rewritten so
00048     - empty patches get zerogradient (value) and facecentre (coordinates)
00049     - separated processor patch faces get interpolate (value) and facecentre
00050       (coordinates). (this is already the default for cyclics)
00051     - non-separated processor patch faces keep opposite value and cell centre
00052 
00053     Now the triangle generation on non-separated processor patch faces
00054     can use the neighbouring value. Any separated processor face or cyclic
00055     face gets handled just like any boundary face.
00056 
00057 
00058 SourceFiles
00059     isoSurface.C
00060 
00061 \*---------------------------------------------------------------------------*/
00062 
00063 #ifndef isoSurface_H
00064 #define isoSurface_H
00065 
00066 #include <triSurface/triSurface.H>
00067 #include <OpenFOAM/labelPair.H>
00068 #include <meshTools/pointIndexHit.H>
00069 #include <OpenFOAM/PackedBoolList.H>
00070 #include <finiteVolume/volFields.H>
00071 #include <finiteVolume/slicedVolFields.H>
00072 
00073 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
00074 
00075 namespace Foam
00076 {
00077 
00078 class fvMesh;
00079 
00080 /*---------------------------------------------------------------------------*\
00081                        Class isoSurface Declaration
00082 \*---------------------------------------------------------------------------*/
00083 
00084 class isoSurface
00085 :
00086     public triSurface
00087 {
00088     // Private data
00089 
00090         enum segmentCutType
00091         {
00092             NEARFIRST,      // intersection close to e.first()
00093             NEARSECOND,     //  ,,                   e.second()
00094             NOTNEAR         // no intersection
00095         };
00096 
00097         enum cellCutType
00098         {
00099             NOTCUT,     // not cut
00100             SPHERE,     // all edges to cell centre cut
00101             CUT         // normal cut
00102         };
00103 
00104 
00105         //- Reference to mesh
00106         const fvMesh& mesh_;
00107 
00108         const scalarField& pVals_;
00109 
00110         //- Input volScalarField with separated coupled patches rewritten
00111         autoPtr<slicedVolScalarField> cValsPtr_;
00112 
00113         //- Isosurface value
00114         const scalar iso_;
00115 
00116         //- Regularise?
00117         const Switch regularise_;
00118 
00119         //- When to merge points
00120         const scalar mergeDistance_;
00121 
00122 
00123         //- Whether face might be cut
00124         List<cellCutType> faceCutType_;
00125 
00126         //- Whether cell might be cut
00127         List<cellCutType> cellCutType_;
00128 
00129         //- Estimated number of cut cells
00130         label nCutCells_;
00131 
00132         //- For every triangle the original cell in mesh
00133         labelList meshCells_;
00134 
00135         //- For every unmerged triangle point the point in the triSurface
00136         labelList triPointMergeMap_;
00137 
00138 
00139     // Private Member Functions
00140 
00141         // Point synchronisation
00142 
00143             //- Does tensor differ (to within mergeTolerance) from identity
00144             bool noTransform(const tensor& tt) const;
00145 
00146             //- Is patch a collocated (i.e. non-separated) coupled patch?
00147             static bool collocatedPatch(const polyPatch&);
00148 
00149             //- Per face whether is collocated
00150             PackedBoolList collocatedFaces(const coupledPolyPatch&) const;
00151 
00152             //- Take value at local point patchPointI and assign it to its
00153             //  correct place in patchValues (for transferral) and sharedValues
00154             //  (for reduction)
00155             void insertPointData
00156             (
00157                 const processorPolyPatch& pp,
00158                 const Map<label>& meshToShared,
00159                 const pointField& pointValues,
00160                 const label patchPointI,
00161                 pointField& patchValues,
00162                 pointField& sharedValues
00163             ) const;
00164 
00165             //- Synchonise points on all non-separated coupled patches
00166             void syncUnseparatedPoints
00167             (
00168                 pointField& collapsedPoint,
00169                 const point& nullValue
00170             ) const;
00171 
00172 
00173         //- Get location of iso value as fraction inbetween s0,s1
00174         scalar isoFraction
00175         (
00176             const scalar s0,
00177             const scalar s1
00178         ) const;
00179 
00180         //- Check if any edge of a face is cut
00181         bool isEdgeOfFaceCut
00182         (
00183             const scalarField& pVals,
00184             const face& f,
00185             const bool ownLower,
00186             const bool neiLower
00187         ) const;
00188 
00189         void getNeighbour
00190         (
00191             const labelList& boundaryRegion,
00192             const volVectorField& meshC,
00193             const volScalarField& cVals,
00194             const label cellI,
00195             const label faceI,
00196             scalar& nbrValue,
00197             point& nbrPoint
00198         ) const;
00199 
00200         //- Set faceCutType,cellCutType.
00201         void calcCutTypes
00202         (
00203             const labelList& boundaryRegion,
00204             const volVectorField& meshC,
00205             const volScalarField& cVals,
00206             const scalarField& pVals
00207         );
00208 
00209         static labelPair findCommonPoints
00210         (
00211             const labelledTri&,
00212             const labelledTri&
00213         );
00214 
00215         static point calcCentre(const triSurface&);
00216 
00217         static pointIndexHit collapseSurface
00218         (
00219             pointField& localPoints,
00220             DynamicList<labelledTri, 64>& localTris
00221         );
00222 
00223         //- Determine per cc whether all near cuts can be snapped to single
00224         //  point.
00225         void calcSnappedCc
00226         (
00227             const labelList& boundaryRegion,
00228             const volVectorField& meshC,
00229             const volScalarField& cVals,
00230             const scalarField& pVals,
00231             DynamicList<point>& snappedPoints,
00232             labelList& snappedCc
00233         ) const;
00234 
00235         //- Determine per point whether all near cuts can be snapped to single
00236         //  point.
00237         void calcSnappedPoint
00238         (
00239             const PackedBoolList& isBoundaryPoint,
00240             const labelList& boundaryRegion,
00241             const volVectorField& meshC,
00242             const volScalarField& cVals,
00243             const scalarField& pVals,
00244             DynamicList<point>& snappedPoints,
00245             labelList& snappedPoint
00246         ) const;
00247 
00248 
00249         //- Return input field with coupled (and empty) patch values rewritten
00250         template<class Type>
00251         tmp<SlicedGeometricField
00252         <Type, fvPatchField, slicedFvPatchField, volMesh> >
00253         adaptPatchFields
00254         (
00255             const GeometricField<Type, fvPatchField, volMesh>& fld
00256         ) const;
00257 
00258         //- Generate single point by interpolation or snapping
00259         template<class Type>
00260         Type generatePoint
00261         (
00262             const scalar s0,
00263             const Type& p0,
00264             const bool hasSnap0,
00265             const Type& snapP0,
00266 
00267             const scalar s1,
00268             const Type& p1,
00269             const bool hasSnap1,
00270             const Type& snapP1
00271         ) const;
00272 
00273         template<class Type>
00274         void generateTriPoints
00275         (
00276             const scalar s0,
00277             const Type& p0,
00278             const bool hasSnap0,
00279             const Type& snapP0,
00280 
00281             const scalar s1,
00282             const Type& p1,
00283             const bool hasSnap1,
00284             const Type& snapP1,
00285 
00286             const scalar s2,
00287             const Type& p2,
00288             const bool hasSnap2,
00289             const Type& snapP2,
00290 
00291             const scalar s3,
00292             const Type& p3,
00293             const bool hasSnap3,
00294             const Type& snapP3,
00295 
00296             DynamicList<Type>& points
00297         ) const;
00298 
00299         template<class Type>
00300         label generateFaceTriPoints
00301         (
00302             const volScalarField& cVals,
00303             const scalarField& pVals,
00304 
00305             const GeometricField<Type, fvPatchField, volMesh>& cCoords,
00306             const Field<Type>& pCoords,
00307 
00308             const DynamicList<Type>& snappedPoints,
00309             const labelList& snappedCc,
00310             const labelList& snappedPoint,
00311             const label faceI,
00312 
00313             const scalar neiVal,
00314             const Type& neiPt,
00315             const bool hasNeiSnap,
00316             const Type& neiSnapPt,
00317 
00318             DynamicList<Type>& triPoints,
00319             DynamicList<label>& triMeshCells
00320         ) const;
00321 
00322         template<class Type>
00323         void generateTriPoints
00324         (
00325             const volScalarField& cVals,
00326             const scalarField& pVals,
00327 
00328             const GeometricField<Type, fvPatchField, volMesh>& cCoords,
00329             const Field<Type>& pCoords,
00330 
00331             const DynamicList<Type>& snappedPoints,
00332             const labelList& snappedCc,
00333             const labelList& snappedPoint,
00334 
00335             DynamicList<Type>& triPoints,
00336             DynamicList<label>& triMeshCells
00337         ) const;
00338 
00339         triSurface stitchTriPoints
00340         (
00341             const bool checkDuplicates,
00342             const List<point>& triPoints,
00343             labelList& triPointReverseMap,  // unmerged to merged point
00344             labelList& triMap               // merged to unmerged triangle
00345         ) const;
00346 
00347         //- Check single triangle for (topological) validity
00348         static bool validTri(const triSurface&, const label);
00349 
00350         //- Determine edge-face addressing
00351         void calcAddressing
00352         (
00353             const triSurface& surf,
00354             List<FixedList<label, 3> >& faceEdges,
00355             labelList& edgeFace0,
00356             labelList& edgeFace1,
00357             Map<labelList>& edgeFacesRest
00358         ) const;
00359 
00360         //- Determine orientation
00361         static void walkOrientation
00362         (
00363             const triSurface& surf,
00364             const List<FixedList<label, 3> >& faceEdges,
00365             const labelList& edgeFace0,
00366             const labelList& edgeFace1,
00367             const label seedTriI,
00368             labelList& flipState
00369         );
00370 
00371         //- Orient surface
00372         static void orientSurface
00373         (
00374             triSurface&,
00375             const List<FixedList<label, 3> >& faceEdges,
00376             const labelList& edgeFace0,
00377             const labelList& edgeFace1,
00378             const Map<labelList>& edgeFacesRest
00379         );
00380 
00381         //- Is triangle (given by 3 edges) not fully connected?
00382         static bool danglingTriangle
00383         (
00384             const FixedList<label, 3>& fEdges,
00385             const labelList& edgeFace1
00386         );
00387 
00388         //- Mark all non-fully connected triangles
00389         static label markDanglingTriangles
00390         (
00391             const List<FixedList<label, 3> >& faceEdges,
00392             const labelList& edgeFace0,
00393             const labelList& edgeFace1,
00394             const Map<labelList>& edgeFacesRest,
00395             boolList& keepTriangles
00396         );
00397 
00398         static triSurface subsetMesh
00399         (
00400             const triSurface& s,
00401             const labelList& newToOldFaces,
00402             labelList& oldToNewPoints,
00403             labelList& newToOldPoints
00404         );
00405 
00406 public:
00407 
00408     //- Runtime type information
00409     TypeName("isoSurface");
00410 
00411 
00412     // Constructors
00413 
00414         //- Construct from cell values and point values. Uses boundaryField
00415         //  for boundary values. Holds reference to cellIsoVals and
00416         //  pointIsoVals.
00417         isoSurface
00418         (
00419             const volScalarField& cellIsoVals,
00420             const scalarField& pointIsoVals,
00421             const scalar iso,
00422             const bool regularise,
00423             const scalar mergeTol = 1E-6    // fraction of bounding box
00424         );
00425 
00426 
00427     // Member Functions
00428 
00429         //- For every face original cell in mesh
00430         const labelList& meshCells() const
00431         {
00432             return meshCells_;
00433         }
00434 
00435         //- For every unmerged triangle point the point in the triSurface
00436         const labelList& triPointMergeMap() const
00437         {
00438             return triPointMergeMap_;
00439         }
00440 
00441         //- Interpolates cCoords,pCoords. Uses the references to the original
00442         //  fields used to create the iso surface.
00443         template <class Type>
00444         tmp<Field<Type> > interpolate
00445         (
00446             const GeometricField<Type, fvPatchField, volMesh>& cCoords,
00447             const Field<Type>& pCoords
00448         ) const;
00449 
00450 };
00451 
00452 
00453 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
00454 
00455 } // End namespace Foam
00456 
00457 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
00458 
00459 #ifdef NoRepository
00460 #   include "isoSurfaceTemplates.C"
00461 #endif
00462 
00463 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
00464 
00465 #endif
00466 
00467 // ************************ vim: set sw=4 sts=4 et: ************************ //
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines