mcpField
G
godot-signals-groups

godot-signals-groups

github.com/gamedev-skills開発5.4k6.9k 回インストール今日更新
リポジトリ

godot-signals-groups について

Godot 4.7 の開発者向けに、シグナルとグループでノードを疎結合にする方法を解説するスキルガイドです。接続パターンや一括処理、よくある問題を扱います。

主な機能

  1. 01型付きシグナルによるイベント通知
  2. 02Callable を使ったシグナル接続
  3. 03グループを介した一括呼び出し
  4. 04シグナルを待ってから処理を続行
  5. 05重複接続や無効なリスナーの回避

活用シーン

  1. 01アイテム取得をゲーム状態へ通知
  2. 02敵グループの一括停止や数の確認
  3. 03アニメーション完了後の戦利品生成

インストール

コマンドをコピーしてターミナルで実行します。

$npx skills add https://github.com/gamedev-skills/awesome-gamedev-agent-skills --skill godot-signals-groups

インストール後、Claude Code で/godot-signals-groupsを入力して読み込まれたか確認します。

同梱ファイルreferences/signal-patterns.md

詳細

Godot Signals & Groups (4.x)

オブザーバーパターン(シグナル)とグループを使ってノードを疎結合にし、シーン間で参照をハードコードすることなく、複数のノードに一度に処理を実行します。対象は Godot 4.7 です。

使用する場面

  • ノードが他のノードを直接参照せずに、「何かが起きた」こと(プレイヤーの死亡、アイテムの取得、ウェーブのクリアなど)を伝える必要がある場合に使用します。
  • ノード全体のカテゴリに一度に処理を実行する必要がある場合(「敵をすべて一時停止する」「すべてのチェックポイントを保存する」など)に使用します。

使用しない場面: シグナルの基本的な 構文 → godot-gdscript。シーン構造とインスタンス化 → godot-nodes-scenes。シーンをまたぐグローバルイベントには、オートロードから発行してください(godot-nodes-scenes を参照)。

基本的なワークフロー

  1. 方向を決めます。 子ノード/サブシーンはシグナルを上位に向けて 発行 し、親ノードが接続します。これにより、子ノードは再利用可能になり、誰がリッスンしているかを知る必要がなくなります。
  2. 発行側で型付きシグナルを宣言し、イベント発生時に emit() で発行します。
  3. Callable で接続します(sig.connect(_on_sig))。必要に応じて、エディターの Node ドックから接続することもできます。1 回だけ実行する場合は CONNECT_ONE_SHOT を使い、追加のコンテキストを渡す場合は bind() を使います。
  4. ブロードキャストにはグループを使います。 ノードを名前付きグループに追加し、get_tree().get_nodes_in_group(...) で反復処理するか、call_group(...) を呼び出します。
  5. 必要に応じて(長寿命のリスナーを解放する前などに)接続を解除し、重複接続を避けるために is_connected() を確認します。

パターン

1. 上位に向けて発行し、親から接続する
# coin.gd (reusable pickup — knows nothing about the player or HUD)
extends Area2D
signal collected(value: int)

func _on_body_entered(body: Node) -> void:
    if body.is_in_group("player"):
        collected.emit(10)
        queue_free()
# level.gd (the parent wires the coin to game state)
func _ready() -> void:
    for coin in get_tree().get_nodes_in_group("coins"):
        coin.collected.connect(_on_coin_collected)

func _on_coin_collected(value: int) -> void:
    GameState.add_score(value)
2. 接続フラグ:1 回限りの接続と追加引数のバインド
func _ready() -> void:
    # Fire exactly once, then auto-disconnect.
    $Door.opened.connect(_on_door_opened, CONNECT_ONE_SHOT)
    # bind() appends arguments supplied at connect time (after the signal's own args).
    $RedButton.pressed.connect(_on_button.bind("red"))

func _on_button(color: String) -> void:
    print("Pressed the %s button" % color)
3. グループ:複数のノードにブロードキャストする
func pause_all_enemies() -> void:
    # Call a method on every node in the "enemies" group (no-op if missing).
    get_tree().call_group("enemies", "set_paused", true)

func count_enemies() -> int:
    return get_tree().get_nodes_in_group("enemies").size()

コードから、またはエディターの Node > Groups タブからノードをグループに追加します。

func _ready() -> void:
    add_to_group("enemies")        # remove_from_group("enemies") to leave
4. シグナルをインラインで待機する
func open_chest() -> void:
    $AnimationPlayer.play("open")
    await $AnimationPlayer.animation_finished   # pause until it emits
    spawn_loot()

注意点

  • 3.x の connect シグネチャは使えません。 connect("died", self, "_on_died") → died.connect(_on_died)。接続先は Callable によって示されます。旧式の Object.connect("died", Callable(self, "_on_died")) は動作しますが、メソッド名を文字列で指定する形式は使えません。
  • 接続が重複すると、ハンドラーが複数回実行されます。 ノードを再追加した後に _ready() で再接続すると、コールバックが積み重なります。if not sig.is_connected(cb): sig.connect(cb) で防止します。
  • 解放済みのノードへの接続はエラーになります。 長寿命のリスナーは接続を解除するか、接続先のオブジェクトが解放された際に Godot が自動で接続を解除する仕組みを利用します(ノードでは自動的に解除されます)。
  • グループはシーンごとではなく SceneTree 全体で共有されます。 同じグループ名を使う 2 つのレベルは、メンバーシップを共有します。必要に応じて、グループ名に名前空間を設けてください。
  • call_group は、対象のメソッドを持たないノードを黙って無視します。 メソッド名の誤りは通知されずに失敗するため、契約が重要な場合は型付きシグナルを優先してください。
  • シグナルの引数は一致している必要があります。 引数の数や型を誤って発行するとエラーになります。型付きパラメーターを宣言し、正確な引数を指定して発行してください。

参考資料

  • 接続フラグ、遅延接続、カスタムシグナル引数、タイムアウト付きの待機、シグナルと直接呼び出しの使い分けについては、references/signal-patterns.md を参照してください。

関連スキル

  • godot-gdscript — シグナル/await 構文の基礎。
  • godot-nodes-scenes — グローバルイベントバス用のオートロード。
  • game-ai — これらのイベントを駆動・処理することの多いステートマシン。

コメント