@@ -26,11 +26,46 @@ public static EntityGameObjectPool CreateInstance() {
2626 public Scene ? targetScene {
2727 get => _targetScene ;
2828 set {
29+ if ( _rootGameObject != null ) {
30+ throw new System . ArgumentException (
31+ "EntityGameObjectPool.targetScene may not be set if " +
32+ "EntityGameObjectPool.rootGameObject is set."
33+ ) ;
34+ }
35+
36+ if ( _targetScene != null && value != null ) {
37+ if ( _targetScene . Equals ( value ) ) {
38+ return ;
39+ }
40+ }
41+
2942 _targetScene = value ;
3043 MoveEntityGameObjectsIfNeeded ( ) ;
3144 }
3245 }
3346
47+ private GameObject ? _rootGameObject ;
48+ public GameObject ? rootGameObject {
49+ get => _rootGameObject ;
50+ set {
51+ if ( _targetScene != null ) {
52+ throw new System . ArgumentException (
53+ "EntityGameObjectPool.rootGameObject may not be set if " +
54+ "EntityGameObjectPool.targetScene is set."
55+ ) ;
56+ }
57+
58+ if ( _rootGameObject != null && value != null ) {
59+ if ( GameObject . ReferenceEquals ( _rootGameObject , value ) ) {
60+ return ;
61+ }
62+ }
63+
64+ _rootGameObject = value ;
65+ ReparentEntityGameObjects ( ) ;
66+ }
67+ }
68+
3469 private EntityGameObjectPool ( ) {
3570 entityComponentIds = new List < ComponentIdsList > ( ) ;
3671 entityGameObjects = new List < GameObject ? > ( ) ;
@@ -101,8 +136,9 @@ public void InitComponent
101136 currentComponentIds : compIds
102137 ) ;
103138
139+ GameObject ? gameObject = null ;
104140 if ( removedTypes . Any ( ) && entityGameObjects [ entityId ] != null ) {
105- var gameObject = entityGameObjects [ entityId ] ! ;
141+ gameObject = entityGameObjects [ entityId ] ! ;
106142 foreach ( var type in removedTypes ) {
107143 if ( gameObject . TryGetComponent ( type , out var removedComponent ) ) {
108144 UnityEngine . Object . Destroy ( removedComponent ) ;
@@ -111,38 +147,78 @@ public void InitComponent
111147 }
112148
113149 if ( addedTypes . Any ( ) ) {
114- var gameObject = EnsureEntityGameObject ( entityId ) ;
150+ gameObject = EnsureEntityGameObject ( entityId ) ;
115151 gameObject . SetActive ( true ) ;
116152 foreach ( var type in addedTypes ) {
117- UnitySyncMonoBehaviours . InvokeOnInit (
118- ( MonoBehaviour ) gameObject . AddComponent ( type ) ,
119- componentId ,
120- in component
121- ) ;
153+ var newMonoBehaviour = ( MonoBehaviour ) gameObject . AddComponent ( type ) ;
154+ IOnInitEntity ? onInitEntity = newMonoBehaviour as IOnInitEntity ;
155+ if ( onInitEntity != null ) {
156+ onInitEntity . OnInitEntity ( entityId ) ;
157+ }
122158 }
123159 }
160+
161+ gameObject = gameObject ?? GetEntityGameObject ( entityId ) ;
162+
163+ if ( gameObject != null ) {
164+ UnitySyncMonoBehaviours . InvokeOnInit (
165+ gameObject ,
166+ componentId ,
167+ in component
168+ ) ;
169+ }
170+ }
171+
172+ public void UpdateComponent < T >
173+ ( System . Int32 entityId
174+ , in T component
175+ ) where T : EcsIdl . Component
176+ {
177+ UpdateComponent (
178+ entityId ,
179+ EcsIdl . Util . GetComponentID ( typeof ( T ) ) ,
180+ component
181+ ) ;
124182 }
125183
126184 public void UpdateComponent
127185 ( System . Int32 entityId
128186 , System . Int32 componentId
129- , object component
187+ , in object component
130188 )
131189 {
132- var gameObject = entityGameObjects [ entityId ] ;
133- if ( gameObject != null ) {
134- UnitySyncMonoBehaviours . InvokeOnUpdate (
135- gameObject ,
136- componentId ,
137- component
190+ var gameObject = GetEntityGameObject ( entityId ) ;
191+ if ( gameObject == null ) {
192+ throw new System . ArgumentException (
193+ $ "EntityGameObjectPool.UpdateComponent called before " +
194+ $ "EntityGameObjectPool.InitComponent. entityId={ entityId } "
138195 ) ;
139196 }
197+
198+ UnitySyncMonoBehaviours . InvokeOnUpdate (
199+ gameObject ,
200+ componentId ,
201+ in component
202+ ) ;
203+ }
204+
205+ public void RemoveComponent < T >
206+ ( System . Int32 entityId
207+ , in T component
208+ ) where T : EcsIdl . Component
209+ {
210+ var compObj = ( object ) component ;
211+ RemoveComponent (
212+ entityId ,
213+ EcsIdl . Util . GetComponentID ( typeof ( T ) ) ,
214+ in compObj
215+ ) ;
140216 }
141217
142218 public void RemoveComponent
143219 ( System . Int32 entityId
144220 , System . Int32 componentId
145- , object component
221+ , in object component
146222 )
147223 {
148224 if ( entityGameObjects [ entityId ] != null ) {
@@ -164,7 +240,7 @@ public void RemoveComponent
164240 UnitySyncMonoBehaviours . InvokeOnRemove (
165241 gameObject ,
166242 componentId ,
167- component
243+ in component
168244 ) ;
169245
170246 foreach ( var type in removedTypes ) {
@@ -178,8 +254,13 @@ public void RemoveComponent
178254 }
179255
180256 foreach ( var type in addedTypes ) {
257+ var newMonoBehaviour = ( MonoBehaviour ) gameObject . AddComponent ( type ) ;
258+ IOnInitEntity ? onInitEntity = newMonoBehaviour as IOnInitEntity ;
259+ if ( onInitEntity != null ) {
260+ onInitEntity . OnInitEntity ( entityId ) ;
261+ }
181262 UnitySyncMonoBehaviours . InvokeOnInit (
182- ( MonoBehaviour ) gameObject . AddComponent ( type ) ,
263+ newMonoBehaviour ,
183264 componentId ,
184265 in component
185266 ) ;
@@ -206,6 +287,8 @@ private GameObject EnsureEntityGameObject
206287 gameObject = new GameObject ( $ "entity ({ entityId } )") ;
207288 if ( _targetScene != null && ! gameObject . scene . Equals ( _targetScene ) ) {
208289 SceneManager . MoveGameObjectToScene ( gameObject , _targetScene . Value ) ;
290+ } else if ( _rootGameObject != null ) {
291+ gameObject . transform . SetParent ( _rootGameObject . transform ) ;
209292 }
210293 entityGameObjects [ entityId ] = gameObject ;
211294 }
@@ -230,6 +313,18 @@ private void EnsureEntityLists
230313 }
231314 }
232315
316+ private void ReparentEntityGameObjects ( ) {
317+ foreach ( var gameObject in entityGameObjects ) {
318+ if ( gameObject != null ) {
319+ if ( _rootGameObject == null ) {
320+ gameObject . transform . SetParent ( null ) ;
321+ } else {
322+ gameObject . transform . SetParent ( _rootGameObject . transform ) ;
323+ }
324+ }
325+ }
326+ }
327+
233328 private void MoveEntityGameObjectsIfNeeded ( ) {
234329 Scene scene = _targetScene == null
235330 ? SceneManager . GetActiveScene ( )
@@ -258,7 +353,7 @@ private void OnChangedActiveScene
258353 , Scene next
259354 )
260355 {
261- if ( _targetScene == null ) {
356+ if ( _targetScene == null && _rootGameObject == null ) {
262357 MoveEntityGameObjectsIfNeeded ( ) ;
263358 }
264359 }
0 commit comments