UE4の勉強記録

UE4の勉強の記録です。個人用です。

「Unreal Engine 4.xを使用してRPGを作成する」の足りない部分を作成する Combat Engineの自作4

f:id:kazuhironagai77:20200524221941p:plain

<前文>

False, null, そしてpingなどの頻繁に使用するプログラミング用語の正しい発音は日本人のプログラマーの間で結構議論になるみたいです。フォルスかファルス、ヌルかナル?ピンもしくはピング?カタカナは英語の発音を正しく表せない以上どちらも間違っているが正解です。私がこのブログで書いているように、発音が曖昧なプログラミング用語はフォルス(false)、ヌル(null)、そしてピン(ping)の様に片仮名の後に括弧で英語を書くのが誤解を与えない正しい書き方なのです。なぜならこれをファルス(false)、ナル(null)、そしてピング(ping)と書いても読む人が意味を間違える事はありません。

正し、今、英語の音素が区別出来るようになるゲームを開発していて発音記号(IPA)に非常に詳しくなっているので、これらの単語の発音記号(IPA)による表記が気になります。それで今回falseの正しい発音記号と日本語にした場合、どっちが近いのか調べて見ました。

False

Wikionary のFalseにはイギリス、ニュージーランド、オーストラリアでは/fɔːls/もしくは/fɒls/、アメリカでは/fɔls/もしくは/fɑls/と書かれています。イギリス、ニュージーランド、オーストラリアの発音ではɔːもしくはɒと表記されているのでオウ、もしくはオーに近い発音です。なのでイギリス、ニュージーランド、オーストラリア式の発音ではフォルスが正しいんでしょう。アメリカ式の発音ではɔもしくはɑと書かれています。

あれ?ɔなんて母音アメリカ式の発音ありましたっけ。

調べて来ました。

ɔは日本語で敢えて言えばオウに近い音でlaw, tall,  そしてdaughterなどに使われる音だそうです。ただし、アメリカ人の間でもɔは発音しない人は結構いてその人達はɔの音はɑで代用するそうです。ɔの音をɑで代用したからと言って通じない事は全くないそうです。ɔの音をɑで代用するのは西海岸の方言だ。と言う人もいますが実際にはアメリカ全体でɔの音をɑで代用する人としない人がいて地域による差はあまり見られないそうです。

フーン。勉強になりました。

因みにɑの音は敢えて日本語で言えばアです。オーといいながらアーと言うと大体近い音になります。となるとアメリカ式の発音ならばfalseはフォルスもしくはファルスになりますね。

となると結論は、ファルスでもフォルスでも両方正しい。となりますね。

それでは今週の勉強を始めます。

<本文>

うーん。あんまりにもPure virtual function…のエラーの修理に時間を取られてしまったので何をやっていたのか正直忘れてしまいました。過去のブログを読み直したら、Pure virtual function…のエラーが出る。直す。直らない。なら最初から作り直す。との流れに成っていました。

前回作成したエラーの出ないprojectであるch4_3は4月19日のブログの途中までやり直したのと同じ状態になっているみたいです。のでその続きからやっていきます。

1. やり直しの続き

1. Enemy Monster Infoの作成

EnemyMonsterInfoクラス、まだ作成していなかったの?正直驚きと失望で一杯です。たった一個のエラーでこんなに予定から遅れてしますとは。仕方ないです。作って行きます。

f:id:kazuhironagai77:20200524222133p:plain

ハイ出来ました。もう何回もやっているので重要な所だけしか書きません。

エディターが一回だけクラッシュしたのも同じです。

2. Enemy Monsterの作成

はい。今度は敵のモンスターのデータテーブルを作成します。

と思ったんですが素直にch3からインポートする事にしました。

f:id:kazuhironagai77:20200524222205p:plain

こいつでCSVファイルでexportします。

そのファイルを今度はch4_3からインポートします。

データテーブルの構造体は先程作成したEnemyMonsterInfoを選択します。

f:id:kazuhironagai77:20200524222229p:plain

f:id:kazuhironagai77:20200524222237p:plain

出来ました。凄い簡単でした。

3. GameCharacterクラス内に敵のモンスターを生み出す関数を作成する。

はい。どんどんやって行きます。

f:id:kazuhironagai77:20200524222310p:plain

f:id:kazuhironagai77:20200524222318p:plain

出来ました。

エラーが起きないかだけチェックします。(ビルドしてプレイ。)

大丈夫でした。

ここで4月19日のブログは終わっています。4月26日のブログに進みます。

4. 作成した関数、CreateEnemyMonster()をテストする。

今度は、CreateEnemyMonster()関数を呼び出してモンスターが作成されているかテストしてます。ブログを読むとTestCombat()関数から読んでいます。全く同じ方法でテストします。

f:id:kazuhironagai77:20200524222404p:plain

f:id:kazuhironagai77:20200524222411p:plain

RPGGameModeBaseクラス内にtestCombat()関数を宣言します。そして以下のように実装します。

f:id:kazuhironagai77:20200524222431p:plain

前述のブログの方では丁寧に一個ずつ試していますが、ぶっちゃけ、動かないはずないので全部実装しちゃいます。

更に、レベルブループリントに

f:id:kazuhironagai77:20200524222448p:plain

を追加して実際にモンスターが生成できているのか確認出来るようにしました。

ビルドします。

f:id:kazuhironagai77:20200524222502p:plain

プレイします。

何もしていない状態でIを押します。

f:id:kazuhironagai77:20200524222525p:plain

TestCombat()関数を呼びます。

f:id:kazuhironagai77:20200524222545p:plain

Iを押します。

f:id:kazuhironagai77:20200524222611p:plain

今度は作成されたモンスターの名前が呼び出されました。成功です。

更にプレイを中止してもエディターがクラッシュする事もありません。

5. EnemyModel の追加

SkeltenCrew bundleをch4_3に追加します。

f:id:kazuhironagai77:20200524222647p:plain

この後、ブログを読むとUE4C++でCharacterクラスからmonsterCharacterクラスを作成してます。monsterCharacterクラスはモンスターの姿形を担当するクラスなんですが、名前のせいでGameCharacterクラスと対比されるクラスと勘違いしやすくなってしまっています。プレイヤーがコントロールするキャラを作成しているThirdPersonCharacterはch4_3Characterクラスから作成されています。本来ならばこのクラスと対比されるべきクラスなので、名前をch4_3Monsterクラスに変更します。

その後で、アニメーションをch2からmigrateします。

f:id:kazuhironagai77:20200524222719p:plain

何故かch3からはmigrate出来ませんでした。

ch4_3Monsterクラスから派生したMosterBPくらすのAnimationとMeshにインポートしたモンスターの姿とアニメーションをセットします。

f:id:kazuhironagai77:20200524222738p:plain

今度はこのモンスターをマップ上に発生させるためのコードを書きます。Ch3のコードをそのまま使用します。

f:id:kazuhironagai77:20200524222800p:plain

f:id:kazuhironagai77:20200524222808p:plain

うおー。何かエラーになっている。なんで?ch3と全く同じに書いたのに。

色々考えたんですが、全く分かりません。のでビルドしてプレイしてみました。

f:id:kazuhironagai77:20200524222832p:plain

普通に出来てました。

それはいいんですが、このSpawnMonsterCharacterが指しているアドレスを指すインスタンスはこのBeginPlay()関数が終わったら無くなっちゃうんじゃないでしょうか?この部分は私が勝手に書いたコードなのでかなり心配です。来週この問題は考えます。

. Combat Engineの自作

やっとCombat Engineの自作に戻ってこれました。5月3日のブログで行った作業をやっていきます。

どの様な戦略で作成するのかすっかり忘れてしまいましたので、ブログをもう一度読み直したら、兎に角、教科書通りに作成してその後で、追加したい機能をどうにかして追加する。と言っています。因みに追加したい機能とは、

f:id:kazuhironagai77:20200524222856p:plain

の事で具体的なイメージは4月12日のブログに描かれています。

うん。同じ作戦で行きます。出来なくなった時に何が問題かはっきりするはずですから。

1. CombatEngineクラスの作成

ブログに書かれているのと同じ方法で作成します。

しました。全く同じやり方したのでスクリーンショットは一部だけ表示します。

f:id:kazuhironagai77:20200524222929p:plain

コードを書いていて思ったんですが、SelectNextCharacter()関数は今回のゲームではプレイヤーが操作するキャラだったら敵のモンスター、敵のモンスターならプレイヤーが操作するキャラを選択すればいいのでこんな大それたシステムは要りませんね。

f:id:kazuhironagai77:20200524222954p:plain

ただ、今直してしまうと残りのブログと違う事をしなければならなくなるので、今までやった事が終わった後で直します。

ビルドも出来ました。

f:id:kazuhironagai77:20200524223010p:plain

突然ですが、ローカルディスクが一杯になってしまったので、VS2015をアンインストールしました。その時windows 10用のwindows SDKが3つもインストールされているのを発見して、流石に3つも要らないでしょうと一番古いバーションのやつも一緒にアンインストールしたのですが、今ビルドした時にvisual studioのoutput見たら、

f:id:kazuhironagai77:20200524223028p:plain

を使用していました。残っている2つバージョンの古い方を使用しています。これって手動で変えないといけないんでしょうか?それとも逆に最新のバーションに変えると逆に問題が出たりするのでしょうか?もし、一番新しいバージョンがあれば十分でしょうと、この16299.0をアンインストールしていたら大変な事が起きたりしてたのでしょうか?

全然分かりません。心配になって来ました。

2. GameCharacterクラスに戦闘に関する関数を作成する。

これも、元のブログと同じに作成します。

f:id:kazuhironagai77:20200524223100p:plain

f:id:kazuhironagai77:20200524223108p:plain

f:id:kazuhironagai77:20200524223123p:plain

ビルドします。

一回エラーが出ましたが、エラーの意味が良く分からないエラーだったので、もう一度ビルドしたら成功しました。

f:id:kazuhironagai77:20200524223150p:plain

ちょっと不安ですが再現出来ないためそれ以上の追及は今は出来ませんので先に進みます。

CombatEngineクラスをForward Declarationします。

f:id:kazuhironagai77:20200524223209p:plain

念のためにビルドしたらまた同じエラーが出ました。

うーん。もう一度ビルドします。

今度は大丈夫でした。取りあえず今日はこのまま続けます。

3. CombatEngineクラスからGameCharacterクラスの関数を呼び出す

f:id:kazuhironagai77:20200524223253p:plain

しました。コードは前の時と全く同じなので小さく載せました。

f:id:kazuhironagai77:20200524223318p:plain

更にThis->watingForCharacter…を追加しました。

ビルドします。

また同じエラーが出ます。もう一度ビルドすると今度は出ません。やっぱり一番古いWindows SDKをアンインストールしたせいでしょうか?ただ面倒臭いのでこのエラーは来週考える事にします。

4. GameCharacterクラスからCombatEngineクラスを呼び出す

今度は逆にGameCharacterクラスにCombatEngineクラスから作成する変数combatInstanceを追加します。

f:id:kazuhironagai77:20200524223349p:plain

その追加したcombatInstance変数はCombatEngineのコンストラクター内でアサイン(assign)されます。

f:id:kazuhironagai77:20200524223415p:plain

コンストラクターアサイン(assign)されたのでdestructorで外します。

f:id:kazuhironagai77:20200524223436p:plain

これも前のブログのままのコードです。

前のブログだとこの後から全く説明しないでRPGGameModeBaseクラスのコードの作成に移っています。いくらなんでもこの書き方は駄目でしょう。一カ月も経っていないのに書いた本人が理解出来ないでGameCharacterクラスに続きを書こうとしてしまいました。

一応ここでもビルドしてみます。

どうせ、またエラーになるのだから、今度はエディターからコンパイルする事にしました。

やっぱりエラーになりました。PCHがどうとか言っています。これももう一度コンパイルすると直りました。

5. RPGGameModeBaseクラスからCombatEngineを使用するためのコードを足す。

今度もブログ通りにやっていきます。RPGGameModeBaseクラスにCurrentCombatInstance変数を追加します。

f:id:kazuhironagai77:20200524223504p:plain

Tick()関数を以下のように作成します。

f:id:kazuhironagai77:20200524223521p:plain

f:id:kazuhironagai77:20200524223534p:plain

ブログに載っているコードと一字一句同じです。

TestCombat()関数内に以下のコードを足します。

f:id:kazuhironagai77:20200524223557p:plain

f:id:kazuhironagai77:20200524223605p:plain

理由は前のブログに書いてある通りです。

最後にコンストラクターに以下のコードを追加します。

f:id:kazuhironagai77:20200524223620p:plain

これでテスト出来るはずです。

ビルドします。

あれ!エラーしないでビルド出来ました。うーん。良く分からない。

テストします。

f:id:kazuhironagai77:20200524223639p:plain

うーん。ブログによると

f:id:kazuhironagai77:20200524223654p:plain

となると書かれていますが…

分かりました。

RPGGameModeBaseくらすのtick()関数の以下のコードが

f:id:kazuhironagai77:20200524223725p:plain

GameOver変数がTrue、つまり戦闘が終了した時のみに実行されなければならないのに、tick()関数が呼ばれるたびに実行されていました。

以下のように直しました。

f:id:kazuhironagai77:20200524223745p:plain

以下にテストの結果を示します。

f:id:kazuhironagai77:20200524223803p:plain

出来ましたね。

6. 急にLog In 出来なくなりました。

休憩中にUnreal Online Learningでも見ようとLauncherからクリックしたらこんなエラーが表示されました。

f:id:kazuhironagai77:20200524223833p:plain

ブラウザーからは普通に入れるのですが

f:id:kazuhironagai77:20200524223848p:plain

Launcherからは何回やっても同じエラーでは入れません。ネットで調べたんですが同じエラーになっている人が見当たらないです。取りあえずは放って置きます。来週以降も同じ問題が起きるならちょっと考えます。

3. まとめと感想

やっと、Pure virtual function…のエラー問題を回避してCombat Engineの自作に入れました。来週からCombat Engineの自作をやって行きます。