SpellDisruptedEvent
A declared spell came to nothing, and the caster lost it anyway.
Full documentation: SpellDisruptedEvent. Wire type: spell_disrupted.
Default visibility: player
Message codes: magic.cast.disrupted, magic.cast.fizzled
JSON Schema
{
"$defs": {
"Visibility": {
"description": "Who is allowed to see an event.\n\nEvery event has one of these two values, and the split exists because B/X keeps some rolls behind the\nreferee's screen. Filter a log on it before you show anything to a player, or call\n`GameSession.view`, which builds the player's and the referee's\nviews for you. A narrator playing referee reads both.\n\nThe values are the lowercase strings and they serialize into every event, so a renamed value is a\n`schema_version` bump.\n\nExamples:\n ```python\n from osrlib.core.events import DamageDealtEvent, HitPointsReportedEvent, Visibility\n\n log = [\n DamageDealtEvent(target_id=\"monster-0001\", amount=5),\n HitPointsReportedEvent(target_id=\"monster-0001\", current_hp=2, max_hp=7),\n ]\n shown = [event.code for event in log if event.visibility is Visibility.PLAYER]\n assert shown == [\"combat.damage.dealt\"] # the goblin's remaining hit points stay hidden\n ```",
"enum": [
"player",
"referee"
],
"title": "Visibility",
"type": "string"
}
},
"description": "A declared spell came to nothing, and the caster lost it anyway.\n\nTwo things produce one, and `code` tells them apart.\n`disrupt_casting` emits `magic.cast.disrupted` when a caster who\ndeclared a spell is hit, or otherwise stopped, before it goes off. The battle round emits\n`magic.cast.fizzled` when it judges the declaration again in the magic phase, just before the spell would\nresolve, and any one of the checks it passed at the top of the round no longer passes, because the phases\nbetween the two changed what that check reads. An ally's *silence 15' radius* anchoring on the party's\ncell and the party's last torch going out as its bearer dies are two that happen; the rule is the whole\nset of checks, not a list of cases. `reason` carries the rejection code behind a fizzle.\n\nEither way nothing resolved and the memorized copy is gone, exactly as if the spell had been cast, so tell\nthe player the spell failed and the prepared copy is spent. A scroll read that fizzles spends the scroll\nthe same way, and the caster loses no memorized copy, because a read never used one.",
"properties": {
"code": {
"default": "magic.cast.disrupted",
"title": "Code",
"type": "string",
"description": "Which of the two failures this is, defaulting to `magic.cast.disrupted`."
},
"visibility": {
"$ref": "#/$defs/Visibility",
"default": "player",
"description": "Player visibility: the caster's spell visibly fails."
},
"event_type": {
"const": "spell_disrupted",
"default": "spell_disrupted",
"title": "Event Type",
"type": "string",
"description": "The wire name for this event type."
},
"caster_id": {
"title": "Caster Id",
"type": "string",
"description": "The entity id of the caster."
},
"spell_id": {
"title": "Spell Id",
"type": "string",
"description": "The spell's content id."
},
"reversed": {
"default": false,
"title": "Reversed",
"type": "boolean",
"description": "True when the lost copy was the spell's reversed form."
},
"reason": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"default": null,
"title": "Reason",
"description": "Why a `magic.cast.fizzled` spell failed: the first rejection code the magic phase's re-check produced.\n\nAny check a declaration passes at the top of the round can produce it, so read the code rather than\nassuming a case: an ally's silence on the party's cell reads `magic.cast.silenced_area`, and a scroll\nread left in the dark reads `exploration.action.requires_light`. Match on this the way you match on a\n`Rejection`'s own code, and\nthe rejection code reference says what each one means. `None` on a\n`magic.cast.disrupted` event, which needs no reason beyond the blow that landed, and on a log written\nbefore the field existed."
}
},
"required": [
"caster_id",
"spell_id"
],
"title": "SpellDisruptedEvent",
"type": "object"
}