とりとめも

藻類が学んだり感じたりしたことを未来の自分のために書き留めるところ

【Godotお勉強メモ】シグナルの使い方で頭がうわーってなるので整理しましょう

前回までのあらすじ

Godotを触り始めました。

marimomemo.hatenablog.jp

今回はシグナルについて、チュートリアル終了時点の理解をまとめます。
バージョン:Godot 4.1.3

シグナルって?

ゲーム内のイベントに伴い発火し、イベントの発生をノードに通知するためのもの。
例えば以下のようなイベントで発火し、事前に設定した接続先に通知されます。

  • オブジェクトの衝突
  • ボタンのクリック
  • スクリプトによる明示的な発火

シグナルの接続先って?

シグナルはノード上の関数に対して「接続」されます。
つまり、シグナルが発火するイベントが生じたとき、接続先の関数が呼び出されます。

シグナルの3ステップ

以下のようなステップを踏むことで、特定のイベントをトリガーに関数を実行させることができます。

  1. シグナルを作成する(ノードの組み込みシグナルなら作成不要)
  2. シグナルの接続先を指定する
  3. シグナルを発火させる

設定方法

前述の3ステップはいずれも、「コードによる設定」と「コード以外による設定」という大きく2通りがあります。
使い分けの方針はまだ咀嚼しきれていませんが、ひとまずそれらの方法をまとめます。

まずは以下の表の通り。

コードによる設定 コード以外による設定
シグナルの作成・定義 signalを使う。
例:signal hoge_signal
ビルトインノードの組み込みシグナルが該当。
例:BaseButtonノードのpressedシグナル
シグナルの接続 connectを使う。
例:connect("hoge_signal", "hoge_node"(または"self"), "hoge_func")
Godotエディタで、対象ノードのシグナルタブで設定
シグナルの発火 1.ノードのemit_signalメソッド
例:emit_signal("hoge_signal")
2.シグナルオブジェクトのemitメソッド
例:hoge_signal.emit()
組み込みシグナルの場合の、それに対応するイベント。
例:ボタンがクリックされたとき

コードで作成したものを カスタムシグナル と呼ぶらしいです。

お悩みポイント

私が何に混乱しているのかわかりました。
シグナルの「接続」方法の使い分けです。

まずは「作成」と「発火」の関係

当然ながら、

  • カスタムシグナル:コードで発火
  • 組み込みシグナル:それに対応するイベントで発火

という方法をとるのが良さそうです。 *1

「接続」は?

一方で、シグナルの接続は、必ずしも「カスタムシグナルはコードで」「組み込みシグナルはGUIで」とはいかないと思います。
チュートリアルでは、signalで宣言したカスタムシグナルをシグナルタブで接続していました。

チュートリアルの例

反対にチュートリアルでは、コードで宣言したシグナルをコード(connect)で接続するケースはありませんでした。
「コードで宣言したシグナルをGUIで接続する」ことになるので、どこで何を接続しているかわからなくなりそうだなあ、と感じており、さらに調べてみれば、コードで接続する方法も用意されているので、頭がぐるぐるしてきたのでした。

オブジェクトクラス — Godot Engine (4.x)の日本語のドキュメント

一旦のまとめ

connectによる接続と、シグナルタブによる接続の違いは、接続されるタイミングだと思います(今の私が理解している限りは)

  • シグナルタブによる接続:シーンツリーが構成された時点
  • connectによる接続:コードが呼ばれた時点

つまり、シーンツリーを構成する時点では接続したくなかったり、動的に接続のオンオフを切り替えたいときなどに、connectを使えばいいのでしょうか?

まだ多数のシーンやシグナルが相互作用するゲームを作成しておらず、実際の状況がイメージできていませんが、今はそれくらいの理解でいようと思います。

とりあえず頭の中が整理できたので良かったです。

*1:そもそもカスタムシグナルはコードで発火させるしかない。組み込みシグナルはコードで発火させることも可能ですが、わざわざ組み込みシグナルを使う以上は、対応するイベントの発生に任せるのが適切に感じます。