Lumberyardに触れる(最終回)-衝突判定編


※2018年1月18日時点の情報です
← Lumberyardに触れる(5)-ゲーム開始編

はじめに

今回はキャラクターが指定範囲に入った場合にゲームをクリアの文字を表示させる処理をいれます。
多分今回が最後になります。

エンティティ作成

到着するべきエリアが分かりづらいので、オブジェクトなどを設置していきます。
Asset Browserでオブジェクトを指定してPersectiveにドラッグすると追加されます。


今回は2つ設置。

次にあたり判定の空間を設定するためにEntityOutlinerにて右クリックしてCreate Entityをします。
下のような構成にしました。

EndPointが範囲を設定するエンティティで
他2つのエンティティが先程追加したオブジェクトになります。

EndPointにBoxShapeとTriggerAreaのコンポーネントを追加します。
BoxShapeの範囲が衝突範囲でTriggerAreaが衝突判定の設定です。

下ような見た目になります。

Luaスクリプト

衝突を判定と、処理を実装するためにスクリプトを追加します。

まず、はじめにTriggerEventのスクリプトをEndPointのEntityに
Add Componentします。
EventNameが衝突時に発行されるイベント名になります。(詳しい中身は自分で読んで下さい)

次にスクリプトを追加し、
イベント受取のスクリプトを自作します。
早速中身を見ていきます。

スクリプト全体

gameend.lua
local gameend =
{
    Properties =
    {
        EventName = { default = "", description = "" },
    }
}

function gameend:OnActivate()
    self.ShowScreenEventId = GameplayNotificationId(self.entityId, self.Properties.EventName, "float");
    self.ShowScreenHandler = GameplayNotificationBus.Connect(self, self.ShowScreenEventId); 
end

function gameend:OnDeactivate()
    if (self.canvasEntityId ~= nil) then
        UiCanvasManagerBus.Broadcast.UnloadCanvas(self.canvasEntityId);
        self.canvasEntityId = nil;
    end
end

function gameend:ShowScreen()
    self.canvasEntityId = UiCanvasManagerBus.Broadcast.LoadCanvas("UI/gameend.uicanvas");
end

function gameend:OnEventBegin(value) 
    if (GameplayNotificationBus.GetCurrentBusId() == self.ShowScreenEventId) then

        self:ShowScreen();
        if(ShowScreenHandler ~nil)
            self.ShowScreenHandler:Disconnect();
            self.ShowScreenHandler = nil;
        end
    end
end

return gameend

OnActivate

gameend.lua
function gameend:OnActivate()
    self.ShowScreenEventId = GameplayNotificationId(self.entityId, self.Properties.EventName, "float");
    self.ShowScreenHandler = GameplayNotificationBus.Connect(self, self.ShowScreenEventId); 
end

OnActivate(エンティティ開始時に動作)で通知バスに接続します。

OnDeactivate

gameend.lua
function gameend:OnDeactivate()
    if (self.canvasEntityId ~= nil) then
        UiCanvasManagerBus.Broadcast.UnloadCanvas(self.canvasEntityId);
        self.canvasEntityId = nil;
    end
end

エンティティ終了時に、キャンバスがロードされていれば、消すようにします。

OnEventBegin

gameend.lua
function gameend:OnEventBegin(value) 
    if (GameplayNotificationBus.GetCurrentBusId() == self.ShowScreenEventId) then

        self:ShowScreen();
        if(ShowScreenHandler ~nil)
            self.ShowScreenHandler:Disconnect();
            self.ShowScreenHandler = nil;
        end
    end
end

イベントが送られた時プロパティで設定したイベントと同じならShowScreenの実行と
通知バスとの接続を切るようにしました。
ShowScreenが実行されたら通知バスはもう要らないので、さっさと接続は切ります。

ShowScreen

gameend.lua
function gameend:ShowScreen()
    self.canvasEntityId = UiCanvasManagerBus.Broadcast.LoadCanvas("UI/gameend.uicanvas");
end

ShowScreenは指定したキャンバスをロードします。
キャンバスはゲームスタートの文字を作った時、同様にUIEditorで作成しました。

Luaスクリプトは以上になります。
しかし、一点だけオブジェクトの修正があります。

オブジェクトの衝突判定

オブジェクトを追加しただけでは下のようにキャラクターがめり込んでしまいます。

解決するためには2つコンポーネントを追加する必要があります。

衝突判定を追加するコンポーネントに追加するのは
RigidBodyPhysicsとMeshColliderです。
(RigidBodyPhysicsではなくStaticPysicsでも良いです)

RigidBodyPhysicsで実装する場合は一点注意が必要で、
今回作ったスクリプトの衝突判定で反応してしまうので
Interacts with triggersのチェックを外す必要があります。
これで実装完了です。

うまく動けばキャラを指定の範囲まで移動した時に
キャンバスが表示されるはずです。

以上で全行程の終了となります。

まとめ

以上で「Lumberyardに触れる」は終了となります。

正直ゲーム以外のコンテンツならAmazon Sumerianっていうものもあるので、そちらにLumberyardの機能が吸収されそうな印象をうけました。
社員の方にたまたま聞く機会があったのですが、newWorldっていうプロジェクト(?)で新しいサンプルを作っているとの噂があるので、まだ進展はあると思いますし、
日本でも手軽にTwitchをつかった色んなゲームが出て欲しいので応援したいところではあります。

しかし、ぶっちゃけ勢いが落ちてるので不安です。
個人的にはCrytekがどうなるか、ECサイトメインであるアマゾンがしっかりゲームづくりをサポートしてくれるのか、今後もちゃんと開発してくれるのかを含めて、どうなるか不安で、どの企業も手を付けられていないような印象をうけました。

暇を持て余して業務中にひたすら触っていましたが、正直触った意味があったのか、よくわかりませんでした。
この資料が、どこかの誰かの役に立つとうれしいです。
最後まで読んでくださり、ありがとうございました。