Net.Like.Xue.Tokyo/Assets/BITKit/Core/Quadtree/QuadtreeNode.cs

96 lines
2.6 KiB
C#
Raw Normal View History

2025-03-12 22:46:37 +08:00
using System;
using System.Buffers;
using System.Collections.Concurrent;
using Unity.Mathematics;
using System.Collections.Generic;
2025-04-17 19:36:08 +08:00
#if UNITY_5_3_OR_NEWER
using Unity.Burst;
#endif
2025-03-12 22:46:37 +08:00
namespace Net.BITKit.Quadtree
{
public struct QuadtreeNode
{
2025-04-17 19:36:08 +08:00
private readonly Quadtree _root;
public int Depth;
2025-03-12 22:46:37 +08:00
public float2 Center; // 节点中心
public float2 Size; // 节点大小
public readonly QuadtreeNode[] Children; // 子节点
public readonly HashSet<int> Objects; // 存储的对象ID
2025-04-17 19:36:08 +08:00
public bool IsLeaf;
2025-03-12 22:46:37 +08:00
public QuadtreeNode(Quadtree root,float2 center, float2 size)
{
2025-04-17 19:36:08 +08:00
_root = root;
2025-03-12 22:46:37 +08:00
Center = center;
Size = size;
Children = new QuadtreeNode[4];
2025-04-17 19:36:08 +08:00
2025-03-12 22:46:37 +08:00
Objects = new HashSet<int>();
2025-04-17 19:36:08 +08:00
//Objects = root.HashSetPool.Take();
//Objects.Clear();
2025-03-12 22:46:37 +08:00
2025-04-17 19:36:08 +08:00
IsLeaf = true;
Depth = 0;
}
#if UNITY_5_3_OR_NEWER
[BurstCompile]
#endif
public readonly bool Contains(float2 point)
2025-03-12 22:46:37 +08:00
{
var min = Center - Size * 0.5f;
var max = Center + Size * 0.5f;
return math.all(point >= min & point <= max);
}
public void Split()
{
2025-04-17 19:36:08 +08:00
if (IsLeaf is false)
{
throw new InvalidOperationException("Node has already been split.");
}
2025-03-12 22:46:37 +08:00
var childSize = Size / 2;
var offset = childSize / 2;
2025-04-17 19:36:08 +08:00
Children[0] = new QuadtreeNode(_root, Center + new float2(-offset.x, offset.y), childSize)
{
Depth = Depth + 1,
};
Children[1] = new QuadtreeNode(_root, Center + new float2(offset.x, offset.y), childSize)
{
Depth = Depth + 1,
};
Children[2] = new QuadtreeNode(_root, Center + new float2(-offset.x, -offset.y), childSize)
2025-03-12 22:46:37 +08:00
{
2025-04-17 19:36:08 +08:00
Depth = Depth + 1,
};
Children[3] = new QuadtreeNode(_root, Center + new float2(offset.x, -offset.y), childSize)
{
Depth = Depth + 1,
};
IsLeaf = false;
foreach (var id in Objects)
{
var pos = _root.Positions[id];
for (var i = 0; i < Children.Length; i++)
2025-03-12 22:46:37 +08:00
{
2025-04-17 19:36:08 +08:00
ref var node =ref Children[i];
if (!node.Contains(pos)) continue;
node.Objects.Add(id);
break;
2025-03-12 22:46:37 +08:00
}
}
Objects.Clear();
}
}
}