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

surfaceSlipDisplacementPointPatchVectorField.C

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 "surfaceSlipDisplacementPointPatchVectorField.H"
00027 #include <OpenFOAM/addToRunTimeSelectionTable.H>
00028 #include <OpenFOAM/Time.H>
00029 #include <OpenFOAM/transformField.H>
00030 #include <finiteVolume/fvMesh.H>
00031 #include <fvMotionSolvers/displacementFvMotionSolver.H>
00032 
00033 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
00034 
00035 namespace Foam
00036 {
00037 
00038 // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
00039 
00040 template<>
00041 const char*
00042 NamedEnum<surfaceSlipDisplacementPointPatchVectorField::projectMode, 3>::
00043 names[] =
00044 {
00045     "nearest",
00046     "pointNormal",
00047     "fixedNormal"
00048 };
00049 
00050 const NamedEnum<surfaceSlipDisplacementPointPatchVectorField::projectMode, 3>
00051     surfaceSlipDisplacementPointPatchVectorField::projectModeNames_;
00052 
00053 
00054 // * * * * * * * * * * * * * Private Member Functions  * * * * * * * * * * * //
00055 
00056 void surfaceSlipDisplacementPointPatchVectorField::calcProjection
00057 (
00058     vectorField& displacement
00059 ) const
00060 {
00061     const polyMesh& mesh = patch().boundaryMesh().mesh()();
00062     const pointField& localPoints = patch().localPoints();
00063     const labelList& meshPoints = patch().meshPoints();
00064 
00065     //const scalar deltaT = mesh.time().deltaT().value();
00066 
00067     // Construct large enough vector in direction of projectDir so
00068     // we're guaranteed to hit something.
00069 
00070     //- Per point projection vector:
00071     const scalar projectLen = mag(mesh.bounds().max()-mesh.bounds().min());
00072 
00073     // For case of fixed projection vector:
00074     vector projectVec;
00075     if (projectMode_ == FIXEDNORMAL)
00076     {
00077         vector n = projectDir_/mag(projectDir_);
00078         projectVec = projectLen*n;
00079     }
00080 
00081 
00082     // Get fixed points (bit of a hack)
00083     const pointZone* zonePtr = NULL;
00084 
00085     if (frozenPointsZone_.size() > 0)
00086     {
00087         const pointZoneMesh& pZones = mesh.pointZones();
00088         label zoneID = pZones.findZoneID(frozenPointsZone_);
00089         if (zoneID == -1)
00090         {
00091             FatalErrorIn
00092             (
00093                 "surfaceSlipDisplacementPointPatchVectorField::calcProjection()"
00094             )   << "Cannot find zone " << frozenPointsZone_ << endl
00095                 << "Valid zones are " << pZones.name() << exit(FatalError);
00096         }
00097 
00098         zonePtr = &pZones[zoneID];
00099 
00100         Pout<< "surfaceSlipDisplacementPointPatchVectorField : Fixing all "
00101             << zonePtr->size() << " points in pointZone " << zonePtr->name()
00102             << endl;
00103     }
00104 
00105     // Get the starting locations from the motionSolver
00106     const pointField& points0 = mesh.lookupObject<displacementFvMotionSolver>
00107     (
00108         "dynamicMeshDict"
00109     ).points0();
00110 
00111 
00112     pointField start(meshPoints.size());
00113     forAll(start, i)
00114     {
00115         start[i] = points0[meshPoints[i]] + displacement[i];
00116     }
00117 
00118     label nNotProjected = 0;
00119 
00120     if (projectMode_ == NEAREST)
00121     {
00122         List<pointIndexHit> nearest;
00123         labelList hitSurfaces;
00124         surfaces().findNearest
00125         (
00126             start,
00127             scalarField(start.size(), sqr(projectLen)),
00128             hitSurfaces,
00129             nearest
00130         );
00131 
00132         forAll(nearest, i)
00133         {
00134             if (zonePtr && (zonePtr->whichPoint(meshPoints[i]) >= 0))
00135             {
00136                 // Fixed point. Reset to point0 location.
00137                 displacement[i] = points0[meshPoints[i]] - localPoints[i];
00138             }
00139             else if (nearest[i].hit())
00140             {
00141                 displacement[i] =
00142                     nearest[i].hitPoint()
00143                   - points0[meshPoints[i]];
00144             }
00145             else
00146             {
00147                 nNotProjected++;
00148 
00149                 if (debug)
00150                 {
00151                     Pout<< "    point:" << meshPoints[i]
00152                         << " coord:" << localPoints[i]
00153                         << "  did not find any surface within " << projectLen
00154                         << endl;
00155                 }
00156             }
00157         }
00158     }
00159     else
00160     {
00161         // Do tests on all points. Combine later on.
00162 
00163         // 1. Check if already on surface
00164         List<pointIndexHit> nearest;
00165         {
00166             labelList nearestSurface;
00167             surfaces().findNearest
00168             (
00169                 start,
00170                 scalarField(start.size(), sqr(SMALL)),
00171                 nearestSurface,
00172                 nearest
00173             );
00174         }
00175 
00176         // 2. intersection. (combined later on with information from nearest
00177         // above)
00178         vectorField projectVecs(start.size(), projectVec);
00179 
00180         if (projectMode_ == POINTNORMAL)
00181         {
00182             projectVecs = projectLen*patch().pointNormals();
00183         }
00184 
00185         // Knock out any wedge component
00186         scalarField offset(start.size(), 0.0);
00187         if (wedgePlane_ >= 0 && wedgePlane_ < vector::nComponents)
00188         {
00189             forAll(offset, i)
00190             {
00191                 offset[i] = start[i][wedgePlane_];
00192                 start[i][wedgePlane_] = 0;
00193                 projectVecs[i][wedgePlane_] = 0;
00194             }
00195         }
00196 
00197         List<pointIndexHit> rightHit;
00198         {
00199             labelList rightSurf;
00200             surfaces().findAnyIntersection
00201             (
00202                 start,
00203                 start+projectVecs,
00204                 rightSurf,
00205                 rightHit
00206             );
00207         }
00208 
00209         List<pointIndexHit> leftHit;
00210         {
00211             labelList leftSurf;
00212             surfaces().findAnyIntersection
00213             (
00214                 start,
00215                 start-projectVecs,
00216                 leftSurf,
00217                 leftHit
00218             );
00219         }
00220 
00221         // 3. Choose either -fixed, nearest, right, left.
00222         forAll(displacement, i)
00223         {
00224             if (zonePtr && (zonePtr->whichPoint(meshPoints[i]) >= 0))
00225             {
00226                 // Fixed point. Reset to point0 location.
00227                 displacement[i] = points0[meshPoints[i]] - localPoints[i];
00228             }
00229             else if (nearest[i].hit())
00230             {
00231                 // Found nearest.
00232                 displacement[i] =
00233                     nearest[i].hitPoint()
00234                   - points0[meshPoints[i]];
00235             }
00236             else
00237             {
00238                 pointIndexHit interPt;
00239 
00240                 if (rightHit[i].hit())
00241                 {
00242                     if (leftHit[i].hit())
00243                     {
00244                         if
00245                         (
00246                             magSqr(rightHit[i].hitPoint()-start[i])
00247                           < magSqr(leftHit[i].hitPoint()-start[i])
00248                         )
00249                         {
00250                             interPt = rightHit[i];
00251                         }
00252                         else
00253                         {
00254                             interPt = leftHit[i];
00255                         }
00256                     }
00257                     else
00258                     {
00259                         interPt = rightHit[i];
00260                     }
00261                 }
00262                 else
00263                 {
00264                     if (leftHit[i].hit())
00265                     {
00266                         interPt = leftHit[i];
00267                     }
00268                 }
00269 
00270 
00271                 if (interPt.hit())
00272                 {
00273                     if (wedgePlane_ >= 0 && wedgePlane_ < vector::nComponents)
00274                     {
00275                         interPt.rawPoint()[wedgePlane_] += offset[i];
00276                     }
00277                     displacement[i] = interPt.rawPoint()-points0[meshPoints[i]];
00278                 }
00279                 else
00280                 {
00281                     nNotProjected++;
00282 
00283                     if (debug)
00284                     {
00285                         Pout<< "    point:" << meshPoints[i]
00286                             << " coord:" << localPoints[i]
00287                             << "  did not find any intersection between"
00288                             << " ray from " << start[i]-projectVecs[i]
00289                             << " to " << start[i]+projectVecs[i] << endl;
00290                     }
00291                 }
00292             }
00293         }
00294     }
00295 
00296     reduce(nNotProjected, sumOp<label>());
00297 
00298     if (nNotProjected > 0)
00299     {
00300         Info<< "surfaceSlipDisplacement :"
00301             << " on patch " << patch().name()
00302             << " did not project " << nNotProjected
00303             << " out of " << returnReduce(localPoints.size(), sumOp<label>())
00304             << " points." << endl;
00305     }
00306 }
00307 
00308 
00309 // * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
00310 
00311 surfaceSlipDisplacementPointPatchVectorField::
00312 surfaceSlipDisplacementPointPatchVectorField
00313 (
00314     const pointPatch& p,
00315     const DimensionedField<vector, pointMesh>& iF
00316 )
00317 :
00318     pointPatchVectorField(p, iF),
00319     projectMode_(NEAREST),
00320     projectDir_(vector::zero),
00321     wedgePlane_(-1)
00322 {}
00323 
00324 
00325 surfaceSlipDisplacementPointPatchVectorField::
00326 surfaceSlipDisplacementPointPatchVectorField
00327 (
00328     const pointPatch& p,
00329     const DimensionedField<vector, pointMesh>& iF,
00330     const dictionary& dict
00331 )
00332 :
00333     pointPatchVectorField(p, iF, dict),
00334     surfacesDict_(dict.subDict("geometry")),
00335     projectMode_(projectModeNames_.read(dict.lookup("projectMode"))),
00336     projectDir_(dict.lookup("projectDirection")),
00337     wedgePlane_(dict.lookupOrDefault("wedgePlane", -1)),
00338     frozenPointsZone_(dict.lookupOrDefault("frozenPointsZone", word::null))
00339 {}
00340 
00341 
00342 surfaceSlipDisplacementPointPatchVectorField::
00343 surfaceSlipDisplacementPointPatchVectorField
00344 (
00345     const surfaceSlipDisplacementPointPatchVectorField& ppf,
00346     const pointPatch& p,
00347     const DimensionedField<vector, pointMesh>& iF,
00348     const pointPatchFieldMapper&
00349 )
00350 :
00351     pointPatchVectorField(p, iF),
00352     surfacesDict_(ppf.surfacesDict_),
00353     projectMode_(ppf.projectMode_),
00354     projectDir_(ppf.projectDir_),
00355     wedgePlane_(ppf.wedgePlane_),
00356     frozenPointsZone_(ppf.frozenPointsZone_)
00357 {}
00358 
00359 
00360 surfaceSlipDisplacementPointPatchVectorField::
00361 surfaceSlipDisplacementPointPatchVectorField
00362 (
00363     const surfaceSlipDisplacementPointPatchVectorField& ppf
00364 )
00365 :
00366     pointPatchVectorField(ppf),
00367     surfacesDict_(ppf.surfacesDict_),
00368     projectMode_(ppf.projectMode_),
00369     projectDir_(ppf.projectDir_),
00370     wedgePlane_(ppf.wedgePlane_),
00371     frozenPointsZone_(ppf.frozenPointsZone_)
00372 {}
00373 
00374 
00375 surfaceSlipDisplacementPointPatchVectorField::
00376 surfaceSlipDisplacementPointPatchVectorField
00377 (
00378     const surfaceSlipDisplacementPointPatchVectorField& ppf,
00379     const DimensionedField<vector, pointMesh>& iF
00380 )
00381 :
00382     pointPatchVectorField(ppf, iF),
00383     surfacesDict_(ppf.surfacesDict_),
00384     projectMode_(ppf.projectMode_),
00385     projectDir_(ppf.projectDir_),
00386     wedgePlane_(ppf.wedgePlane_),
00387     frozenPointsZone_(ppf.frozenPointsZone_)
00388 {}
00389 
00390 
00391 // * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
00392 
00393 const searchableSurfaces&
00394 surfaceSlipDisplacementPointPatchVectorField::surfaces() const
00395 {
00396     if (surfacesPtr_.empty())
00397     {
00398         surfacesPtr_.reset
00399         (
00400             new searchableSurfaces
00401             (
00402                 IOobject
00403                 (
00404                     "abc",                              // dummy name
00405                     db().time().constant(),             // directory
00406                     "triSurface",                       // instance
00407                     db().time(),                        // registry
00408                     IOobject::MUST_READ,
00409                     IOobject::NO_WRITE
00410                 ),
00411                 surfacesDict_
00412             )
00413         );
00414     }
00415     return surfacesPtr_();
00416 }
00417 
00418 
00419 void surfaceSlipDisplacementPointPatchVectorField::evaluate
00420 (
00421     const Pstream::commsTypes commsType
00422 )
00423 {
00424     vectorField displacement(this->patchInternalField());
00425 
00426     // Calculate displacement to project points onto surface
00427     calcProjection(displacement);
00428 
00429     // Get internal field to insert values into
00430     Field<vector>& iF = const_cast<Field<vector>&>(this->internalField());
00431 
00432     //setInInternalField(iF, motionU);
00433     setInInternalField(iF, displacement);
00434 
00435     pointPatchVectorField::evaluate(commsType);
00436 }
00437 
00438 
00439 void surfaceSlipDisplacementPointPatchVectorField::write(Ostream& os) const
00440 {
00441     pointPatchVectorField::write(os);
00442     os.writeKeyword("geometry") << surfacesDict_
00443         << token::END_STATEMENT << nl;
00444     os.writeKeyword("projectMode") << projectModeNames_[projectMode_]
00445         << token::END_STATEMENT << nl;
00446     os.writeKeyword("projectDirection") << projectDir_
00447         << token::END_STATEMENT << nl;
00448     os.writeKeyword("wedgePlane") << wedgePlane_
00449         << token::END_STATEMENT << nl;
00450     if (frozenPointsZone_ != word::null)
00451     {
00452         os.writeKeyword("frozenPointsZone") << frozenPointsZone_
00453             << token::END_STATEMENT << nl;
00454     }
00455 }
00456 
00457 
00458 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
00459 
00460 makePointPatchTypeField
00461 (
00462     pointPatchVectorField,
00463     surfaceSlipDisplacementPointPatchVectorField
00464 );
00465 
00466 
00467 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
00468 
00469 } // End namespace Foam
00470 
00471 // ************************ vim: set sw=4 sts=4 et: ************************ //
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines