Skip to main content

manabrew_engine/ability/effects/
encode_effect.rs

1use forge_foundation::ZoneType;
2
3use super::EffectContext;
4
5/// `SP$ Encode` — exile the spell card and encode it onto a creature (Cipher).
6///
7/// Mirrors Java's `EncodeEffect.java`.
8/// The encoded spell is exiled attached to the chosen creature. Whenever that
9/// creature deals combat damage to a player, its controller may cast a copy
10/// of the encoded card without paying its mana cost.
11///
12/// Simplified: exiles the spell card and stores its ID in the creature's
13/// `encoded_cards` list. The combat damage copy trigger is handled separately
14/// in the trigger system.
15///
16/// # Card script examples
17/// ```text
18/// A:SP$ Encode | Defined$ Self
19/// ```
20/// Struct form of this effect so it can participate in the
21/// `SpellAbilityEffect` trait hierarchy — mirrors Java's
22/// `EncodeEffect` class extending `SpellAbilityEffect`.
23#[manabrew_engine_macros::spell_effect(EncodeEffect)]
24fn resolve(ctx: &mut EffectContext, sa: &crate::spellability::SpellAbility) {
25    let controller = sa.activating_player;
26
27    let spell_card = match sa.source {
28        Some(id) => id,
29        None => return,
30    };
31
32    // Find a creature to encode onto — use target or let player choose
33    let target = sa.target_chosen.target_card.or_else(|| {
34        let bf = ctx
35            .game
36            .cards_in_zone(ZoneType::Battlefield, controller)
37            .to_vec();
38        let creatures: Vec<_> = bf
39            .into_iter()
40            .filter(|&cid| {
41                let c = ctx.game.card(cid);
42                c.is_creature() && c.controller == controller
43            })
44            .collect();
45
46        if creatures.is_empty() {
47            return None;
48        }
49
50        let chosen =
51            ctx.agents[controller.index()].choose_cards_for_effect(controller, &creatures, 1, 1);
52        chosen.into_iter().next()
53    });
54
55    let creature_id = match target {
56        Some(id)
57            if ctx.game.card(id).zone == ZoneType::Battlefield
58                && ctx.game.card(id).is_creature() =>
59        {
60            id
61        }
62        _ => return,
63    };
64
65    // Exile the spell card
66    let owner = ctx.game.card(spell_card).owner;
67    if ctx.game.card(spell_card).zone != ZoneType::Exile {
68        ctx.move_card(spell_card, ZoneType::Exile, owner);
69    }
70
71    // Encode it onto the creature
72    ctx.game
73        .card_mut(creature_id)
74        .encoded_cards
75        .push(spell_card);
76}