예제 #1
0
    public bool MoveBlock(int id)
    {
        PuzzleBlock tb          = BlockForID(id);
        int         moveableDir = MoveableDirection(id);

        if (moveableDir < 0)
        {
            return(false);
        }

        Vector2 wantedPos = Vector2.zero;

        switch (moveableDir)
        {
        case 0: wantedPos = tb.curPosition + Vector2.up; break;

        case 1: wantedPos = tb.curPosition + Vector2.down; break;

        case 2: wantedPos = tb.curPosition + Vector2.left; break;

        case 3: wantedPos = tb.curPosition + Vector2.right; break;
        }

        PuzzleBlock cache = BlockAtPosition(wantedPos);

        if (cache != null)
        {
            cache.curPosition = tb.curPosition;
        }
        tb.curPosition = wantedPos;

        return(true);
    }
예제 #2
0
    private Puzzle(PuzzleBlock[,] p, int cs)
    {
        PuzzleBlock[,] n = new PuzzleBlock[cs, cs];
        //lock (puzzle) {
        for (int x = 0; x < cs; x++)
        {
            for (int y = 0; y < cs; y++)
            {
                //Debug.Log (puzzle [x, y]);
                if (p [x, y] != null)
                {
                    n [x, y] = new PuzzleBlock {
                        curPosition    = p [x, y].curPosition,
                        wantedPosition = p [x, y].wantedPosition,
                        id             = p [x, y].id
                    };
                }
                else
                {
                    n [x, y] = null;
                }
            }
        }
        //}

        puzzle      = n;
        currentSize = cs;
    }
예제 #3
0
    private void ActivateTransform(Transform _transform)
    {
        if (_selection && _activeBlock != null)
        {
            StartCoroutine(SwitchBlocks(_transform));

            return;
        }

        // Activation switch
        //
        // Disable previous block
        if (_activeBlock != null)
        {
            _activeBlock.ActivatedSprites.ForEach(s => s.SetActive(false));
        }

        _activeTransform = _transform;
        _activeBlock     = Blocks.Find(block => block.transform == _activeTransform);

        // Enable block
        if (_activeBlock != null)
        {
            _activeBlock.ActivatedSprites.ForEach(s => s.SetActive(true));
            if (!_firstSound)
            {
                ToggleAudioSource.Play();
            }

            _firstSound = false;
        }
    }
예제 #4
0
 public static void UnRegistBlock(PuzzleBlock block)
 {
     if (mItemBlock.ContainsKey(block.Item.ItemName))
     {
         mItemBlock[block.Item.ItemName].Remove(block);
     }
 }
예제 #5
0
    public int MoveableDirection(int id)
    {
        PuzzleBlock tb = BlockForID(id);

//		if (tb == null)
//			return -1;
        if (InsidePuzzle(tb.curPosition + Vector2.up) && BlockAtPosition(tb.curPosition + Vector2.up) == null)
        {
            return(0);
        }
        else if (InsidePuzzle(tb.curPosition + Vector2.down) && BlockAtPosition(tb.curPosition + Vector2.down) == null)
        {
            return(1);
        }
        else if (InsidePuzzle(tb.curPosition + Vector2.left) && BlockAtPosition(tb.curPosition + Vector2.left) == null)
        {
            return(2);
        }
        else if (InsidePuzzle(tb.curPosition + Vector2.right) && BlockAtPosition(tb.curPosition + Vector2.right) == null)
        {
            return(3);
        }
        else
        {
            return(-1);
        }
    }
    public void start(Puzzle p, Action <List <int> > callback)
    {
        cb = callback;
        iSCentralDispatch.DispatchNewThread(() => {
            Node root = new Node(p);
            Debug.Log("brain start...");
            List <Node> frontier = new List <Node>();
            List <Puzzle> es     = new List <Puzzle>();
            frontier.Add(root);

            while (true)
            {
                frontier = frontier.OrderBy(n => n.f()).ToList();

                Node cn = frontier [0];
                frontier.RemoveAt(0);
                es.Add(cn.cp);

                if (cn.goal())
                {
                    iSCentralDispatch.DispatchMainThread(() => {
                        cb(cn.solution());
                    });

                    break;
                }

                Node[] proceeds = cn.proceed();
//				frontier.AddRange(proceeds)
                foreach (Node n in proceeds)
                {
                    bool hasSame = false;
                    foreach (Puzzle esp in es)
                    {
                        bool hasDifferent = false;
                        for (int i = 0; i < esp.puzzle.Length; i++)
                        {
                            PuzzleBlock b1 = esp.BlockForID(i);
                            PuzzleBlock b2 = n.cp.BlockForID(i);
                            if (b1 != null && b2 != null && b1.curPosition != b2.curPosition)
                            {
                                hasDifferent = true;
                            }
                        }
                        if (!hasDifferent)
                        {
                            hasSame = true;
                            break;
                        }
                    }

                    if (hasSame)
                    {
                        continue;
                    }
                    frontier.Add(n);
                }
            }
        });
    }
예제 #7
0
    public void AddBlockTo(Direction dir, PuzzleBlock newBlock)             //add block to one direction
    {
        LevelGrid grid         = GetGrid(dir);                              //Get grid
        LevelGrid coveringGrid = newBlock.GetGrid(GetOpposeDirection(dir)); //also get covering grid

        SetSprayable(false, dir);                                           //This Grid is Not Sprayable Any More!
        newBlock.SetSprayable(false, GetOpposeDirection(dir));              //set covering grid to not sprayable
        grid.SetCoveringGrid(coveringGrid);
        coveringGrid.SetCoveringGrid(grid);

        for (int i = 1; i <= 4; i++)   // Change All Nearby Grid And Status
        {
            //Get near Grid and new Grid
            LevelGrid nearGrid = grid.GetNearGrid((Direction)i);
            if (nearGrid == null)//this situation only happen when processing multiple covered grid
            {
                continue;
            }

            LevelGrid newGrid = newBlock.GetSelfRelativeDirectionGrid(dir, (Direction)i);

            //Get height status
            int height = grid.GetHeight((Direction)i);
            //Get Relative Direction
            Direction nearGridRelativeDirection = GetRelativeDirection(dir, (Direction)i, height);
            Direction newGridRelativeDirection;
            //Change nearby grids status
            if (height < 2)
            {
                int h = nearGrid.AddHeight(nearGridRelativeDirection, 1); // Change near grid height Status
                newGridRelativeDirection = GetRelativeDirection(nearGrid.direction, nearGridRelativeDirection, nearGrid.GetHeight(nearGridRelativeDirection));
                newGrid.SetHeight(newGridRelativeDirection, h);           //Also Change new grid height status = near grid height status
                nearGrid.SetNearGrid(newGrid, nearGridRelativeDirection); //Set new Nearby Grid
                newGrid.SetNearGrid(nearGrid, newGridRelativeDirection);  // Set new Nearby Grid
            }
            else//if height = 2, it means this grid is covered too.
            {
                newGridRelativeDirection = GetRelativeDirection(nearGrid.direction, nearGridRelativeDirection, nearGrid.GetHeight(nearGridRelativeDirection));
                nearGrid.block.SetSprayable(false, nearGrid.direction); // Change status to not sprayable
                nearGrid.SetCoveringGrid(newGrid);
                nearGrid.SetNearGrid(null, nearGridRelativeDirection);  //set to null
                newGrid.SetCoveringGrid(nearGrid);
                newGrid.SetNearGrid(null, newGridRelativeDirection);
            }
            //clear grid and covering grid connection
            grid.SetConnection((Direction)i, false);
            grid.SetNearGrid(null, (Direction)i);
            coveringGrid.SetNearGrid(null, (Direction)i);
            //also delete the connection of near grid
            nearGrid.SetConnection(nearGridRelativeDirection, false);
            nearGrid.UpdateAllVisual(0);
            newGrid.UpdateAllVisual(0);
        }

        grid.UpdateAllVisual(0);
        coveringGrid.UpdateAllVisual(0);
    }
예제 #8
0
    private void PlayerMoveBlockInput(PuzzleBlock puzzleToMove)
    {
        if (Mathf.Floor((puzzleToMove.transform.position - emptyBlock.transform.position).sqrMagnitude) == 1)
        {
            Vector2Int targetCoord = emptyBlock.coord;
            emptyBlock.coord   = puzzleToMove.coord;
            puzzleToMove.coord = targetCoord;

            Vector2 targetPosition = emptyBlock.transform.position;
            emptyBlock.transform.position = puzzleToMove.transform.position;
            puzzleToMove.MoveToPosition(targetPosition, duration);
        }
    }
예제 #9
0
    private void RespawnBlock()
    {
        if (mSpawnBlock.Count == 0) return;
        mBlockCurTime += Time.deltaTime;
        if (mBlockCurTime < mBlockSpawnTime) return;

        PuzzleBlock block = mSpawnBlock[Random.Range(0, mSpawnBlock.Count)];
        block.Item = mSpawnItem.Peek();
        mSpawnItem.Dequeue();
        block.itemImg.sprite = block.Item.Sprite;
        block.gameObject.SetActive(true);
        mSpawnBlock.Remove(block);

        mBlockCurTime = 0f;
    }
예제 #10
0
    public static void RegistBlock(PuzzleBlock block)
    {
        LinkedList <PuzzleBlock> temp = null;

        if (mItemBlock.TryGetValue(block.Item.ItemName, out temp))
        {
            temp.AddLast(block);
        }
        else
        {
            temp = new LinkedList <PuzzleBlock>();
            mItemBlock.Add(block.Item.ItemName, temp);
            temp.AddLast(block);
        }
    }
예제 #11
0
    public void GeneratePuzzle(int size)
    {
        currentSize = size;
        puzzle      = new PuzzleBlock[size, size];
        int count = 0;

        for (int x = 0; x < size; x++)
        {
            for (int y = 0; y < size; y++)
            {
                PuzzleBlock pb = new PuzzleBlock {
                    curPosition    = new Vector2(x, y),
                    wantedPosition = new Vector2(x, y),
                    id             = count
                };
                count++;
                puzzle [x, y] = pb;
            }
        }
        puzzle [size - 1, size - 1] = null;
    }
예제 #12
0
 private void Start()
 {
     pBlock = GetComponentInParent <PuzzleBlock>();
 }
예제 #13
0
    private void CreatePuzzle()
    {
        generateBoolArray();
        puzzleBlocks        = new PuzzleBlock[blocksPerLine * blocksPerLine];
        Texture2D[,] images = ImageSlicer.GetSlices(image, blocksPerLine);
        int[] numbersInOrder = new int[blocksPerLine * blocksPerLine];
        for (int x = 0; x < blocksPerLine; x++)
        {
            for (int y = 0; y < blocksPerLine; y++)
            {
                GameObject blockObj   = GameObject.CreatePrimitive(PrimitiveType.Quad);
                int        pos        = randomPosition();
                int        blockObj_x = generateX(pos);
                int        blockObj_y = generateY(pos);

                blockObj.transform.position = -Vector2.one * (blocksPerLine - 1) * 0.5f + new Vector2(blockObj_x, blockObj_y);
                blockObj.transform.parent   = transform;

                PuzzleBlock puzzleBlock = blockObj.AddComponent <PuzzleBlock>();
                puzzleBlock.OnBlockPressed   += AddMoveBlockToQueue;
                puzzleBlock.OnFinishedMoving += OnFinishedMoving;
                int order = (blocksPerLine * blocksPerLine) - (blocksPerLine - (x + 1) + y * blocksPerLine);
                if (order == 9)
                {
                    numbersInOrder[pos] = -1;
                }
                else
                {
                    numbersInOrder[pos] = order;
                }
                puzzleBlock.Init(new Vector2Int(blockObj_x, blockObj_y), images[x, y], order);
                puzzleBlocks[blocksPerLine * x + y] = puzzleBlock;
                if (y == 0 && x == blocksPerLine - 1)
                {
                    blockObj.SetActive(false);
                    emptyBlock = puzzleBlock;
                }
            }
        }
        int[] numbersOrdered = new int[blocksPerLine * blocksPerLine];
        int   j = 0;

        for (int i = 6; i < 9; i++)
        {
            if (numbersInOrder[i] != -1)
            {
                numbersOrdered[j] = numbersInOrder[i];
                j++;
            }
        }
        for (int i = 3; i < 6; i++)
        {
            if (numbersInOrder[i] != -1)
            {
                numbersOrdered[j] = numbersInOrder[i];
                j++;
            }
        }

        for (int i = 0; i < 3; i++)
        {
            if (numbersInOrder[i] != -1)
            {
                numbersOrdered[j] = numbersInOrder[i];
                j++;
            }
        }
        int inversions = 0;

        for (int i = 0; i < numbersOrdered.Length - 1; i++)
        {
            for (int j1 = i + 1; j1 < numbersOrdered.Length - 1; j1++)
            {
                if (numbersOrdered[j1] > numbersOrdered[i])
                {
                    inversions++;
                }
            }
        }
        if (inversions % 2 == 1)
        {
            pab.restartPuzzleButton();
        }
        Camera.main.orthographicSize = blocksPerLine * 0.65f;
        blocksQueue = new Queue <PuzzleBlock>();
    }
예제 #14
0
    public void RegistSpawnBlock(PuzzleBlock block)
    {
        if (mSpawnBlock.Contains(block)) return;

        mSpawnBlock.Add(block);
    }
예제 #15
0
 private void AddMoveBlockToQueue(PuzzleBlock puzzleToMove)
 {
     blocksQueue.Enqueue(puzzleToMove);
     MakeNextPlayerMove();
 }
예제 #16
0
    private void SetBlockInfo()
    {
        totalPlaceCount = data.puzzleInfo.Count;
        for (int i = 0; i < data.puzzleInfo.Count; i++)
        {
            BlockInfo  info   = data.puzzleInfo[i];
            GameObject parent = Instantiate(blockParent, blockParent.transform.parent);
            parent.name = info.blockNum.ToString();
            //设置方块的父物体
            Vector2 min = CalculateBlockPos(info.blockRect.min.y, info.blockRect.min.x);
            Vector2 max = CalculateBlockPos(info.blockRect.max.y, info.blockRect.max.x);
            parent.GetComponent <RectTransform> ().anchoredPosition = CalculateCenter(min, max);


            //计算对应单词的中心点
            Vector2 wordMin    = CalculateWordPos(info.wordRect.min.y, info.wordRect.min.x);
            Vector2 wordMax    = CalculateWordPos(info.wordRect.max.y, info.wordRect.max.x);
            Vector2 wordCenter = CalculateCenter(wordMin, wordMax);
            //设置父物体的信息
            int   row    = info.blockRect.max.x - info.blockRect.min.x;
            int   col    = info.blockRect.max.y - info.blockRect.min.y;
            float width  = Mathf.Abs((max.x - min.x) / 2) == 0 ? 0 : Mathf.Abs((max.x - min.x) / 2);
            float height = Mathf.Abs((max.y - min.y) / 2) == 0 ? 0 : Mathf.Abs((max.y - min.y) / 2);
            BlockParentManager manager = parent.GetComponent <BlockParentManager> ();
            manager.blockNum = info.blockNum;
            manager.SetBlockInfo(wordCenter, width + minSize / 2, height + minSize / 2, row, col, info.blockRect.min);
            manager.SetRightCells(AddCorrectCells(info.wordPos));
            for (int j = 0; j < info.blockPos.Count; j++)
            {
                int         x    = info.blockPos[j].pos.x;
                int         y    = info.blockPos[j].pos.y;
                PuzzleBlock cell = Instantiate(block, blockGroup);
                cell.GetComponent <RectTransform> ().anchoredPosition = CalculateBlockPos(y, x);
                cell.pos.x = x;
                cell.pos.y = y;
                cell.SetSize(minSize);
                cell.SetBlockInfo(info.blockPos[j].letter, colors[info.blockNum], parent.transform);
                cell.gameObject.SetActive(true);
                manager.SetPos(x, y);
                manager.AddBlock(cell);
            }
            //读取进度
            if (saveData != null)
            {
                PuzzleBlockPosition pos = saveData.blockPosition[i];
                parent.GetComponent <RectTransform> ().anchoredPosition = new Vector2(float.Parse(pos.x), float.Parse(pos.y));
                if (saveData.HintBlock.Contains(info.blockNum))
                {
                    notPlaceRightBlock.Add(manager);
                }
                for (int m = 0; m < saveData.blockNum.Count; m++)
                {
                    if (saveData.blockNum[m] == info.blockNum)
                    {
                        List <PuzzleLetterCell> letters = new List <PuzzleLetterCell> ();
                        for (int n = 0; n < saveData.blockPlaceCell[m].Count; n++)
                        {
                            letters.Add(cellGroup[saveData.blockPlaceCell[m][n]]);
                        }
                        manager.cells = letters;
                        saveData.blockNum.RemoveAt(m);
                        break;
                    }
                }
                for (int k = 0; k < saveData.placeBlock.Count; k++)
                {
                    if (saveData.placeBlock[k] == info.blockNum)
                    {
                        place.Add(manager);
                        place.RemoveAt(k);
                        break;
                    }
                }
            }
            else
            {
                notPlaceRightBlock.Add(manager);
            }
            blocks.Add(manager);
        }
    }
 int h(PuzzleBlock b)
 {
     return((int)(Math.Abs(b.curPosition.x - b.wantedPosition.x)
                  + Math.Abs(b.curPosition.y - b.wantedPosition.y)));
 }