card-game
Compare original and translation side by side
🇺🇸
Original
English🇨🇳
Translation
ChineseCard Game
卡牌游戏
A playbook for card games — card data, the deck/hand/discard zones, the turn structure, and
how card effects resolve. This is a compositional skill: it models cards as data and wires
them to UI. It does not re-teach data assets or UI nodes; it defines the zone model, the draw
machinery, and the effect-resolution rules that keep a card game correct and bug-free.
一份卡牌游戏指南——涵盖卡牌数据、牌库/手牌/弃牌区、回合结构以及卡牌效果的结算方式。这是一项组合式技能:将卡牌建模为数据并与UI关联。它不会重新讲解数据资源或UI节点;而是定义区域模型、抽牌机制以及效果结算规则,确保卡牌游戏运行正确且无bug。
When to use
使用场景
- Use when building any game where the core objects are cards moving between zones (deck → hand → play → discard): deckbuilder, TCG/CCG, solitaire, roguelike deckbuilder.
- Use when designing draw/shuffle/reshuffle, turn structure, card costs, or how effects resolve.
When not to use: board/tile state with matching rules → . RPG with an
incidental card battler → start from . For defining cards as assets, use
/ ; for the hand/drag UI, use .
puzzlerpggodot-resourcesunity-scriptableobjectsgodot-ui-control- 当构建核心对象为卡牌并在不同区域间移动(牌库→手牌→战场→弃牌区)的游戏时使用:卡组构筑游戏、TCG/CCG、纸牌接龙、Roguelike卡组构筑游戏。
- 当设计抽牌/洗牌/重洗、回合结构、卡牌消耗或效果结算逻辑时使用。
不适用场景: 包含匹配规则的棋盘/tile状态游戏→使用技能。附带卡牌战斗系统的RPG游戏→从技能开始。若要将卡牌定义为资源,使用/;若要实现手牌拖拽UI,使用。
puzzlerpggodot-resourcesunity-scriptableobjectsgodot-ui-controlCore loop
核心循环
Draw to your hand → spend resources to play cards → effects resolve and change the board →
end the turn (cleanup/discard) → opponent/next phase → repeat until a win condition. Depth
comes from the combinations a hand allows; the engine's job is to resolve them unambiguously.
抽牌到手牌→消耗资源打出卡牌→效果结算并改变战场状态→结束回合(清理/弃牌)→对手/下一阶段→重复直至达成胜利条件。 游戏深度来自手牌允许的组合玩法;引擎的职责是明确无误地解析这些组合。
Must-have systems
必备系统
- Card data — id, name, cost, type, text, and an effect spec (data, not code).
- Zones — deck (draw pile), hand, play/board, discard, exile/removed; cards live in exactly one.
- Draw + shuffle + reshuffle — draw from deck to hand; reshuffle discard into deck when empty.
- Turn structure — phases (untap/draw/main/combat/end) as a state machine.
- Resource system — mana/energy/actions that gate how much you do per turn.
- Effect resolution — apply a card's effects in a defined order; handle targets and triggers.
- Win/loss condition — life total, deck-out, objective.
- UI — hand layout, drag/drop or tap-to-play, zone counts, targeting affordances.
- 卡牌数据——ID、名称、消耗、类型、描述文本以及效果规格(数据形式,而非代码)。
- 区域系统——牌库(抽牌堆)、手牌、战场/桌面、弃牌区、放逐/移除区;每张卡牌始终仅属于一个区域。
- 抽牌+洗牌+重洗——从牌库抽牌到手牌;牌库为空时将弃牌区重洗入牌库。
- 回合结构——将阶段(重置/抽牌/主要/战斗/结束)作为状态机实现。
- 资源系统——mana/能量/行动点数,限制每回合可执行的操作次数。
- 效果结算——按既定顺序应用卡牌效果;处理目标选择与触发事件。
- 胜负条件——生命值、牌库耗尽、目标达成。
- UI系统——手牌布局、拖拽/点击出牌、区域卡牌计数、目标选择提示。
Design knobs
设计调节项
| Knob | Effect | Notes |
|---|---|---|
| Starting hand / draw-per-turn | tempo, consistency | More draw = less variance. |
| Hand size limit | hoarding vs. use | Discard down at end of turn. |
| Deck size (min) | consistency | Smaller = more reliable combos. |
| Resource curve | what's playable when | "Mana curve" paces power. |
| Card rarity / power budget | balance | Stronger cards cost more / are rarer. |
| Determinism vs. randomness | skill vs. swing | Shuffle + random effects add variance. |
| Reshuffle rules | deck-out, fatigue | Reshuffle discard, or punish empty deck. |
| Removal / answers | counterplay | Every threat needs an answer in the pool. |
| 调节项 | 影响 | 说明 |
|---|---|---|
| 初始手牌数量/每回合抽牌数 | 节奏、稳定性 | 抽牌越多,随机性越低。 |
| 手牌上限 | 囤积vs使用 | 回合结束时弃牌至上限。 |
| 牌库最小规模 | 稳定性 | 规模越小,组合玩法越可靠。 |
| 资源曲线 | 不同阶段可玩卡牌 | “mana曲线”控制节奏与强度。 |
| 卡牌稀有度/强度预算 | 平衡性 | 强力卡牌消耗更高/稀有度更高。 |
| 确定性vs随机性 | 技巧vs运气 | 洗牌+随机效果增加变数。 |
| 重洗规则 | 牌库耗尽、疲劳 | 将弃牌区重洗入牌库,或对空牌库进行惩罚。 |
| 移除/应对手段 | 反制玩法 | 每个威胁都需要在卡牌池中存在对应的应对手段。 |
Patterns
模式示例
1. Zones + draw with automatic reshuffle
1. 区域系统+自动重洗的抽牌机制
python
undefinedpython
undefinedPseudocode. A card is in exactly one zone at a time; moving = remove here, add there.
伪代码。每张卡牌同一时间仅属于一个区域;移动操作=从当前区域移除,添加至目标区域。
def draw(n):
for _ in range(n):
if not deck:
if not discard: # truly empty: deck-out (lose, or take fatigue)
on_deck_out(); return
deck.extend(discard) # reshuffle discard into deck
discard.clear()
shuffle(deck, rng) # use a seeded RNG (see save-systems for replays)
hand.append(deck.pop())
undefineddef draw(n):
for _ in range(n):
if not deck:
if not discard: # 完全空牌:牌库耗尽(失败,或触发疲劳)
on_deck_out(); return
deck.extend(discard) # 将弃牌区重洗入牌库
discard.clear()
shuffle(deck, rng) # 使用带种子的随机数生成器(参考存档系统实现回放)
hand.append(deck.pop())
undefined2. Card as data + effect resolution
2. 卡牌数据化+效果结算
python
undefinedpython
undefinedPseudocode. Effects are a data list interpreted by the engine — not bespoke code per card.
伪代码。效果为数据列表,由引擎解析——而非每张卡牌编写定制代码。
card = {
"id": "fireball", "cost": 3, "type": "spell",
"effects": [ {"op": "damage", "amount": 6, "target": "chosen_enemy"} ],
}
def play(card, caster):
if resources[caster] < card.cost: return False # can't afford
resources[caster] -= card.cost
move(card, from_zone=hand, to_zone=play_or_discard(card))
for fx in card.effects:
resolve_effect(fx, caster) # one interpreter handles every card
return True
undefinedcard = {
"id": "fireball", "cost": 3, "type": "spell",
"effects": [ {"op": "damage", "amount": 6, "target": "chosen_enemy"} ],
}
def play(card, caster):
if resources[caster] < card.cost: return False # 资源不足,无法打出
resources[caster] -= card.cost
move(card, from_zone=hand, to_zone=play_or_discard(card))
for fx in card.effects:
resolve_effect(fx, caster) # 一个解析器处理所有卡牌
return True
undefined3. Turn structure as a phase machine
3. 回合结构作为阶段状态机
python
undefinedpython
undefinedPseudocode. Fixed phases keep timing windows (triggers, priority) unambiguous.
伪代码。固定阶段确保时间窗口(触发事件、优先权)明确无误。
PHASES = ["untap", "draw", "main", "combat", "end"]
def take_turn(player):
for phase in PHASES:
enter_phase(player, phase) # fire "on_phase" triggers here
if phase == "draw": draw(1)
if phase == "main": await player_plays_cards()
if phase == "combat": resolve_combat()
if phase == "end": discard_to_hand_limit(player); clear_temporary_effects()
undefinedPHASES = ["untap", "draw", "main", "combat", "end"]
def take_turn(player):
for phase in PHASES:
enter_phase(player, phase) # 在此触发“进入阶段”事件
if phase == "draw": draw(1)
if phase == "main": await player_plays_cards()
if phase == "combat": resolve_combat()
if phase == "end": discard_to_hand_limit(player); clear_temporary_effects()
undefinedPitfalls / failure modes
常见陷阱/失败模式
- A card existing in two zones at once → duplication/loss bugs. Enforce "exactly one zone"; move = remove-then-add, and assert no card appears twice.
- Forgetting to reshuffle → draws silently fail or crash on empty deck. Reshuffle discard, or define deck-out/fatigue explicitly (Pattern 1).
- One function per card → unmaintainable and untestable. Make effects data interpreted by a small set of operations (Pattern 2).
- Ambiguous effect order / simultaneous triggers → nondeterministic outcomes. Resolve in a defined order (a queue or stack); document LIFO vs. FIFO (refs).
- Unseeded shuffle in a game that needs replays/undo → can't reproduce. Use a seeded RNG.
- No hand limit / no answers → degenerate hoarding or unbeatable threats. Add a hand cap and ensure removal exists for every threat archetype.
- Targeting state leaks → a cancelled play leaves the board mid-targeting. Make play atomic: validate cost + targets first, then commit.
- 一张卡牌同时存在于两个区域→导致卡牌复制/丢失bug。强制“每张卡牌仅属于一个区域”;移动操作=先移除再添加,并断言卡牌不会重复出现。
- 忘记重洗→牌库为空时抽牌静默失败或崩溃。重洗弃牌区,或明确定义牌库耗尽/疲劳规则(参考模式1)。
- 每张卡牌对应一个函数→难以维护和测试。将效果设计为数据,由少量操作解析(参考模式2)。
- 效果顺序模糊/触发事件同时发生→结果不确定。按既定顺序(队列或栈)结算;文档说明LIFO或FIFO规则(参考资料)。
- 需要回放/撤销功能的游戏中使用无种子洗牌→无法复现操作。使用带种子的随机数生成器。
- 无手牌上限/无应对手段→出现囤积卡牌或无法击败的威胁。添加手牌上限,并确保每个威胁类型都有对应的移除手段。
- 目标选择状态泄露→取消出牌后战场仍处于目标选择状态。使出牌操作原子化:先验证资源+目标,再执行操作。
Composition (build it from these skills)
组合构建(基于以下技能)
- Card content: /
godot-resources— define each card as a data asset.unity-scriptableobjects - UI: for layout, scaling, and focus navigation;
game-ui-uxfor hand layout, drag/drop, zone counts, and targeting prompts.godot-ui-control - Persistence/replays: for collection, run state (roguelike deckbuilder), and seeded replays.
save-systems - Opponent AI: for an AI that evaluates playable cards and picks targets.
game-ai - Animation/feedback: the engine animation skill for card movement; for cues.
audio-design - Scripting: /
godot-gdscriptfor the effect interpreter.unity-csharp-scripting
- 卡牌内容: /
godot-resources——将每张卡牌定义为数据资源。unity-scriptableobjects - UI: 用于布局、缩放和焦点导航;
game-ui-ux用于手牌布局、拖拽、区域计数和目标选择提示。godot-ui-control - 持久化/回放: 用于卡牌收集、运行状态(Roguelike卡组构筑游戏)和带种子的回放。
save-systems - 对手AI: 用于评估可打出卡牌并选择目标的AI。
game-ai - 动画/反馈: 引擎动画技能用于卡牌移动;用于音效提示。
audio-design - 脚本: /
godot-gdscript用于效果解析器。unity-csharp-scripting
References
参考资料
- For the effect queue/stack, keywords/triggers, targeting, deckbuilder vs. constructed
archetypes, and shuffle fairness, read .
references/effect-resolution.md
- 关于效果队列/栈、关键词/触发事件、目标选择、卡组构筑vs预设卡组类型以及洗牌公平性,请阅读。
references/effect-resolution.md