🫰

【Godot4.2】固有名でアクセスすると NULL が格納される場合の原因から解決まで。【解決】

2024/02/08に公開

【問題】

まず、

# コード1
button = get_tree().current_scene.get_node("%Button")

%Button ノードにアクセスできていたものが、

# コード2
button = get_tree().current_scene.get_node("%Button")

では、%Button ノードにアクセスができなくなりました。button のデータは null でした。


【整理】

「コード1」と「コード2」では、シーン内の状況に変更があります。
以下に、その変更点を列挙します。

  • 親ノードを Control ノードとし、 %Button ノードをブランチとしてシーンに保存しました。

  • 一つだけだった

変更の結果、「コード2」では %Button ノードにアクセスすることができないという問題が発生しました。


原因を教えてもらおうと思います。Copilot で検索してみました。

Q: Godot4で固有名でノードにアクセスできないときの原因を詳しく教えて

【 Copilot 】

Godot4で固有名を使用してノードにアクセスできない場合、以下のような原因が考えられます:

  • 固有名が正しく設定されていない:固有名は、ノードを右クリックして「Access as Unique Name」を選択することで設定します。しかし、この手順が正しく行われていない場合、または固有名が間違っている場合、ノードにアクセスできません。
  • ノードが存在しない:指定した固有名のノードがシーンツリーに存在しない場合、ノードにアクセスすることはできません。
  • ノードがまだロードされていない:シーンがまだ完全にロードされていない場合、ノードにアクセスすることはできません。

これらの問題を解決するには、固有名が正しく設定されていることを確認し、ノードがシーンツリーに存在することを確認し、シーンが完全にロードされてからノードにアクセスするようにします。


Q: 固有名が正しく設定されていて、ノードがシーンツリーに存在していて、シーンが完全にロードされている場合、固有名を使用してノードにアクセスできない原因を教えて

【 Copilot 】

固有名が正しく設定されていて、ノードがシーンツリーに存在し、シーンが完全にロードされているにもかかわらず、固有名を使用してノードにアクセスできない場合、以下のような原因が考えられます:

  • ノードの再親指定(reparent):ノードの親を変更した場合、固有名でのアクセスが失われることがあります。これは、ノードのパスが変更されるためです。
  • 固有名のスコープ:固有名は、そのノードが属するシーン内でのみ有効です。そのため、別のシーンから固有名を使用してノードにアクセスしようとすると、そのノードを見つけることができません。
  • 固有名の競合:同じ固有名を持つノードが複数存在する場合、どのノードにアクセスすべきかが不明確になり、エラーが発生する可能性があります。

これらの問題を解決するには、ノードの再親指定を避け、固有名のスコープを理解し、固有名の競合を避けることが重要です。


Q: 固有名が正しく設定されていて、ノードがシーンツリーに存在していて、シーンが完全にロードされている場合、固有名を使用してノードにアクセスできない原因を教えてください。Pathを使うとアクセスできますが、固有名でアクセスすることができません

【 Copilot 】

固有名が正しく設定されていて、ノードがシーンツリーに存在し、シーンが完全にロードされているにもかかわらず、固有名を使用してノードにアクセスできない場合、以下のような原因が考えられます:

  • 固有名のスコープ:固有名は、そのノードが属するシーン内でのみ有効です。そのため、別のシーンから固有名を使用してノードにアクセスしようとすると、そのノードを見つけることができません。
  • ノードの再親指定(reparent):ノードの親を変更した場合、固有名でのアクセスが失われることがあります。これは、ノードのパスが変更されるためです。
  • 固有名の競合:同じ固有名を持つノードが複数存在する場合、どのノードにアクセスすべきかが不明確になり、エラーが発生する可能性があります。

これらの問題を解決するには、固有名のスコープを理解し、ノードの再親指定を避け、固有名の競合を避けることが重要です。


以上から、以下の原因を求めることができました。

  • 固有名のスコープ:固有名は、そのノードが属するシーン内でのみ有効です。そのため、別のシーンから固有名を使用してノードにアクセスしようとすると、そのノードを見つけることができません。

固有名のスコープを理解することで問題を解決することができるとわかりました。


【解決】

固有名ではなくパスを用いてアクセスするように変更を加えました。

# コード3. 原因対策後
button = get_tree().current_scene.get_node("xxx/Control/Button")

その結果、%Button ノードにアクセスすることができるようになりました。


ここまで見ていただき、ありがとうございます

Discussion