27#ifndef FD_BOUNDARIES_2D_H
28#define FD_BOUNDARIES_2D_H
41template <
typename T,
typename DESCRIPTOR,
int direction,
int orientation>
48 template <concepts::DynamicCell CELL>
52 template <
int deriveDirection,
typename CELL,
typename V=CELL::value_t>
53 void interpolateGradients(CELL& blockLattice, V velDeriv[DESCRIPTOR::d])
const any_platform;
64template<
typename T,
typename DESCRIPTOR,
int NORMAL_X,
int NORMAL_Y>
73 template <concepts::DynamicCell CELL>
76 cell.template setField<descriptors::CHEM_POTENTIAL>(
77 cell.neighbor({-NORMAL_X,-NORMAL_Y}).template getField<descriptors::CHEM_POTENTIAL>());
79 T rho0 = cell.computeRho();
80 T rho1 = cell.neighbor({-NORMAL_X,-NORMAL_Y}).computeRho();
82 cell.template setField<descriptors::CHEM_POTENTIAL>(
89template<
typename T,
typename DESCRIPTOR,
int NORMAL_X,
int NORMAL_Y>
98 template <concepts::DynamicCell CELL>
101 cell.template setField<descriptors::CHEM_POTENTIAL>(
102 cell.neighbor({-NORMAL_X,-NORMAL_Y}).template getField<descriptors::CHEM_POTENTIAL>());
108template<
typename T,
typename DESCRIPTOR,
int NORMAL_X,
int NORMAL_Y>
117 template <concepts::DynamicCell CELL>
120 T rhoBoundaryNew, rhoBoundaryOld, rhoBulk, u[2];
122 rhoBoundaryOld = cell.computeRho();
124 cell.neighbor({-NORMAL_X,-NORMAL_Y}).computeRhoU(rhoBulk, u);
130 if (normalVec[0] == 0) {
131 uPerp = normalVec[1] * u[1];
132 }
else if (normalVec[1] == 0) {
133 uPerp = normalVec[0] * u[0];
136 rhoBoundaryNew = (rhoBoundaryOld + uPerp * rhoBulk) / (1. + uPerp);
137 cell.defineRho(rhoBoundaryNew);
139 cell.template setField<descriptors::CHEM_POTENTIAL>(
140 cell.neighbor({-NORMAL_X,-NORMAL_Y}).template getField<descriptors::CHEM_POTENTIAL>());
142 cell.template setField<descriptors::CHEM_POTENTIAL>(
149template<
typename T,
typename DESCRIPTOR,
int NORMAL_X,
int NORMAL_Y>
158 template <concepts::DynamicCell CELL>
161 T rhoBoundaryNew, rhoBoundaryOld, rhoBulk, u[2];
163 rhoBoundaryOld = cell.computeRho();
165 cell.neighbor({-NORMAL_X,-NORMAL_Y}).computeRhoU(rhoBulk, u);
171 if (normalVec[0] == 0) {
172 uPerp = normalVec[1] * u[1];
173 }
else if (normalVec[1] == 0) {
174 uPerp = normalVec[0] * u[0];
177 rhoBoundaryNew = (rhoBoundaryOld + uPerp * rhoBulk) / (1. + uPerp);
178 cell.defineRho(rhoBoundaryNew);
180 cell.template setField<descriptors::CHEM_POTENTIAL>(
181 cell.neighbor({-NORMAL_X,-NORMAL_Y}).template getField<descriptors::CHEM_POTENTIAL>());
192template<
typename T,
typename DESCRIPTOR,
int NORMAL_X,
int NORMAL_Y>
203 template <concepts::DynamicCell CELL,
typename PARAMETERS>
206 auto addend =
parameters.template get<descriptors::ADDEND>();
208 T rhoBulk = cell.neighbor({-NORMAL_X,-NORMAL_Y}).computeRho();
211 for (
int iPop = 1; iPop < DESCRIPTOR::q ; ++iPop) {
212 rhoTmp += cell[iPop];
215 T rhoBoundary = rhoBulk + addend;
216 rhoBoundary -= rhoTmp;
218 cell[0] = rhoBoundary - 1.;
220 cell.template setField<descriptors::CHEM_POTENTIAL>(
221 cell.neighbor({-NORMAL_X,-NORMAL_Y}).template getField<descriptors::CHEM_POTENTIAL>());
223 cell.template setField<descriptors::CHEM_POTENTIAL>(
230template<
typename T,
typename DESCRIPTOR,
int NORMAL_X,
int NORMAL_Y>
240 template <concepts::DynamicCell CELL,
typename PARAMETERS>
243 auto addend =
parameters.template get<descriptors::ADDEND>();
245 T rhoBulk = cell.neighbor({-NORMAL_X,-NORMAL_Y}).computeRho();
248 for (
int iPop = 1; iPop < DESCRIPTOR::q ; ++iPop) {
249 rhoTmp += cell[iPop];
252 T rhoBoundary = rhoBulk + addend;
253 rhoBoundary -= rhoTmp;
255 cell[0] = rhoBoundary - 1.;
257 cell.template setField<descriptors::CHEM_POTENTIAL>(
258 cell.neighbor({-NORMAL_X,-NORMAL_Y}).template getField<descriptors::CHEM_POTENTIAL>());
267template <
typename T,
typename DESCRIPTOR,
int NORMAL_X,
int NORMAL_Y>
276 template <concepts::DynamicCell CELL>
283template <
typename T,
typename DESCRIPTOR,
int direction,
int orientation>
290 util::populationsContributingToVelocity<DESCRIPTOR, direction,
298 template <concepts::DynamicCell CELL>
301 template <concepts::DynamicCell CELL>
309template <
typename T,
typename DESCRIPTOR>
313 int discreteNormalX_,
int discreteNormalY_);
314 int extent()
const override {
return 0; }
315 int extent(
int whichDirection)
const override {
return 0; }
318 int x1_,
int y0_,
int y1_)
override;
321 int reflectionPop[DESCRIPTOR::q];
325template <
typename T,
typename DESCRIPTOR>
330 int discreteNormalX_,
int discreteNormalY_);
345template <
typename T,
typename DESCRIPTOR,
int xNormal,
int yNormal>
354 template <concepts::DynamicCell CELL>
362template<
typename T,
typename DESCRIPTOR,
int xNormal,
int yNormal>
371 template <
typename CELL,
typename PARAMETERS>
374 auto u_conv =
parameters.template get<descriptors::MAX_VELOCITY>();
376 auto cell1 = cell.neighbor(normal);
377 auto outlet_cell = cell.template getField<descriptors::CONV_POPS>();
379 for (
int iPop=0; iPop < DESCRIPTOR::q; ++iPop) {
380 outlet_cell[iPop] = (outlet_cell[iPop] + u_conv * cell1[iPop]) / ((T)1 + u_conv);
381 cell[iPop] = outlet_cell[iPop];
383 cell.template setField<descriptors::CONV_POPS>(outlet_cell);
392template<
typename T,
typename DESCRIPTOR,
int xNormal,
int yNormal>
401 template <
typename CELL,
typename PARAMETERS>
404 auto u_conv =
parameters.template get<descriptors::MAX_VELOCITY>();
406 auto outlet_cell = cell.template getField<descriptors::CONV_POPS>();
408 for (
int iPop=0; iPop < DESCRIPTOR::q; ++iPop) {
409 cell[iPop] = outlet_cell[iPop];
412 auto phi = cell.template getField<descriptors::STATISTIC>();
413 phi[0] = cell.computeRho();
414 cell.template setField<descriptors::STATISTIC>(phi);
415 auto phiGhost = cell.neighbor(normal).template getField<descriptors::STATISTIC>();
416 phiGhost[0] = (phiGhost[0] + u_conv * phi[0]) / ((T)1 + u_conv);
417 if (phiGhost[0] > 1.0001) phiGhost[0] = 1;
418 if (phiGhost[0] < -0.0001) phiGhost[0] = 0;
419 cell.neighbor(normal).template setField<descriptors::STATISTIC>(phiGhost);
422 if (cell.neighbor(tangent).template getField<descriptors::SCALAR>() == 2 ||
423 cell.neighbor(tangent).template getField<descriptors::BOUNDARY>() == 2) {
424 cell.neighbor(normal+tangent).template setField<descriptors::STATISTIC>(phiGhost);
427 if (cell.neighbor(tangent).template getField<descriptors::SCALAR>() == 2 ||
428 cell.neighbor(tangent).template getField<descriptors::BOUNDARY>() == 2) {
429 cell.neighbor(normal+tangent).template setField<descriptors::STATISTIC>(phiGhost);
439template<
typename T,
typename DESCRIPTOR>
447 template <
typename CELL>
449 auto outlet_cell = cell.template getField<descriptors::CONV_POPS>();
450 for (
int iPop=0; iPop < DESCRIPTOR::q; ++iPop) {
451 cell[iPop] = outlet_cell[iPop];
PostProcessor for pressure / velocity outflow boundaries in the free energy model.
static constexpr OperatorScope scope
void apply(CELL &cell) any_platform
This class computes the skordos BC in 2D on a convex corner but with a limited number of terms added ...
void apply(CELL &cell) any_platform
static constexpr OperatorScope scope
Interface of 2D post-processing steps.
This class computes a slip BC in 2D.
void processSubDomain(BlockLattice< T, DESCRIPTOR > &blockLattice, int x0_, int x1_, int y0_, int y1_) override
Execute post-processing step on a sublattice.
SlipBoundaryProcessor2D(int x0_, int x1_, int y0_, int y1_, int discreteNormalX_, int discreteNormalY_)
int extent(int whichDirection) const override
Extent of application area along a direction (0 or 1)
void process(BlockLattice< T, DESCRIPTOR > &blockLattice) override
Execute post-processing step.
int extent() const override
Extent of application area (0 for purely local operations)
PostProcessorGenerator2D< T, DESCRIPTOR > * clone() const override
PostProcessor2D< T, DESCRIPTOR > * generate() const override
SlipBoundaryProcessorGenerator2D(int x0_, int x1_, int y0_, int y1_, int discreteNormalX_, int discreteNormalY_)
This class computes a convection BC on a flat wall in 2D.
void initialize(CELL &cell) any_platform
void apply(CELL &cell) any_platform
static constexpr OperatorScope scope
This class computes the skordos BC on a flat wall in 2D but with a limited number of terms added to t...
void apply(CELL &cell) any_platform
static constexpr OperatorScope scope
constexpr T invCs2() any_platform
Top level namespace for all of OpenLB.
OperatorScope
Block-wide operator application scopes.
@ PerCell
Per-cell application, i.e. OPERATOR::apply is passed a CELL concept implementation.
@ PerCellWithParameters
Per-cell application with parameters, i.e. OPERATOR::apply is passed a CELL concept implementation an...
Interface for post-processing steps – header file.
This class overcomes overwriting populations from streaming for convective boundary conditions.
void apply(CELL &cell) any_platform
static constexpr OperatorScope scope
This class computes the convective boundary condition for the populations of a phase field solving LB...
static constexpr OperatorScope scope
void apply(CELL &cell, PARAMETERS ¶meters) any_platform
This class computes the convective boundary condition for phi at ghost nodes for a phase field solvin...
static constexpr OperatorScope scope
void apply(CELL &cell, PARAMETERS ¶meters) any_platform
PostProcessors for the chemical potential boundary condition in the free energy model.
static constexpr OperatorScope scope
void apply(CELL &cell) any_platform
static constexpr OperatorScope scope
void apply(CELL &cell) any_platform
static constexpr OperatorScope scope
void apply(CELL &cell) any_platform
void apply(CELL &cell) any_platform
static constexpr OperatorScope scope
PostProcessor for the wetting boundary condition in the free energy model.
static constexpr OperatorScope scope
void apply(CELL &cell, PARAMETERS ¶meters) any_platform
void apply(CELL &cell, PARAMETERS ¶meters) any_platform
static constexpr OperatorScope scope
Base of a field whose size is defined by [C_0,C_1,C_2]^T * [1,D,Q].