UE4の勉強記録

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

「Unreal Engine 4.xを使用してRPGを作成する」の足りない部分を作成する。アニメレンダリングの勉強など 9

<前文>

<今週のDirectXの勉強>

今週も3つの本で勉強していきます。

先週、 C++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window [1] で勉強したところと、大体同じ箇所を勉強する事にします。

<<DirectX 12の魔導書>>

今週は3.1 最初のProjectをやってみます。

先週、DownloadしたSample Codeの最初のProjectを見たら、いきなりこんなにやるのか。というぐらいのCodeが書かれていました。

しかし後で、じっくり教科書読んだら、その最初のSample Codeは3章全部のSample Codeでした。

今週はその一番最初の3.1の部分だけやります。

あんまり理解していませんが、とりあえずCodeを打ち込みました。

実行すると

が表示されました。

ただし

以下の警告が表示されました。

単なる警告なので無視しても良いんですが、一応直します。

としました。

次のReturn Value ignoredってどういう意味なんでしょうか?

変数を作成してこの関数の結果を保存しろって事でしょうか?

調べたら分かりました。

Stack Overflowの6031: return value ignored (getchar()) In visual studio 2019 [2]に書いてありました。

まずここでgetchar()関数が使用されている目的ですが、単にWindow(Consoleの事?)を閉じるの防ぐためだそうです。

うーん。

そうだったのか。

それ故にこのWarningは無視しても問題ないそうですが、以下に示した様に

(void)を最初につければ警告は消えるそうです。

うーん。

試してみます。

警告は消えました。

試しにgetchar()関数を消してWindowが閉じるか試してみました。

結果です。

なんかの設定で変えるとConsoleは自動で閉じるようになるけど。と書かれていました。

だんたんC++を思い出してきました。

普通にcodeを書いて実行すると、一瞬で実行してConsoleが閉じられて正常に動いたのかどうか分からないので、Consoleが閉じないようにするんでした。

その方法が何個かあってgetchar()関数を使用したり、Consoleの設定を変えたりしたんでした。

うーん。

このくらいだと、まだC++の復習って感じですね。

Codeも何回も読んでいる内に、何が書いてあるのか全部理解しました。

その次の3.2.1もやりますか。

うーん。

読んだらC++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window [1] で勉強した範囲より一寸だけ先に進んでしまいます。

これは来週やる事にします。

<HLSLシェーダーの魔導書>

この本はいきなりDirect X12を使用して三角形を書く話から始まっています。

一応、最初のSample Codeの例は空のWindowを表示させるProjectですが、それについては何も解説がありません。

今週は、C++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window [1] で勉強した範囲と大体同じ個所を勉強するのが目的なので、この空のWindowを表示させるSampleを見て勉強する事にします。

これです。

Codeを見ます。

あれ、これ本で解説している内容がCodeに書かれています。

うーん。

これは今週はHL SLの魔導書の勉強はなしにします。

一つ気が付いたんですが、HLSLの魔導書に限らないですが、GitHubにMIT LICENSEで公開しているCodeをここで引用する事は、全く問題ないですね。

MIT LICENSEが禁止しているのは、他人が作成した物を、自分で作成したと称して公開する事です。

来週から実際のCodeもここに貼って色々検証する事にします。

Direct3D 12 ゲームグラフィック実践ガイド>

はい。

この本はHLSLの魔導書とは反対で、最初のwindowの作成について滅茶苦茶詳しく書いてありました。

まず本を読んでから実際のsample codeを読んで、更に自分でも作成してみます。

その前に、先週の

この問題についての結論を記録しておきます。

まずAssimpとDirectX Took Kitを追加する方法ですが、ここの書かれている通りNuGetを使用して追加するのは簡単に出来る事は確認出来ました。

NuGetを使用しないで手動でAssimpとDirectX Tool Kitを追加する方法はまだ分かりません。

これをしないと勉強にならない気はしています。

それよりももっと重要な事が分かったんですが、このSample Codeの最初の幾つかは純粋にWindowの作成についての説明なので、AssimpもDirectX Tool Ketを追加する必要がありませんでした。

なのでこの問題は、実際にAssimpとDirectX Tool Kitを追加する必要がある時に改めて考える事にします。

はい。

第2章を読んだら、Projectの設定方法から詳しい解説が載っていました。

これは C++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window [1]では2022-10-23のBlogで勉強した内容と全く同じです。

ただしProjectの設定が全く同じである訳がなく、違う部分を記録して何故、Projectの設定が違うのかについての検証・考察を行う必要があります。

うーん。

いきなり重いのが来た。

大体、 C++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window [1]でProjectをどう設定したのか既に忘れています。

まず2022-10-23のBlogを読み返して C++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window [1]でどのような設定をProjectに対して行ったのかを確認します。

以下に C++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window [1]で行った設定を簡単にまとめます。

  1. VSから表示されているFolderの名前や位置を変更
  2. 実際のFoloerの名前や位置も変更

そしてProjectのConfigurationの設定を行います。

  • X86 を対象から外す
  • Output DirectroyIntermeditate Directoryの設定を変更して生成される場所を変更
  • WindowSDKVersionが最新になっているかを確認
  • C++CVersionが最新になっているかを確認
  • Linker SystemSubSystem設定をWindowsに変更

非常に簡単にまとめるとこれらの事をやっていました。

それでは「Direct3D 12 ゲームグラフィック実践ガイド」の第2章を読んで違っている部分を書きだします。

まず「Direct3D 12 ゲームグラフィック実践ガイド」でやっていて C++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window [1]では2022-10-23のBlogでやっていない設定です。

Unicodeの設定をしています。

この設定をしている場所が分かりづらいのでScreenshotで表します。

これは日本語を表示するための設定でしょうね。

私、VSの日本語の言語Packを入れていないんですが、それでも日本語で表示されていますね。

この辺はVSをInstallする時に勉強した内容です。

次に、 C++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window [1]でやっていて「Direct3D 12 ゲームグラフィック実践ガイド」ではやっていない設定です。

まずVSのFolderを使いやすいように名前や位置を移動させる事とそれに伴う設定の変更です。

これ、他のGame Engineを作成するTutorialでも同じ事していたので、おそらく英語圏Visual StudioDirectXを扱う人達にとっては常識みたいな事だと理解しています。

ただこれが、本当に必要でやっているのか、単なる文化的な慣習でやっているのかは分かりません。

やらんでも実際は問題ない気もします。

私がアメリカにいた時は、兎に角、VSの画面を黒くするのが流行っていました。

私はそれに全く意義を見出せなかったので断固としてVSは白いままで使用していました。

まあ白人の人達は、目の色が青や緑が多いので、明るい画面で目が疲れやすい可能性はあるかもしれませんが、私には関係ない話ですし。

後、この設定はDirctX 12を勉強するには必要ないけどGame Engineを作成するには必要な設定の可能性もありますね。

次にこれです。

  • X86 を対象から外す

これは本では書いていないですが、Sample Codeの設定は以下の様になっていました。

 これは別にX86 を敢えて消す必要まではなくて実行する時にX64が選択されていればいいはずです。

元々のVSの元々の設定がどうなっているのかは実際に実装する時に確認します。

  • C++CVersionが最新になっているかを確認

これは確か何もしなくてなっているはずです。

  • Linker SystemSubSystem設定をWindowsに変更

これ。

これどうなっているんでしょう。

何も指定していませんでした。

これはWindowを実際に作成する時になってから変更するのかもしれませんね。

<<比較して分かったこと>>

 C++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window [1]でやったProjectの設定は、DirectX 12をVSで使用するためには絶対に必要な事だと思っていましたが、そうでもない可能性がある事が分かりました。

特にFolderの名前や位置の変更と、それに伴うConfigrationの設定の変更は、実際に必要な事なのか、単なる文化の違いなのか分からなくなってきました。

日本人が思っている程、英語圏の文化は合理的ではなく、私の個人的な経験から言っても無条件に英語圏の文化をまねると手痛い結果になる場合が多いです。

ただし、逆もまた真なりで、大量の優れた人材と潤滑な資金を使用して研究・開発している英語圏におけるProjectの設定の常識を、一人の日本人が個人的に研究(しかも自分のお金を使用)して得た知見の方が、正しいと結論づけるのもまた軽率でしょう。

これは両方の意見を聞きつつ、その違いがある部分を認識しておくぐらいが正しい選択だと思います。

後、実装は来週以降やる事にします。

<本文>

1.今週の勉強について

今週も以下の内容についてやって行きます。

  • Niagara: CGHOW氏のTutorialをやる
  • Materialの勉強
  • RPGPackagingについて
  • Open Worldの検証
  • Gaeaの勉強
  • 雪山のMapの作成
  • 報酬システムの研究
  • Anime Renderingの勉強
  • DirectX 12の勉強

2.Niagara: CGHOW氏のTutorialをやる

先週、Unreal Engine 5 Tutorial - Niagara Fluids & Characters/Skeletal Mesh Collisions [3]を勉強しましたが、UE5.1 にはUse Physics Asset Collisionが存在していなくて5.0で実装しました。

後で気が付いたんですが、5.1のContent Exampleを見れば、Use Physics Asset Collisionが本当に存在していなのかどうか簡単に分かるはずです。

2.1 Content Example5.1 Use Physics Asset Collisionを確認する

ので今週はこれをやる事にします。

Downloadしました。

開きます。

ありました。

これです。

中を開いてGrid3D_FLIP_FluidControl_Emitterを調べます。

まずEmitter SummaryのCollisionです。

うーん。

Use Physics Asset Collisionは使用していませんね。

Emitter全体で調べましたが、 Use Physics Asset Collision は無かったです。

流石にここで諦めるのは、一寸早すぎます。

Use Physics Asset Collisionを使用しないでも液体とSkeletal Meshがcollisionを起こしている原因を探します。

このEmitterのCompute Boundary SectionにあるGrid 3D Compute Boundary Moduleに

以下のAttributeがあります。

この中で怪しいのがUse Mesh CollisionsとUse Free Surfaceです。

もう一つ怪しいのが、このSkeletal Mesh

TagsにColliderがセットしています。

先週勉強したTutorialではSkeletal MeshのTagにColliderをセットしてもCollisionは起きなかったはずです。

取りあえずこの2つを試してみましょう。

先週Poolを作成した5.1のProjectを開きます。

まずEmitterの Compute Boundary SectionにあるGrid 3D Compute Boundary Moduleをチェックします。

設定はContent Exampleと全部同じでした。

今度は、BP_ThirdPersonCharacterを開いて

ActorのTagにColliderを追加します。

テストします。

全くCollisionは起きません。

確認のためにCubeに

をセットしてテストしました。

普通にCollisionしていました。

うーん。

分かりません。

このContent Exampleにある3D Liquid Collisionが本当にSkeletal MeshとCollisionするのか確認します。

これをMigrateして今のProjectに持ってきました。

ここにThirdPaersonで突っ込んでみます。

勿論、ThirdPersonのTagには

がついています。

全くCollideしません。

うーん。

Content ExamploeのこのSkeletal MeshもMigrateしてこのProjectに持ってきました。

これを使用してCollisionが起きるのか確認してみます。

起きないです。

Tagsに何もついていなかったです。

もう一回、テストします。

Collisionするようになりました。

このSkeletal MeshをThirdPerson Characterで使用しているのと同じSkeletal Meshに変更しました。

そしたらCollideしなくなりました。

うーん。

なんで?

元に戻したらCollisionするようになりました。

これは原因は分からんかもしれませんね。

今週はこのくらいで諦めます。

2.2 UE5.0のGrid3D_ComputeBoundary Moduleの実装を見る

諦めたとたんに、あるIdeaが思いつきました。

UE5.0のGrid3D_ComputeBoundary Moduleの実装のUse Physices Asset Collisionsの部分をCopyしてScratch Padで同じ実装を作成してしまえば良いんじゃないのかという事です。

これ試してみます。

UE5.0のGrid3D_ComputeBoundary Moduleの実装のUse Physices Asset Collisionsの部分です。

これが

から派生して

に戻っています。

まずはこのBoundaryというParameterがどんなParameterなのかを調べます。

[TRNSIENT] Boundaryがそれにあたるみたいです。

Grid3D_ComputeBoundary Moduleの最後のMap Setで[TRANSIENT] Boundaryがありました。

[TRNSIENT]のScopeがどの範囲なのか分かりません。

この実装を見ると同じModule内だけという事はないと思います。

一番、手っ取り早いのは5.1の Grid3D_ComputeBoundary Moduleでも [TRANSIENT] Boundaryが使用されている事です。

この場合はその [TRANSIENT] Boundaryに値を追加すれば良いだけになります。

確認します。

全く同じでした。

[TRANSIENT] Boundaryはそのまま使用出来そうです。

次のNiagara Parameter Mapですが、これは単なるMapの事だと思われます。

ではPhysics Assetの中身を読んでみます。

まずMap Getノードです。

こんなにInputがあるの?

順番に確認していきます。

[INPUT] PhysicsAssetです。

当然ですが、System StackのUser ParameterにあるPhysics Collisionで値をセットされています。

次の[INPUT] dtですが、

5.1のGrid3D_ComputeBoundaryにもそのままあります。

残りのParameterも全部ありました。

はい。

これで Use Physices Asset Collisionsの実装の周りは理解出来ました。

2.3 UE5.1の Grid3D_ComputeBoundary ModuleをDuplicateしたModuleにUE5.0の Grid3D_ComputeBoundary Moduleの Use Physices Asset Collisionsの実装を追加する

ではこれをやってみます。

まずはUE5.1の Grid3D_ComputeBoundary ModuleをDuplicateします。

名前は Grid3D_ComputeBoundaryMeとしました。

まずはこのModuleを Grid3D_ComputeBoundary Moduleの代わりに使用します。

Attributeの設定をGrid 3D Compute Boundary ModuleからCopyします。

ここでStatic MeshとCollisionするか確認します。

普通にしています。

では、この Grid3D_ComputeBoundaryMeにUE5.0の Use Physices Asset Collisionsの部分をCopyします。

しました。

5.0の Grid3D_ComputeBoundary Moduleと全く同じつなぎ方にしました。

と警告が出てきました。

こっちは先程私が作成したModuleだからEditしても問題ないはずです。

Compileします。

ErrorなくCompile出来ました。

これでテストしてみます。

ダメでした。

うーん。

何故?

Static SwitchのSelectorがOffになっていました。

Onにしました。

ああ、

ずごいErrorが。

まず最初のErrorですが、以下のNodeが

5.1では以下の様に変更されたので、Fefleshしないと使用できないとありました。

5.1ではOutputのCloset PositionとCloset VelocityはFloatになっていました。

当然、Refleshすると

Errorが起こります。

5.0のGet Element Pointノードの実装をCopyして新しいNodeを作成すれば良いじゃないかと思いましたが、 Get Element Pointノードは開けませんでした。

色々弄った結果、以下の2つのNodeの親のInterfaceである

Niagara Data Interface Vector Curveが変更されているのでこのNodeはこのままでは使用できないと出てきました。

うーん。

原因かもしれない事が分かりました。

5.0の方の[INPUT] Physics AssetにはPhysics Assetという項目が出てきます。

所が、5.1のCopyした方の [INPUT] Physics Assetには

Physics Assetが出てきません。

試しに5.1の方でPhysics Asset typeのInputを新しく作成してみました。

すると

こっちにはPhysics Assetがありました。

更にこの[INPUT] MyPhysicsAssetから呼び出したGet Element PointノードのClosest PoisitonはきちんとVector Typeになっています。

Mat Getノードは単純にコピペしてはいけないみたいですね。

一回全部消して作り直します。

Map Getノードです。

[INPUT] PhysicsタイプのParameterが既に使用していてそれはさっきコピペした時に作成されたものだとは思いますが、念のために新しいParameter、[INPUT] MyPhysicsAssetを作成しました。

残りのParameterは元々存在しているParameterを追加しました。

Get Closest Elementノードを追加しました。

Time Fractionの値は5.0の方が1.0になっているのでそのまま1.0をセットしました。

Get Element Pointノードを繋ぎました。

Closest PositionのtypeがVectorになっています。

Get Element Distanceノードを追加します。

Custom Hlsl 005ノードを追加します。

これは何をやっているのかまだ不明なので、5.0から丸Copyして使います。

Maxノードを追加します。

Multiplyノードも追加します。

更にMultiplyノードの計算結果をAddのAにパスして[TRANSIENT]Solid Velocityの値を足します。

その結果をMap Setの [TRANSIENT]Solid Velocityに新しい値としてセットします。

その結果をStatic Switchノードに繋ぎます。

これでこの部分の実装はきちんと動くはずです。

テストしてみます。

Errorになりました。

うーん。

これがErrorになったそうです。

IntからNiagara IDには変換出来ません。って俺はそれやってないし。

うーん。

これは時間切れです。

ここで本当にGive upです。

2.4 後、一寸だけSkeletal Meshと3D FluidとのCollisionについてまとめる

もう時間はないんですが、分かったことで、記録しておくべき内容を書いておきます。

Content Exampleの

これは、Skeletal Mesh Actorに

Skeletal Meshをセットして

Static Meshと同じようにActorのTagに

FluidのSystem StackのUser Parameterの

Actor Tagsにセットされている値(この場合はCollider)と同じ値をセットすれば

Collisionするようになります。

このBlogの2.1でSKM_QuinnSimpleがCollisionしなかった理由は、

名前にSKMを含むSkeletal MeshをSKeletal Mesh Assetにセットして

CompileするとErrorになっているからです。

なので、ThirdPerson CharacterとNiagara FluidをCollisionさせるためには、

以下に示した様にThirdPerson CharacterのActorのTagに FluidのSystem StackのUser ParameterのActor Tagsにセットされている値(この場合はCollider)と同じ値をセット

してもCollisionしない事を考慮すると

RenderBucket氏のやり方しかないみたいです。

つまり、このBlogの2.3のやり方で出来るようにする必要があるわけです。

となるとここはやっぱり大切な箇所です。

ThirdPerson CharacterでNiagara FluidとCollision出来ることは重要なんです。

以下の箇所が何でErrorになるのかもう少しだけ調査します。

2.5 Physics Assetについての調査

以下の図を見ても明白なようにPhysics Assetが何かうまく動かない原因だと考えられます。

このPhysics Asset、ThirdPerson Characterで使用しているSkeletal MeshであるSKM_QuinnSimpleには、5.0の場合は以下に示した様に

Physics AssetにPA_Mannequinがsetされていますが、5.1の場合は以下に示した様に何もセットされていません。

これも原因の一つであると考えられます。

ので5.1の方もSK_Mannequin_PhysicsAssetをセットしました。

この状態から色々弄っていたら、5.1でもCollision出来ました。

何を直したのかを以下にまとめます。

まず SK_Mannequin_PhysicsAssetをセットした状態でGrid3D_ComputeBoundaryのCopyにPhysics Assetsの実装を足したGrid3D_ComputeBoundaryMeをCompileしましたがErrorは消えませんでした。

もうPhysics AssetsのどこでErrorが起きているのかを調べるためにNodeを全部外して一個ずつ繋げてはCompileしました。

すると以下のCustom HLSL ノードがErrorを起こしていることが分かりました。

ので新しくCustom HLSLノードを書き直しました。

ここで何回かErrorがあって直してを繰り返しました。

そしたらErrorがなくなり

と表示されました。

あれ、出来たかもと、残りの実装を完成させてもう一回Compileしました。

そしたらCompileに成功しました。

おお、出来たかと。テストしたらダメでした。

よく見たら最後のBoundaryの部分を繋ぐのを忘れていました。

そこを繋いでもう一回Compileしました。

Compileは成功して、テストしました。

そうしたら、以下の様にThirdPerson CharacterとNiagara FluidがCollision出来るようになりました。

最後に Grid3D_ComputeBoundaryMeに追加したPhysics Assetsの実装を示しておきます。

うーん。

この方法を追加する事で、5.1でもRenderBucket氏のやり方で操作中のThirdPerson CharacterでもNiagara FluidとCollision出来る事を発見しました。

2.6 UE5.1でPlayerの操作するキャラがNiagara Fluid SimulationとCollisionする方法に関するまとめ

これは結構凄い内容なので、ここにまとめ直す事にしました。

Skeletal MeshがNiagra Fluid SimulationとCollisionする方法は、Content Exampleの以下に示した場所で紹介されています。

ただし、ここで紹介されたやり方は、Skeletal Mesh ActorにSkeletal Meshをsetした状態でのみ適用可能です。

しかも名前にSKM_が入っているSkeletal MeshをSkeletal Mesh ActorにSetするとErrorになって使用出来ません。

このように非常に狭い条件のみで使用可能な方法です。

それに対して、RenderBucket氏がUnreal Engine 5 Tutorial - Niagara Fluids & Characters/Skeletal Mesh Collisions [3]で紹介したやり方は、Playerが操作するCharacterでも、そのCharacterのSkeletal Meshの名前にSKMが入っていてもNiagara FluidとCollision出来る素晴らしい方法です。

しかしRenderBucket氏の方法は、UE5.1 では使用する事は出来ません。

何故なら、UE5.1 ではNiagara Fluidを生成するNiagara SystemのEmitter Stackに使用されているGrid 3D Compute Boundary ModuleのAttributeにUse Physics Asset Collisiionが無いからです。

以下にUE5.0 のEmitter StackのGrid 3D Compute Boundary ModuleのAttributeを示しますが、こっちにはUse Physics Asset Collisiionがあります。

この為、UE5.1 でPlayerの操作するキャラとNiagara Fluid SimulationとをCollisionする事は(少なくとも現状では)出来なかったです。

今回、UE5.0 のGrid 3D Compute Boundary Module内でUse Physics Assets Collisionを実行する為に、実装されているPhysics Assets Block、

と同じ機能の実装を、UE5.1 のGrid 3D Compute Boundary Moduleに追加(実際はGrid 3D Compute Boundary ModuleをDuplicateしたModuleに追加した。)する事、

そしてPlayer が操作するキャラのSkeletal MeshにPhysics Assetをセットする事、

でUE5.1 でも、Player が操作するキャラとNiagara Fluid とCollision出来る事を発見しました。

このやり方で、UE5.1 でもPlayer が操作するキャラとNiagara Fluid とCollision出来る事は、まだ何処にも(少なくともGoogleの検索に引っかかる範囲内では何処にも)発表されていません。

私が初めてやりました。

2.7 今回のNiagaraの勉強の感想

もうUEの勉強を始めて何年も経ちましたが、今まで誰かが「この方法だったら○○が出来る。」と言う事を確認する事は有っても、誰もやった事が無い事を、自分で方法を考えて、やってみて、その結果、今まで出来なかった事が出来るようになった事はありません。

今回のこれが初めてです。

私にとって、今週のこの結果はとても重要な成果です。

今、このBlogを見直すと、結果が出る前に2回も「諦めた。」と書いています。実際その時は本当に諦めて次の勉強を始めようとしていました。

でもそのたびに新たなIdeaが出て来たりして、もう一寸だけ試してみようと思いました。

その結果、とうとうUE5.1 でもPlayer が操作するキャラとNiagara Fluid とCollision出来る方法を編み出す事に成功しました。

これ、ボクシングのコーチがYouTubeで言っていたんですが、人間がフルマラソンを走れるのは、どこまで走れば終わりがあるのか分かっているからで、終わりが分からない状態で走らされると、屈強な精神と肉体を持つプロの選手でも10km位でDownして動けなくなるそうです。

それ聞いた時は、ふーん。と思っていましたが、今回、本当に出来るかどうか分からない状態で挑戦してみて、こんなに限界が早くるのかとびっくりしました。

今回の「UE5.1 でもPlayer が操作するキャラとNiagara Fluid とCollision出来る方法」は、見つかれば凄いですが、見つからなければ単なる時間の浪費です。その時間に、別なTutorialを勉強したら少なくともいつもと同じ成果を得る事は確定しています。

なので、今回もこのやり方なら出来るはずと思ってTryして出来ないと分かると、早くこの挑戦は諦めて別なTutorialの勉強を始めようという気持ちになりました。

その気持ちを乗り越えてUE5.1 でPlayer が操作するキャラとNiagara Fluid とCollision出来る方法を発見したのは、今までの勉強が間違っていないかった事の証明だと思っています。そしてそれは自分のやり方に対しての自信にも繋がりました。

3.Materialの勉強

先週、何をやったのかを忘れてしまったので、先週のBlogを読み直しました。特にやり残した事はないみたいなので次のTutorialの勉強を始めます。

VHS FilterのPart 2、Post Process VHS Filter Part 2 - Shader Graph Basics - Episode 60 [4] を勉強します。

3.1 Post Process VHS Filter Part 2 - Shader Graph Basics - Episode 60 [4]を勉強する

まず軽く全部見ます。

見ました。

今週のTutorialは以下に示した

Noiseの横線を追加します。

実際にはさらにWorn outしているEffectも追加しています。

この2つを作成しています。

はっきり言って、最終的な結果は驚きの凄さです。

VHSのnoiseがあるだけで、昔の犯罪記録か何かの秘密の動画を見ている気がします。

Postprocessの中でもStylized Effectと並ぶぐらいのImpactがありました。

何なんでしょうか?

こういうのは記号的なものなんでしょうか?

後、このEffectを作成するにあたって、前に作成したHash23という名前のMaterial Functionを使用しています。

これは前にPC1号で作成しましたが、今回はPC2号で実装する予定なのでもう一回作成します。

確か前に作成した時はそんなに難しくなかったはずです。

Timeノードを使用した計算が結構そこかしこにありました。

計算そのものは単純なものばかりでしたが、その理論はあんまりなじみがないものでした。

その辺もしっかり勉強したいと思います。

以下にTutorialのやり方を簡単にまとめます。

<Worn Out

こっちのEffectは動画を見てる限りじゃあんまり分からないですが、その辺は実際に実装する時に確認します。

まず以下の実装でTexCoord[0]ノードのGの値とTimeノードの値をAppendします。

うーん。

何がしたいのか分かりませんね。続きを見ます。

なんとそこにHash23を追加しました。

このHash23は今回、新しく作り直します。

結果です。

うーん。

Hash23の実装を覚えていないので何故こうなるのか不明です。

別に色は要らないのでMaskノードでRの値だけ抽出します。

Tutorialではこの事をMonochromaticと言っていました。

凄い長い単語ですね。Monoが単一を示していて、Chormaticが色を示しているので、Monochromaticで単一色と言う意味になるのか。

Monoの発音は、Ben Cloward先生はモノとはっきりアイウエオのオの音で言っています。

が、Googleの発音はかなりアに近い音で、マナとモノの間位の発音でした。

これはYouglish先生の出番ですね。

調べました。

30人位見ましたが、全員Monoの発音はモノって言っています。

マナとモノの間位の発音で言っている人は一人もいませんでした。後一人ぐらいはマナって発音しているかと思ったんですが、YouGlish上では一人もいませんでした。

今、色を示す値の範囲は0~1の間です。

今度は子の範囲を-0.5~0.5の間に変更するそうです。

何が目的でこの計算をしたのかは今のところは不明です。

あ、分かった。

今のままだとNoiseが強すぎるので弱くしているんです。

次のDivideノードも全く同じ理由です。

ここでViewSizeノードが使用されているのは、画面のサイズが違う場合も同じ割合でNoiseを弱くする為です。

ここまでの実装の結果です。

正直、どこが変わっているのか分かりません。

Tutorialの解説でどこが変わっているのか分かりました。

以下に示したTableの端ですが、ギザギザが波打っています。

成程。

言われると確かに古いVideoとか見るとモノと背景の境界がギザギザしていますわ。

<Tracking

今度はTrackingというEffectを作成します。

あれ、これって横線のNoiseの事、それとも全く別のEffect?

最初に動画を見た時は軽く見ているので、この部分は見逃してしまったのかもしれません。

説明を見たら横線のNoiseの事でした。

はい。

横線のNoiseの事をTrackingと言うのかと思ったんですがGoogle検索しても出てこないですね。

もう一回、Tutorialの説明を聞いたら、Tracking out of phase featureって言っていました。

この文が横線のNoiseを意味しているのは文脈から間違いないんですが、この文そのものの意味が分かりません。

うーん。

調べます。

はい。

まずTrackingですが、collins辞書のtrackingによると

という意味がある事が分かりました。

成程。Trackingって専門用語としてVideo Tapeの頭を揃えるって意味があるんですね。

となると次のOut of phaseは、Out of orderとかの用法と同じで、上手く行っていないとか失敗していると言う意味で捉えるべきですね。

つまりTracking out of phaseで

Trackingが上手く行ってない。とかTarckingが失敗している。

と言う意味ですね。

そして、最後にFeatureがあるので、

Trackingが上手く行ってない様子。とかTarckingが失敗している様子。

位の意味になるんでしょうか。

成程。

Trackingが失敗すると横線のNoiseが現れるって訳ですな。

分かりました。

と言うかTutorialを見たらこの後で、Trackingについて簡単に説明していました。

うん。完全に聞き逃していました。

それでは実装を勉強していきます。

これ一体、何しているんでしょうか?

XとYを一寸だけずらしているってTutorialでは説明していました。

そしてまたHash23を追加しました。

更に以下の実装を追加しました。

この部分は分かります。

Monochromatic して色の変化を小さくしています。

これはHash23の返し値が0~1の間なのかどうかが重要ですね。もし0~1の間ならそれを10分の1にしているわけですから、真っ黒になりそうです。

この辺は実装した時に確認します。

これでNoiseの部分の実装は一応終わりだそうです。

今度はScrolling Barの部分を作成するそうです。

まずは以下の実装を組みます。

Smooth Stepノードの機能は完全に覚えています。

まずMinの値以下は0です。Maxの値以上は1です。その間の値はSmooth なCurveに基づいて、0~1の間の値に変換されます。

そして先週実装した部分の以下に示したAddノードにMaskしてGの値を取り出します。

これに8を掛けます。

以下の様なImageになりました。

うーん。これをどうするんでしょうか?

この結果に更に以下の計算を追加しています。

Timeノードが出て来ましたね。

どんな結果になるのか一寸想像つかないですね。

次です。

成程、Sineノードを足す事で同じ結果を繰り返させる訳ですね。

後SineのPeriodの値は6.28だそうです。

これ0.28って言っていますが、6.28と書いてありますし、Sineの360度で一回転に設定するなら、6.28じゃないとおかしいです。

結果です。

白いBarが下から上に上がっています。

この結果を、先程作成したSmoothStepノードのValueに繋ぎます。

結果です。

これに先程作成したNoiseを組み合わせます。

以下に示したように、NoiseをTimeに追加します。

結果ですが、以下の白いBarがブルブル震えながら上に上がっていました。

しかしScreenshotにはそのブルブルは写りませんでした。

敢えてこの為に、Gifで撮影する必要も感じませんのでこのままにしておきます。

これにScan Lineを追加します。

既にScan Lineは作成してあるので、以下の実装をそのまま使用します。

Maskノードを使用してGの値のみを使用します。

その値をSmoothStepで調整します。

これ白の部分と黒の部分を増やしていますね。

そしてこの結果と先程のScroll Barの結果を掛けます。

結果です。

実際はこの結果がブルブルしています。

この結果をまた以下の値で割ります。

これは割っているので色を濃くしているのでしょうか?

View Sizeノードを使用しているのは画面の大きさによって影響受けないようにする為でしょうね。

先程作成したNoiseと合体させたScroll BarはこのUV値のUの値にだけ影響してほしいそうです。

また先程の先週作成した実装のAddノードのところに戻って来ました。

Addノードの値をUとVに分けます。

そしてUの値からNoiseと合体させたScroll Barの値を引きます。

その後でAppendノードを使用して元に戻します。

この結果を先週のUV値を使用している箇所に繋ぎます。

Previewの結果です。

あんまりNoiseのLineがはっきりしていませんね。

実際のLevelでの画面です。

こっちは凄いですね。

Screenshotではあんまり伝わりませんが、本当に古い動画を再生している感じがします。

最後にもう一工夫するそうです。

なんと、このNoiseのあるScroll Barの色を変更し、もっと本物のNoiseに近づけるそうです。

先週作成したYIQの変換の実装部分を改良します。

RGBをYIQ方式に変換して色を青くした後の部分です。

まずMaskを使用してGBの値を抽出してRotatorノードを繋ぎます。

これ図ではMask(G)になっていますが、IQの値をRotateする必要があるのでMask(GB)が正しいです。

Rotatorノードの設定は以下の通りです。

AnimateはしたくないのでXとYの値は0にセットするそうです。

Speedは単なるMultiplierなので1をセットしておきます。

RotatorノードのTimeの値ですが、以下のSmooth Stepの値をパスするそうです。

繋ぐ前に値を小さくします。

繋ぎました。

Tutorialに分かり易い説明がありました。

0.3を掛けた値は以下の様なImageになっているそうです。

これにRotateするので、黒い部分は回転は0、白い部分は100%の回転が掛かります。回転が掛かると言う事はこの場合、色が変わると言う事です。

0.3を掛けているので真っ白だった箇所30%位の回転しか掛かりません。

一寸だけ色が変化すると言う事です。

Previewの結果です。

NoiseのScall Barの色が一寸だけ変わっています。

実際のLevel上のImageです。

凄い。もうVHSの古い動画を再生しているような気になります。

何か、何処かの犯罪現場の映像でも見てるみたいです。

3.2 Post Process VHS Filter Part 2 - Shader Graph Basics - Episode 60 [4]を実装する

100%理解したかと言うと一寸怪しい所が、何か所かあります。

兎に角、先に実装する事にします。

<Hash23の作成>

まずHash23を作成します。

前に一回作成したことがあるので、理論的な部分の復習は最低限だけやります。

実装です。

Random Noise - Shader Graph Basics - Episode 35 [5]の通りに作成しました。

これはTexCoord[0]のそれぞれの位置をRandomに配置し直してNoiseを作成しているみたいです。

それ以上のことは分かりません。

Worn out Effect

それではWorn out Effectの部分から作成します。

最初の部分の実装を作成しました。

まずこの実装の意味が分からないです。

この実装の結果を先に見てみましょう。

うーん。

NoiseがY軸だけになっていますね。

Maskの値をRにしてみました。

縦線になりましたね。

うーん。

Hash23の実装を見た後なら理解できると思っていましたが、理屈は分かりません。

自分で実装しても何も新しい知見は得られませんね。

以下の所まで実装してしまいました。

特に新しい知見とかもないです。

Tutorialのこの部分を見直したら以下の実装を追加して実際の画像を確認しています。

これは自分でも確認します。

結果です。

Noiseだけですね。

以下の実装でNoiseを割りました。

結果です。

Noiseだけですね。

あれ?

Tutorialの結果と全然違いますね。

Projectを再起動したら直りました。

うーん。

何だったんだろう?

ちなみにDivideする前の状態のPreviewも取り直しました。

これならTutorialと同じ結果です。

動画では確認できなかったギザギザがブルブルしている様がよく見えます。

これをVHSがWorn outした時に見られるEffectと言っていたんですね。

うーん。

Ben Cloward先生の動画、4kまで対応しているんですが、私の今のPCのMoniterは、1kまでしか対応していません。しかも21 inchesの大きさです。

大体アメリカの家のTVって55 Inchesが普通じゃないですか。

55 Inches のMoniter+4kで見たら、このsubtleなEffectもくっきり分かるかもしれませんが、今の私のPCで、Tutorialの動画からこのブルブルを確認する事は不可能です。

うーん。

まあ、私が見る分には直接確認出来なくても問題はあんまりないですが、私が作成したGameをUserが見るときに問題になるかもしれませんね。

55 inchesの大きな画面 + 4Kで見たらナニコレ?的な映像になっているかもしれません。

UE5の美麗なRenderingを最大限に生かした作品を完成するためには、画像確認用にでかいMonitorが必要になるかもしれませんね。

また、お金が必要になるのか...。

Levelでの画像です。

Screenshotでは分かりにくいですが、画像がブルブルしていて古いVHSの動画を再生している感じが凄いしています。

Tracking out of Phase

今度は、横線の作成です。

その前に先程作成したWorn out Effectを先週の実装に繋ぎます。

結果です。

結果が見えやすいようにScreenの一部を切り取って拡大しました。

うーん。

もう凄いとしか言いようがないです。

次に横線のノイズを作成するためにMaskを作成します。

これですね。

まず以下の実装を作成します。

この0.67と0.57を掛けない場合との違いを見ようとしたんですが、両方単なるNoiseで違いは分かりませんでした。

この後、以下の実装になってMonochromaticで色が黒に近くなっているはずです。

色がMonochromaticになっているのは確認出来ましたが、その後のMutiplyノードの影響はよくわからなかったです。

Screenshotを取ろうとすると、一枚の画像だけしか写らないので、Noiseとして私の目に見えている画像と全然違う絵になってしまいます。

ので結果の画像はなしです。

段々気が付いてきましたが、このVHSのPostprocess、簡単に理解できるほど浅い内容じゃないです。

このSeriesを勉強し終わったら、Triplanear Projectionの勉強の時の様にもう一回まとめ直して考察や検証を新たに行います。

取りあえずNoise部分の実装は完成しました。

今度は、本当に以下の部分を実装します。

今度は以下のAddノードにMaskを追加します。

これ、先週作成した部分だとずっと思っていましたが、実際は先程作成したWorn out Effectの最後の部分でした。

以下の部分を追加しました。

この部分の結果です。

この部分敢えてWorn outの結果を使用する意味あるんでしょうか?

そういうところも後で検証します。

Smooth Stepノードを追加します。

結果です。

出来ましたね。

この結果だけ見るとあえてWorn out Effectの結果を使用している意味はなさそうですね。

今度はこの結果に先程作成したNoiseを追加します。

TimeノードとNoiseの結果をAddノードで足します。

白いBarがブルブルしています。

Screenshotには取れないので結果のImageはなしです。

Tutorialでは、このブルブルをJigglyと表現しています。

そういえばPokemonのプリンちゃんの英名はJiggly-puffでこのブルブル感とプリンちゃんに何か関係があるんでしょうか?

あんまりプリンちゃんがブルブル震えているイメージはないですね。

ちなみに、Puffの意味はフグみたいに息を吹き込んで膨らんでいるイメージです。

兎に角、これで白いBarの部分は完成しました。

この白いBarに先程のWorn out Effectを追加します。

Worn out EffectのHash23ノードから

MaskしてGの値を抽出してSmoothStepのValueに使用します。

その結果と先程の白いBarの結果を追加します。

結果です。

勿論、実際はこの結果がブルブルしています。

今度はこのLineの色を少しだけ調節します。

以下の実装を追加しました。

これ、Lineの色を黒くしているはずです。

確認してみます。

やっぱり黒くなっていました。

次ですが、いきなりさっきのWorn out Effectの最後に戻ってRとGの値を分けています。

いきなり何しているのかと思ったら以下の実装を組みました。

そしてSubtractノードのBに先程のLineの値をパスしました。

その結果を先週の実装に繋ぎます。

結果です。

静止画ですのであんまり実際の迫力が伝わりませんが、

LineのNoiseが下から上に移動していて画像が乱れている感じが出ています。

最後にこのLineの色を変更します。

以下の実装をYIQ変換した後に追加しました。

結果です。

Lineの色が緑になりました。

Level上での結果です。

凄い。

でも、あんまり理解していませんね。

今週のMaterialを勉強する時間はもうないです。

理論的な勉強とか、このVHSのSeriesの勉強が終わってからやる事にします。

4.RPGPackagingについて

今週はもうPackagingの勉強している時間がないので一個だけ確認して終わりにします。

それは先週の作業で.ini Fileの名前の書き換えをしなかった事です。

これらのFileに昔のProjectの名前が残っていた場合、新しいProjectの名前に書き変えてもう一回Editorが開けるか試してみます。

DefaultEngine.iniに以下の記述があります。

ここで昔の名前のch4_3がNew Gameの名前として使用されています。

まずこのOld Game Nameですが、ThirdPerson○○となっています。

うーん。

どう直すのが正解なのか分かりません。

よし決めました。

まず先週、変更したDefaultGame.iniのProject Nameを元に戻します。

そして以下の部分のch4_3をCh5_1に変更します。

これをまず試してみます。

直しました。

これでテストしてみます。

まず確認のためにBuildします。

はい。

Buildは普通に出来るんです。

しかしここからEditorが開けなかったです。

実行を押します。

先週と同じ位置でexceptionが投げられました。

Logを読むと

/Script/ch4_3': Can't find file.

と言うCommentがずらっとならんでします。

これ自体は警告ですが、これが原因でErrorに成っている可能性もあります。

うーん。

これBPとProjectの名前だけ変更してC++の方は触らない方がいいのかもしれません。

今度はそれで試してみます。

だたしもう今週は時間がないので来週やる事にします。

これで駄目だった場合は、Projectの名前の変更は諦めてこの名前のままpackagingをやる事にします。

Cloneだけ作成しておきます。

今度はLauncher からCloneをしてみました。

C++のCodeがあるからClone出来ませんよ。と警告が出ましたがOKを押しました。

Launcherが反応しなくなりました。

指定した先にCloneは出来ているみたいです。

しばらく放置して置いたらLauncherが反応するようになりました。

5.Open Worldの検証

建物の作成は、今週はEventでドアが開くようにします。

Naniteの勉強はLandscapeのNanite化について調査します。

5.1 ドアの開閉のTutorialを調べる

まずTutorialを探します。

たくさん出てきました。

どのやり方を採用しようかな。

そういえば人を採用する時に、以下の方法がある事を最近知りました。

兎に角、一番の人は断って、基準にします。

次に来た人が、一番の人より優れていたら即採用します。劣っていたら断ります。

断った場合は、その次に来た人が一番の人より優れていたら即採用します。

というやり方を採用した場合、採用試験に来た人の中で一番優れた人を採用出来る確率が最も高くなるそうです。

だたほかにも条件があったみたいで、さかのぼって前の人を採用する事は出来ない。とか採用試験に来る人が全部で4人とかもあった気がします。

その辺は覚えていません。

でもこの採用基準でやった場合、本当に最も優れた人が採用されやすいのか、疑問に思ったので、この方法で実装するTutorialを選んでみたいと思います。

取りあえず最初のTutorialを見て基準にします。

それで次のTutorialが最初のTutorialより優れていた場合は2番目のTutorialで実装します。

2番目のTutorialが最初のTutorialよりダメだった場合は、3番目のTutorialを見ます。

3番目のTutorialが1番目のTutorialより優れていた場合は3番目のTutorialで実装します。

3番目のTutorialが1番目のTutorialより劣っていた場合は4番目のTutorialを見ます。

4番目のTutorialが1番目のTutorialより優れていた場合は4番目のTutorialで実装します。

4番目のTutorialが1番目のTutorialより劣っていた場合は1番目のTutorialを見ます。

このやり方だと、一番短い場合はTutorialを2つ見るだけで済みます。

最長の場合は4つのTutorialを見る必要があります。

今回は多分、4つのTutorialを全部見て、甲乙つけますが、忙しくて時間を短縮したい時には、上記のやり方でやってもそれなりに優れたTutorialを見つけられるかどうかを判断します。

Unreal Engine 5 Tutorial: How to make a Door that opens! [6]

見ました。

まず開閉方法にTimelineノードを使用していてその点が目新しかったです。

後、以下の点が素晴らしいかったです。

  • 時間が6分と短い
  • 英語が聞き取りやすい(私に取って)
  • 見ていて苦痛にならない。

以下の点に不安を感じました。

  • 登録者数が少ない
  • 作者が十代後半なんじゃないかと思われる

これを基準にして次のTutorialを見ます。

How To Open And Close A Door In Unreal Engine 5 | Efficient Methods And An In-Depth Explanation [7]

Matt Aspland氏のTutorialです。

まず見てから感想を書きます。

見ました。

これ見て思ったのがやっぱりKeyboardのInputはしっかり管理しておいた方が良いです。

前のTutorialではdoorのBP内でKeyboardのEが押された場合の処理を全部やっていましたが、このTutorialではProject SettingのInputやThird Person Character内でInputの処理を行うなどの基本に忠実に実装しています。

更にInterfaceを使用してDoorの開閉の処理を行っているのも興味深いです。

私、Interfaceの存在自体は知っていましたが、自分で使用した事が無くて、最近、日本語のUEのTutorialを見る事が多くなったんですが、ほぼ全員がInterfaceについて語っています。

ので一寸Interfaceについて勉強しようかなと思っていたところに丁度良くこのTutorialが現れました。

それでは前のTutorialと比較して採点してみます。

  • Tutorialの長さは20分で、前のTutorialと比較すると3倍も長い。―>×
  • 製作者がイギリス人で英語が聞き取りくい。(私に取って)->×
  • 見ていて苦痛にはならない。―>引き分け
  • 私が何度もお世話になっているMatt Aspland氏の作成で内容に信頼が持てる。―>〇
  • Inputの処理をThird Person Characterに担当させていて、それは正しいやり方だと思う。
  • Interfaceを使用していて、Interfaceの勉強をしたい私には丁度良い。―>〇

はい。

〇3つ、×2つ、引き分け一つで、このTutorialの勝ちです。

先程説明したどのTutorialを採用するかに基づくと、これでこのTutorialを採用して終です。しかし今回は本当にこのTutorialが一番優れているか確認するために後2つ程Tutorialを見る事にします。

Learn How to Open and Close Doors in Unreal Engine 5 [8]

ではこのTutorialを見てみます。

10分位のTutorialで大した内容じゃないという先入観を持って見たんですが、それなりに勉強になりました。

まずDoorを開けるEventを呼び出すのにLine Trace By Channelノードを使用しています。

これは前2つのTutorialには無いやり方で興味深かったです。

後、Inputの処理をThird Person Characterでやっていました。

採点します。

  • Tutorialの長さは10分で、一番目のTutorialと比較すると少しだけ長いが気になるほどではない―>引き分け
  • 製作者がアメリカ人で英語が聞き取りやすい。(私に取って)->引き分け
  • 見ていて苦痛にはならない。―>引き分け
  • Inputの処理をThird Person Characterに担当させている―>〇
  • 登録者数は4千人程度で内容にまずまず信用がおけるー>〇
  • 作者は声からして若い感じがするが、結構責任感がある感じがする。それなりに信頼は出来る感じはある。->〇

となり最初のTutorialよりは良い結果になりました。

次に2番目のTutorialと比較すると

  • Tutorialの長さー>〇
  • 英語の聞き取り安さー>〇
  • 製作者の信頼度>やや×
  • Inputの処理>このTutorialProject SettingInputは使用していないので、ややX
  • Interfaceを使用していない。->×

となりました。

引き分けかやや2番目のTutorialの勝ちとなりました。

Simple Animated Door UE4 [9]

このTutorialは5分の長さで今まで見たTutorialの中で最も短いです。

何とこのTutorialではSequencerを使用してドアの開閉をAnimateしていました。

後は、特に記録すべき点はないです。

Inputの処理もLevel BPでやっています。

Doorの開閉を管理する所がSequencerを使用している所とTutorialが短い所以外は他のTutorialと比較して勝っている点はないです。

<4つのTutorialを見て>

先程の戦略に従ってどのTutorialを採用するかを決定すると2番目のTutorialが採用となります。

そして4つのTutorialを全部見た結果、私が一番優れていると思うTutorialは2番目でした。

つまり先程の戦略に従ってどのTutorialを採用するか決めた場合と、全部のTutorialを見て一番優れたTutorialを決定した場合の結果が同じになりました。

たしか、このやり方で一番優れているTutorialを選べる割合が50%弱だったと思います。

驚きの結果ですが、時間が無い時は、このやり方に賭けるのは有りだと思いました。

今週は実装までやるつもりでしたが、建物の作成に使用出来る時間はもう無くなってしまったので実装は来週やる事にします。

5.2 NaniteのLandscapeへの応用

何でこんなことをやるかというとVally of ancientのDemoでLandscapeもNaniteになっていた気がするからです。

まずそれを確認します。

見渡す限りnaniteが採用されています。

でもLandscapeは無かったです。

あれ?

Vally of ancientではLandscapeそのものが使用されていませんでした。

この後調べましたが、LandscapeをNaniteにする事は出来なくはないですが、全くお勧めしないみたいです。

はい。

のでLandscapeをNaniteに変換するのは中止です。

6.Gaeaの勉強

先週、一寸時間が空いた時に、Gaeaを使用して自分でTerrainを作成してHeight MapとMaskとしてExportしてUEで開いてみました。

そしたら凄い変な形状になっていました。

どこを間違えたんでしょうか?

でもそれが以外と勉強になりそうだったので、もう一回同じ様にやってみてそれを記録します。

そしてその後で、Klaus氏のTutorialで正しいやり方(特にBuildのやり方)を確認してそれで間違いを直します。

まずこれをします。

その後で、時間があったらGaea Tutorial for Beginners #5 | Creating the shape of our first terrain [10] の続きを勉強します。

6.1 Gaeaを使って自分でTerrainを作成してみる

自由に作成すると言う事で、以下のようにやってみました。

まずPrimitiveノードとしてMountainを選びました。

こんな感じです。

次にTransformノードをつけて山の位置を移動します。

こんな設定で移動しました。

結果です。

山の位置が移動しました。

今度は平らな空間にNoiseを追加します。

Rockyノードを追加します。

こういうTerrainです。

これと先程の山をCombineで合体させます。

Methodの設定をMaxに変更します。

結果です。

これにErosionを追加します。

結果です。

これをHeight MapとしてExportします。

更にMaskとして

Slop、

Flow、

そしてRiverのDepthを

Exportします。

6.2 作成したTerrainをBuildしてExportする

以下のNodeの結果をExportします。

Pngに変更しました。

何とFlowには以下に示したように沢山のOutputがあります。

これの内のどれが必要なのか確認します。

最初のOutputだけが必要でした。

設定は以下のようにしました。

あっているかは分かりません。

後で検討する時に確認します。

Buildしました。

結果です。

大きさの定義をするのを忘れていました。

設定を以下のように変更しました。

Scaleは1009mです、Pixelが1009なら100倍になるはずです。

何故か0.985mになっています。

Heightは適当です。

後、Buildの設定も変更しました。

白黒でBuildするのにsRGBを使用する必要があるのか不明です。RangeはNormalizedに変更しました。前にBuildした時、これを使用していた気がするからです。

間違えて前のDataを上書きしてしまいました。

6.2 作成したHeight MapMaskを使用してUE5Landscapeを作成する

以下の条件でHieght MapをImportします。

Scaleが100倍になっていて、Resolutionが1009x1009なので、多分あっているでしょう。

結果です。

山が高過ぎました。

LandscapeのZのScaleを50に変更しました。

結果です。

うん。これなら良いでしょう。

一回、playしてみます。

Landscapeの大体中心に降りてみました。

良い感じです。

今度はMaskを追加するためにLandscape用のMaterialを作成します。

Maskが効いているのかを確認するためのものなので簡単にしました。

LandscapeのMaterialにこのMaterialをセットしました。

この後、それぞれのLayerを作成したんですが、

これにMaskをImportする方法を忘れてしまいました。

適当にClickしていたら以下のBoxに飛ばされました。

ここでそれぞれのLayerにMaskをセットしました。

結果です。

Play画面です。

うーん。

Slopの部分が全部になっていますね。

なんでなんでしょう。

色を変えたら分かりました。

Flowと重なっている部分が黄色くなっていたんです。

Layerを選んでそのLayerだけにFoliageをPaintしようとしたんですが、

やり方を忘れてしまいました。

鬼の様に増やしてみました。

Naniteの視点です。

結構凄いと思いますがPCはいたって静かです。

Foliageで生成した岩、Collisionしませんね。

Show CollisionでCollisionを確認しましたが、Foliageで生成した岩にはcollisionはないです。

これぐらいにしておきますか。

課題を整理します。

6.3 Gaeaの使用に関しての課題

以下の課題が出て来ました。

まずBuildする時の正しい条件が分からなかったです。

次にUEでImportする時の条件が分かりませんでした。

ただこれはそんなに間違ってはいないと思っています。

Scaleはきちんと100倍になっていますし、Height MapのResolutionも1009になっています。

Section SizeとかNumber of Componentとかの値がEpic Game社が進める比率に成っているかどうかがだけが問題だと思います。

MaterialのLayerに作成したMaskを指定する方法が分からないかったです。

今回適当に何かを弄っていたら以下のようにLayerが表示されてMaskを指定出来る様になりました。

Layer同士がBlendしている時は、両方のLayerがBlendするのではなく、後のLayerが100%上書きするような設定にしたいです。

Layerを選んでそのLayerだけにFoliageをPaintする方法を忘れてしまいました。

Foliageで生成した岩とCollisionする方法も忘れてしまいました。

はい。

もう一回以下にまとめます。

  • Buildする時の正しい条件が分からない。
  • UEImportする時の条件が分からない。
  • Layer同士がBlendしている時は、両方のLayerBlendするのではなく、後のLayer100%上書きするような設定
  • Layerを選んでそのLayerだけにFoliagePaintする方法
  • Foliageで生成した岩とCollisionする方法

これらのやり方を確認します。

これは来週やります。

6.4 Gaea Tutorial for Beginners #5 | Creating the shape of our first terrain [10] の続きを勉強する

この山のshapeな感じが嫌なのでそれを直すそうです。

Wrap ノードとErosionノードの間にApertureノードを追加します。

ApertureノードのMethodをSpreadに変更しました。

結果です。

<Changing Parameters

何と、この期に及んで、この山の形が気に入らないからMountainノードのParameterから変更するとか言っています。

TypeをBからDに変更しました。

うーん。私も自分のMountainノードのTypeをA~Dまで試しましたが元々使用していたCが一番良い結果になるので、私はそのままにしておきます。

LookDevを使用して見た目をもっとRealにしていくそうです。

ああ、LookDevにあるNodeはそうやって使用するのか、Terrainにさいごの化粧をするためのNode達なのね。

と納得してたら、このTutorial、LookDevは本来Terrainの形状がまだ決まっていない初期の段階で使用すべきですが、とか言っています。

これはどうなんでしょうね。

Surfaceを追加しました。

StyleにTutorialと同じRockyをセットしたらTerrainが粒々になってしました。

偽物っぽくなるのでRoughに戻します。

<Adding Breakers

次はBreakerを追加します。

BreakerはTerrainに亀裂を追加します。

これが

こうなります。

<Other Changes

SwirlノードのParameterの値を調整したとか、そんな話をしています。

私のSwirlノードのParameterはTutorialとは全然違う値なので何もしないでほって置きます。

Adding Other Primitives

Mountainの回りにTerrainを作成するそうです。

Ridgeノードを追加します。

こういうやつです。

Combineノードを使用して繋ぎました。

TutorialではMethodにAddを使用していましたが、Maxの方がよりRidgeを強調出来ます。Maxに変えてしまいます。

結果です。

<Bypass Node

以下のBypass を初めて使用しました。

以下のSurfaceに対して使用しました。

SurfaceノードをBypassした場合です。

しない時です。

この例ではあんまり変化はみられないですね。

<Micro erosion

最後にMicro Erosion ノードを追加しました。

名前の通り細かいErosionが追加されました。

これでこのTutorialは終わりでした。

6.5 Gaea Tutorial for Beginners #5 | Creating the shape of our first terrain [10]を勉強して

最後に追加するのはLookDevよりErosionの方が見た目が本物っぽくなります。

次のTutorialからTextureを貼る方法を教えるそうです。

7.雪山のMapの作成

今週もVolumetric Cloudの勉強をします。

7.1 Painted CloudErrorを直す

先週、Painted Cloudで作成した雲が表示出来なくなりました。

Playを終了すると以下の様なErrorが表示されていました。

この原因を解明します。

まず先週、作成したPainted CloudのあるMapを開きます。

雲の欠片もありません。

もう一回作成しました。

一回閉じてまた開きます。

作成した雲は跡形もなく消えてしまいました。

Play中に表示されるLoadボタンは

以下の箇所にあるWidget内で作成されていました。

そこにはSaveノードもありました。

これだけ見ると描いた雲をどこかでSaveする必要がありそうです。

色々弄ってみて、分かったのはMaterialを変更してShaderをCompileした時は、前に作成した雲が表示されるみたいです。

ただし、Materialを変更したらいつもCompileするわけではないです。

つまり、このやり方で作成した雲は消えたり現れたりします。

こんな感じで突然雲が表示されます。

今のPainted Cloudの知識でこのSave問題がなぜ起きるのかの原因を解明するのは難しい気がします。

兎に角、描いた雲のDataはどこかに保存されているようです。

はい。

Zero Conditional 氏のVolumetric Paint Clouds FIX in Unreal Engine 4.26 [11]で

BP_PaintCloudsの

Render Targetsに保存されている

とありました。

Could Mask RTにセットされている、RT_CloudMask_01を開くと以下のようなImageがありました。

今、表示されている雲を上から覗くと以下のような形状をしています。

これをPaintで以下のような形状に変更しました。

Could Mask RTにセットされている、RT_CloudMask_01を開くと

同じ形状に変化しています。

一回、このMapを閉じます。

そしてもう一回開きました。

Could Mask RTにセットされている、RT_CloudMask_01を開くと

になっていました。

はい。

分かってきました。

雲を以下の形状に変更しました。

RT_CloudMask_01も同じように変更されています。

これを RT_CloudMask_01からSaveします。

これならどうでしょうか?

あ。

問題の本質はそこでは無かったです。

Placeable Cloudを使用したMapを開くと RT_CloudMask_01に保存されたImageが

に上書きされます。

はい。

Paintした雲をSaveするやり方が分かりました。

Paintした雲は RT_CloudMask_01に保存されています。

ただし、Placeable Cloudを開くと RT_CloudMask_01の内容は上書きされてしまいます。

RT_CloudMask_01に保存されている内容は、他のMapを開けても保存されていますが、

Projectを閉じたら消えてしまいます。

先週、Painted Cloudの雲が保存されていたかのように錯覚したのは、Placeable Cloudを先に開いたため、 RT_CloudMask_01に雲が描かれ、それが Painted Cloudの雲が保存されていたかのように見えたんです。

おそらく、Play中に現れる以下のLoadボタンを

押すとError表示になりますが、本来の機能は、このLoadボタンを押すと、どこかにSaveした雲のImageを RT_CloudMask_01に写すと思われます。

そして このLoadボタンを生成しているWidgetであるUI_VolumetricPainting_Toolbarの以下の実装部分にある、繋がっていないSaveノードが

RT_CloudMask_01のImageをどこかに保存するための機能を有していると考えられます。

かなり重要な内容になりましたが、あまりまとまっていないのでもう一回まとめ直します。

7.2 Painted Cloudの勉強をまとめ直す

まず、以下のErrorですが、

Play中にLoad Buttonを押すと出ます。

Painted Cloudで前に描いた雲が保存されたり、されなかったりする問題とは何の関係も有りません。

単にこのButtonを生成しているWidget側の問題です。

Painted Cloudで前に描いた雲が保存されたり、されなかったりする問題についての解答をまとめます。

まずPainted Cloudで描いた雲は、BP_PaintCloudsの

Could Mask RTにセットされている、RT_CloudMask_01

に保存されています。

こんな感じです。

このImageはProjectが開いている間は保持されていますが、Projectを閉じたら全部消えます。

RT_CloudMask_01に描かれているImageがProjectを終了した後も保存される事はありません。

では、何故、時々は前に描いたPainted Cloudが表示される事が有ったのかと言うと、Placeable Cloudを使用しているMapを先に開いたからです。

このRT_CloudMask_01は、Painted CloudだけでなくPlaceable Cloudでも使用しています。

Placeable Cloudを使用しているMapを開くと、Placeable CloudにあるVolumetric CloudがRT_CloudMask_01に雲を描きます。そのDataはProjectが閉じるまではRT_CloudMask_01に保存されています。

その状態でPainted Cloudを使用しているMapを開くと、RT_CloudMask_01に雲のDataが保存されているので、最初からVolumetric Cloudが表示される訳です。

恐らくですが、このPainted Cloudで描いたRT_CloudMask_01に保持されている雲のDataはどこか別のTextureにDataとして保存出来るはずです。

その根拠はPainted Cloud用のMapでPlay中に表示されるWidgetにあるLoad Buttonです。

これが存在していると言う事は、前に描いた雲をSaveしたりLoadしたりする事が出来るはずです。

この辺は来週以降、調査していきます。

8.報酬システムの研究

報酬システムを作成する前に、セリフを表示するシステムを作成する必要が出て来ました。

今作成中のRPGで使用している、私が一から作成したDialogue Systemを使用しても良いんですが、AssetにTree Systemを使用しているDialogue Systemがあったのでそれを使う事にしました。

報酬システムを作成するのがこの節の目的なので、このDialogue Systemを今ここで勉強するの主旨に反します。ので一寸、改良して使用するつもりでした。

しかし、それは無理でした。

そして先週の結論は

となりました。

ので、今週からしばらくの間、Dialogue Systemの勉強をします。

8.1 Dialogue SystemWidgetについて

このWidgetがどうやって

以下のDialogue ClassのDataを受け取っているのかを調べます。

ただし実際には以下のDemo Dialogue WidgetをCopyして作成したWidgetで調査します。

まずこのWidgetを生成する時には、Dialogue ClassをParameterとしてパスする必要があります。

Demo Dialogue Widgetを開くと

InDialogueという名前の変数があります。

当然、Espose on SpawnにCheckが付いています。

まずConstructorから見てみます。

ここでは3つの事を行っています。

Dialogue Classにある関数、Assign Persisitent Outer()を呼び出し、Game Insatanceをパスします。

この関数が何をしているのかは不明です。

儀式的なものとして納得しておきます。

次です。

In dialogueから何かのArrayであるDataを取り出してそのDataの最初の要素をTo Npc Reply()関数にpassしています。

To NPC Reply()関数が何をしているかも確認します。

以下の実装でした。

軽く読んでいきます。

Input ノードです。

Inputに先程のDataの最初の要素をパスしたPlayer ReplyとFire Eventsの2つがあります。

このPlayer ReplyはDialogue StructというTypeだそうです。

どんな変数で構成されているかを確認します。

結構、ありますね。

大体は意味分かりますが、CoordinateとかDialogue Waveとか全く意味が分からないものもあります。

もう一つのInputであるFire Eventですが、こんなありましたっけ?

ありました。

次です。

Found ValidってLocal変数でしかもDefault値はFalseになっていました。

ここで敢えてFalseにセットする必要あるんでしょうか?

一寸この変数を追ってみます。

Display NPC Node()関数の後でTrueにセットされています。

その後以下の実装に戻ります。

Breakなんでおしまいです。

そうじゃない場合はCompletedから下の実装を実行します。

その場合、Found ValidがFalseの場合だけ実行します。

うーん。

今軽く読んだだけだと、このFound ValidがFalseの指定は入らない気がします。

次です。

BranchノードですがTrueしかないので、その次のDo Eventsが実装されます。

Do Eventsノードは何をやっているのでしょうか?

開いて確認します。

こんな実装いる?

ただこのRun Events for Node、開けません。中で何をしているのかは不明です。

次です。

このNodeも開けません。何をしているNodeなのか不明です。

ただ名前から推測するとDialogue にある次のNodeを指している気がします。

ここでパスされているDialogue ClassであるReward System Dialogueをみると

次のNodeは赤線で囲ったNodeですね。

次の実装のBlockです。

一個ずつノードを確認していきます。

Get Next Nodeノードが次のNodeを返すならArrayである必要はないはずです。

しかしArrayで帰ってきてしっかりFor Each Loopしています。

一つの可能性としては以下に示した様に次のNodeが3つある場合です。

この場合3つのNodeを全部返す訳です。

取りあえずこの推測が正しいとして次に行きます。

Check Condition()関数ですが、これも開けません。これが何をCheckしているのか不明です。

Trueを返した場合です。

Display NPC Nodeです。

これは開けました。

何をしているのか確認します。

まずパスされたNPC NodeをCurrent Node変数にセットします。

次にDo EventノードでEventを実行します。

またこのNodeか!

当然、中身は見られません。

何をしているのかは不明です。

次ですが、Dialogue Nodeを分解して

Soundを

にパスしています。

これはSoundの音をPlayするNodeでしょう。

次ですが、もうGet Next Nodesが呼ばれています。

Player VBoxにあるChildren Classが消されました。

Demo Dialogue WidgetをCopyして作成したWidgetでは以下の赤線で囲った部分です。

この Player VBox 内にChildren Classとして何が入っているのかを調べます。

見つけました。

以下の箇所で

Demo Replay Widgetを追加していました。

ただし、このWidgetはもとのWidgetをCopyしたやつなのでこの追加するWidgetも Demo Replay WidgetをCopyしてやつです。

このWidget基本的にはセリフを保持するだけなんですが、その作りは結構複雑です。

Rich Textなんかを採用してたりもします。

このWidgetは後で勉強します。

次のNodeです。

NPC Text(下の赤い線で囲った部分)に

以下のTextをセットします。

うーん。

何でセリフがNPCのものであるって分かるんでしょうか?

これやな。

これがDialogue Nodeの

をCheckしていたんでしょうね。

次はBranchです。

このLengthは

の返し値の数です。

最後のNode出ない限り0以上にはならないのでTrueに行きます。

と思ったんですが、Falseの方が簡単なので先にFalseを見ておきます。

セリフが全部終わった時ですね。

このDialogue NodeがPlayerかどうか確認しています。

あれ、これってさっきの

でやっているんじゃないの?

ちなみに私が作った唯一のDialogue ClassであるRewardSystemDialogueのDialogue NodeはPlayerではありません。

のでFalseの方から見ます。

Textがあるかないか聞いています。

無いですので、Falseの方に行きます。

Continue Buttonを表示して終わりです。

これは、先週最後に見つけたNodeです。

Continueは(続きを表示します。)に書き換えてあります。

セリフがあった場合です。

Do Eventsノードです。

次のNodeです。

あれ。次のDialogue Nodeを取りに行っています。そしてDisplay Repliesノードで。

うーん。

このNodeのTextureはどこで表示しているの?

どっかで勘違いしている?

これは来週、もう一回読み直す事にします。

取りあえず、Playerだった場合まで戻ります。

こっちもDisplay Repliesノードでした。

今週のDialogueの勉強はここまでにします。

来週はこのDisplay Repliesノードの実装から読んでいきます。

9.Anime Renderingの勉強

9.1 Vroidで作成したModelUEImportするの続き

今週もVRM4U [12]のMaterialを読んで勉強します。

今週はLight Directionノード周りの実装を読んでいきます。

Light Direction ノードはMF_VrmMToonBase内で2か所で使用されているので、今週は以下の緑色のBox内のLight Direction ノードの実装をみます。

なんと、このBoxの名前、陰となっています。

ここでVroidの洋服などの影を作成しているみたいです。

後、陰影と言う表現で、Object上の凹凸を陰、Objectが光を遮って地面に出来る暗い部分を影と呼ぶ事は知っていますし、実際私もその定義で使用していた時期もありました。

が、陰という漢字にそういう意味は無いですよ。

のでここでは両方、影を使います。

Shade とShadowの違いも一般的な英語としては、Shadeは影の塊そのものを指しているのに対して、Shadowは影の形状を指している場合が多い位の違いしかないです。

Normal VectorとDot Productしています。

これは影の強さでも計算しているんでしょうか?

Dot #1ノードの先は3つに分かれてます。一番上のLineは別のBlockに繋がっています。

2番目は以下のSubtract#3ノードのAにつながっています。

このSubtract#3ノードのBの実装を見てみます。

ここに繋がっていました。

此処で何を計算しているのかまだ良く分かっていませんが、Default値だと合計で0です。

Subtract#3ノードで0を引いて、次にDivide#7ノードのAに繋がっています。

Bで割っていますね。

Bを遡ってみます。

Max#3ノードです。

Bが1x10^(-5)です。

とんでもない小さい値ですね。

Divide#7ノードの後にはSaturate#4ノードがあります。

例えばMax#3ノードの結果が1x10^(-5)でその後のDivide#7ノードの結果が100000になったとしてもSaturate#4ノードで1に戻ります。

この辺の計算の目的が見えないですね。

Subtract#2ノードのBですが、

またこの実装に繋がっていました。

ここは0と仮定するとSubtract#2のAの実装が重要になります。Aを追います。

Lerp#14ノードがありました。

Aには1がセットされています。

Bを追います。

-1~1でClampされています。

0~1ではなく-1~1です。

珍しいですね。

またここに来ました。

これ非常に簡単にまとめると以下の計算をしている事になります。

基本的にはDotの値を微調整しているだけみたいです。

で、今度はこの計算結果が最終的にどこに使用されているかを確認します。

何と、Add#1ノードのBに繋がっていました。

更に言うとこの後にあるAdd#9ノードとAdd#10ノードにも繋がっていました。

ここで影の計算を足しているのは間違いないみたいです。

Light DirectionとNormal VectorのDot値を利用して本当に影を投影できるのか、自分でMaterialを作成して確認します。

来週やります。

今週はこれだけです。

9.2 公式のDocumentStylized Rendering [17]の勉強

今週もWorld Aligned Blendノードの勉強をします。

先週、以下の事を今週やると言って終わりました。

のでやって行きます。

World Aligned BlendノードとLandscapeNormal値について

最初、World Aligned Blendノードを開いて

とか、

があるのを見て、やっぱりあるじゃん。で終わりになると思ったんですが、この実装、w/Explicit Normalを使用しています。

w/Explicit Normalの実装を見たんですが、どこにもLandscapeのNormalを使用していません。

分からん、分からんと30分位悩みました。

しかしとうとう見つけました。

これです。

Normal VectorをTangent SpaceからWorld Spaceに変換しています。

ここでLandscapeのNormal Vectorに変換されているんです。

Tangent SpaceのNormal Vectorだと一律に(0,0,1)です。所がWorld SpaceのNormal VectorだとそのLandscapeの形状によって値が変化します。

以下に簡単な例を示します。

Landscape用のMaterialにConstant(0,0,1)をセットします。

結果です。

当然ですが、青一色です。

今度は間にTransformノードを挟み、Tangent SpaceからWorld Spaceに変換します。

結果です。

はい。見事にLandscapeの情報が追加されました。

この例、非常に簡単ですが、Tangent SpaceにおけるNormal VectorとWorld SpaceにおけるNormal Vectorの違いを一発で表す事が出来る極めて優れた方法だと思います。

これでWorld Aligned Blendノードの先週の謎が解けました。

World Aligned Blendノードに関して今まで勉強した内容

2021-04-04Blog

ここでUnreal Sensei氏のHow to INSTANTLY TEXTURE your landscapes in UE4 - Unreal Engine tutorial [13]を勉強しています。

その中でWorld Aligned BlendノードのAlphaの値を使用していますが、

何か色々やっています。

説明を何度も読み返したんですが良く分かりません。

ので、もう一回、Unreal Sensei氏のHow to INSTANTLY TEXTURE your landscapes in UE4 - Unreal Engine tutorial [13]を見直します。

分かりました。

以下に示したようにWorld Aligned BlendノードのAlphaの値を使用するとBlend Material AttributesノードがErrorを返すんです。

World Aligned BlendノードのAlphaの値を使用するためにはどうしたら良いのかについて解説しています。

まずそれについてまとめ直します。

まずMatLayerBlend_Standardノードを使用します。

ただしこのノードをそのまま使用しても駄目でこのNodeを改良して使用する必要があります。

このNodeの改良方法は今回はSkipします。

そして以下のように繋ぎます。

My BlendノードがMatLayerBlend_Standardノードを改良して作成したNodeです。

これでMatLayerBlend_StandardノードのAlphaの値を使用して2つのLayerをBlend出来ました。

これが2021-04-04のBlogで勉強した内容でした。

Unreal Sensei氏のHow to INSTANTLY TEXTURE your landscapes in UE4 - Unreal Engine tutorial [13]をもう一回見た感想

約2年前に、このTutorialを勉強したんですが、今見てもとても勉強になる所が沢山あります。

その中で2年前には良く分からなかったWorld Aligned Blendノードの返し値であるAlpha、w/Vertex Normal、そしてw/Explicit Normal

の3つの違いですが、この違いについてもう少しこのTutorialで勉強し直した方が良い気がします。

2年前はこの3つの返し値を比較して「正直違いが分からない。」と書いています。

Unreal Sensei氏が敢えてこの中からAlpha値を選択したと言う事はAlpha値を使う事による優位性が何処かにあるはずです。

これが良く分かっていません。

次に何故、World Aligned BlendノードのAlphaをBlend Material Attributesノードに繋ぐとErrorになるのかについてです。

これについては、2021-04-04のBlogで調べてはあります。

この調査結果がどの程度正しいのか、今のそれなりにMaterialを理解した立場から再評価する必要があります。更に言うとこの原因に対しての再調査もする必要があります。

最後にMatLayerBlend_Standardノードの改良方法についてです。

まずどのような改良方法を行ったのかについて、2021-04-04のBlogではまとめられていません。これは新たに勉強し直してまとめ直す必要があります。

次に何故、Tutorialで行った改良によってWorld Aligned BlendノードのAlphaをBlendに使用出来る様になったのかについて理解する必要があります。

<来週以降の予定について>

以下に、来週以降やるべき内容についてもう一度まとめます。

  • World Aligned Blendノードの返し値であるAlphaw/Vertex Normal、そしてw/Explicit Normalの違いについて
  • Unreal Sensei氏がこの返し値の中で、敢えてこの中からAlpha値を選択した理由
  • 何故、World Aligned BlendノードのAlphaBlend Material Attributesノードに繋ぐとErrorになるのか
  • MatLayerBlend_Standardノードの改良方法について
  • Tutorialで行った改良によってWorld Aligned BlendノードのAlphaBlendに使用出来る様になった理由について

これらについて来週から勉強する事にします。

10.DirectX 12の勉強

今週も C++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window [14]の続きを勉強します。

10.1 Display our windowを実装する

先週勉強したC++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window [14]のDisplay our windowを実装します。

まずCreateWindow()関数を作成します。

あれ、WindowWidth,とWindowHeightは作成するんでしょうか?

覚えていません。

まずはWindowTitleを作成します。

Global変数として宣言しました。

WinMain()関数内で初期化しました。

次にWindowWidth,とWindowHeightを作成します。

宣言しました。

初期化しました。

これでCreateWindow()関数の実装は終わりです。

今度は作成されたWindowを表示するための実装です。

以上です。

まあ、この辺はUEのBPのWidgetの作成と表示に似ていますね。

最後にWindowが作成されなかった場合の対応を実装します。

はい。

これでWindowの作成方法、表示方法について理解出来ました。

今週はここまでです。

11.まとめと感想

今週は結構集中しました。

最初のNiagara Fluidの問題が解けたのが大きかったです。

12.参照Reference

[1] OlympusMonsTutorials. (2021, February 17). C++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window. YouTube. https://www.youtube.com/watch?v=2vrEIhAajhM

[2] 6031: return value ignored (getchar()) In visual studio 2019. (2019, April 9). Stack Overflow. https://stackoverflow.com/questions/55583364/6031-return-value-ignored-getchar-in-visual-studio-2019

[3] renderBucket. (2022, September 12). Unreal Engine 5 Tutorial - Niagara Fluids & Characters/Skeletal Mesh Collisions. YouTube. https://www.youtube.com/watch?v=oAYkob_ciqc

[4] Ben Cloward. (2022b, September 8). Post Process VHS Filter Part 2 - Shader Graph Basics - Episode 60. YouTube. https://www.youtube.com/watch?v=Wyz1lDBrDzE

[5] Ben Cloward. (2022, February 24). Random Noise - Shader Graph Basics - Episode 35. YouTube. https://www.youtube.com/watch?v=5v6tvkb63XU

[6] Just Kedryn. (2022, May 15). Unreal Engine 5 Tutorial: How to make a Door that opens! #ue5 #unrealenginetutorial. YouTube. https://www.youtube.com/watch?v=tbDP-UITrtU

[7] Matt Aspland. (2022, April 15). How To Open And Close A Door In Unreal Engine 5 | Efficient Methods And An In-Depth Explanation [Video]. YouTube. https://www.youtube.com/watch?v=Eakt2hBd3YY

[8] Gorka Games. (2022, September 4). Learn How to Open and Close Doors in Unreal Engine 5 [Video]. YouTube. https://www.youtube.com/watch?v=O7vmp73ue4Y

[9] Upside Down. (2022, March 29). Simple Animated Door UE4 [Video]. YouTube. https://www.youtube.com/watch?v=vS6IOqj5EX0

[10] Andrea Cantelli. (2020b, June 2). Gaea Tutorial for Beginners #5 | Creating the shape of our first terrain. YouTube. https://www.youtube.com/watch?v=swAL_i4jPO4

[11] Zero Conditional. (2021, January 11). Volumetric Paint Clouds FIX in Unreal Engine 4.26 [Video]. YouTube. https://www.youtube.com/watch?v=Q5taeumHw3M

[12] Harube, R. (n.d.). VRM4U. VRM4U. https://ruyo.github.io/VRM4U/

[13] Unreal Sensei. (2020, August 7). How to INSTANTLY TEXTURE your landscapes in UE4 - Unreal Engine tutorial. YouTube. https://www.youtube.com/watch?v=mP8eHwVEA0o

[14] OlympusMonsTutorials. (2021, February 17). C++ DirectX 12 Game Engine - [S01E01] - Creating Our First Window. YouTube. https://www.youtube.com/watch?v=2vrEIhAajhM