From 22cefff4a8a64cde6ce51734c4b354b9aaed2c2f Mon Sep 17 00:00:00 2001 From: Mark Olesen Date: Wed, 7 Aug 2019 12:33:23 +0200 Subject: [PATCH] ENH: add toopSet attachedToCell (#1394) - grows or shrinks a cellSet based on its external perimeter. Not yet working across coupled boundaries. --- src/meshTools/Make/files | 1 + .../attachedToCell/attachedToCell.C | 277 ++++++++++++++++++ .../attachedToCell/attachedToCell.H | 115 ++++++++ 3 files changed, 393 insertions(+) create mode 100644 src/meshTools/sets/cellSources/attachedToCell/attachedToCell.C create mode 100644 src/meshTools/sets/cellSources/attachedToCell/attachedToCell.H diff --git a/src/meshTools/Make/files b/src/meshTools/Make/files index 28b8b4f24f..fb78d1f065 100644 --- a/src/meshTools/Make/files +++ b/src/meshTools/Make/files @@ -152,6 +152,7 @@ sets/topoSetSource/topoSetSource.C cellSources = sets/cellSources $(cellSources)/topoSetCellSource/topoSetCellSource.C +$(cellSources)/attachedToCell/attachedToCell.C $(cellSources)/boundaryToCell/boundaryToCell.C $(cellSources)/boxToCell/boxToCell.C $(cellSources)/cellToCell/cellToCell.C diff --git a/src/meshTools/sets/cellSources/attachedToCell/attachedToCell.C b/src/meshTools/sets/cellSources/attachedToCell/attachedToCell.C new file mode 100644 index 0000000000..3938c245c2 --- /dev/null +++ b/src/meshTools/sets/cellSources/attachedToCell/attachedToCell.C @@ -0,0 +1,277 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / O peration | + \\ / A nd | Copyright (C) 2019 OpenCFD Ltd. + \\/ M anipulation | +------------------------------------------------------------------------------- +License + This file is part of OpenFOAM. + + OpenFOAM is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with OpenFOAM. If not, see . + +\*---------------------------------------------------------------------------*/ + +#include "attachedToCell.H" +#include "polyMesh.H" +#include "cellSet.H" +#include "syncTools.H" +#include "addToRunTimeSelectionTable.H" + +// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * // + +namespace Foam +{ + defineTypeNameAndDebug(attachedToCell, 0); + addToRunTimeSelectionTable(topoSetSource, attachedToCell, word); + addToRunTimeSelectionTable(topoSetSource, attachedToCell, istream); + addToRunTimeSelectionTable(topoSetCellSource, attachedToCell, word); + addToRunTimeSelectionTable(topoSetCellSource, attachedToCell, istream); + addNamedToRunTimeSelectionTable + ( + topoSetCellSource, + attachedToCell, + word, + attached + ); + addNamedToRunTimeSelectionTable + ( + topoSetCellSource, + attachedToCell, + istream, + attached + ); +} + + +Foam::topoSetSource::addToUsageTable Foam::attachedToCell::usage_ +( + attachedToCell::typeName, + "\n Usage: attachedToCell\n\n" + " Select attached cells\n\n" +); + + +// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // + +void Foam::attachedToCell::combine(topoSet& set, const bool add) const +{ + const cellList& cells = mesh_.cells(); + const labelList& faceOwn = mesh_.faceOwner(); + const labelList& faceNei = mesh_.faceNeighbour(); + const label nIntFaces = mesh_.nInternalFaces(); + const polyBoundaryMesh& patches = mesh_.boundaryMesh(); + + boolList isCoupled(mesh_.nBoundaryFaces(), false); + + for (const polyPatch& pp : patches) + { + if (pp.coupled()) + { + label facei = pp.start(); + forAll(pp, i) + { + isCoupled[facei-nIntFaces] = true; + ++facei; + } + } + } + + // The starting set of cells + bitSet current(cells.size()); + + for (const label celli : set) + { + current.set(celli); + } + + // The perimeter faces of the cell set + bitSet outsideFaces(mesh().nFaces()); + + // Get coupled cell status + boolList neiInSet(mesh_.nFaces()-nIntFaces, false); + + bitSet updates(current); + + for (label stepi = 0; stepi < steps_; ++stepi) + { + // Mark up all perimeter faces + + // Don't attempt extra efficiency with caching old values, + // this make the parallel transfer too troublesome + + outsideFaces.reset(); + for (const label celli : current) + { + for (const label facei : cells[celli]) + { + outsideFaces.flip(facei); + } + } + + // Coupled faces + neiInSet = false; + + for + ( + bitSet::const_iterator iter = outsideFaces.cbegin(nIntFaces); + iter != outsideFaces.cend(); + ++iter + ) + { + const label facei = *iter; + + if (isCoupled[facei-nIntFaces]) + { + neiInSet[facei-nIntFaces] = true; + } + } + + syncTools::swapBoundaryFaceList(mesh_, neiInSet); + + forAll(neiInSet, bfacei) + { + if (neiInSet[bfacei]) + { + outsideFaces.flip(bfacei+nIntFaces); + } + } + + updates.reset(); + + for (const label facei : outsideFaces) + { + updates.set(faceOwn[facei]); + if (mesh_.isInternalFace(facei)) + { + updates.set(faceNei[facei]); + } + } + + if (add) + { + // Face information retained for next loop + + // Changed cells + updates -= current; + + if (verbose_) + { + Info<< " Grow " << current.count() + << " by " << updates.count() << endl; + } + + current |= updates; + } + else + { + // Changed cells + updates &= current; + + if (verbose_) + { + Info<< " Shrink " << current.count() + << " by " << updates.count() << endl; + } + + current -= updates; + } + + for (const label celli: updates) + { + addOrDelete(set, celli, add); + } + + if (updates.none()) + { + break; + } + } +} + + +// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // + +Foam::attachedToCell::attachedToCell +( + const polyMesh& mesh, + const label steps +) +: + topoSetCellSource(mesh), + steps_(max(steps, 1)) +{} + + +Foam::attachedToCell::attachedToCell +( + const polyMesh& mesh, + const dictionary& dict +) +: + attachedToCell(mesh, dict.getOrDefault