Exemple #1
0
    public void InsertObject(IQuadObject in_obj)
    {
        if (_objs_ht.ContainsKey(in_obj.GetId()))
        {
            Debug.LogError(string.Format("Object with ID = {0} already exists", in_obj.GetId()));
            return;
        }

        CQuadLeaf current_quad = _initial_quad;
        int       comparator   = 1;
        RectInt   object_sides = GetObjectSidesOnQuadMap(in_obj.GetAABB());

        for (int i = _tree_depth; i > 0; i--)
        {
            int k = comparator << i - 1;
            int x = (k & object_sides.xMin) > 0 ? 1 : 0;
            int y = (k & object_sides.yMax) > 0 ? 1 : 0;
            if (x > 0 != (k & object_sides.xMax) > 0 || y > 0 != (k & object_sides.yMin) > 0)
            {
                break;
            }
            int index = (y << 1) + x;
            current_quad = current_quad.GetQuadOrCreateNewIfNonExist(index);
        }

        CObj obj = new CObj(in_obj, new AABB2D(object_sides.xMin, object_sides.yMax, object_sides.xMax, object_sides.yMin), current_quad);

        current_quad.AddObject(obj);
        _objs_ht.Add(in_obj.GetId(), obj);
    }
        /// <summary>
        /// 更新指定的对象(一般情况下,由于对象发生了位置变化造成AABB变化后需要更新)
        /// </summary>
        /// <param name="quadObject"></param>
        public void UpdateObject(IQuadObject quadObject)
        {
            if (m_ObjectToNodeDic.TryGetValue(quadObject, out var node))
            {
                RemoveObjectFromNode(node, quadObject);

                QuadNode targetNode = node;
                while (targetNode != null)
                {
                    if (targetNode.Bounds.Contains(quadObject.Bounds))
                    {
                        break;
                    }
                    targetNode = targetNode.ParentNode;
                }
                if (targetNode != null)
                {
                    targetNode = InsertObjectToNode(targetNode, quadObject);

                    if (targetNode != node)
                    {
                        MergeNode(node);
                    }
                }
                else
                {
                    CoreLogger.Error(QuadTree.LOG_TAG, "the object hasn't been added to tree");
                }
            }
            else
            {
                CoreLogger.Error(QuadTree.LOG_TAG, "the object hasn't been added to tree");
            }
        }
        private QuadNode InsertObjectToNode(QuadNode node, IQuadObject quadObject)
        {
            if (!node.Bounds.Contains(quadObject.Bounds))
            {
                CoreLogger.Error(LOG_TAG, "QuadTree::InsertObjectToNode->Object's bounds is not fit within node bounds");
                return(null);
            }

            if (node.IsLeaf && node.Depth < m_MaxDepth && node.ObjectCount >= m_NodeSplitThreshold)
            {
                SplitNode(node);
                ResetNodeObjects(node);
            }

            if (!node.IsLeaf)
            {
                QuadNode[] childNodes = node.ChildNodes;
                foreach (var childNode in childNodes)
                {
                    if (childNode.Bounds.Contains(quadObject.Bounds))
                    {
                        return(InsertObjectToNode(childNode, quadObject));
                    }
                }
            }

            node.InsertObject(quadObject);
            m_ObjectToNodeDic[quadObject] = node;

            return(node);
        }
 /// <summary>
 /// 向树中插入对象
 /// </summary>
 /// <param name="quadObject"></param>
 public void InsertObject(IQuadObject quadObject)
 {
     if (quadObject.IsBoundsChangeable)
     {
         quadObject.OnBoundsChanged += OnHandleObjectBoundsChanged;
     }
     InsertObjectToNode(Root, quadObject);
 }
 internal bool TryInsertObject(IQuadObject obj)
 {
     if (Bounds.Contains(obj.Bounds))
     {
         InsideObjects.Add(obj);
         return(true);
     }
     return(false);
 }
Exemple #6
0
 public void GetSelectedObjects(Vector3 in_mouse_point, List <IQuadObject> out_selected_objects)
 {
     foreach (CObj obj in _objects)
     {
         IQuadObject unit = obj.GetQuadObject();
         if (unit.GetAABB().Contains(in_mouse_point))
         {
             out_selected_objects.Add(unit);
         }
     }
 }
Exemple #7
0
    public void ChangeTreeOnMove(Bounds in_old_object_aabb, IQuadObject in_new_pos_object)
    {
        RectInt old_pos_box_sides = GetObjectSidesOnQuadMap(in_old_object_aabb);
        RectInt new_pos_box_sides = GetObjectSidesOnQuadMap(in_new_pos_object.GetAABB());

        if (old_pos_box_sides.EqualSides(new_pos_box_sides))
        {
            return;
        }

        DeleteObjectByID(in_new_pos_object.GetId());
        InsertObject(in_new_pos_object);
    }
        /// <summary>
        /// 删除指定的对象
        /// </summary>
        /// <param name="quadObject"></param>
        public void RemoveObject(IQuadObject quadObject)
        {
            if (m_ObjectToNodeDic.TryGetValue(quadObject, out var node))
            {
                if (quadObject.IsBoundsChangeable)
                {
                    quadObject.OnBoundsChanged -= OnHandleObjectBoundsChanged;
                }

                RemoveObjectFromNode(node, quadObject);
                MergeNode(node);
            }
        }
 internal void RemoveObject(IQuadObject obj)
 {
     InsideObjects.Remove(obj);
 }
 internal void InsertObject(IQuadObject obj)
 {
     InsideObjects.Add(obj);
 }
Exemple #11
0
 public CObj(IQuadObject in_quad_obj, AABB2D in_box2D, CQuadLeaf in_leaf)
 {
     _quad_obj = in_quad_obj;
     _box2D    = in_box2D;
     _leaf     = in_leaf;
 }
 private void RemoveObjectFromNode(QuadNode node, IQuadObject quadObject)
 {
     m_ObjectToNodeDic.Remove(quadObject);
     node.RemoveObject(quadObject);
 }
 private void OnHandleObjectBoundsChanged(IQuadObject quadObject, AABB2D oldBounds, AABB2D newBounds)
 {
     UpdateObject(quadObject);
 }