はじめに
Unity の ECS で Entity が破棄された際にクリーンアップを行いたいと思ったことはありますか?
ICleanupComponentData
を使うと実現することができます!
- Entity が破棄された際に、その Entity から
ICleanupComponentData
以外のコンポーネントが削除される - Entity が破棄されているかどうかを判別するために、
ICleanupComponentData
以外の通常のタグコンポーネントなどを追加しておく - 通常通りにクリーンアップコンポーネントを利用する System では、タグコンポーネントがあることを条件に加える
- クリーンアップシステムでは、タグコンポーネントがないことを条件に加える
- クリーンアップシステムでは、必要であれば
OnDestroy
でもクリーンアップを行う
実行環境
- Unity6000.0.23f1
- Unity.Entities 1.3.5
Unity や ECS などの説明はありません。
必要であれば、公式のマニュアルやその他記事などをご覧ください。
※ECS の記事やマニュアルはバージョンが古い情報も多いので、ご注意ください
流れ
CleanupSampleAuthoring
でクリーンアップコンポーネントを追加するための印を追加AddCleanupComponentSampleSystem
でクリーンアップコンポーネントを追加SampleDestroySystem
で通常通りにコンポーネントを利用や破棄するCleanupSampleSystem
で Entity をクリーンアップする
コンポーネントデータ追加
StillNoCleanupComponent
クリーンアップコンポーネントを持つ Entity が「まだクリーンアップする必要がない(Entity が破棄されていない)」かどうかを判別するために使います。
StillNoCleanupComponent
が追加されている場合は、Entity が破棄されていないと判断できます。
StillNoCleanupComponent
が追加されていない場合は、Entity が破棄されていると判断できます。
AddCleanupSampleComponent
このコンポーネントを使ってクリーンアップコンポーネントを Runtime で追加します。
Baker ではクリーンアップコンポーネントを追加することができないため、Runtime で追加するための印として使用します。
クリーンアップコンポーネント追加後は不要なので Remove します。
Make sure to add it to entities at runtime, because cleanup components cannot be baked.
(DeepL 翻訳:クリーンアップ・コンポーネントはベイクできないので、必ず実行時にエンティティに追加すること。)
CleanupSampleComponent
今回の目玉のクリーンアップコンポーネントです。
破棄していない間は通常通りに値を利用したり、変更したりします。
クリーンアップする際に必要なデータを持っておきます。
クリーンアップコンポーネントを追加するための印を Baker で追加
CleanupSampleAuthoring
コンポーネントでも書きましたが、Baker ではクリーンアップコンポーネントを追加できないため、追加するためのマーク用コンポーネントだけ追加しておきます。
Make sure to add it to entities at runtime, because cleanup components cannot be baked.
(DeepL 翻訳:クリーンアップ・コンポーネントはベイクできないので、必ず実行時にエンティティに追加すること。)
クリーンアップコンポーネントを追加するシステム
AddCleanupComponentSampleSystem
ここでクリーンアップコンポーネントを追加します。
通常通りにコンポーネントデータを利用する場合はここで値を追加することもできます。
クリーンアップコンポーネントを追加するためのマーク用コンポーネントは、もう不要なので Remove します。
コンポーネントを利用や破棄するシステム
SampleDestroySystem
この時点では、Entity は以下のようになっています。
▼ コンポーネントを追加し終えて処理中の Entity の Inspector
StillNoCleanupComponent
があることを条件に加えることで、
クリーンアップコンポーネントを通常のコンポーネントとして扱うことができます。
破棄されたクリーンアップコンポーネントをクリーンアップするシステム
CleanupSampleSystem
クリーンアップを行うシステムです。
StillNoCleanupComponent
が存在しないことを条件に加えることで、
クリーンアップが必要な状態(Entity が破棄されている状態)であることを確認します。
つぶやき
CleanupEntity
というタグがついているのでこれを使えるとStillNoCleanupComponent
がいらないのになあ、と思いました。
internal なので残念ながら使用できません。
▼ Entity が破棄されクリーンアップコンポーネントだけが残っている状態