「Unity/DIフレームワーク/Extenject/基本」の版間の差分
(→起動時のエラー) |
(→起動時のエラー) |
||
| 行28: | 行28: | ||
*2020.2や2020.3だから起こるのかも、ほかバージョンにすれば良いかもとあるかも? | *2020.2や2020.3だから起こるのかも、ほかバージョンにすれば良いかもとあるかも? | ||
*確認すると、UnityPackages/com.svermeulen.extenject/OptionalExtras/Asyncにmetaがない模様・・。 | *確認すると、UnityPackages/com.svermeulen.extenject/OptionalExtras/Asyncにmetaがない模様・・。 | ||
| − | * | + | *UnityAssetstore側からDLすると直った。 |
==サンプル== | ==サンプル== | ||
2023年4月5日 (水) 19:05時点における版
目次
Extenjectとは
UnityのDIフレームワーク。Zenjectは、作者が前務めてた会社で作られたDIフレームワークの名前。
ダウンロード
unityのassetstore
https://assetstore.unity.com/packages/tools/utilities/extenject-dependency-injection-ioc-157735
公式 https://github.com/modesttree/Zenject/releases
インストール確認
Assets/Plugins/Zenjectにデータが有ればOK
PackageManagerでインストール
- Unityメインメニュー/Window/PackageManager/右上の+
- Add package from git URL
https://github.com/svermeulen/Extenject.git?path=/UnityProject/Assets/Plugins/Zenject
インストール確認
Packages/manifest.jsonに、以下のようにextenjectが追加されていればOK
"com.svermeulen.extenject": "https://github.com/svermeulen/Extenject.git?path=/UnityProject/Assets/Plugins/Zenject",
起動時のエラー
詳細
Asset Packages/com.svermeulen.extenject/OptionalExtras/Async has no meta file, but it's in an immutable folder. The asset will be ignored.
- 2020.2や2020.3だから起こるのかも、ほかバージョンにすれば良いかもとあるかも?
- 確認すると、UnityPackages/com.svermeulen.extenject/OptionalExtras/Asyncにmetaがない模様・・。
- UnityAssetstore側からDLすると直った。
サンプル
Installerからデータを入れて、[Inject]部分に入る。
ILogic.cs
public interface ILogic
{
bool Exec();
}
HogeLogic.cs
public class HogeLogic : ILogic
{
public bool Exec()
{
Debug.Log("HogeLogc Exec");
return true;
}
}
SampleMain.cs
using UnityEngine;
using Zenject;
public class SampleMain : MonoBehaviour
{
[Inject] ILogic _logic;
void Start()
{
if (_logic != null)
{
_logic.Exec();
}
}
}
HogeLogicInstaller.cs
using Zenject;
public class HogeLogicInstaller : MonoInstaller
{
public override void InstallBindings()
{
Container
.Bind<ILogic>()
.To<HogeLogic>()
.AsCached();
}
}
- Scene選択
- Hierarchyに、Create EmptyでGameObjectを作り、SampleMainの名前に変更し、SampleMain.csを、AddCompornentする。
- Hierarchyに、Create EmptyでGameObjectを作り、HogeLogicInstallerの名前に変更し、HogeLogicInstaller.csを、AddCompornentする。
- Hierarchyから右クリックし、Zenject/SceneContextを追加
- 作成した、SceneContextを選択し、InspectorのMonoInstallersに、HogeLogicInstallerのGameObjectをドラッグする。
- 実行するとCarのHogeLogicが実行できる
installer<TDerived>エラー
public class HogeLogicInstaller : Installer<HogeLogic>の部分で、 以下エラーが発生。
unity はジェネリック型またはメソッド installer<TDerived> 内で型パラメーター'TDerived として使用できません。
InstallBindingsメソッドを実行するクラスの継承元を : Installer<HogeLogic> などから MonoInstaller へ
参考:https://github.com/modesttree/Zenject
引数に入れるサンプル
public class SampleMain : MonoBehaviour
{
[Inject]
void StartInject(ILogic _logic
)
{
if (_logic != null)
{
_logic.Exec();
}
}
}
StartInject()とか適当なメソッドを作って、[Inject]をつけると、勝手にこのメソッドが起動して、実行される。
AsSingleとAsCachedとAsTransient
- AsSingle:インスタンスは一つで、シングルトンと同じ。
- AsCached:インスタンスを、キャッシュする。UnBindで破棄される。
- AsTransient:インスタンスは毎回作る。
AsCachedについて
Container
.Bind<ILogic>()
.To<HogeLogic>()
.AsCached(); // キャッシュする
Container
.Unbind<ILogic>(); // キャッシュを削除
Container
.Bind<ILogic>()
.To<HogeLogic>()
.AsCached(); // キャッシュする
Container
.Resolve<HogeLogic>()
.Exec(); // 実行
キャッシュを削除して、再度Bindして実行
インスタンスを入れる場合
Container
.Bind<ILogic>()
.FromInstance(new HogeLogic())
.AsSingle();
参考:https://light11.hatenadiary.com/entry/2019/02/20/234834
Bind処理いろいろ
IfNotBound()を使えば、既に同じintarfaceのインスタンスを作っていれば、作らない。
NonLazy()を使えば、最初にインスタンスが作られる。
参考:https://light11.hatenadiary.com/entry/2019/02/22/005845#WithId
エラーについて
こんな感じのエラーのときは
while building object with type Object graph:
Installerに、Containerがたりないので、以下のような感じで、追加すれば良い。
Container
.Bind<IHogeLogic>()
.FromInstance(new HogeLogic())
.AsCached()
.IfNotBound();
参考:https://adarapata.hatenablog.com/entry/2019/01/02/000848
インストーラーからコンテナを削除したときのエラー
Container
.Bind<IHogeLogic>()
.FromInstance(new HogeLogic())
.AsCached()
.IfNotBound();
を削除したときは、以下がエラーとして出てくる。
ZenjectException: Unable to resolve 'IHogeLogic' while building object with type 'HogeLogicInstaller'. Object graph: HogeLogicInstaller
"Found multiple matches when only one was expected for type"エラーが出る場合
エラー詳細
ZenjectException: Found multiple matches when only one was expected for type 'ILogic' while building object with type 'SampleMain'. Object graph: SampleMain
ILogicに入れるInstallerが2つ以上あるので、このエラーが起こってる。
対応方法は、
- Installerを1つにするか。
- WithId()を使うなどをつけるか。
- Unbind()して、キャッシュを削除するか。
- IfNotBound()って、同じintarfaceのインスタンスを無視するか。
WithId()を使うなどをつける方法
例:
Container
.Bind<ILogic>()
.WithId("exampleId")
.To<PiyoLogic>()
.AsSingle();
- [Inject] ILogic _logic; + [Inject(Id = "exampleId")] ILogic _logic;
参考:https://light11.hatenadiary.com/entry/2019/02/22/005845#WithId
Unbindでキャッシュを削除する方法
初回のBindのキャッシュを削除
Container
.Unbind<ILogic>();
IfNotBound()って、同じintarfaceのインスタンスを無視する方法
Container
.Bind<ILogic>()
.To<PiyoLogic>()
.AsCached();
.IfNotBound();
参考
DIフレームワーク「Extenject(Zenject)」についてまとめました https://www.theylive.co.jp/unitydi%E3%83%95%E3%83%AC%E3%83%BC%E3%83%A0%E3%83%AF%E3%83%BC%E3%82%AFextenjectzenject%E3%81%AB%E3%81%A4%E3%81%84%E3%81%A6%E3%81%BE%E3%81%A8/
依存性注入とは?と、なっているのでZenject(Extenject)を入門 https://qiita.com/4_mio_11/items/4306732bc47780802b74
Zenject READMEの日本語訳 https://qiita.com/rookx/items/3510467a2b57d3e39bc1
