Skip to main content

RuleBindings

Trait RuleBindings 

Source
pub trait RuleBindings<P: EffectProvider + ?Sized>: 'static {
Show 16 methods // Required methods fn apply_boost( &self, b: &mut BattlerState<P>, stat_index: usize, stages: i8, ) -> bool; fn set_status(&self, b: &mut BattlerState<P>, status_index: usize) -> bool; fn has_type(&self, b: &BattlerState<P>, type_index: usize) -> bool; // Provided methods fn set_status_with_amount( &self, b: &mut BattlerState<P>, status_index: usize, _amount: u16, ) -> bool { ... } fn make_volatile( &self, _name: &str, _amount: u16, ) -> Option<P::EffectStateKind> { ... } fn type_chart_mult( &self, _ctx: &BattleCtx<'_, P>, _move_type_index: usize, _defender: BattlerRef, ) -> (u32, u32) { ... } fn current_stat_index(&self, _ctx: &BattleCtx<'_, P>) -> Option<usize> { ... } fn has_volatile( &self, _ctx: &BattleCtx<'_, P>, _who: BattlerRef, _name: &str, ) -> bool { ... } fn redirect_hp_loss( &self, _ctx: &mut BattleCtx<'_, P>, _who: BattlerRef, _source: BattlerRef, _amount: u16, ) -> bool { ... } fn move_type_is_defender_type( &self, ctx: &BattleCtx<'_, P>, move_type_index: usize, who: BattlerRef, ) -> bool { ... } fn has_status(&self, _b: &BattlerState<P>, _status_index: usize) -> bool { ... } fn has_any_status(&self, _b: &BattlerState<P>) -> bool { ... } fn battler_level(&self, _b: &BattlerState<P>) -> u16 { ... } fn resource_id(&self, resource_index: usize) -> u16 { ... } fn can_pay_resource( &self, b: &BattlerState<P>, resource_index: usize, amount: u16, ) -> bool { ... } fn pay_resource( &self, b: &mut BattlerState<P>, resource_index: usize, amount: u16, ) { ... }
}
Expand description

Resolves interned data-layer indices to concrete P::Stat/P::Status and supplies the type-chart fold + defender-type membership, all pure.

A game implements this once for its provider; the loader carries it so the zero-capture interpret bridge can reach it. The trait is generic over P: EffectProvider, so the engine learns nothing.

Required Methods§

Source

fn apply_boost( &self, b: &mut BattlerState<P>, stat_index: usize, stages: i8, ) -> bool

Apply a signed stat-stage delta to who for the interned stat_index. Returns false if the index is unknown (a no-op; the loader validates names at compile, so this is defense-in-depth). Phase 1 applies directly; the nested-TryBoost veto is driver orchestration (doc 11 §3).

Source

fn set_status(&self, b: &mut BattlerState<P>, status_index: usize) -> bool

Set who’s non-volatile status for the interned status_index. Returns false if the index is unknown.

Source

fn has_type(&self, b: &BattlerState<P>, type_index: usize) -> bool

Whether who has the type with interned chart type_index (the HasType predicate, doc 11 §1.1). Pure read.

Provided Methods§

Source

fn set_status_with_amount( &self, b: &mut BattlerState<P>, status_index: usize, _amount: u16, ) -> bool

Set who’s non-volatile status carrying a game-interpreted numeric amount (e.g. Gen-1 sleep turns). The engine resolves amount from the op’s AmountSpec — drawing its OWN rng — and hands the pure number here. Defaulted to delegate to set_status and ignore the amount, so a game whose statuses carry no duration is unaffected. Pure; no entropy.

Source

fn make_volatile(&self, _name: &str, _amount: u16) -> Option<P::EffectStateKind>

Build the game’s OPAQUE P::EffectStateKind volatile for the vocabulary name + already-resolved amount (the InflictVolatile op). The engine installs whatever is returned generically (fresh arena id) and never learns what the volatile means — only the game does. Defaulted to None ⇒ a game with no volatiles (or that doesn’t recognise name) makes the op inert. Pure — the engine already drew any rng needed for amount.

Source

fn type_chart_mult( &self, _ctx: &BattleCtx<'_, P>, _move_type_index: usize, _defender: BattlerRef, ) -> (u32, u32)

The chart fold for the in-flight move_type_index against defender’s type(s), as ONE pre-combined integer rational (num, den) (doc 12 §3.2, §5.3 — one rational ⇒ exactly one scale, avoiding per-step truncation). Default (1, 1) ⇒ inert (no chart). Pure / RNG-free.

Source

fn current_stat_index(&self, _ctx: &BattleCtx<'_, P>) -> Option<usize>

The in-flight folded stat index, if the driver stashed one for a StatIs predicate (the Sandstorm WeatherModifyStat case, doc 11 §1). Default NoneStatIs never matches. Pure.

Source

fn has_volatile( &self, _ctx: &BattleCtx<'_, P>, _who: BattlerRef, _name: &str, ) -> bool

Whether who currently has the live volatile named by name (the HasVolatile predicate, blueprint 15 §2/§3 — the Substitute block on side-status). The game inspects its own ctx.effects arena (the engine treats EffectStateKind opaquely, so only the game can tell which arena entry IS “Substitute”). Defaulted to false so a game with no volatiles (every game built so far) is unaffected and the predicate never matches. Pure read; no entropy.

Source

fn redirect_hp_loss( &self, _ctx: &mut BattleCtx<'_, P>, _who: BattlerRef, _source: BattlerRef, _amount: u16, ) -> bool

Damage-redirection seam for the DIRECT-MUTATE ops (SetHp / DamageFraction / DamageCurrentHpFraction / RepeatHits) that apply HP OUTSIDE the driver’s Event::Damage fold. Before such an op subtracts amount HP from who (attributed to source), the interpreter asks the game whether a damage sink on who should swallow it instead — a monster Substitute doll, a cross-game shield/ward/decoy. Returning true means the game HANDLED the loss (it mutated its own sink via ctx); the interpreter then SKIPS the direct HP write. Returning false (the default) leaves the op to apply HP exactly as before.

This is the ONLY binding permitted to MUTATE through ctx (every other is a pure read) — it is the redirect analogue of the TryBoost/Event::Damage interception the driver already fires for formula damage, extended to the ops the driver never routes. Defaulted to false so every existing game (and every op) is byte-identical: the loss applies unredirected, no ctx mutation, no entropy. source lets a game exempt self-inflicted loss (recoil / self-KO) from its own sink. Draws NO randomness.

Source

fn move_type_is_defender_type( &self, ctx: &BattleCtx<'_, P>, move_type_index: usize, who: BattlerRef, ) -> bool

Whether the in-flight move’s type (move_type_index, recovered from the record’s type:) equals one of who’s types (the MoveTypeIsDefenderType predicate — Gen-1 burn/freeze/paralyze self-type-immunity quirk #23, blueprint 15 §2/§3). Defaulted to false ⇒ the quirk never fires for a game that does not implement it. Pure read; no entropy. The default body delegates to has_type so a game whose has_type already answers chart membership gets the quirk for free by overriding nothing — but the engine has no move_type_index for a generic predicate, so the loader passes it through and the binding decides.

Source

fn has_status(&self, _b: &BattlerState<P>, _status_index: usize) -> bool

Whether who currently has the non-volatile status at interned status_index (the TargetHasStatus predicate — the Dream Eater sleep gate, blueprint 15 §2). The status index is the game’s vocabulary (the same indices set_status consumes). Defaulted to false ⇒ a game that does not implement it never matches. Pure read; no entropy.

Source

fn has_any_status(&self, _b: &BattlerState<P>) -> bool

Whether b has ANY non-volatile status (the TargetHasAnyStatus predicate — the Toxic “already-statused ⇒ fail” guard). The engine knows no concrete status, so the game answers. Defaulted to false ⇒ a game that doesn’t implement it never matches. Pure read; no entropy.

Source

fn battler_level(&self, _b: &BattlerState<P>) -> u16

The level of battler b (the LevelGE predicate’s gate + the level-based SetDamage sources — Seismic Toss / Night Shade / Psywave; blueprint 15 §2/§3). BattlerState<P> carries no level field (the engine is level-agnostic), so the game answers it here. Defaulted to 0 ⇒ a game that authors no level-gated op is unaffected (it never calls this) and LevelGE is 0 >= 0 == true. Pure read; no entropy. Game-agnostic: “a number the binding supplies per battler”.

Source

fn resource_id(&self, resource_index: usize) -> u16

Map an interned resource index (the ruleset’s resources: order) to the engine’s opaque resource id used in ResourcePool / BattleProvider::move_cost (the MP/SP/mana cost gate, doc 13 §4). Defaulted so games with no resources need not implement it — they never reference a resource, so it is never called. Default: identity (index as u16). Pure.

Source

fn can_pay_resource( &self, b: &BattlerState<P>, resource_index: usize, amount: u16, ) -> bool

Whether b can pay amount of the resource at interned resource_index (the PayResource op’s gate, doc 13 §4). Pure read. The default delegates to the engine’s ResourcePool via resource_id — a game that stores its pool on BattlerState.resources (the engine default) gets correct behavior for free.

Source

fn pay_resource( &self, b: &mut BattlerState<P>, resource_index: usize, amount: u16, )

Deduct amount of the resource at interned resource_index from b (the PayResource op’s deduction). Pure arithmetic — no rng. Default delegates to the engine ResourcePool.

Dyn Compatibility§

This trait is dyn compatible.

In older versions of Rust, dyn compatibility was called "object safety".

Implementors§