æè¿ã Unite Europe 2016ã«ã³ãã¡ã¬ã³ã¹ã§ã¢ã ã¹ãã«ãã ã蚪åããŸãããããã§ã¯ãå€ãã®ææ ãšèå³æ·±ãçµéšãåãåããŸããã ãã®äŒè°ã§ã¯ãããŸããŸãªæ¹åãšããŸããŸãªã¬ãã«ã®è€éãã«é¢ããèå³æ·±ãã¬ããŒãããããããããŸããã ã¹ããŒãã®1ã€ã®ããŒãã¯ããæ å ã®ScriptableObjecté©åœã«ãããMonoBehaviorå°å¶æ¿æ²»ã®æåãã§ãããUnity Technologiesã®ã¹ãã·ã£ãªã¹ãã§ããRichard FineïŒ https://twitter.com/superpig / https://github.com/richard-fine ïŒåœŒã¯ScriptableObjectã«ã€ããŠè©³ãã話ããããããããžã§ã¯ãã«é©çšããæ¹æ³ãäŸã§ç€ºããŸããã
ãªãã£ãŒãã¯åœŒã®å ±åæžã§ã次ã®åé¡ã«åãçµãã ã
- MonoBehaviour ïŒä»¥äžãåã«MBïŒãã²ã©ãã®ã¯ãªãã§ãã ã
- ScriptableObject ïŒä»¥äžSO ãšåŒã³ãŸã ïŒãšã¯äœã§ããïŒãªããããåªããŠããã®ã§ããã
- SOã®äœ¿çšæ¹æ³ã
- SOã®äœ¿çšãã¿ãŒã³ã
- ãã¢ãããžã§ã¯ãPimp My Tanksã®äŸã§ã®SOã®å®æŒïŒãã®èšäºã§ã¯èª¬æããŸãããã¬ãã¥ãŒçšã«https://bitbucket.org/richardfine/scriptableobjectdemoã確èªã§ããŸãïŒã
次ã¯ããªãã£ãŒãã話ããŠããããšãç¡æã§ç¿»èš³/èªãçŽããããŸããŸãªè¿œå ãå ãããã®ã§ãã
ã¿ã€ã©ããŒMB
MBäžè¬æ å ±ïŒ
- ã»ãšãã©ã®ã¹ã¯ãªããã¯MBãšããŠæžã蟌ãŸããŸãã
- ãããã¯GameObject ïŒä»¥éGOãšåŒã³ãŸã ïŒã«æ·»ä»ãããŸã ã
- ã·ãŒã³ããã¬ããã«äœãã§ããŸãã
- ãšã³ãžã³ããããã€ãã®ã³ãŒã«ããã¯ãååŸããŸãïŒStartãUpdateãªã©ïŒã
æ¬ ç¹ã¯äœã§ããïŒ
- playmodãçµäºãããšãªã»ãããããŸãã
- ã€ã³ã¹ã¿ã³ã¹åæã«ãå®å šãªã³ããŒãäœæãããŸãã
- ã€ã³ã¹ã¿ã³ã¹ã¯ã·ãŒã³éã§ãææ¢ããããã®ã«äžäŸ¿ã§ãã
- ã€ã³ã¹ã¿ã³ã¹ã¯ããããžã§ã¯ãéã§ãææ¢ããããã®ã«äžäŸ¿ã§ãã
- äžæ£ãªVCSã°ã©ãã¥ã¬ãŒã·ã§ã³ ïŒã·ãŒã³ãªããžã§ã¯ãã®ã¹ã¯ãªãããå€æŽãããšãã·ãŒã³å šäœãå€æŽããã競åãé »ç¹ã«çºçãããªã©ïŒã
- äžè²«æ§ãªãã«ã¹ã¿ãã€ãºãããå ŽåããããŸãã ã·ãŒã³ã«è€æ°ã®åäžã®ãªããžã§ã¯ããããå Žåããããã®1ã€ã®ããããã£ã誀ã£ãŠå€æŽããå¯èœæ§ããããŸããããã¯ãæ€åºã容æã§ã¯ãªããã²ãŒã ãã¶ã€ã³ã®èŠ³ç¹ããã¯å®å šã«æ£ãããããŸããããã¹ãŠã®ã²ãŒã ãªããžã§ã¯ããåãã§ããå Žåããããã®ããããã£ã¯åãã§ããå¿ èŠãããããã§ã ãã®åäœã䟿å©ãªå Žåã¯äŸå€ããããŸããããããã¯ãããŸããªã±ãŒã¹ã§ãã
- æŠå¿µçã«ã¯å®å šã«é©åã§ã¯ãããŸããïŒéåžžã«å€ãã®å Žåã空éå ã®ç¹å®ã®äœçœ®ã«ããã³ã³ããŒãã³ã/ãªããžã§ã¯ãã§ã¯ãªããã€ã³ã¹ãã¯ã¿ãŒã§ãã€ãã£ãããã³èªåã·ãªã¢ã«åã®å¯èœæ§ãããã¯ãªãŒã³ãªããŒã¿ã§æäœããå¿ èŠããããŸãïŒ
MBã®å°å¶ããéããã«ã¯ã©ãããã°ããã§ããïŒ
çŽç²ãªéçCïŒã¯ã©ã¹ïŒ
- playmodãçµäºããŠããªã»ãããããŸãã
- ããããæåã§ã·ãªã¢ã«åããå¿ èŠããããŸãã
- ãã®ãããªã¯ã©ã¹å ã§ã¯ãUnityãªããžã§ã¯ããæäœããã®ã¯äžäŸ¿ã§ãã
- ç§ã¯èªåã®æ€æ»å®ãæžããªããã°ãªããŸããã
ããããçµå±ã®ãšãããäžäŸ¿ãé¿ããããã«ãã®ãç®±ããåºããŠããã«ãæäŸãããšã³ãžã³ãå ·äœçã«äœ¿çšããŸãïŒ
ãã¬ããã¯ã©ãã§ããïŒ
ã¹ãã¬ãŒãžãšã·ãŒã³éããã³ãããžã§ã¯ãéã®è»¢éã®åé¡ã解決ããVCSã°ã©ãã¥ã¬ãŒã·ã§ã³ã«éåããŸããã ãããããã®ãœãªã¥ãŒã·ã§ã³ã«ã¯æ¬ ç¹ããããŸãã
- ããšãã°ã誀ã£ãŠã€ã³ã¹ã¿ã³ã¹å/ã·ãŒã³ãžã®ãã©ãã°ãè¡ãããšã«ããããã¹ãŠãç°¡åã«ç Žå£ã§ããŸãã
- è¿œå ã®ã³ã³ããŒãã³ãïŒAudioSourceãªã©ïŒãååšããå ŽåããããŸãããããŒã¿ã¯ãã®ãããªãã®ããåé¢ããå¿ èŠãããããããªãå¿ èŠãªã®ã§ãããïŒ
- æŠå¿µçã«ã¯ãããã¯ãŸã çæ³çãªè§£æ±ºçã§ã¯ãªãããããã蚱容å¯èœãªè§£æ±ºçã§ããã...
ããã§æå©ã«æ¥ãŸã
SOã¯ãã¹ã¯ãªããã®ãµã³ãã«ã«é¢ä¿ãªãéä¿¡ããã倧éã®æ å ±ãä¿åã§ããã¯ã©ã¹ã§ãã GOã«ã¢ã¿ãããããªããªããžã§ã¯ããäœæããå¿ èŠãããå Žåããã®ã¯ã©ã¹ããç¶æ¿ã§ããŸãã
100äžã®æŽæ°ã®é åãæã€ã¹ã¯ãªãããåãããã¬ããããããšæ³åããŠãã ããã ã¢ã¬ã€ã¯4ã¡ã¬ãã€ãã®ã¡ã¢ãªãå æãããã¬ããã«å±ããŸãã ãã®ãã¬ããã®ã€ã³ã¹ã¿ã³ã¹ãäœæãããã³ã«ããã®é åã®ã€ã³ã¹ã¿ã³ã¹ãäœæãããŸãã 10åã®ã²ãŒã ãªããžã§ã¯ããäœæãããšããããã®10åã®ã€ã³ã¹ã¿ã³ã¹ã®é åãå æããã¡ã¢ãªã®ãµã€ãºã¯40ã¡ã¬ãã€ãã«ãªããŸãã
SOã䜿çšããå Žåãçµæã¯å®å šã«ç°ãªããŸãã Unityã¯ããã¹ãŠã®ã¿ã€ãã®ããªããã£ããæååãé åããªã¹ããVector3ãªã©ã®ç¹å®ã®ã¿ã€ããããã³å®çŸ©å¯èœãªãªããžã§ã¯ãã«é¢é£ããã³ããŒãšããŠSerializableå±æ§ãæã€ã«ã¹ã¿ã ã¯ã©ã¹ãã·ãªã¢ã«åããŸãã ã€ãŸãã100äžåã®æŽæ°ã®é åã宣èšãããSOã¯ã©ã¹ã®ã€ã³ã¹ã¿ã³ã¹ãäœæãããšããã®é åã¯ãµã³ãã«ãšãšãã«éä¿¡ãããŸãã ãã®å Žåã圌ãã¯ç°ãªãããŒã¿ãæã£ãŠãããšä¿¡ããŠããŸãã SOãã£ãŒã«ãããŸãã¯MonoBehaviourãMeshãGameObjectãªã©ã®UnityEngine.Objectãã£ãŒã«ãã¯ãå€ãšã¯ç°ãªãããªã³ã¯ã«ä¿åãããŸãã 100äžåã®æŽæ°ãå«ãSOãåç §ããã¹ã¯ãªãããããå ŽåãUnityã¯ã¹ã¯ãªããããŒã¿ã«SOãžã®åç §ã®ã¿ãä¿åããŸãã SOã¯é åãæ ŒçŽããŸãã 4ã¡ã¬ãã€ãã®ã¡ã¢ãªã䜿çšããSOã¯ã©ã¹ãåç §ãã10ã®ãã¬ããã€ã³ã¹ã¿ã³ã¹ã¯ãäžèšã®40ã®ä»£ããã«4ã¡ã¬ãã€ããå æããŸãã ããã¯ãã¹ã¯ãªããå ã®å€æ°ã®ãªããžã§ã¯ãã倧éã®ããŒã¿ã«é¢ããŠç¹ã«éèŠã§ãã
ã ããããïŒ
- ããã¯MBã®ãããªãã®ã§ãããã³ã³ããŒãã³ãã§ã¯ãããŸããïŒMBããã§ã¯ãªãSOããã«ã¹ã¿ã ã¯ã©ã¹ãç¶æ¿ããå¿ èŠããããŸãïŒã
- GO /ãã¬ããã«åãä»ããããšã¯ã§ããŸããã
- MBã®ããã«ãã€ã³ã¹ãã¯ã¿ãŒã§ã·ãªã¢ã«åããŠæ€æ»ã§ããŸãã
- .assetãã¡ã€ã«ã«é 眮ã§ããŸãïŒãã¯ã¹ãã£/ãããªã¢ã«ãªã©ãé 眮ããããšã§ã«ã¹ã¿ã ã¢ã»ãããäœæã§ããŸãïŒã
- å€åã®ããã€ãã®åé¡ã解決ããŸãã Unityã®ã·ãªã¢ã«åã³ãŒãã詳ããèŠããšãç¶æ¿ã®éã«ããã¹ãŠã®ãã®ãæ£ããã·ãªã¢ã«åã§ããããã§ã¯ãªãããšãããããŸããSOã®å Žåããã®ãããªåé¡ã¯ãããŸããã
SOãåé¡ããç§ãã¡ãæãæ¹æ³ïŒ
- ã¢ã»ããã«ä¿åãããšããã¬ã€ã¢ãŒããçµäºããéã®ãªã»ãããé²æ¢ãããŸãã
- ã€ã³ã¹ã¿ã³ã¹åäžã«åç §ããããšã¯ã§ããŸãããã³ããŒããããšã¯ã§ããŸããïŒã¡ã¢ãªæ¶è²»ãæžå°ããã€ã³ã¹ã¿ã³ã¹åã®é床ãåäžããŸãïŒã
- ä»ã®ã¢ã»ãããšåæ§ã«ãã·ãŒã³éã§äœ¿çšãããããæºãåããããšãã§ããŸãã
- ãããžã§ã¯ãéã§ãææ¢ããããæ¹ãç°¡åã§ãã1ã€ã®ã¢ã»ãããã¡ã€ã«ã転éããã ãã§ãéå±€å šäœãæãäžããŠäŸåé¢ä¿ãæ¢ãå¿ èŠã¯ãããŸããã
- çæ³çãªVCSââã°ã©ãã¥ã¬ãŒã·ã§ã³ïŒ1ãã¡ã€ã«-1ãªããžã§ã¯ãïŒã
- è¿œå ã®äžèŠãªéšåã¯ãããŸããïŒäŸïŒå€æïŒã
ããããSOãå®ç§ã§ã¯ãããŸããã
- 3ã€ã®ã³ãŒã«ããã¯ã®ã¿ïŒOnEnable / OnDisableãOnDestroyã ãã®åé¡ã¯ãMBããããã·ãšããŠäœ¿çšããŠè§£æ±ºã§ããŸããã
- å®éãäžè¬çãªããŒã¿ã¯å®å šã«äžè¬çãªãã®ã§ã¯ãããŸããã ç¹å®ã®ãšã³ãã£ãã£ã«å¯ŸããŠã¯å€æŽã§ããŸãããç¹å®ã®ãšã³ãã£ãã£ã«ã¯é·æãšçæããããéžæãããããŒã«äŸåããŸãã
SOã®äœ¿çšæ¹æ³
SOã¯ã©ã¹ã¯ãå€ã®ã³ããŒãé¿ããŠã¡ã¢ãªæ¶è²»ãåæžããå¿ èŠãããå Žåã«äœ¿çšããå¿ èŠããããŸãã ãã ããå«ããããŒã¿ã»ããã決å®ããããã«ã䜿çšã§ããŸãã ã¬ãã«èšå®ãã°ããŒãã«ã²ãŒã èšå®ããã£ã©ã¯ã¿ãŒ/æµ/建ç©ãªã©ã®åå¥èšå®ãªã©ã®æ§æãã¡ã€ã«ã«æé©ã§ãïŒããšãã°ãæ倧ã®å¥åº·ç¶æ ããã¡ãŒãžããã®ä»ã®ãã©ã¡ãŒã¿ãŒãä¿åã§ããŸãïŒã SOã¯ãã«ã¹ã¿ã ããŒã«ãã¬ãã«ãšãã£ã¿ãŒãªã©ã®äœæã«ã圹ç«ã¡ãŸãã
SOã€ã³ã¹ã¿ã³ã¹ãããè¿ éãã€äŸ¿å©ã«ã«ã¹ã¿ã ã¢ã»ãããäœæãåå©çšããããã¯ãŒã¯çµç±ã§ããŒãããããšãã§ããŸããSOã¯ã©ã¹ã®ç¶æ¿è ã宣èšããå Žåã CreateAssetMenuå±æ§ã§ããŒã¯ã§ããŸããããã«ãããAssets / Createã³ã³ããã¹ãã¡ãã¥ãŒã«ãã®ãªããžã§ã¯ãã®ã¢ã»ããäœæã¢ã€ãã ãè¿œå ãããŸãã
èšå®ã䜿çšããç°¡åãªã¹ã¯ãªããã®äŸïŒ
using UnityEngine; [CreateAssetMenu(fileName="EnemyData", menuName="Prefs/Characters/Enemy", order=1)] public class EnemyPrefs : ScriptableObject { public string objectName = "Enemy"; [Range(10f, 100f)] public float maxHP = 50f; [Range(1f, 10f)] public float maxDamage = 5f; public Vector3[] spawnPoints; }
è³ç£ã®äœæïŒ
ã€ã³ã¹ãã¯ã¿ãŒã§ããŒã¿ã䜿çšããŠã¢ã»ãããã·ãªã¢ã«åããïŒ
SOã€ã³ã¹ã¿ã³ã¹ã䜿çšããŠã€ã³ã¹ãã¯ã¿ãŒã§äœæ¥ããŠããå Žåããªã³ã¯ãã£ãŒã«ããããã«ã¯ãªãã¯ããŠSOã®ã€ã³ã¹ãã¯ã¿ãŒãéãããšãã§ããŸãã ãŸããã«ã¹ã¿ã ãšãã£ã¿ãŒãäœæããŠã¿ã€ãã®ã€ã³ã¹ãã¯ã¿ãŒã®ã¿ã€ãã決å®ãããããè¡šãããŒã¿ã®ç®¡çã«åœ¹ç«ãŠãããšãã§ããŸãã
SOã€ã³ã¹ã¿ã³ã¹ã¯ã.assetãã¡ã€ã«ãåç §ããã«äœæã§ããŸããããã°ã©ã ã§ã SriptableObject.CreateInstance<>ã䜿çšããŸãã
SOã©ã€ãã¿ã€ã ïŒ
- ä»ã®ã¢ã»ãããšåãã§ãã
- æ°žç¶çãªå ŽåïŒ.assetãã¡ã€ã«ãAssetBundleãªã©ã«æ·»ä»ïŒïŒ
- SOã¯Resources.UnloadUnusedAssetsãä»ããŠGCã«ãã£ãŠã¢ã³ããŒãã§ããŸãã
- ä»ã®ã¹ã¯ãªããã«ãªã³ã¯ãããå Žåãã¡ã¢ãªå ã«ååšãç¶ããŸãã
- å¿ èŠã«å¿ããŠããªããŒãã§ããŸãã
- æ°žç¶çã§ãªãå ŽåïŒCreateInstance <>ã䜿çšããŠäœæãããã©ã®.assetã«ãé¢é£ä»ããããŠããªãå ŽåïŒïŒ
- ã¢ã³ããŒãããã ãã§ãªããGCã«ãã£ãŠç Žæ£ããããšãã§ããŸãã
- HideFlags.HideAndDontSaveã䜿çšããŠã¡ã¢ãªã«æ®ãããšãã§ããŸãã
䜿çšãã¿ãŒã³
ã»ãšãã©ã®éçºè ã¯SOãããŒã¿ã³ã³ãããŒãšèŠãªããŠããŸãããå®éã«ã¯ãã以äžã®ãã®ã§ãã ãã®ã¢ããªã±ãŒã·ã§ã³ã®ããã€ãã®ãã¿ãŒã³ãèããŠã¿ãŸãããã
ããŒã¿ãªããžã§ã¯ããšããŒãã«ã®ããã«ïŒ
- .assetãã¡ã€ã«ã«ãã€ã³ããããPlain-Old-DataïŒPODïŒã¯ã©ã¹ã
- ã€ã³ã¹ãã¯ã¿ãŒã§ç·šéããVCSã§åäžã®ãã¡ã€ã«ãšããŠã³ãããã§ããŸãã ããšãã°ãã²ãŒã ãã¶ã€ããŒã¯ãã·ãŒã³ããã¬ããã«åœ±é¿ãäžããã«èšå®ããã®ä»ã®ããŒã¿ãå€æŽã§ããŸããããã¯éåžžã«äŸ¿å©ã§ãã
- ã«ã¹ã¿ã ãšãã£ã¿ãŒã䜿çšãããšãã€ã³ã¹ãã¯ã¿ãŒã§èšå®ã䜿çšãããšãã«ããã«äŸ¿å©ã«ãªããŸãã
- SOã䜿çšããå Žåãã¢ãããŒããéžæãã䟡å€ããããŸãããšã³ãã£ãã£ããšã«1ã€ã®ãªããžã§ã¯ããé©çšããããããŒãã«/ãšã³ãã£ãã£ã»ããããšã«1ã€ã®ãªããžã§ã¯ããé©çšããŸãã ããšãã°ãããŒã«ã©ã€ãºããŒãã«ãŸãã¯æ§æãã¡ã€ã«ãäœæããå Žåã1ã€ã®å ±éãªããžã§ã¯ãã§ååã§ãããç°ãªããŠãããçšã®ãã³ãã¬ãŒããäœæããå¿ èŠãããå Žåãããããã«ç¬èªã®ãã³ãã¬ãŒããå¿ èŠã§ãã
- 䜿çšäŸïŒããŒã«ãªãŒãŒã·ã§ã³ããŒãã«ãã€ã³ãã³ããªã¢ã€ãã ããŠããããã³ãã¬ãŒããã¬ãã«æ§æãªã©ãäžèšã®ããããã空éå ã®äœçœ®ããŸãã¯äœããã®ããžãã¯ãå¿ èŠãšããŸããã ããã¯ãã·ãŒã³ããã¬ããã«åœ±é¿ãäžããã«å€æŽã§ããåãªãããŒã¿ã§ãããä»ã®ããŒã ã¡ã³ããŒã®äœæ¥ã劚ããããšã¯ãããŸããã
äŸïŒ
class EnemyInfo : ScriptableObject { public int MaximumHealth; public int DamagePerMeleeHit; } class Enemy : MonoBehaviour { public EnemyInfo info; }
æ¡åŒµå¯èœãªãªã¹ããšããŠïŒ
- .assetãã¡ã€ã«ã«ãã€ã³ããããã空ã®SOã®åœ¢åŒã
- ãããã¯ãä»ã®ãã®ãããªãªããžã§ã¯ããšã®åçæ§ã®ãã§ãã¯ããŸãã¯nullã®ãã§ãã¯ã«ã®ã¿äœ¿çšã§ããŸãã
- Enumã«äŒŒãŠããŸãããã³ãŒããèšè¿°ãã代ããã«ããã¶ã€ããŒããšãã£ã¿ãŒã§çŽæ¥äœæã§ããŸãã
- 䜿çšäŸïŒã€ã³ãã³ããªã¢ã€ãã ãã€ãã³ãã«ããŽãªãæå·ã¿ã€ãããŠãããã¿ã€ããªã©
- å¿ èŠã«å¿ããŠãå¿ èŠãªããããã£ãè¿œå ããããšã§ãããŒã¿/ããŒãã«ãªããžã§ã¯ãã«ç°¡åã«æ¡åŒµã§ããŸãã
äŸïŒ
class AmmoType : ScriptableObject { } ⊠if (inventory[weapon.ammoType] == 0) { PlayOutOfAmmoSound(); return; } ⊠inventory[weapon.ammoType] -= 1; ...
ãã¥ã¢ã«ã·ãªã¢ã«å
åè¿°ã®ãšãããSOã®å©ç¹ã®1ã€ã¯ãUnityã·ãªã¢ã«åã·ã¹ãã ãšã®å®å šãªäºææ§ã§ãã ãã®å ŽåïŒ
- SOã¯JsonUtilityãšå¯Ÿè©±ã§ããŸãã
- ãã®çµæãUnityã·ãªã¢ã©ã€ã¶ãŒã䜿çšããŠèšèšæ®µéã§äœæãããã¢ã»ãããšãJsonUtilityã䜿çšããŠããã°ã©ã ã§äœæãããã¢ã»ããã®æ··åç©ãååŸã§ããŸãã
- 䜿çšäŸïŒçµã¿èŸŒã¿ã¬ãã«ïŒãã¶ã€ã³ãUnityã·ãªã¢ã©ã€ã¶ãŒã§ä¿åïŒ+ãŠãŒã¶ãŒã¬ãã«ïŒã©ã³ã¿ã€ã ã§äœæãããJsonUtilityã䜿çšããŠä¿åïŒã ã¢ãŒããã¯ãã£ã®èŠ³ç¹ããã¯ããªããã®ãããªã¬ãã«ãäœæãããã®ããå¿é
ããå¿
èŠã¯ãããŸãããSOãšããŠã¡ã¢ãªã«ããŒãããæ®éçã«äœæ¥ã§ããŸãã
äŸïŒ
[CreateAssetMenu] class LevelData : ScriptableObject { /*...*/ }
- ã¡ãã¥ãŒãããšãã£ã¿ãŒã§çŽæ¥äœæããããå€ã調æŽãããã§ããŸãã
LevelData LoadLevelFromFile(string path) { string json = File.ReadAllText(path); LevelData result = CreateInstance<>(LevelData); JsonUtility.FromJsonOverwrite(result, json); return result; }
- ãã®ã¡ãœããã䜿çšãããšãJSONïŒã¬ãã«ã®äœæããã»ã¹ã§ããŒã«ã«ã«äœæãããããŸãã¯ãµãŒããŒããååŸããããã®ãªã©ïŒãå«ãããã¹ããã¡ã€ã«ãèªã¿åããSO
ã·ã³ã°ã«ããŒã³ã®ããã«ïŒ
- SO +éçã€ã³ã¹ã¿ã³ã¹å€æ°ïŒSOã€ã³ã¹ã¿ã³ã¹ãäœæããããããžã®ãªã³ã¯ãéçå€æ°ã«æ ŒçŽãããŸãïŒã
- ã¬ãã«ã®ãªããŒãåŸã«ã€ã³ã¹ã¿ã³ã¹ã埩å ããFindObjectWithTypeã
- 䜿çšäŸïŒã°ããŒãã«ã²ãŒã ã®ç¶æ ã
äŸïŒ
class GameState: ScriptableObject { public int lives, score; static GameState _instance; public GameState Instance { get { if (!_instance) _instance = FindObjectOfType<GameState>(); if (!_instance) _instance = CreateDefaultGameState(); return _instance; } } }
代ç人ãšããŠïŒ
- ã¡ãœãããå«ãSOã
- MBã¯SOã¡ãœããã§ããèªäœãžã®åç §ãæž¡ããSOã¯å¿ èŠã«å¿ããŠMBã䜿çšããŠäœæ¥ãè¡ããŸãã
- ããã«ãããåã蟌ã¿åäœãšã«ã¹ã¿ã åäœãå®è£ ã§ããŸãã
- 䜿çšäŸïŒAIã¿ã€ããããŸããŸãªãã¯ãŒã¢ããããã/ãããã
äŸïŒ
abstaract class PowerupEffect : ScriptableObject { public abstract void ApplyTo(GameObject go); } class HealthBooster : PowerupEffect { public int Amount; public override void ApplyTo(GameObject go) { go.GetComponent<Health>().currentValue += Amount; } } class Powerup : MonoBehaviour { public PowerupEffect effect; public void OnTriggerEnter(Collider other) { effect.ApplyTo(other.gameObject); } }
ãããã£ãŠãPowerup MBã¯ããã®äœæ¥ããã¿ãŒã³ã§ããPowerupEffect SOã«å§ä»»ããŸãã
ãããã«
äžèšãèŠçŽãããšãSOã«ã¯é·æãšçæãããããã®ããã€ãã以äžã«ç€ºããŸãã
å©ç¹ïŒ
- JsonUtilityã䜿çšããŠããšãã£ã¿ãŒã§èŠèŠçã«ïŒããšãã°ãéçã¯ã©ã¹ãšã¯ç°ãªãïŒå®å šã«ã·ãªã¢ã«åãããŸãã
- å€æŽã¯ä¿åãããplaymodã®çµäºåŸã«ç Žæ£ãããŸããã
- ä»ã®ã¹ã¯ãªããéãç°¡åã«ç§»åã§ããŸãã
- ç°¡åã«ç¶æ¿ã§ããŸãã
- ã€ã³ã¹ãã¯ã¿ãŒã«é 眮ãããªãããããã¿ãåºãŸããã
- ãªãŒããŒãããããªããMBããã軜éã§ãã
- ããããGOã«ã¢ã¿ãããããããªããžã§ã¯ããç Žæ£ããããšãã«åé€ãããŸããã
- ãã®ã·ãŒã³å ã®å°ãªããšã1ã€ã®ãªããžã§ã¯ããåç §ãããŸã§ãã·ãŒã³ã«ä¿åã§ããŸãã
- ã¢ã»ããã«ä¿åããAssetDatabaseã䜿çšããŠä»ã®ã·ãŒã³ã§åå©çšããããæ¢ã«ãããã€ããããã«ãã®ã©ã³ã¿ã€ã ã§åå©çšãããã§ããŸãã
çæïŒ
- ã·ãŒã³ã«ã¯è¡šç€ºãããŸãã-çŸåšäœ¿çšãããŠããSOã€ã³ã¹ã¿ã³ã¹ã®æ°ãèŠèŠçã«äžæã§ããããããããã°ãå°é£ã«ãªãå¯èœæ§ããããŸãã
- ïŒã·ãŒã³å ã§ïŒãããåç §ããæåŸã®ãªããžã§ã¯ããç Žå£ãããšãæé»çã«ç Žå£ããå¯èœæ§ããããŸãã
- ãã¬ããã§ã®äœ¿çšã¯ããã»ã©äŸ¿å©ã§ã¯ãããŸããã
- ãªããžã§ã¯ãã誰ã«å±ããŠããã®ãããã€ç Žæ£ããã®ããã©ã®å¯èŠé åã«ããã®ãã¯æããã§ã¯ãããŸããã
- SOã¯GOã«ã¢ã¿ãããããŠããªããããGetComponentsãä»ããŠãªã³ã¯ããã°ããååŸããæ¹æ³ã¯ãããŸããã
SOã¯éåžžã«éèŠãªããŒã«ã§ãããMBãå®å šã«çœ®ãæããããšã¯ã§ããŸããããMBãšçµã¿åãããŠäœ¿çšââã§ãããããå°å¶æ¿æ²»ãæé€ã§ããŸãã SOã¯ãã¹ãŠã«äœ¿çšãããã¹ãã§ã¯ãããŸããããããæè»æ§ããããŸãã è¡šé¢çã«SOã«ç²ŸéããŠãã人ããŸãã¯ãŸã£ããèããŠããªã人ãããã¯ããã«å€ãã ãŸãããããžã§ã¯ãã®åªããã¯ãŒã¯ãããŒãæ§ç¯ãããããã¶ã€ããŒã«ãšã£ãŠäŸ¿å©ã§äŸ¿å©ãªããŒã«ããã³ãã¬ãŒããäœæãããããæ©äŒãæäŸããŸãã
ãªãã£ãŒãã¯æŒèª¬ã®åé ã§ããMonoBehavior sucksãïŒMonoBehavior sucks :)ïŒãšè¿°ã¹ãŸããã ããã«å®å šã«åæããããšã¯å°é£ã§ããäœãšãããŠããããªãã§ã¯ã§ããªãïŒMBïŒããã§ãã ããããäž»ãªããšã¯ããã€ã§ãã©ãã§ãããã䜿çšããã¹ãã§ã¯ãªãã匷åãªãæè»ã§äŸ¿å©ãªScriptableObjectã§ããããŸããŸãªéžæè¢ãããããšãç解ããããšã§ãã ç¹å®ã®æ¡ä»¶äžã§ã®ã¿ã¹ã¯ã«åºã¥ããŠãããããŸãã¯ä»ã®æ段ãæ£ããéžæããå¿ èŠããããŸãã