1 /*---------------------------------------------------------------------------*\
3 \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
5 \\ / A nd | Copyright held by original author
7 -------------------------------------------------------------------------------
9 This file is part of OpenFOAM.
11 OpenFOAM is free software; you can redistribute it and/or modify it
12 under the terms of the GNU General Public License as published by the
13 Free Software Foundation; either version 2 of the License, or (at your
14 option) any later version.
16 OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
17 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
18 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
21 You should have received a copy of the GNU General Public License
22 along with OpenFOAM; if not, write to the Free Software Foundation,
23 Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
27 \*---------------------------------------------------------------------------*/
30 #include "faMeshLduAddressing.H"
31 #include "dimensionSet.H"
32 #include "areaFields.H"
33 #include "edgeFields.H"
34 #include "primitiveFacePatch.H"
36 #include "processorFaPatch.H"
37 #include "wedgeFaPatch.H"
38 #include "PstreamCombineReduceOps.H"
39 #include "coordinateSystem.H"
40 #include "scalarMatrices.H"
42 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
47 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
49 void faMesh::calcLduAddressing() const
53 Info<< "void faMesh::calcLduAddressing() const : "
54 << "Calculating addressing" << endl;
61 "void faMesh::calcLduAddressing() const"
62 ) << "lduPtr_ already allocated"
66 lduPtr_ = new faMeshLduAddressing(*this);
70 void faMesh::calcPatchStarts() const
74 Info<< "void faMesh::calcPatchStarts() const : "
75 << "Calculating patch starts" << endl;
82 "void faMesh::calcPatchStarts() const"
83 ) << "patchStartsPtr_ already allocated"
87 patchStartsPtr_ = new labelList(boundary().size(), -1);
88 labelList& patchStarts = *patchStartsPtr_;
90 patchStarts[0] = nInternalEdges();
92 for (label i = 1; i < boundary().size(); i++)
95 patchStarts[i - 1] + boundary()[i - 1].size();
100 void faMesh::calcLe() const
104 Info<< "void faMesh::calcLe() const : "
105 << "Calculating local edges" << endl;
112 "void faMesh::calcLe() const"
113 ) << "LePtr_ already allocated"
114 << abort(FatalError);
123 mesh_.pointsInstance(),
131 edgeVectorField& Le = *LePtr_;
134 const pointField& pPoints = points();
135 const edgeList& pEdges = edges();
137 const edgeVectorField& eCentres = edgeCentres();
138 const areaVectorField& fCentres = areaCentres();
140 const edgeVectorField& edgeNormals = edgeAreaNormals();
142 vectorField& leInternal = Le.internalField();
143 const vectorField& edgeNormalsInternal = edgeNormals.internalField();
144 const vectorField& fCentresInternal = fCentres.internalField();
145 const vectorField& eCentresInternal = eCentres.internalField();
146 const scalarField& magLeInternal = magLe().internalField();
148 forAll (leInternal, edgeI)
151 pEdges[edgeI].vec(pPoints) ^ edgeNormalsInternal[edgeI];
158 fCentresInternal[owner()[edgeI]]
159 - eCentresInternal[edgeI]
164 magLeInternal[edgeI]/mag(leInternal[edgeI]);
167 forAll (boundary(), patchI)
169 const unallocLabelList& bndEdgeFaces =
170 boundary()[patchI].edgeFaces();
172 const edgeList::subList bndEdges =
173 boundary()[patchI].patchSlice(pEdges);
175 const vectorField& bndEdgeNormals =
176 edgeNormals.boundaryField()[patchI];
178 vectorField& patchLe = Le.boundaryField()[patchI];
179 const vectorField& patchECentres = eCentres.boundaryField()[patchI];
181 forAll (patchLe, edgeI)
184 bndEdges[edgeI].vec(pPoints) ^ bndEdgeNormals[edgeI];
191 fCentresInternal[bndEdgeFaces[edgeI]]
192 - patchECentres[edgeI]
197 magLe().boundaryField()[patchI][edgeI]
198 /mag(patchLe[edgeI]);
204 void faMesh::calcMagLe() const
208 Info<< "void faMesh::calcMagLe() const : "
209 << "Calculating local edge magnitudes" << endl;
216 "void faMesh::calcMagLe() const"
217 ) << "magLePtr_ already allocated"
218 << abort(FatalError);
227 mesh_.pointsInstance(),
235 edgeScalarField& magLe = *magLePtr_;
238 const pointField& localPoints = points();
240 const edgeList::subList internalEdges =
241 edgeList::subList(edges(), nInternalEdges());
244 forAll (internalEdges, edgeI)
246 magLe.internalField()[edgeI] =
247 internalEdges[edgeI].mag(localPoints);
251 forAll (boundary(), patchI)
253 const edgeList::subList patchEdges =
254 boundary()[patchI].patchSlice(edges());
256 forAll (patchEdges, edgeI)
258 magLe.boundaryField()[patchI][edgeI] =
259 patchEdges[edgeI].mag(localPoints);
264 void faMesh::calcAreaCentres() const
268 Info<< "void faMesh::calcAreaCentres() const : "
269 << "Calculating face centres" << endl;
276 "void faMesh::calcAreaCentres() const"
277 ) << "centresPtr_ already allocated"
278 << abort(FatalError);
287 mesh_.pointsInstance(),
294 areaVectorField& centres = *centresPtr_;
296 const pointField& localPoints = points();
297 const faceList& localFaces = faces();
299 forAll (localFaces, faceI)
301 centres.internalField()[faceI] =
302 localFaces[faceI].centre(localPoints);
305 forAll (boundary(), patchI)
307 if (!boundary()[patchI].coupled())
309 const edgeList::subList patchEdges =
310 boundary()[patchI].patchSlice(edges());
312 forAll (patchEdges, edgeI)
314 centres.boundaryField()[patchI][edgeI] =
315 patchEdges[edgeI].centre(localPoints);
320 centres.correctBoundaryConditions();
324 void faMesh::calcEdgeCentres() const
328 Info<< "void faMesh::calcEdgeCentres() const : "
329 << "Calculating edge centres" << endl;
336 "void faMesh::calcEdgeCentres() const"
337 ) << "edgeCentresPtr_ already allocated"
338 << abort(FatalError);
347 mesh_.pointsInstance(),
355 edgeVectorField& edgeCentres = *edgeCentresPtr_;
357 const pointField& localPoints = points();
359 const edgeList::subList internalEdges =
360 edgeList::subList(edges(), nInternalEdges());
363 forAll (internalEdges, edgeI)
365 edgeCentres.internalField()[edgeI] =
366 internalEdges[edgeI].centre(localPoints);
370 forAll (boundary(), patchI)
372 const edgeList::subList patchEdges =
373 boundary()[patchI].patchSlice(edges());
375 forAll (patchEdges, edgeI)
377 edgeCentres.boundaryField()[patchI][edgeI] =
378 patchEdges[edgeI].centre(localPoints);
384 void faMesh::calcS() const
388 Info<< "void faMesh::calcS() const : "
389 << "Calculating areas" << endl;
396 "void faMesh::calcS() const"
397 ) << "SPtr_ already allocated"
398 << abort(FatalError);
401 SPtr_ = new DimensionedField<scalar, areaMesh>
414 DimensionedField<scalar, areaMesh>& S = *SPtr_;
416 const pointField& localPoints = points();
417 const faceList& localFaces = faces();
421 S[faceI] = localFaces[faceI].mag(localPoints);
426 void faMesh::calcFaceAreaNormals() const
430 Info<< "void faMesh::calcFaceAreaNormals() const : "
431 << "Calculating face area normals" << endl;
434 if (faceAreaNormalsPtr_)
438 "void faMesh::calcFaceAreaNormals() const"
439 ) << "faceAreaNormalsPtr_ already allocated"
440 << abort(FatalError);
443 faceAreaNormalsPtr_ =
449 mesh_.pointsInstance(),
457 areaVectorField& faceAreaNormals = *faceAreaNormalsPtr_;
459 const pointField& localPoints = points();
460 const faceList& localFaces = faces();
462 vectorField& nInternal = faceAreaNormals.internalField();
463 forAll (localFaces, faceI)
466 localFaces[faceI].normal(localPoints)/
467 localFaces[faceI].mag(localPoints);
470 forAll (boundary(), patchI)
472 if (!boundary()[patchI].coupled())
474 faceAreaNormals.boundaryField()[patchI] =
475 edgeAreaNormals().boundaryField()[patchI];
479 faceAreaNormals.correctBoundaryConditions();
483 void faMesh::calcEdgeAreaNormals() const
487 Info<< "void faMesh::calcEdgeAreaNormals() const : "
488 << "Calculating edge area normals" << endl;
491 if (edgeAreaNormalsPtr_)
495 "void faMesh::calcEdgeAreaNormals() const"
496 ) << "edgeAreaNormalsPtr_ already allocated"
497 << abort(FatalError);
500 edgeAreaNormalsPtr_ =
506 mesh_.pointsInstance(),
514 edgeVectorField& edgeAreaNormals = *edgeAreaNormalsPtr_;
517 // Point area normals
518 const vectorField& pointNormals = pointAreaNormals();
521 // // Primitive patch edge normals
522 // const labelListList& patchPointEdges = patch().pointEdges();
524 // vectorField patchEdgeNormals(nEdges(), vector::zero);
526 // forAll (pointNormals, pointI)
528 // const labelList& curPointEdges = patchPointEdges[pointI];
530 // forAll (curPointEdges, edgeI)
532 // label curEdge = curPointEdges[edgeI];
534 // patchEdgeNormals[curEdge] += 0.5*pointNormals[pointI];
538 // patchEdgeNormals /= mag(patchEdgeNormals);
541 // // Edge area normals
542 // label nIntEdges = patch().nInternalEdges();
544 // for (label edgeI = 0; edgeI < nIntEdges; edgeI++)
546 // edgeAreaNormals.internalField()[edgeI] =
547 // patchEdgeNormals[edgeI];
550 // forAll (boundary(), patchI)
552 // const labelList& edgeLabels = boundary()[patchI];
554 // forAll (edgeAreaNormals.boundaryField()[patchI], edgeI)
556 // edgeAreaNormals.boundaryField()[patchI][edgeI] =
557 // patchEdgeNormals[edgeLabels[edgeI]];
562 forAll (edgeAreaNormals.internalField(), edgeI)
564 vector e = edges()[edgeI].vec(points());
568 // 1.0 - sqr(mag(e^pointNormals[edges()[edgeI].end()]));
571 // 1.0 - sqr(mag(e^pointNormals[edges()[edgeI].start()]));
576 // edgeAreaNormals.internalField()[edgeI] =
577 // wStart*pointNormals[edges()[edgeI].start()]
578 // + wEnd*pointNormals[edges()[edgeI].end()];
580 // vector eC = 0.5*(points()[edges()[edgeI].start()] + points()[edges()[edgeI].end()]);
584 // points()[edges()[edgeI].start()] + pointNormals[edges()[edgeI].start()]
585 // points()[edges()[edgeI].end()] +
588 edgeAreaNormals.internalField()[edgeI] =
589 pointNormals[edges()[edgeI].start()]
590 + pointNormals[edges()[edgeI].end()];
592 edgeAreaNormals.internalField()[edgeI] -=
593 e*(e&edgeAreaNormals.internalField()[edgeI]);
596 edgeAreaNormals.internalField() /=
597 mag(edgeAreaNormals.internalField());
599 forAll (boundary(), patchI)
601 const edgeList::subList patchEdges =
602 boundary()[patchI].patchSlice(edges());
604 forAll (patchEdges, edgeI)
606 edgeAreaNormals.boundaryField()[patchI][edgeI] =
607 pointNormals[patchEdges[edgeI].start()]
608 + pointNormals[patchEdges[edgeI].end()];
610 vector e = patchEdges[edgeI].vec(points());
613 edgeAreaNormals.boundaryField()[patchI][edgeI] -=
614 e*(e&edgeAreaNormals.boundaryField()[patchI][edgeI]);
617 edgeAreaNormals.boundaryField()[patchI] /=
618 mag(edgeAreaNormals.boundaryField()[patchI]);
623 void faMesh::calcFaceCurvatures() const
627 Info<< "void faMesh::calcFaceCurvatures() const : "
628 << "Calculating face curvatures" << endl;
631 if (faceCurvaturesPtr_)
635 "void faMesh::calcFaceCurvatures() const"
636 ) << "faceCurvaturesPtr_ already allocated"
637 << abort(FatalError);
646 mesh_.pointsInstance(),
654 areaScalarField& faceCurvatures = *faceCurvaturesPtr_;
658 // fac::edgeIntegrate(Le()*edgeLengthCorrection())
659 // &faceAreaNormals();
662 fac::edgeIntegrate(Le()*edgeLengthCorrection());
664 faceCurvatures = sign(kN&faceAreaNormals())*mag(kN);
668 void faMesh::calcEdgeTransformTensors() const
672 Info<< "void faMesh::calcEdgeTransformTensors() const : "
673 << "Calculating edge transformation tensors" << endl;
676 if (edgeTransformTensorsPtr_)
680 "void faMesh::calcEdgeTransformTensors() const"
681 ) << "edgeTransformTensorsPtr_ already allocated"
682 << abort(FatalError);
685 edgeTransformTensorsPtr_ = new FieldField<Field, tensor>(nEdges());
686 FieldField<Field, tensor>& edgeTransformTensors =
687 *edgeTransformTensorsPtr_;
689 const areaVectorField& Nf = faceAreaNormals();
690 const areaVectorField& Cf = areaCentres();
692 const edgeVectorField& Ne = edgeAreaNormals();
693 const edgeVectorField& Ce = edgeCentres();
695 // Internal edges transformation tensors
696 for (label edgeI=0; edgeI<nInternalEdges(); edgeI++)
698 edgeTransformTensors.set(edgeI, new Field<tensor>(3, I));
700 vector E = Ce.internalField()[edgeI];
704 E -= skewCorrectionVectors().internalField()[edgeI];
707 // Edge transformation tensor
708 vector il = E - Cf.internalField()[owner()[edgeI]];
710 il -= Ne.internalField()[edgeI]
711 *(Ne.internalField()[edgeI]&il);
715 vector kl = Ne.internalField()[edgeI];
718 edgeTransformTensors[edgeI][0] =
721 il.x(), il.y(), il.z(),
722 jl.x(), jl.y(), jl.z(),
723 kl.x(), kl.y(), kl.z()
726 // Owner transformation tensor
727 il = E - Cf.internalField()[owner()[edgeI]];
729 il -= Nf.internalField()[owner()[edgeI]]
730 *(Nf.internalField()[owner()[edgeI]]&il);
734 kl = Nf.internalField()[owner()[edgeI]];
737 edgeTransformTensors[edgeI][1] =
740 il.x(), il.y(), il.z(),
741 jl.x(), jl.y(), jl.z(),
742 kl.x(), kl.y(), kl.z()
745 // Neighbour transformation tensor
746 il = Cf.internalField()[neighbour()[edgeI]] - E;
748 il -= Nf.internalField()[neighbour()[edgeI]]
749 *(Nf.internalField()[neighbour()[edgeI]]&il);
753 kl = Nf.internalField()[neighbour()[edgeI]];
756 edgeTransformTensors[edgeI][2] =
759 il.x(), il.y(), il.z(),
760 jl.x(), jl.y(), jl.z(),
761 kl.x(), kl.y(), kl.z()
765 // Boundary edges transformation tensors
766 forAll (boundary(), patchI)
768 if (boundary()[patchI].coupled())
770 const unallocLabelList& edgeFaces =
771 boundary()[patchI].edgeFaces();
774 Cf.boundaryField()[patchI].patchNeighbourField();
777 Nf.boundaryField()[patchI].patchNeighbourField();
779 forAll(edgeFaces, edgeI)
781 edgeTransformTensors.set
783 boundary()[patchI].start() + edgeI,
784 new Field<tensor>(3, I)
787 vector E = Ce.boundaryField()[patchI][edgeI];
791 E -= skewCorrectionVectors()
792 .boundaryField()[patchI][edgeI];
795 // Edge transformation tensor
796 vector il = E - Cf.internalField()[edgeFaces[edgeI]];
798 il -= Ne.boundaryField()[patchI][edgeI]
799 *(Ne.boundaryField()[patchI][edgeI]&il);
803 vector kl = Ne.boundaryField()[patchI][edgeI];
806 edgeTransformTensors[boundary()[patchI].start() + edgeI][0] =
809 il.x(), il.y(), il.z(),
810 jl.x(), jl.y(), jl.z(),
811 kl.x(), kl.y(), kl.z()
814 // Owner transformation tensor
815 il = E - Cf.internalField()[edgeFaces[edgeI]];
817 il -= Nf.internalField()[edgeFaces[edgeI]]
818 *(Nf.internalField()[edgeFaces[edgeI]]&il);
822 kl = Nf.internalField()[edgeFaces[edgeI]];
825 edgeTransformTensors[boundary()[patchI].start() + edgeI][1] =
828 il.x(), il.y(), il.z(),
829 jl.x(), jl.y(), jl.z(),
830 kl.x(), kl.y(), kl.z()
833 // Neighbour transformation tensor
834 il = ngbCf[edgeI] - E;
836 il -= ngbNf[edgeI]*(ngbNf[edgeI]&il);
844 edgeTransformTensors[boundary()[patchI].start() + edgeI][2] =
847 il.x(), il.y(), il.z(),
848 jl.x(), jl.y(), jl.z(),
849 kl.x(), kl.y(), kl.z()
855 const unallocLabelList& edgeFaces = boundary()[patchI].edgeFaces();
857 forAll(edgeFaces, edgeI)
859 edgeTransformTensors.set
861 boundary()[patchI].start() + edgeI,
862 new Field<tensor>(3, I)
865 vector E = Ce.boundaryField()[patchI][edgeI];
869 E -= skewCorrectionVectors()
870 .boundaryField()[patchI][edgeI];
873 // Edge transformation tensor
874 vector il = E - Cf.internalField()[edgeFaces[edgeI]];
876 il -= Ne.boundaryField()[patchI][edgeI]
877 *(Ne.boundaryField()[patchI][edgeI]&il);
881 vector kl = Ne.boundaryField()[patchI][edgeI];
884 edgeTransformTensors[boundary()[patchI].start() + edgeI][0] =
887 il.x(), il.y(), il.z(),
888 jl.x(), jl.y(), jl.z(),
889 kl.x(), kl.y(), kl.z()
892 // Owner transformation tensor
893 il = E - Cf.internalField()[edgeFaces[edgeI]];
895 il -= Nf.internalField()[edgeFaces[edgeI]]
896 *(Nf.internalField()[edgeFaces[edgeI]]&il);
900 kl = Nf.internalField()[edgeFaces[edgeI]];
903 edgeTransformTensors[boundary()[patchI].start() + edgeI][1] =
906 il.x(), il.y(), il.z(),
907 jl.x(), jl.y(), jl.z(),
908 kl.x(), kl.y(), kl.z()
916 labelList faMesh::internalPoints() const
920 Info<< "labelList faMesh::internalPoints() const : "
921 << "Calculating internal points" << endl;
924 const edgeList& edges = patch().edges();
925 label nIntEdges = patch().nInternalEdges();
927 List<bool> internal (nPoints(), true);
929 for (label curEdge = nIntEdges; curEdge < edges.size(); curEdge++)
931 internal[edges[curEdge].start()] = false;
933 internal[edges[curEdge].end()] = false;
936 SLList<label> internalPoints;
938 forAll (internal, pointI)
940 if (internal[pointI])
942 internalPoints.append(pointI);
946 labelList result(internalPoints);
952 labelList faMesh::boundaryPoints() const
956 Info<< "labelList faMesh::boundaryPoints() const : "
957 << "Calculating boundary points" << endl;
960 const edgeList& edges = patch().edges();
961 label nIntEdges = patch().nInternalEdges();
963 List<bool> internal (nPoints(), true);
965 for (label curEdge = nIntEdges; curEdge < edges.size(); curEdge++)
967 internal[edges[curEdge].start()] = false;
969 internal[edges[curEdge].end()] = false;
972 SLList<label> boundaryPoints;
974 forAll (internal, pointI)
976 if (!internal[pointI])
978 boundaryPoints.append(pointI);
982 labelList result(boundaryPoints);
988 void faMesh::calcPointAreaNormals() const
990 if (pointAreaNormalsPtr_)
994 "void faMesh::calcPointAreaNormals() const"
995 ) << "pointAreaNormalsPtr_ already allocated"
996 << abort(FatalError);
1000 pointAreaNormalsPtr_ =
1007 vectorField& result = *pointAreaNormalsPtr_;
1010 labelList intPoints = internalPoints();
1011 labelList bndPoints = boundaryPoints();
1013 const pointField& points = patch().localPoints();
1014 const faceList& faces = patch().localFaces();
1015 const labelListList& pointFaces = patch().pointFaces();
1017 forAll (intPoints, pointI)
1019 label curPoint = intPoints[pointI];
1021 faceList curFaceList(pointFaces[curPoint].size());
1023 forAll (curFaceList, faceI)
1025 curFaceList[faceI] = faces[pointFaces[curPoint][faceI]];
1028 primitiveFacePatch curPatch(curFaceList, points);
1030 labelList curPointPoints = curPatch.edgeLoops()[0];
1032 for (int i = 0; i < curPointPoints.size(); i++)
1035 points[curPatch.meshPoints()[curPointPoints[i]]]
1040 if (i == (curPointPoints.size() - 1))
1046 points[curPatch.meshPoints()[curPointPoints[p]]]
1049 vector n = (d1^d2)/mag(d1^d2);
1051 scalar sinAlpha = mag(d1^d2)/(mag(d1)*mag(d2));
1053 scalar w = sinAlpha/(mag(d1)*mag(d2));
1055 result[curPoint] += w*n;
1059 forAll (bndPoints, pointI)
1061 label curPoint = bndPoints[pointI];
1063 faceList curFaceList(pointFaces[curPoint].size());
1065 forAll (curFaceList, faceI)
1067 curFaceList[faceI] = faces[pointFaces[curPoint][faceI]];
1070 primitiveFacePatch curPatch (curFaceList, points);
1072 labelList agglomFacePoints = curPatch.edgeLoops()[0];
1074 SLList<label> slList;
1076 label curPointLabel = -1;
1078 for (label i=0; i<agglomFacePoints.size(); i++)
1080 if (curPatch.meshPoints()[agglomFacePoints[i]] == curPoint)
1084 else if ( curPointLabel != -1 )
1086 slList.append(curPatch.meshPoints()[agglomFacePoints[i]]);
1090 for (label i=0; i<curPointLabel; i++)
1092 slList.append(curPatch.meshPoints()[agglomFacePoints[i]]);
1095 labelList curPointPoints(slList);
1097 for (label i=0; i < (curPointPoints.size() - 1); i++)
1099 vector d1 = points[curPointPoints[i]] - points[curPoint];
1101 vector d2 = points[curPointPoints[i + 1]] - points[curPoint];
1103 vector n = (d1^d2)/mag(d1 ^ d2);
1105 scalar sinAlpha = mag(d1 ^ d2)/(mag(d1)*mag(d2));
1107 scalar w = sinAlpha/(mag(d1)*mag(d2));
1109 result[curPoint] += w*n;
1113 // Correcte wedge points
1114 forAll (boundary(), patchI)
1116 if (boundary()[patchI].type() == wedgeFaPatch::typeName)
1118 const wedgeFaPatch& wedgePatch =
1119 refCast<const wedgeFaPatch>(boundary()[patchI]);
1121 labelList patchPoints = wedgePatch.pointLabels();
1127 wedgePatch.centreNormal()
1132 forAll (patchPoints, pointI)
1134 result[patchPoints[pointI]]
1135 -= N*(N&result[patchPoints[pointI]]);
1140 // Axis point correction
1141 forAll (boundary(), patchI)
1143 if (boundary()[patchI].type() == wedgeFaPatch::typeName)
1145 const wedgeFaPatch& wedgePatch =
1146 refCast<const wedgeFaPatch>(boundary()[patchI]);
1148 if (wedgePatch.axisPoint() > -1)
1150 result[wedgePatch.axisPoint()] =
1154 &result[wedgePatch.axisPoint()]
1162 // Boundary points correction
1163 forAll (boundary(), patchI)
1165 if (correctPatchPointNormals(patchI) && !boundary()[patchI].coupled())
1167 if (boundary()[patchI].ngbPolyPatchIndex() == -1)
1171 "void faMesh::calcPointAreaNormals const"
1172 ) << "Neighbour polyPatch index is not defined "
1173 << "for faPatch " << boundary()[patchI].name()
1174 << abort(FatalError);
1177 labelList patchPoints = boundary()[patchI].pointLabels();
1178 vectorField N = boundary()[patchI].ngbPolyPatchPointNormals();
1180 forAll (patchPoints, pointI)
1182 result[patchPoints[pointI]]
1183 -= N[pointI]*(N[pointI]&result[patchPoints[pointI]]);
1188 // Processor patch points correction
1189 forAll (boundary(), patchI)
1191 if(boundary()[patchI].type() == processorFaPatch::typeName)
1193 const processorFaPatch& procPatch =
1194 refCast<const processorFaPatch>(boundary()[patchI]);
1196 labelList patchPointLabels = procPatch.pointLabels();
1198 vectorField patchPointNormals
1200 patchPointLabels.size(),
1204 forAll (patchPointNormals, pointI)
1206 patchPointNormals[pointI] =
1207 result[patchPointLabels[pointI]];
1214 procPatch.neighbProcNo(),
1215 reinterpret_cast<const char*>(patchPointNormals.begin()),
1216 patchPointNormals.byteSize()
1220 vectorField ngbPatchPointNormals
1222 procPatch.neighbPoints().size(),
1230 procPatch.neighbProcNo(),
1231 reinterpret_cast<char*>(ngbPatchPointNormals.begin()),
1232 ngbPatchPointNormals.byteSize()
1236 const labelList& nonGlobalPatchPoints =
1237 procPatch.nonGlobalPatchPoints();
1239 forAll (nonGlobalPatchPoints, pointI)
1241 result[patchPointLabels[nonGlobalPatchPoints[pointI]]] +=
1242 ngbPatchPointNormals
1244 procPatch.neighbPoints()[nonGlobalPatchPoints[pointI]]
1251 // Correct global points
1253 if (globalData().nGlobalPoints() > 0)
1255 const labelList& spLabels =
1256 globalData().sharedPointLabels();
1258 vectorField spNormals(spLabels.size(), vector::zero);
1259 forAll (spNormals, pointI)
1261 spNormals[pointI] = result[spLabels[pointI]];
1264 const labelList& addr = globalData().sharedPointAddr();
1266 vectorField gpNormals
1268 globalData().nGlobalPoints(),
1274 gpNormals[addr[i]] += spNormals[i];
1277 combineReduce(gpNormals, plusEqOp<vectorField>());
1279 // Extract local data
1282 spNormals[i] = gpNormals[addr[i]];
1285 forAll (spNormals, pointI)
1287 result[spLabels[pointI]] = spNormals[pointI];
1291 result /= mag(result);
1295 void faMesh::calcPointAreaNormalsByQuadricsFit() const
1297 vectorField& result = *pointAreaNormalsPtr_;
1300 labelList intPoints = internalPoints();
1301 labelList bndPoints = boundaryPoints();
1303 const pointField& points = patch().localPoints();
1304 const faceList& faces = patch().localFaces();
1305 const labelListList& pointFaces = patch().pointFaces();
1307 forAll(intPoints, pointI)
1309 label curPoint = intPoints[pointI];
1311 labelHashSet faceSet;
1312 forAll(pointFaces[curPoint], faceI)
1314 faceSet.insert(pointFaces[curPoint][faceI]);
1316 labelList curFaces = faceSet.toc();
1318 labelHashSet pointSet;
1320 pointSet.insert(curPoint);
1321 for(label i=0; i<curFaces.size(); i++)
1323 const labelList& facePoints = faces[curFaces[i]];
1324 for(label j=0; j<facePoints.size(); j++)
1326 if(!pointSet.found(facePoints[j]))
1328 pointSet.insert(facePoints[j]);
1332 pointSet.erase(curPoint);
1333 labelList curPoints = pointSet.toc();
1335 if (curPoints.size() < 5)
1339 Info << "WARNING: Extending point set for fitting." << endl;
1342 labelHashSet faceSet;
1343 forAll(pointFaces[curPoint], faceI)
1345 faceSet.insert(pointFaces[curPoint][faceI]);
1347 labelList curFaces = faceSet.toc();
1348 forAll(curFaces, faceI)
1350 const labelList& curFaceFaces =
1351 patch().faceFaces()[curFaces[faceI]];
1353 forAll(curFaceFaces, fI)
1355 label curFaceFace = curFaceFaces[fI];
1357 if(!faceSet.found(curFaceFace))
1359 faceSet.insert(curFaceFace);
1363 curFaces = faceSet.toc();
1365 labelHashSet pointSet;
1367 pointSet.insert(curPoint);
1368 for(label i=0; i<curFaces.size(); i++)
1370 const labelList& facePoints = faces[curFaces[i]];
1371 for(label j=0; j<facePoints.size(); j++)
1373 if(!pointSet.found(facePoints[j]))
1375 pointSet.insert(facePoints[j]);
1380 pointSet.erase(curPoint);
1381 curPoints = pointSet.toc();
1384 vectorField allPoints(curPoints.size());
1385 scalarField W(curPoints.size(), 1.0);
1386 for(label i=0; i<curPoints.size(); i++)
1388 allPoints[i] = points[curPoints[i]];
1389 W[i] = 1.0/magSqr(allPoints[i] - points[curPoint]);
1392 // Transforme points
1393 vector origin = points[curPoint];
1394 vector axis = result[curPoint]/mag(result[curPoint]);
1395 vector dir = (allPoints[0] - points[curPoint]);
1396 dir -= axis*(axis&dir);
1398 coordinateSystem cs("cs", origin, axis, dir);
1400 forAll(allPoints, pI)
1402 allPoints[pI] = cs.localPosition(allPoints[pI]);
1405 scalarRectangularMatrix M
1412 for(label i = 0; i < allPoints.size(); i++)
1414 M[i][0] = sqr(allPoints[i].x());
1415 M[i][1] = sqr(allPoints[i].y());
1416 M[i][2] = allPoints[i].x()*allPoints[i].y();
1417 M[i][3] = allPoints[i].x();
1418 M[i][4] = allPoints[i].y();
1421 scalarSquareMatrix MtM(5, 0.0);
1423 for (label i = 0; i < MtM.n(); i++)
1425 for (label j = 0; j < MtM.m(); j++)
1427 for (label k = 0; k < M.n(); k++)
1429 MtM[i][j] += M[k][i]*M[k][j]*W[k];
1434 scalarField MtR(5, 0);
1436 for (label i=0; i<MtR.size(); i++)
1438 for (label j=0; j<M.n(); j++)
1440 MtR[i] += M[j][i]*allPoints[j].z()*W[j];
1444 scalarSquareMatrix::LUsolve(MtM, MtR);
1446 vector curNormal = vector(MtR[3], MtR[4], -1);
1448 curNormal = cs.globalVector(curNormal);
1450 curNormal *= sign(curNormal&result[curPoint]);
1452 result[curPoint] = curNormal;
1456 forAll (boundary(), patchI)
1458 if(boundary()[patchI].type() == processorFaPatch::typeName)
1460 const processorFaPatch& procPatch =
1461 refCast<const processorFaPatch>(boundary()[patchI]);
1463 labelList patchPointLabels = procPatch.pointLabels();
1465 labelList toNgbProcLsPointStarts(patchPointLabels.size(), 0);
1466 vectorField toNgbProcLsPoints
1468 10*patchPointLabels.size(),
1473 for (label pointI=0; pointI<patchPointLabels.size(); pointI++)
1475 label curPoint = patchPointLabels[pointI];
1477 toNgbProcLsPointStarts[pointI] = nPoints;
1479 labelHashSet faceSet;
1480 forAll(pointFaces[curPoint], faceI)
1482 faceSet.insert(pointFaces[curPoint][faceI]);
1484 labelList curFaces = faceSet.toc();
1486 labelHashSet pointSet;
1488 pointSet.insert(curPoint);
1489 for (label i=0; i<curFaces.size(); i++)
1491 const labelList& facePoints = faces[curFaces[i]];
1492 for (label j=0; j<facePoints.size(); j++)
1494 if(!pointSet.found(facePoints[j]))
1496 pointSet.insert(facePoints[j]);
1500 pointSet.erase(curPoint);
1501 labelList curPoints = pointSet.toc();
1503 for (label i=0; i<curPoints.size(); i++)
1505 toNgbProcLsPoints[nPoints++] =
1506 points[curPoints[i]];
1510 toNgbProcLsPoints.setSize(nPoints);
1513 OPstream toNeighbProc
1516 procPatch.neighbProcNo(),
1517 toNgbProcLsPoints.byteSize()
1518 + toNgbProcLsPointStarts.byteSize()
1522 toNeighbProc << toNgbProcLsPoints
1523 << toNgbProcLsPointStarts;
1528 forAll (boundary(), patchI)
1530 if(boundary()[patchI].type() == processorFaPatch::typeName)
1532 const processorFaPatch& procPatch =
1533 refCast<const processorFaPatch>(boundary()[patchI]);
1535 labelList patchPointLabels = procPatch.pointLabels();
1537 labelList fromNgbProcLsPointStarts(patchPointLabels.size(), 0);
1538 vectorField fromNgbProcLsPoints;
1541 IPstream fromNeighbProc
1544 procPatch.neighbProcNo(),
1545 10*patchPointLabels.size()*sizeof(vector)
1546 + fromNgbProcLsPointStarts.byteSize()
1550 fromNeighbProc >> fromNgbProcLsPoints
1551 >> fromNgbProcLsPointStarts;
1554 const labelList& nonGlobalPatchPoints =
1555 procPatch.nonGlobalPatchPoints();
1557 forAll(nonGlobalPatchPoints, pointI)
1560 patchPointLabels[nonGlobalPatchPoints[pointI]];
1562 procPatch.neighbPoints()[nonGlobalPatchPoints[pointI]];
1564 labelHashSet faceSet;
1565 forAll(pointFaces[curPoint], faceI)
1567 faceSet.insert(pointFaces[curPoint][faceI]);
1569 labelList curFaces = faceSet.toc();
1571 labelHashSet pointSet;
1573 pointSet.insert(curPoint);
1574 for(label i=0; i<curFaces.size(); i++)
1576 const labelList& facePoints = faces[curFaces[i]];
1577 for(label j=0; j<facePoints.size(); j++)
1579 if(!pointSet.found(facePoints[j]))
1581 pointSet.insert(facePoints[j]);
1585 pointSet.erase(curPoint);
1586 labelList curPoints = pointSet.toc();
1588 label nAllPoints = curPoints.size();
1590 if (curNgbPoint == fromNgbProcLsPointStarts.size() - 1)
1593 fromNgbProcLsPoints.size()
1594 - fromNgbProcLsPointStarts[curNgbPoint];
1599 fromNgbProcLsPointStarts[curNgbPoint + 1]
1600 - fromNgbProcLsPointStarts[curNgbPoint];
1603 vectorField allPointsExt(nAllPoints);
1605 for (label i=0; i<curPoints.size(); i++)
1607 allPointsExt[counter++] = points[curPoints[i]];
1610 if (curNgbPoint == fromNgbProcLsPointStarts.size() - 1)
1614 label i=fromNgbProcLsPointStarts[curNgbPoint];
1615 i<fromNgbProcLsPoints.size();
1619 allPointsExt[counter++] = fromNgbProcLsPoints[i];
1626 label i=fromNgbProcLsPointStarts[curNgbPoint];
1627 i<fromNgbProcLsPointStarts[curNgbPoint+1];
1631 allPointsExt[counter++] = fromNgbProcLsPoints[i];
1635 // Remove duplicate points
1636 vectorField allPoints(nAllPoints, vector::zero);
1637 boundBox bb(allPointsExt, false);
1638 scalar tol = 0.001*mag(bb.max() - bb.min());
1641 forAll(allPointsExt, pI)
1643 bool duplicate = false;
1644 for (label i=0; i<nAllPoints; i++)
1663 allPoints[nAllPoints++] =
1668 allPoints.setSize(nAllPoints);
1674 "void faMesh::calcPointAreaNormals() const"
1675 ) << "There are no enough points for quadrics "
1676 << "fitting for a point at processor patch"
1677 << abort(FatalError);
1680 // Transforme points
1681 vector origin = points[curPoint];
1682 vector axis = result[curPoint]/mag(result[curPoint]);
1683 vector dir = (allPoints[0] - points[curPoint]);
1684 dir -= axis*(axis&dir);
1686 coordinateSystem cs("cs", origin, axis, dir);
1688 scalarField W(allPoints.size(), 1.0);
1690 forAll(allPoints, pI)
1692 W[pI] = 1.0/magSqr(allPoints[pI] - points[curPoint]);
1695 cs.localPosition(allPoints[pI]);
1698 scalarRectangularMatrix M
1705 for(label i=0; i<allPoints.size(); i++)
1707 M[i][0] = sqr(allPoints[i].x());
1708 M[i][1] = sqr(allPoints[i].y());
1709 M[i][2] = allPoints[i].x()*allPoints[i].y();
1710 M[i][3] = allPoints[i].x();
1711 M[i][4] = allPoints[i].y();
1714 scalarSquareMatrix MtM(5, 0.0);
1716 for (label i = 0; i < MtM.n(); i++)
1718 for (label j = 0; j < MtM.m(); j++)
1720 for (label k = 0; k < M.n(); k++)
1722 MtM[i][j] += M[k][i]*M[k][j]*W[k];
1727 scalarField MtR(5, 0);
1729 for (label i = 0; i < MtR.size(); i++)
1731 for (label j = 0; j < M.n(); j++)
1733 MtR[i] += M[j][i]*allPoints[j].z()*W[j];
1737 scalarSquareMatrix::LUsolve(MtM, MtR);
1739 vector curNormal = vector(MtR[3], MtR[4], -1);
1741 curNormal = cs.globalVector(curNormal);
1743 curNormal *= sign(curNormal&result[curPoint]);
1745 result[curPoint] = curNormal;
1750 // Correct global points
1751 if (globalData().nGlobalPoints() > 0)
1753 const labelList& spLabels =
1754 globalData().sharedPointLabels();
1756 const labelList& addr = globalData().sharedPointAddr();
1758 for (label k=0; k<globalData().nGlobalPoints(); k++)
1760 List<List<vector> > procLsPoints(Pstream::nProcs());
1762 label curSharedPointIndex = findIndex(addr, k);
1766 if (curSharedPointIndex != -1)
1768 label curPoint = spLabels[curSharedPointIndex];
1770 labelHashSet faceSet;
1771 forAll(pointFaces[curPoint], faceI)
1773 faceSet.insert(pointFaces[curPoint][faceI]);
1775 labelList curFaces = faceSet.toc();
1777 labelHashSet pointSet;
1778 pointSet.insert(curPoint);
1779 for (label i=0; i<curFaces.size(); i++)
1781 const labelList& facePoints = faces[curFaces[i]];
1782 for (label j=0; j<facePoints.size(); j++)
1784 if (!pointSet.found(facePoints[j]))
1786 pointSet.insert(facePoints[j]);
1790 pointSet.erase(curPoint);
1791 labelList curPoints = pointSet.toc();
1793 vectorField locPoints(points, curPoints);
1795 procLsPoints[Pstream::myProcNo()] = locPoints;
1797 boundBox bb(locPoints, false);
1798 tol = 0.001*mag(bb.max() - bb.min());
1801 Pstream::gatherList(procLsPoints);
1802 Pstream::scatterList(procLsPoints);
1804 if (curSharedPointIndex != -1)
1806 label curPoint = spLabels[curSharedPointIndex];
1808 label nAllPoints = 0;
1809 forAll(procLsPoints, procI)
1811 nAllPoints += procLsPoints[procI].size();
1814 vectorField allPoints(nAllPoints, vector::zero);
1817 forAll(procLsPoints, procI)
1819 forAll(procLsPoints[procI], pointI)
1821 bool duplicate = false;
1822 for (label i=0; i<nAllPoints; i++)
1829 - procLsPoints[procI][pointI]
1841 allPoints[nAllPoints++] =
1842 procLsPoints[procI][pointI];
1847 allPoints.setSize(nAllPoints);
1853 "void faMesh::calcPointAreaNormals() const"
1854 ) << "There are no enough points for quadrics "
1855 << "fitting for a global processor point "
1856 << abort(FatalError);
1859 // Transforme points
1860 vector origin = points[curPoint];
1861 vector axis = result[curPoint]/mag(result[curPoint]);
1862 vector dir = (allPoints[0] - points[curPoint]);
1863 dir -= axis*(axis&dir);
1865 coordinateSystem cs("cs", origin, axis, dir);
1867 scalarField W(allPoints.size(), 1.0);
1869 forAll(allPoints, pointI)
1872 1.0/magSqr(allPoints[pointI] - points[curPoint]);
1875 cs.localPosition(allPoints[pointI]);
1878 scalarRectangularMatrix M
1885 for (label i=0; i<allPoints.size(); i++)
1887 M[i][0] = sqr(allPoints[i].x());
1888 M[i][1] = sqr(allPoints[i].y());
1889 M[i][2] = allPoints[i].x()*allPoints[i].y();
1890 M[i][3] = allPoints[i].x();
1891 M[i][4] = allPoints[i].y();
1894 scalarSquareMatrix MtM(5, 0.0);
1895 for (label i = 0; i < MtM.n(); i++)
1897 for (label j = 0; j < MtM.m(); j++)
1899 for (label k = 0; k < M.n(); k++)
1901 MtM[i][j] += M[k][i]*M[k][j]*W[k];
1906 scalarField MtR(5, 0);
1907 for (label i = 0; i < MtR.size(); i++)
1909 for (label j = 0; j < M.n(); j++)
1911 MtR[i] += M[j][i]*allPoints[j].z()*W[j];
1915 scalarSquareMatrix::LUsolve(MtM, MtR);
1917 vector curNormal = vector(MtR[3], MtR[4], -1);
1919 curNormal = cs.globalVector(curNormal);
1921 curNormal *= sign(curNormal&result[curPoint]);
1923 result[curPoint] = curNormal;
1928 result /= mag(result);
1932 tmp<edgeScalarField> faMesh::edgeLengthCorrection() const
1936 Info<< "tmp<edgeScalarField> faMesh::edgeLengthCorrection() const : "
1937 << "Calculating edge length correction" << endl;
1940 tmp<edgeScalarField> tcorrection
1946 "edgeLengthCorrection",
1947 mesh_.pointsInstance(),
1955 edgeScalarField& correction = tcorrection();
1958 const vectorField& pointNormals = pointAreaNormals();
1961 forAll (correction.internalField(), edgeI)
1963 scalar sinAlpha = mag
1965 pointNormals[edges()[edgeI].start()]^
1966 pointNormals[edges()[edgeI].end()]
1969 scalar alpha = asin(sinAlpha);
1971 correction.internalField()[edgeI] = cos(alpha/2.0);
1975 forAll (boundary(), patchI)
1977 const edgeList::subList patchEdges =
1978 boundary()[patchI].patchSlice(edges());
1980 forAll (patchEdges, edgeI)
1982 scalar sinAlpha = mag
1984 pointNormals[patchEdges[edgeI].start()]^
1985 pointNormals[patchEdges[edgeI].end()]
1988 scalar alpha = asin(sinAlpha);
1990 correction.boundaryField()[patchI][edgeI] = cos(alpha/2.0);
1999 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
2001 } // End namespace Foam
2003 // ************************************************************************* //