🔌 Status Effects — Integration Surfaces¶
This page explains where new gameplay logic should integrate with the RevFramework Status Effects system.
If you're adding a new mechanic, start here.
The Status Effects architecture is intentionally modular. Each behaviour belongs to a specific extension surface. Choosing the correct surface keeps statuses predictable, testable, and compatible with the rest of the framework.
🧠 Extension Surfaces Overview¶
| Goal | Extension Point | Example |
|---|---|---|
| Implement a new status behaviour | TimedStatusEffect / IStatusEffect |
poison, bleed, stun |
| Provide effect metadata | IStatusMetadata |
tags, dispel type |
| Allow dispels | IDispellable |
poison cleanse |
| Allow potency scaling | IAdjustableMagnitude |
damage scaling |
| Amplify incoming statuses | IStatusPotency |
aura, difficulty modifiers |
| Reduce duration of statuses | IStatusResistance |
CC resistance |
| Block statuses entirely | IStatusImmunity |
poison immunity |
| Control mutation authority | IStatusAuthority |
server authority |
| Control time flow | ITimeSource |
pause, replay |
| Construct effects by id | StatusRegistry |
plugin systems |
| Create data-driven effects | StatusEffectDefinitionBase |
designer-authored assets |
| Drive gameplay behaviour | Your own code calling StatusEffectController |
abilities, items |
⚙ Example Decision Flow¶
Create a New Damage Over Time Effect¶
Use:
TimedStatusEffect
Effects implement behaviour such as damage ticks in OnTick(...).
Apply a Status From an Ability¶
Use:
StatusEffectController.ApplyStatus(...)
Abilities, items, and pickups should apply effects through the controller, never by modifying effect state directly.
The StatusEffectController is the only supported mutation entry point.
All effect application, refresh, and removal must go through the controller.
Directly modifying effect instances or bypassing the controller is unsupported.
Create a Potency Aura¶
Use:
IStatusPotency
Auras modify effect magnitude, so they belong in potency providers.
Reduce Stun Duration¶
Use:
IStatusResistance
Resistance modifies how long effects last, not whether they apply.
Make an Actor Immune to Poison¶
Use:
IStatusImmunity
Immunity decides whether an effect may apply at all.
Server‑Authoritative Status Simulation¶
Use:
IStatusAuthority
Authority determines who may tick and mutate statuses.
Authority gates both ticking and mutation.
If authority is denied, effects will not apply or update.
Pause Status Effects During Cutscenes¶
Use:
ITimeSource
Custom time sources control how delta time flows through the controller.
🛡 Potency vs Resistance¶
These are frequently confused.
| Behaviour | Correct Surface |
|---|---|
| Increase poison damage | Potency |
| Reduce stun duration | Resistance |
| Block poison entirely | Immunity |
Rule of thumb:
- Strength changes → Potency
- Duration changes → Resistance
- Permission changes → Immunity
These are separated to keep effect behaviour deterministic and composable.
Potency affects magnitude.
Resistance affects lifetime.
They do not overlap.
📦 Effect Definitions vs Runtime Effects¶
Status Effects supports two construction workflows.
Runtime Effects¶
Created directly in code.
Example:
controller.ApplyStatus(new PoisonStatus(5f, 10f));
Use this when effects are procedural or code-driven.
Definition Assets¶
Use:
StatusEffectDefinitionBase
Definitions are ScriptableObject blueprints used by designers.
They build runtime effect instances via:
BuildEffect()
Definitions never contain runtime behaviour.
⚖ Controller vs Effect Responsibilities¶
Understanding this boundary is critical.
| Behaviour | Correct Location |
|---|---|
| Ticking effects | Controller |
| Stacking logic | Controller |
| Immunity checks | Controller |
| Effect behaviour | Effect implementation |
| Potency / resistance scaling | Providers + math service |
Effects are not orchestrators.
They are executed by the controller.
Effects should never:
- tick themselves
- query the controller's internal list
- modify other effects directly
🔗 Integrations¶
Status Effects integrates with other RevFramework modules through adapters and bridges.
Examples:
| Integration | Surface |
|---|---|
| Health system (DoT / HoT / shields) | HealthIntegration |
| Movement scaling | MovementSpeedScaler |
| Cooldown scaling | ICooldownScaleSink |
| Damage amplification | IDamageTakenModifier |
The core system never depends on these integrations.
If a required integration is not present:
- the effect still applies
- the effect still ticks
- the effect still expires
- only the integration behaviour is skipped
⚠ Common Mistakes¶
Avoid the following:
- Applying effects without a
StatusEffectController - Letting effects tick themselves
- Encoding stacking logic inside effects
- Mutating the controller’s internal active list
- Using UI to drive effect state
- Implementing potency inside effect logic instead of providers
🧩 Architecture Summary¶
Apply
├─ Immunity
├─ Stacking Rules
├─ Potency Scaling
└─ Duration Scaling
↓
Active Effects
↓
Controller Tick
↓
Effect Behaviour (OnTick)
↓
Expire / Remove
Note: Exact ordering may vary internally, but these stages are always applied within the controller pipeline.
Every extension surface plugs into one of these stages.
🔗 Related Docs¶
- Mental Model
- Public API
- System Guarantees Matrix
- FAQ