20 #ifndef OPM_BOUNDARYPERIODICITY_HEADER_INCLUDED 21 #define OPM_BOUNDARYPERIODICITY_HEADER_INCLUDED 23 #include <dune/common/fvector.hh> 25 #include <opm/common/ErrorMacros.hpp> 65 return cmpval() < other.cmpval();
83 bool match(std::vector<BoundaryFaceInfo>& bfaces,
int face,
int lower,
int upper);
86 template <
class Gr
idView>
88 std::array<double, 6>& side_areas,
90 const std::array<bool, 2*GridView::dimension>& is_periodic,
91 double spatial_tolerance = 1e-6)
95 const int dim = GridView::dimension;
96 typedef typename GridView::template Codim<0>::Iterator CI;
97 typedef typename GridView::IntersectionIterator FI;
98 typedef Dune::FieldVector<double, dim> Vector;
99 std::vector<FI> bface_iters;
103 for (CI c = g.template begin<0>(); c != g.template end<0>(); ++c) {
104 for (FI f = g.ibegin(*c); f != g.iend(*c); ++f) {
105 if (f->boundaryId()) {
106 bface_iters.push_back(f);
107 Vector fcent = f->geometry().center();
108 for (
int dd = 0; dd < dim; ++dd) {
109 low[dd] = std::min(low[dd], fcent[dd]);
110 hi[dd] = std::max(hi[dd], fcent[dd]);
112 max_bid = std::max(max_bid, f->boundaryId());
116 int num_bdy = bface_iters.size();
117 if (max_bid != num_bdy) {
118 OPM_THROW(std::runtime_error,
"createPeriodic() assumes that every boundary face has a unique boundary id. That seems to be violated.");
122 std::ranges::fill(side_areas, 0.0);
124 bfinfo.reserve(num_bdy);
125 for (
int i = 0; i < num_bdy; ++i) {
128 bf.
bid = bface_iters[i]->boundaryId();
132 bf.
area = bface_iters[i]->geometry().volume();
133 bf.
centroid = bface_iters[i]->geometry().center();
134 for (
int dd = 0; dd < dim; ++dd) {
136 if (fabs(coord - low[dd]) <= spatial_tolerance) {
139 }
else if (fabs(coord - hi[dd]) <= spatial_tolerance) {
145 std::cerr <<
"Centroid: " << bf.
centroid <<
"\n";
146 std::cerr <<
"Bounding box min: " << low <<
"\n";
147 std::cerr <<
"Bounding box max: " << hi <<
"\n";
148 OPM_THROW(std::runtime_error,
"Boundary face centroid not on bounding box. Maybe the grid is not an axis-aligned shoe-box?");
152 bfinfo.push_back(bf);
154 assert(bfinfo.size() == bface_iters.size());
157 std::sort(bfinfo.begin(), bfinfo.end());
160 for (
int i = 0; i < num_bdy; ++i) {
161 if (bfinfo[i].partner_face_index != -1) {
164 if (!is_periodic[bfinfo[i].canon_pos]) {
167 int lower = std::max(0, i - 10);
168 int upper = std::min(num_bdy, i + 10);
169 bool ok =
match(bfinfo, i, lower, upper);
172 ok =
match(bfinfo, i, 0, num_bdy);
174 OPM_MESSAGE(
"Warning: No partner found for boundary id " << bfinfo[i].bid);
282 #endif // OPM_BOUNDARYPERIODICITY_HEADER_INCLUDED int partner_face_index
Face index of periodic partner, or -1 if no partner.
Definition: BoundaryPeriodicity.hpp:52
double area
Face area.
Definition: BoundaryPeriodicity.hpp:56
bool match(std::vector< BoundaryFaceInfo > &bfaces, int face, int lower, int upper)
Find a match (periodic partner) for the given face.
Definition: BoundaryPeriodicity.cpp:25
int face_index
Face index in [0, ..., #faces - 1].
Definition: BoundaryPeriodicity.hpp:41
Definition: BoundaryPeriodicity.hpp:38
Inverting small matrices.
Definition: ImplicitAssembly.hpp:43
Dune::FieldVector< double, 3 > centroid
Face centroid.
Definition: BoundaryPeriodicity.hpp:58
int canon_pos
Canonical position of face: 0 -> xmin 1 -> xmax 2 -> ymin 3 -> ymax ...
Definition: BoundaryPeriodicity.hpp:50
bool operator<(const BoundaryFaceInfo &other) const
Comparison operator.
Definition: BoundaryPeriodicity.hpp:63
void findPeriodicPartners(std::vector< BoundaryFaceInfo > &bfinfo, std::array< double, 6 > &side_areas, const GridView &g, const std::array< bool, 2 *GridView::dimension > &is_periodic, double spatial_tolerance=1e-6)
Common implementation for the various createPeriodic functions.
Definition: BoundaryPeriodicity.hpp:87
int bid
Boundary id of this face.
Definition: BoundaryPeriodicity.hpp:43
int partner_bid
Boundary id of periodic partner face, or 0 if no parner.
Definition: BoundaryPeriodicity.hpp:54