BUG: cvMesh: Orientation of faces across processor boundaries fixed.

This commit is contained in:
laurence
2012-02-15 14:33:35 +00:00
parent eb3eacd114
commit 3fd8fb20a0
2 changed files with 215 additions and 0 deletions

View File

@ -707,6 +707,12 @@ private:
DynamicList<Foam::point>& existingEdgeLocations
) const;
//- Return a list of the nearest feature edge locations
List<pointIndexHit> nearestFeatureEdgeLocations
(
const Foam::point& pt
) const;
//- Check if a point is near any feature edge points.
bool pointIsNearFeatureEdgeLocation(const Foam::point& pt) const;
@ -983,6 +989,27 @@ private:
labelList& neighbour
) const;
//- Rotates a face by an amount nPos
face rotateFace
(
const face& f,
const label nPos
) const;
//- Rotate the faces on processor patches if necessary
void reorderProcessorPatches
(
const word& meshName,
const fileName& instance,
const pointField& points,
faceList& faces,
const wordList& patchTypes,
const wordList& patchNames,
const labelList& patchSizes,
const labelList& patchStarts,
const labelList& procNeighbours
) const;
//- Disallow default bitwise copy construct
conformalVoronoiMesh(const conformalVoronoiMesh&);

View File

@ -562,6 +562,178 @@ void Foam::conformalVoronoiMesh::writeMesh
}
Foam::face Foam::conformalVoronoiMesh::rotateFace
(
const face& f,
const label nPos
) const
{
face newF(f.size());
forAll(f, fp)
{
label fp1 = (fp + nPos) % f.size();
if (fp1 < 0)
{
fp1 += f.size();
}
newF[fp1] = f[fp];
}
return newF;
}
void Foam::conformalVoronoiMesh::reorderProcessorPatches
(
const word& meshName,
const fileName& instance,
const pointField& points,
faceList& faces,
const wordList& patchTypes,
const wordList& patchNames,
const labelList& patchSizes,
const labelList& patchStarts,
const labelList& procNeighbours
) const
{
fvMesh tempMesh
(
IOobject
(
meshName,
instance,
runTime_,
IOobject::NO_READ,
IOobject::NO_WRITE
),
xferCopy(pointField()),
xferCopy(faceList()),
xferCopy(cellList())
);
List<polyPatch*> patches(patchStarts.size());
forAll(patches, p)
{
if (patchTypes[p] == processorPolyPatch::typeName)
{
patches[p] = new processorPolyPatch
(
patchNames[p],
patchSizes[p],
patchStarts[p],
p,
tempMesh.boundaryMesh(),
Pstream::myProcNo(),
procNeighbours[p]
);
}
else
{
patches[p] = polyPatch::New
(
patchTypes[p],
patchNames[p],
patchSizes[p],
patchStarts[p],
p,
tempMesh.boundaryMesh()
).ptr();
}
}
// Rotation on new faces.
labelList rotation(faces.size(), 0);
PstreamBuffers pBufs(Pstream::nonBlocking);
// Send ordering
forAll(patches, patchI)
{
if (isA<processorPolyPatch>(*patches[patchI]))
{
static_cast<processorPolyPatch*>(patches[patchI])->initOrder
(
pBufs,
primitivePatch
(
SubList<face>
(
faces,
patchSizes[patchI],
patchStarts[patchI]
),
points
)
);
}
}
pBufs.finishedSends();
// Receive and calculate ordering
bool anyChanged = false;
forAll(patches, patchI)
{
if (isA<processorPolyPatch>(*patches[patchI]))
{
labelList patchFaceMap(patchSizes[patchI], -1);
labelList patchFaceRotation(patchSizes[patchI], 0);
bool changed =
static_cast<processorPolyPatch*>(patches[patchI])->order
(
pBufs,
primitivePatch
(
SubList<face>
(
faces,
patchSizes[patchI],
patchStarts[patchI]
),
points
),
patchFaceMap,
patchFaceRotation
);
if (changed)
{
// Merge patch face reordering into mesh face reordering table
label start = patchStarts[patchI];
forAll(patchFaceRotation, patchFaceI)
{
rotation[patchFaceI + start] =
patchFaceRotation[patchFaceI];
}
anyChanged = true;
}
}
}
reduce(anyChanged, orOp<bool>());
if (anyChanged)
{
// Rotate faces (rotation is already in new face indices).
forAll(rotation, faceI)
{
if (rotation[faceI] != 0)
{
faces[faceI] = rotateFace(faces[faceI], rotation[faceI]);
}
}
}
}
void Foam::conformalVoronoiMesh::writeMesh
(
const word& meshName,
@ -583,6 +755,22 @@ void Foam::conformalVoronoiMesh::writeMesh
writeObjMesh(points, faces, word(meshName + ".obj"));
}
if (Pstream::parRun())
{
reorderProcessorPatches
(
meshName,
instance,
points,
faces,
patchTypes,
patchNames,
patchSizes,
patchStarts,
procNeighbours
);
}
fvMesh mesh
(
IOobject