public virtual void UpdateBelongBounds
            (BoundsBasedManagedObject <BOUNDS, DATA> managedObject, BOUNDS previousBounds)
        {
            if (!this.IsManage(managedObject))
            {
                return;
            }

            if (previousBounds != null)
            {
                var managedObjectsInBounds = this.managedObjectsInBounds[previousBounds];

                int index = managedObjectsInBounds.IndexOf(managedObject);

                if (index < 0)
                {
                    return;
                }

                managedObjectsInBounds.RemoveAt(index);
            }

            if (managedObject.BelongBounds != null)
            {
                this.managedObjectsInBounds[managedObject.BelongBounds].Add(managedObject);
            }
        }
        public virtual void UpdateBelongBoundsIndex(BoundsBasedManagedObject <S, T> managedObject)
        {
            if (!CheckObjectIsManaged(managedObject))
            {
                return;
            }

            int belongBoundsIndex = GetBelongBoundsIndex(managedObject.transform.position,
                                                         managedObject.BelongBoundsIndex);

            if (managedObject.BelongBoundsIndex == belongBoundsIndex)
            {
                return;
            }

            if (managedObject.BelongBoundsIndex != -1)
            {
                this.managedObjectsInBounds[managedObject.BelongBoundsIndex].Remove(managedObject);
            }

            if (belongBoundsIndex != -1)
            {
                this.managedObjectsInBounds[belongBoundsIndex].Add(managedObject);
            }

            managedObject.UpdateBelongBounds(this, belongBoundsIndex);
        }
        public virtual void ReleaseManagedObject(BoundsBasedManagedObject <BOUNDS, DATA> managedObject)
        {
            if (this.IsManage(managedObject))
            {
                if (this.managedObjects.Remove(managedObject))
                {
                    if (managedObject.BelongBounds != null)
                    {
                        this.managedObjectsInBounds[managedObject.BelongBounds].Remove(managedObject);
                    }

                    // NOTE:
                    // ManagedObject.OnDestroy() will call this function again,
                    // but this.IsManage() step will be failed.

                    GameObject.Destroy(managedObject);
                }
            }
        }
        public override bool ReleaseManagedObject(ManagedObject <T> managedObject, bool fromOnDestroy = false)
        {
            if (!base.CheckObjectIsManaged(managedObject))
            {
                return(false);
            }

            BoundsBasedManagedObject <S, T> boundsBaseManagedObject = managedObject as BoundsBasedManagedObject <S, T>;

            if (boundsBaseManagedObject == null)
            {
                return(false);
            }

            if (fromOnDestroy)
            {
                base.managedObjects.Remove(managedObject);

                // NOTE:
                // Comment out following code when refactored this.
                // Maybe thorwing Exception is more better for debug.
                //
                // if (boundsBaseManagedObject.BelongBoundsIndex != -1
                //  && boundsBaseManagedObject.BelongBoundsIndex < this.managedObjectsInBounds.Count)
                // {
                // }

                this.managedObjectsInBounds[boundsBaseManagedObject.BelongBoundsIndex].Remove(boundsBaseManagedObject);
            }
            else
            {
                GameObject.Destroy(managedObject);
            }

            return(true);
        }
 public bool IsManage(BoundsBasedManagedObject <BOUNDS, DATA> managedObject)
 {
     return(managedObject.Manager == this);
 }