zoomy_core.model.boundary_conditions module#
Module zoomy_core.model.boundary_conditions.
- class zoomy_core.model.boundary_conditions.BoundaryCondition(*, tag, name)#
Bases:
ParameterizedDefault implementation. The required data for the ‘ghost cell’ is the data from the interior cell. Can be overwritten e.g. to implement periodic boundary conditions.
- tag = 'bc'#
- compute_boundary_condition(time, X, dX, Q, Qaux, parameters, normal)#
Symbolic builder for the boundary value — used by
BoundaryConditions.get_boundary_condition_function()to assemble the indexedPiecewiseBC kernel.
- compute_boundary_gradient(time, X, dX, Q, Qaux, parameters, normal)#
Symbolic builder for the boundary normal-direction gradient
∂Q/∂nat the face — used byBoundaryConditions.get_boundary_gradient_function()to assemble the indexedPiecewiseboundary-gradient kernel (consumed by the diffusion path).Default: zero Neumann. Subclasses override when a non-zero gradient is part of the BC (e.g. prescribed-flux Robin BCs).
- face_state(Q_face, Qaux_face, normal, parameters)#
Compute the boundary-side Riemann state from the reconstructed face value.
Called at boundary faces inside the flux operator.
Q_faceis the MUSCL-reconstructed interior state at the face. Returns the state that the Riemann solver sees on the boundary side.Default: same as Q_face (Neumann / zero-flux).
Deprecated since version Use:
face_valueinstead.
- face_value(Q_inner, Qaux_inner, normal, d_face, time, parameters)#
Boundary-side Riemann state for convective flux (ghost-cell-free).
- Parameters:
Q_inner (ndarray, shape (n_vars,)) – Cell-center values of the adjacent interior cell.
Qaux_inner (ndarray, shape (n_aux,)) – Auxiliary variables of the adjacent interior cell.
normal (ndarray, shape (dim,)) – Outward unit face normal.
d_face (float) – Distance from interior cell center to face center.
time (float) – Current simulation time.
parameters (ndarray, shape (n_params,)) – Model parameters.
- Returns:
The state that the Riemann solver sees on the boundary side.
- Return type:
ndarray, shape (n_vars,)
- face_gradient(Q_inner, Q_face, Qaux_inner, normal, d_face, time, parameters)#
Face-normal gradient dQ/dn for diffusive flux at boundary.
- Parameters:
Q_inner (ndarray, shape (n_vars,)) – Cell-center values of the adjacent interior cell.
Q_face (ndarray, shape (n_vars,)) – The
face_valueresult (already computed upstream).Qaux_inner (ndarray, shape (n_aux,)) – Auxiliary variables of the adjacent interior cell.
normal (ndarray, shape (dim,)) – Outward unit face normal.
d_face (float) – Distance from interior cell center to face center.
time (float) – Current simulation time.
parameters (ndarray, shape (n_params,)) – Model parameters.
- Returns:
Face-normal gradient at the boundary face.
- Return type:
ndarray, shape (n_vars,)
- name = 'BoundaryCondition'#
- class zoomy_core.model.boundary_conditions.Extrapolation(*, use_gradient, tag, name)#
Bases:
BoundaryConditionExtrapolation. (class).
- use_gradient = True#
- compute_boundary_condition(time, X, dX, Q, Qaux, parameters, normal)#
Compute boundary condition.
- face_state(Q_face, Qaux_face, normal, parameters)#
Extrapolation: boundary state = interior face state (zero flux).
- face_value(Q_inner, Qaux_inner, normal, d_face, time, parameters)#
Extrapolation: boundary state = interior cell state.
- face_gradient(Q_inner, Q_face, Qaux_inner, normal, d_face, time, parameters)#
Extrapolation: zero Neumann (no normal gradient).
- name = 'Extrapolation'#
- class zoomy_core.model.boundary_conditions.InflowOutflow(*, prescribe_fields, tag, name)#
Bases:
BoundaryConditionInflow / outflow boundary — prescribe selected state fields, extrapolate the rest.
prescribe_fieldsmaps a state index to a spec. A spec is either a bare value (scalar or symbolic expression — the field is replaced by it) or adictcarrying a"mode"key:{"mode": "replace", "value": v}—Q_out[k] = v.{"mode": "inlet_outlet", "value": v}— OpenFOAMinletOutletstyle: the field takesvwhere the interior is inflowing (Q[k] >= 0) and keeps the interior value otherwise (so backflow is never overridden):Q_out[k] = conditional(Q[k] >= 0, v, Q[k]). The indexkis assumed to be a momentum component whose positive direction points into the domain.{"mode": "blend", "target": t, "weight": w}— a soft inflow:Q_out[k] = Q[k] + max(0, t - Q[k]) * w.w = 0means “no inflow” (the field stays at its interior value);w = 1pulls it fully tot.
Every
value/target/weightis a scalar or a symbolic expression — typically built by the codegen driver from model parameters (e.g. a piecewise-linear Q(t) timeline interpolated over a fixed block of timeline parameters). The BC plugs the expressions in; it never builds them and it never reads data.- prescribe_fields = {}#
- compute_boundary_condition(time, X, dX, Q, Qaux, parameters, normal)#
Compute boundary condition.
- face_value(Q_inner, Qaux_inner, normal, d_face, time, parameters)#
InflowOutflow (numpy path): prescribe selected fields, rest from the interior. Supports constant
replacespecs only — the symbolicinlet_outlet/blendmodes and parameter-valued prescriptions flow through the codegen path (compute_boundary_condition).
- name = 'InflowOutflow'#
- class zoomy_core.model.boundary_conditions.Lambda(*, prescribe_fields, tag, name)#
Bases:
BoundaryConditionLambda. (class).
- prescribe_fields = {}#
- compute_boundary_condition(time, X, dX, Q, Qaux, parameters, normal)#
Compute boundary condition.
- name = 'Lambda'#
- class zoomy_core.model.boundary_conditions.FromData(*, prescribe_fields, timeline, tag, name)#
Bases:
BoundaryConditionFromData. (class).
- prescribe_fields = {}#
- timeline = None#
- compute_boundary_condition(time, X, dX, Q, Qaux, parameters, normal)#
Compute boundary condition.
- name = 'FromData'#
- class zoomy_core.model.boundary_conditions.CharacteristicReflective(*, D, L, M, R, S, tag, name)#
Bases:
BoundaryConditionCharacteristicReflective. (class).
- R = None#
- L = None#
- D = None#
- S = None#
- M = None#
- compute_boundary_condition(time, X, dX, Q, Qaux, parameters, normal)#
Compute boundary condition.
- name = 'CharacteristicReflective'#
- class zoomy_core.model.boundary_conditions.Wall(*, blending, momentum_field_indices, permeability, use_gradient, wall_slip, tag, name)#
Bases:
BoundaryConditionWall. (class).
- momentum_field_indices = [[1, 2]]#
- permeability = 0.0#
- wall_slip = 1.0#
- blending = 0.0#
- use_gradient = True#
- compute_boundary_condition(time, X, dX, Q, Qaux, parameters, normal)#
Compute boundary condition.
- face_state(Q_face, Qaux_face, normal, parameters)#
Wall: reflect normal momentum component of the reconstructed face value.
- face_value(Q_inner, Qaux_inner, normal, d_face, time, parameters)#
Wall: reflect normal momentum, copy scalars.
- Momentum decomposition:
u_wall = slip * u_tangential - (1 - perm) * u_normal
Scalars are extrapolated (copied from interior).
- name = 'Wall'#
- class zoomy_core.model.boundary_conditions.RoughWall(*, CsW, Ks, blending, momentum_field_indices, permeability, use_gradient, wall_slip, tag, name)#
Bases:
WallRoughWall. (class).
- CsW = 0.5#
- Ks = 0.001#
- compute_boundary_condition(time, X, dX, Q, Qaux, parameters, normal)#
Compute boundary condition.
- face_value(Q_inner, Qaux_inner, normal, d_face, time, parameters)#
RoughWall: Wall reflection with distance-dependent slip.
- name = 'RoughWall'#
- class zoomy_core.model.boundary_conditions.Periodic(*, periodic_to_physical_tag, tag, name)#
Bases:
BoundaryConditionPeriodic. (class).
- periodic_to_physical_tag = ''#
- compute_boundary_condition(time, X, dX, Q, Qaux, parameters, normal)#
Compute boundary condition.
- name = 'Periodic'#
- class zoomy_core.model.boundary_conditions.WindStress(*, prescribe_gradients, prescribe_values, tag, name)#
Bases:
BoundaryConditionMixed Neumann + Dirichlet BC — POM-style wind-stress surface.
Some state rows get a prescribed value (Dirichlet); others get a prescribed face-normal gradient (Neumann). Rows mentioned in neither default to zero-gradient extrapolation. Symbolic specs in state / aux / parameter symbols are supported on the codegen and Firedrake-DG paths (boundary kernels lambdify the resulting expressions); the numpy paths require numeric specs.
Built for the canonical POM surface BC (BM87 §2.15):
ρ_o K_M ∂_z U = τ_o ← Neumann on the velocity row ∂_z T = 0 ← Neumann on the tracer row q² = B₁^(2/3) u_τs² ← Dirichlet on the q² row q²ℓ = 0 ← Dirichlet on the q²ℓ row
For the velocity Neumann gradient
∂_z U = u_*² / K_Mthe user pulls the symbolicK_Mfrom the model so the BC stays consistent with the interior closure:sm = SystemModel.from_model(my_col) K_M_sym = sm.diffusion_matrix[0, 0, 0, 0] bc = WindStress( tag="surface", prescribe_gradients={0: sm.parameters.u_star**2 / K_M_sym, 1: 0}, prescribe_values={2: sm.parameters.B1 ** sp.Rational(2, 3) * sm.parameters.u_star**2, 3: 0}, )
Same mechanism handles the bottom BC (no-slip + zero heat flux + bottom-stress q² + zero q²ℓ) with different per-row specs.
- prescribe_values = {}#
- prescribe_gradients = {}#
- compute_boundary_condition(time, X, dX, Q, Qaux, parameters, normal)#
Dirichlet rows take the prescribed value; others extrapolate.
- compute_boundary_gradient(time, X, dX, Q, Qaux, parameters, normal)#
Neumann rows take the prescribed gradient; others zero.
- face_value(Q_inner, Qaux_inner, normal, d_face, time, parameters)#
Numpy: Dirichlet rows get the prescribed value, others extrapolate. Only numeric specs work here; symbolic specs need to flow through the codegen / Firedrake-DG path.
- face_gradient(Q_inner, Q_face, Qaux_inner, normal, d_face, time, parameters)#
Numpy: Neumann rows get the prescribed gradient; others zero. Numeric specs only (same caveat as
face_value).
- name = 'WindStress'#
- class zoomy_core.model.boundary_conditions.SystemExtrapolation(tag=None)#
Bases:
objectApply Extrapolation to all equations in the system.
- apply_to_system_bcs(system_bcs, tag=None)#
- class zoomy_core.model.boundary_conditions.SystemPeriodic(tag=None, periodic_to_physical_tag='')#
Bases:
objectApply Periodic to all equations in the system.
- apply_to_system_bcs(system_bcs, tag=None)#
- class zoomy_core.model.boundary_conditions.SystemWall(tag=None, permeability=0.0, wall_slip=1.0)#
Bases:
objectSystem-aware wall BC: Extrapolation for scalars, reflection for momentum.
Applied via
system.boundary_conditions.apply(SystemWall(), tag="right"). The Wall BC holds a reference to the system and reads its equations to determine scalar vs momentum fields automatically.- Parameters:
tag (str) – Boundary tag (e.g. “right”, “bottom”).
permeability (float) – 0 = impermeable (default), 1 = fully permeable.
wall_slip (float) – 1 = free-slip (default), 0 = no-slip.
- apply_to_system_bcs(system_bcs, tag=None, system=None)#
- class zoomy_core.model.boundary_conditions.WallMomentumBC(tag, system_bcs, permeability=0.0, wall_slip=1.0, use_gradient=True)#
Bases:
objectWall BC for momentum equations — reads the system to build reflection.
Holds a reference to the
SystemBoundaryConditions(and thus knows which equations exist). At compile time, determines the momentum vector grouping automatically from the equation names.The normal/tangential decomposition works for any system derived from INS: SWE (hu), SME (hu0, hu1, …), VAM (hu, hv, hw moments), full INS.
- property momentum_equations#
Momentum equations in the current system.
- zoomy_core.model.boundary_conditions.compile_system_bcs(system_bcs, equation_variable_map, dimension)#
Translate system-aware BCs into the legacy BoundaryConditions container.
Reads per-equation, per-tag BCs from
system_bcsand produces aBoundaryConditionswith one entry per tag. Theequation_variable_mapmaps equation names to variable indices so the Wall BC knows which indices form the momentum vector.- Parameters:
system_bcs (SystemBoundaryConditions) –
equation_variable_map (dict) –
{equation_name: [var_index, ...]}dimension (int) – Model dimension (1 or 2 for horizontal).
- Return type:
- class zoomy_core.model.boundary_conditions.BoundaryConditions(boundary_conditions=None, **params)#
Bases:
ParameterizedBoundaryConditions. (class).
- boundary_conditions_list = []#
- property list_sorted_function_names#
List sorted function names.
- property boundary_conditions_list_dict#
Boundary conditions list dict.
- get_boundary_condition_function(time, X, dX, Q, Qaux, parameters, normal, function_name='boundary_conditions')#
Get boundary condition function.
- name = 'BoundaryConditions'#
- get_boundary_gradient_function(time, X, dX, Q, Qaux, parameters, normal, function_name='boundary_gradients')#
Indexed symbolic kernel for the boundary face-normal gradient
∂Q/∂n.Same shape and contract as
get_boundary_condition_function(): aFunctionwhose first argument is the BC index, with aPiecewisebody dispatching to each BC subclass’sBoundaryCondition.compute_boundary_gradient(). The default per BC is zero Neumann (matchesExtrapolation’s gradient); subclasses override when a non-zero gradient is part of the BC.