そうだ、ゲームを作ろう

現状や学んだことなど記録するブログ。間違ってたらごめんね

AIで色々悩んでみた:Blackboard編

さてお次はBlackboardです。

f:id:wvigler:20191114111324p:plain

 

BlackboardはAIの「記憶容量」を司るComponentであり、個々のAIがそれぞれ違ったBlackboardを持っています。人間がひとりひとり違った記憶を持っているのと同様です。

ただし人間とは違い、「何を記憶するか」は予め決めておくことが必要です。要は変数(記憶)の「型」を決める必要があります。BlackboardのBPの中身を見ていくと、Structureに若干似ていることが分かります。

f:id:wvigler:20191115043929p:plain

左側のKeysカテゴリの下にいくつか変数が並んでいますが、これらが記憶できる領域となっています。

 

BlackboardはBlackboardAssetというBehaviorTree側のパラメーターによってBehaviorTreeに関連付けられています。RunBehaviorTree()を呼ぶと、基本的にはBlackboardAssetによって関連付けられたBlackboardが呼び出し側にComponentとして追加されます。

f:id:wvigler:20191115065537p:plain

ただこれは絶対というわけではなくUseBlackboard()呼び出すことにより全く関連付けされていないBlackboardを使うことも可能です。…まあBehaviorTreeに関連付けられていないBlackboardを使いたい、なんて状況あまりないと思いますが。

f:id:wvigler:20191115071210p:plain

 

Blackboard内のデータの書き換え、読み取りはBehaviorTree側とPawn、Controller側で別になっています。まずBehaviorTree側(つまりTask、Decolator、Serviceのいずれか)からはBP内からSetBlackboardValue()を使って書き換え、GetBlackboardValue()を使って読み取ります。ちなみにClearBlackboardValue()という関数を使ってBlackboard内のデータを初期化することも可能です。

f:id:wvigler:20191115073657p:plain

さて、上の画像ではKeyという入力ピンが見えています。これはBlackboardKeySelector型というStructureのピンでこの型がBlackboard内の変数とこれらの関数をつなぐ橋渡しをします。この変数をBP内で用意し、EditableにしておくことでBehaviorTree内から関連付けられているBlackboardの変数を指定することができます。

f:id:wvigler:20191115075538p:plain

f:id:wvigler:20191115080208p:plain

 

お次はPawn及びController側からの操作です。こちらはSetValueAs???()とGetValueAs???()を使用します。

f:id:wvigler:20191115081929p:plain

Blackboardの指定はGetBlackboard()やUseBlackboard()などからComponentを取得して行います。そしてKeyの指定はNameと呼ばれる文字列に変数名を入力します。つまり由緒正しい文字列指定です。変数化してもいいし、上の画像のようにMakeLiteralで直接書き込んでも問題ありません。

 

さて、Blackboardの操作には注意点があります。それはBlackboardEditor、BehaviorTreeEditor、その他のBPなど画面を行ったり来たりする機会が多い上に、文字列指定はもちろん、BlackboardKeySelectorも間違ったデータを指定していたとしてもエラーが基本的には出ない、ということです。

実際入力ミスの多発地帯で、なんか妙な動きをするなと思ったら入力し忘れだったり、指定ミスだったりすることがしょっちゅうあります。AI全般に言えることですが、入力ミスの可能性は常に頭に入れておきましょう。

 

ということでBlackboardについてはこんな感じです。次はNavMeshにするかぁ…画像を用意するのが一番キツい…orz

 

なにか間違い、ご指摘、ご質問等があれば是非お願いいたします。