public static unsafe (PathStatus PathStatus, List <GridNode> NodePath, List <Vector3> VectorPath) Complete(BurstAStarPathFinder pathFinder, ref NativeArray3D <GridNode> grid,
                                                                                                                       INativeArrayProducer <NativeAreaDefinition> areas, int queryId, GridPoint start, GridPoint end, ulong allowedFlags, float4x4 localToWorld)
            {
                using (var nativeAreas = areas.ToNativeArray(Allocator.TempJob))
                    using (var nativePath = new NativeList <GridNode>(grid.Length, Allocator.TempJob))
                        using (var nativeVectorPath = new NativeList <Vector3>(grid.Length, Allocator.TempJob))
                            using (var nativePriorityQueue = new NativePriorityQueue(grid.Length / 8, Allocator.TempJob))
                            {
                                var result = new PathFindingJobResult();
                                var job    = new PathFindingJob
                                {
                                    QueryId         = queryId,
                                    AllowedFlags    = allowedFlags,
                                    StartPoint      = start,
                                    EndPoint        = end,
                                    OpenQueue       = nativePriorityQueue,
                                    Grid            = grid,
                                    Areas           = nativeAreas,
                                    Path            = nativePath,
                                    MaxPoints       = 5000,
                                    WorldPath       = nativeVectorPath,
                                    TransformMatrix = localToWorld,
                                    ResultPtr       = &result
                                };

                                pathFinder.Stopwatch.Restart();
                                job.Run();
                                pathFinder.Stopwatch.Stop();

                                var path      = job.Path.ToArray().ToList();
                                var worldPath = nativeVectorPath.ToArray().ToList();
                                return(result.PathStatus, path, worldPath);
                            }
            }
Exemplo n.º 2
0
    private static void Allocate(int capacity, Allocator allocator, out NativePriorityQueue <T> nativePriorityQueue)
    {
        var size = (long)UnsafeUtility.SizeOf <MinHeapNode <T> >() * capacity;

        if (allocator <= Allocator.None)
        {
            throw new ArgumentException("Allocator must be Temp, TempJob or Persistent", nameof(allocator));
        }
        if (capacity < 0)
        {
            throw new ArgumentOutOfRangeException(nameof(capacity), "Length must be >= 0");
        }
        if (size > int.MaxValue)
        {
            throw new ArgumentOutOfRangeException(nameof(capacity),
                                                  $"Length * sizeof(T) cannot exceed {(object) int.MaxValue} bytes");
        }

        nativePriorityQueue.m_Buffer         = UnsafeUtility.Malloc(size, UnsafeUtility.AlignOf <MinHeapNode <T> >(), allocator);
        nativePriorityQueue.m_capacity       = capacity;
        nativePriorityQueue.m_AllocatorLabel = allocator;
        nativePriorityQueue.m_MinIndex       = 0;
        nativePriorityQueue.m_MaxIndex       = capacity - 1;
        nativePriorityQueue.m_head           = -1;
        nativePriorityQueue.m_length         = 0;

#if ENABLE_UNITY_COLLECTIONS_CHECKS
        DisposeSentinel.Create(out nativePriorityQueue.m_Safety, out nativePriorityQueue.m_DisposeSentinel, 1, allocator);
#endif
    }
Exemplo n.º 3
0
        public void TestNative()
        {
            const int count = 100;
            var       data  = new int[count];
            var       rand  = new Random((int)DateTime.Now.Ticks);

            for (var i = count - 1; i >= 0; i--)
            {
                data[i] = rand.Next();
            }

            using var q = new NativePriorityQueue <int>(0, count);
            for (int i = 0; i < count; i++)
            {
                q.Enqueue(data[i]);
                Assert.True(q.Count == i + 1);
            }

            Array.Sort(data);
            var t = 0;

            while (!q.IsEmpty)
            {
                Assert.True(q.Peek() == data[t++]);
                q.Dequeue();
            }
        }
Exemplo n.º 4
0
        private static void Attempt(ref SimpleBoard board, Move move, ref NativeHashMap <Piece, bool> alreadyPassed,
                                    ref NativePriorityQueue <Move> checkQueue, Instruction instruction, int maxBoardHeight,
                                    NativeArray <int4x4> pieceShapes, bool repeat = false)
        {
            if (repeat && !(instruction == Left || instruction == Right))
            {
                throw new ArgumentException();
            }

            var piece = move.piece;

            if (!TryApplyInstruction(ref board, piece, instruction, out var result, pieceShapes))
            {
                return;
            }
            piece = result;

            var t = 0;

            if (instruction == SonicDrop)
            {
                t += 2 * move.piece.y - result.y;
            }
            else
            {
                t = 1;
            }

            if (move.length != 0 && move.GetInstructionAt(move.length - 1) == instruction)
            {
                t += 1;
            }

            move.Append(instruction, t, result);

            while (repeat && !move.IsFull &&
                   TryApplyInstruction(ref board, piece, instruction, out result, pieceShapes))
            {
                piece = result;
                move.Append(instruction, 2, result);
            }

            if (result.tSpin != TSpinStatus.None || !IsAboveStacking(result, maxBoardHeight))
            {
                // We should do further checks
                if (alreadyPassed.TryAdd(result, true) && !move.IsFull)
                {
                    var dropped = board.SonicDropFast(piece, pieceShapes);
                    if (piece.y != dropped.y)
                    {
                        move.Append(SonicDrop, (piece.y - dropped.y) * 2, dropped);
                    }
                    checkQueue.Enqueue(move);
                }
            }
        }
Exemplo n.º 5
0
        public void Setup()
        {
            _cmp      = new CompareVec4();
            _priority = new PriorityQueue <Vector4>(1000000, _cmp);
            _native   = new NativePriorityQueue <Vector4>(0, 1000000);
            _data     = new Vector4[1000000];
            var rand = new Random();

            for (int i = 0; i < _data.Length; i++)
            {
                _data[i] = new Vector4(
                    rand.Next(1000000),
                    rand.Next(1000000),
                    rand.Next(1000000),
                    rand.Next(1000000));
            }
        }
Exemplo n.º 6
0
        public void TestPriorityQueue()
        {
            using (var pq = new NativePriorityQueue <int>(Allocator.Temp))
            {
                pq.Enqueue(2);
                pq.Enqueue(3);
                pq.Enqueue(1);
                pq.Enqueue(666);
                pq.Enqueue(23);
                pq.Enqueue(233);

                Assert.True(pq.Dequeue() == 1);
                Assert.True(pq.Dequeue() == 2);
                Assert.True(pq.Dequeue() == 3);
                Assert.True(pq.Dequeue() == 23);
                Assert.True(pq.Dequeue() == 233);
                Assert.True(pq.Dequeue() == 666);
            }
        }
Exemplo n.º 7
0
        public static NativeHashMap <Piece, Move> Generate(ref SimpleBoard board, Piece spawned,
                                                           NativeArray <int4x4> pieceShapes, bool holdUse)
        {
            var columns    = stackalloc int[10];
            var maxHeights = stackalloc byte[10];

            board.GetColumns(columns, maxHeights);

            var lookup     = new NativeHashMap <Piece, Move>(200, Allocator.Temp);
            var passed     = new NativeHashMap <Piece, bool>(200, Allocator.Temp);
            var checkQueue = new NativePriorityQueue <Move>(false, 100, Allocator.Temp);


            var maxHeight = 0;

            for (var i = 0; i < 10; i++)
            {
                if (maxHeights[i] > maxHeight)
                {
                    maxHeight = maxHeights[i];
                }
            }

            if (maxHeight < 16)
            {
                var starts = GenerateStarts(spawned.kind, holdUse);
                for (var i = 0; i < starts.Length; i++)
                {
                    var start   = starts[i];
                    var originY = start.piece.y;
                    var piece   = board.SonicDropFast(start.piece, pieceShapes);
                    start.piece = piece;
                    Confirm(ref board, ref lookup, start, pieceShapes);
                    var m2 = start;
                    var dY = originY - piece.y;
                    m2.instructions[m2.length++] = (byte)SonicDrop;
                    m2.time += dY * 2;
                    checkQueue.Enqueue(m2);
                }

                starts.Dispose();
            }
            else
            {
                var p = new Piece(spawned.kind);
                var d = board.SonicDropFast(p, pieceShapes);
                var m = new Move();
                m.hold            = holdUse;
                m.piece           = d;
                m.instructions[0] = (byte)SonicDrop;
                m.length          = 1;
                m.time            = 2 * (p.y - d.y);
                checkQueue.Enqueue(m);
            }

            while (checkQueue.TryDequeue(out var mv))
            {
                if (!mv.IsFull)
                {
                    Attempt(ref board, mv, ref passed, ref checkQueue, Left, maxHeight, pieceShapes);
                    Attempt(ref board, mv, ref passed, ref checkQueue, Right, maxHeight, pieceShapes);

                    if (mv.piece.kind != O)
                    {
                        Attempt(ref board, mv, ref passed, ref checkQueue, Cw, maxHeight, pieceShapes);
                        Attempt(ref board, mv, ref passed, ref checkQueue, Ccw, maxHeight, pieceShapes);
                    }

                    Attempt(ref board, mv, ref passed, ref checkQueue, Left, maxHeight, pieceShapes, true);
                    Attempt(ref board, mv, ref passed, ref checkQueue, Right, maxHeight, pieceShapes, true);

                    Attempt(ref board, mv, ref passed, ref checkQueue, SonicDrop, maxHeight, pieceShapes);
                }

                //Finally add this placement(harddropped) to return array
                var pl    = board.SonicDropFast(mv.piece, pieceShapes);
                var mHard = mv;
                mHard.piece = pl;
                Confirm(ref board, ref lookup, mHard, pieceShapes);
            }

            passed.Dispose();
            checkQueue.Dispose();
            return(lookup);
        }