Beispiel #1
0
    // As a fan, walk randomly (avoiding going out of bounds, non-steppable tiles, and other fans)
    public void FanRandomWalk()
    {
        // Which tiles can we move to
        List <IntPoint> allowedTileMoves = new List <IntPoint>();

        foreach (char s in "NSEW")
        {
            IntPoint newPos = IntPoint.FromCardinal(TileX, TileY, s);
            if (MapHandler.GetComponent <MapHandler> ().CanMove(newPos))
            {
                allowedTileMoves.Add(newPos);
            }
        }

        // No moves?
        if (allowedTileMoves.Count == 0)
        {
            // TEMP
            //gameObject.transform.RotateAround (gameObject.transform.position, Vector3.forward, 90f);
            return;
        }

        // Get one
        IntPoint pt = allowedTileMoves[GameState.rng.Next(allowedTileMoves.Count)];

        MoveToTile(pt.x, pt.y);
    }
Beispiel #2
0
    public static List <Vector2Int> GetNeighbors(Vector2Int pos, MapHandler mapHnd)
    {
        // check that pos is a valid coordinate
        if (pos.x < 0 || pos.x >= mapHnd.mapTileWidth || pos.y < 0 || pos.y >= mapHnd.mapTileHeight)
        {
            return(null);
        }

        List <Vector2Int> neighbors = new List <Vector2Int> ();

        foreach (char s in "NSEW")
        {
            IntPoint newPos = IntPoint.FromCardinal(pos.x, pos.y, s);
            if (mapHnd.CanMove(newPos))
            {
                neighbors.Add(new Vector2Int(newPos.x, newPos.y));
            }
        }

        return(neighbors);
    }
Beispiel #3
0
    /*public void GetClickTile () {
     * }*/

    // Find the next NPC that hasn't moved and move it randomly.
    // Return true if an NPC moved
    // TEMP function
    public bool MoveNextNPC()
    {
        // Find the NEAREST fan that hasn't moved
        GameObject nextFan = null;

        foreach (GameObject fanObj in fans)
        {
            TokenHandler fan = fanObj.GetComponent <TokenHandler> ();
            if (fan.MovedThisTurn)
            {
                continue;
            }

            // Set/compare it
            if (nextFan == null)
            {
                nextFan = fanObj;
            }
            else
            {
                TokenHandler curr     = nextFan.GetComponent <TokenHandler> ();
                int          currDist = getMinDistFromPlayer(new IntPoint(curr.TileX, curr.TileY));
                int          nxtDist  = getMinDistFromPlayer(new IntPoint(fan.TileX, fan.TileY));
                if (nxtDist < currDist)
                {
                    nextFan = fanObj;
                }
            }
        }

        // Anything?
        if (nextFan != null)
        {
            TokenHandler fan = nextFan.GetComponent <TokenHandler> ();
            fan.MovedThisTurn = true;

            // Are we moving or attacking?
            foreach (char s in "NSEW")
            {
                IntPoint next = IntPoint.FromCardinal(fan.TileX, fan.TileY, s);
                if (SingleCollide(leadPlayer, next) || SingleCollide(leadDate, next))
                {
                    //leadPlayer.GetComponent<TokenHandler> ().LeadObj.SelfEsteem -= 1;

                    // TODO: Show animation

                    // TODO: Play damage sound (placeholder)
                    //sfxSource.clip = movementSFX[ Random.Range(0, movementSFX.Length) ];
                    //sfxSource.Play();
                    GameObject source = Instantiate(soundSource, mainCamera.transform.position, Quaternion.identity);
                    source.transform.SetParent(mainCamera.transform);
                    source.GetComponent <AudioSource>().clip = movementSFX[Random.Range(0, movementSFX.Length)];
                    source.GetComponent <AudioSource> ().Play();

                    // Destroy this fan
                    leadPlayer.GetComponent <TokenHandler>().HighlightToken();
                    leadDate.GetComponent <TokenHandler> ().HighlightToken();

                    DestroyFanNew(nextFan);

                    // Damage player
                    LeadPlayerScript.SelfEsteem -= 1;

                    return(true);
                }
            }

            // Ok, we're walking
            bool didAWalk = fan.FanWalkTowards(LeadDate, LeadPlayer);

            // Safety save
            if (!didAWalk)
            {
                // Find the two closest tiles, and choose between them (if moveable).
                // Never move heuristically away
                List <IntPoint> options = new List <IntPoint>();

                // Horizontal
                IntPoint eTile = IntPoint.FromCardinal(fan.TileX, fan.TileY, 'E');
                IntPoint wTile = IntPoint.FromCardinal(fan.TileX, fan.TileY, 'W');
                if (getMinDistFromPlayer(eTile) < getMinDistFromPlayer(wTile))
                {
                    options.Add(eTile);
                }
                else
                {
                    options.Add(wTile);
                }



                // Vertical
                IntPoint nTile = IntPoint.FromCardinal(fan.TileX, fan.TileY, 'N');
                IntPoint sTile = IntPoint.FromCardinal(fan.TileX, fan.TileY, 'S');
                if (getMinDistFromPlayer(nTile) < getMinDistFromPlayer(sTile))
                {
                    options.Add(nTile);
                }
                else
                {
                    options.Add(sTile);
                }

                // Now check.
                if (!CanMove(options [1]))
                {
                    options.RemoveAt(1);
                }
                if (!CanMove(options [0]))
                {
                    options.RemoveAt(0);
                }

                // Anything left?
                if (options.Count > 0)
                {
                    IntPoint pt = options[GameState.rng.Next(options.Count)];
                    fan.MoveToTile(pt.x, pt.y);
                    didAWalk = true;
                    Debug.Log("SAVE");
                }
            }

            // Play movement SFX
            if (didAWalk)
            {
                GameObject source = Instantiate(soundSource, mainCamera.transform.position, Quaternion.identity);
                source.transform.SetParent(mainCamera.transform);
                source.GetComponent <AudioSource>().clip = movementSFX[Random.Range(0, movementSFX.Length)];
                source.GetComponent <AudioSource> ().Play();

                return(true);
            }
            else
            {
                return(false);
            }
        }
        return(false);
    }
Beispiel #4
0
    // More accurate BFS lookup
    private List <IntPoint> MakeNewTravelPlan()
    {
        MapHandler mapHnd = MapHandler.GetComponent <MapHandler>();


        // TODO: Allow appearing NEXT to either of these.
        TokenHandler other1 = mapHnd.LeadDate.GetComponent <TokenHandler>();
        TokenHandler other2 = mapHnd.LeadPlayer.GetComponent <TokenHandler>();


        Vector2Int start    = new Vector2Int(TileX, TileY);
        Vector2Int dest     = new Vector2Int(other1.TileX, other1.TileY);
        int        infinity = 100 * 100;

        // Step 1: Make a new array with the "moves from destination" count.
        List <int> lookup = new List <int>();

        for (int i = 0; i < mapHnd.mapTileWidth * mapHnd.mapTileHeight; i++)
        {
            lookup.Add(infinity);
        }

        // Step 1.1: Start at the destination and work outwards
        List <Vector2Int>             todo      = new List <Vector2Int>();
        Dictionary <Vector2Int, bool> blacklist = new Dictionary <Vector2Int, bool>();

        todo.Add(dest);
        blacklist.Add(dest, true);
        lookup [mapHnd.GetTileIndex(dest.x, dest.y)] = 0;
        while (todo.Count > 0)
        {
            // Next tile to consider
            Vector2Int next = todo [0];
            todo.RemoveAt(0);

            // Consider all 4 neighbors
            foreach (char dir in "NSEW")
            {
                IntPoint   newPosI = IntPoint.FromCardinal(next.x, next.y, dir);
                Vector2Int newPos  = new Vector2Int(newPosI.x, newPosI.y);

                // Can we move here normally?
                if (!mapHnd.CanMove(newPosI))
                {
                    continue;
                }

                // Have we already queued up this tile?
                if (blacklist.ContainsKey(newPos))
                {
                    continue;
                }

                // Ok, enqueue it
                todo.Add(newPos);
                blacklist.Add(newPos, true);
                int newDist = lookup [mapHnd.GetTileIndex(next.x, next.y)] + 1;
                lookup [mapHnd.GetTileIndex(newPos.x, newPos.y)] = newDist;

                // TEMP: Useful debugging
                if (false)                   //mapHnd.showDebugMoves
                {
                    mapHnd.debugArray [mapHnd.GetTileIndex(newPos.x, newPos.y)].text = "" + newDist;
                }
            }
        }

        // Step 2: Start from the source, and try to find a path forward.
        // Choose the least-cost pat at east junction, unless there is none.
        List <IntPoint> res  = new List <IntPoint>();
        IntPoint        curr = new IntPoint(start.x, start.y);

        while (true)
        {
            // Are we done?
            if (lookup [mapHnd.GetTileIndex(curr.x, curr.y)] == 1)
            {
                return(res);
            }

            // Find the next jump
            List <IntPoint> options = new List <IntPoint>();
            foreach (char dir in "NSEW")
            {
                IntPoint next = IntPoint.FromCardinal(curr.x, curr.y, dir);
                if (next.x >= 0 && next.x < mapHnd.mapTileWidth && next.y >= 0 && next.y < mapHnd.mapTileHeight)
                {
                    int myDist = lookup [mapHnd.GetTileIndex(next.x, next.y)];
                    if (myDist != infinity)
                    {
                        // Compare it to the current best distance.
                        if (options.Count > 0)
                        {
                            int otherDist = lookup [mapHnd.GetTileIndex(options [0].x, options [0].y)];
                            if (myDist < otherDist)
                            {
                                // It's strictly better
                                options.Clear();
                            }
                            if (myDist <= otherDist)
                            {
                                // It's tied or better (we're considering it)
                                options.Add(next);
                            }
                        }
                        else
                        {
                            // No contest
                            options.Add(next);
                        }
                    }
                }
            }

            // Take it
            if (options.Count > 0)
            {
                IntPoint next = options[GameState.rng.Next(options.Count)];
                res.Add(next);
                curr = next;
            }
            else
            {
                // Shouldn't happen
                break;
            }
        }

        return(null);
    }