Exemplo n.º 1
0
    private bool AttackAction(Character enemyToAttack)
    {
        RotateDirectly(enemyToAttack.transform.position);
        AttackAlgorithm a = GetComponent <AttackAlgorithm>();

        return(a.DoDamage(enemyToAttack));
    }
Exemplo n.º 2
0
    public void CreateAcceptButtonAttack(Character enemy)
    {
        if (!created)
        {
            created = true;
            // Kept for now. Possibly change
            // What it does : Checks if an accept attack button is already present. If not, add.
            if (!buttonList.Any(b => b.name == "Accept attack"))
            {
                Transform canvas       = GameObject.Find("Canvas").transform;
                Button    actionButton = Instantiate(_attackWhereButton, new Vector3(0, 0, 0), Quaternion.identity) as Button;
                actionButton.transform.SetParent(canvas);
                actionButton.GetComponent <RectTransform>().anchoredPosition3D = new Vector3(0, -25, 0);
                actionButton.GetComponentInChildren <Text>().text = "Accept attack";

                actionButton.onClick.AddListener(delegate
                {
                    UIManager.Instance.Attack();
                });
                buttonList.Add(actionButton);
            }
        }

        selectedEnemy = enemy;

        Character selected = _human.SelectedCharacter;

        AttackAlgorithm attack = selected.GetComponent <AttackAlgorithm>();

        damage = attack.GetDamage(enemy);

        Debug.LogWarning("Press middle button to accept");
    }
Exemplo n.º 3
0
    /// <summary>
    /// Calculate reward of an attack
    /// The highest the reward, the better
    /// </summary>
    private float AttackReward(Character target, Tile goToTile)
    {
        AttackAlgorithm attack = GetComponentInChildren <AttackAlgorithm>();
        //calculate hypothetical damage done to target
        int damageDone = attack.GetDamage(target, goToTile);

        int targetHealth = target.GetComponent <PokemonStats>().CurrentHealth;
        int maxHealth    = target.GetComponent <PokemonStats>().MaxHealth;

        // if attack would kill the target, return high cost
        if (targetHealth - damageDone < 0)
        {
            return(1000f);
        }

        // calculate hypothetical damage received from target
        int damageReceived = target.GetComponentInChildren <AttackAlgorithm>().GetDamage(GetComponent <Character>(), target._currentTile);

        // calculate reward of an attack. Emphasis on damage done over received
        float reward = damageDone + (maxHealth - targetHealth) / 5 - (0.5f * damageReceived);

        return(reward);
    }
Exemplo n.º 4
0
    /* public Tile FindBestTile(Character c, Dictionary<Tile, int> possible)
     * {
     *  Dictionary<Tile, int> possibleTiles = c._currentTile.GetTiles(0, 1);
     *  foreach (Tile t in possibleTiles.Keys)
     *  {
     *      if (!possible.ContainsKey(t))
     *      {
     *          possibleTiles.Remove(t);
     *      }
     *  }
     *
     *  return FindBestTile(possibleTiles, c);
     * }*/

    public Tile FindBestTile(Dictionary <Tile, int> possibleTiles, Character enemy = null)
    {
        // Get all possible tiles, including the ones where character can't move bu can attack to
        List <Tile> tilesWithEnemy = new List <Tile>();
        int         movementRange  = Stats.MovementRange;

        if (enemy == null)
        {
            //get a list of the tiles in range that contain an enemy
            foreach (Tile t in possibleTiles.Keys)
            {
                if (t.HasPlayer && t._character.tag == "Human")
                {
                    tilesWithEnemy.Add(t);
                }
            }
        }
        else
        {
            tilesWithEnemy.Add(enemy._currentTile);
        }

        //if there are at least one enemy in range
        // TODO add more conditions?
        if (tilesWithEnemy.Count > 0)
        {
            Tile            bestTile    = null;
            AttackAlgorithm attack      = GetComponentInChildren <AttackAlgorithm>();
            float           highestCost = 0f;
            //Find an initial empty best tile
            foreach (Tile t in tilesWithEnemy)
            {
                for (int i = 0; i < t.neighbours.Count; i++)
                {
                    if (possibleTiles.ContainsKey(t.neighbours[i]) && (!t.neighbours[i].IsOccupied || t.neighbours[i] == Character._currentTile))
                    {
                        // when no player on the tile, break
                        if (possibleTiles.ContainsKey(t) && possibleTiles[t] <= movementRange)
                        {
                            //highestDamage = attack.GetDamage(tilesWithEnemy[0]._character, bestTile);
                            bestTile      = t.neighbours[i];
                            highestCost   = AttackReward(t._character, bestTile);
                            enemyToAttack = t._character;
                            bestTile      = t;
                            break;
                        }
                    }
                }
            }

            // for each tile t with an enemy in range
            foreach (Tile t in tilesWithEnemy)
            {
                // for each neighbour of t
                Dictionary <Tile, int> possibleAttackingTiles = t.GetTiles(0, 1);
                foreach (Tile tt in possibleAttackingTiles.Keys)
                {
                    // if (neighbour is empty or neighbour is where we currently are) and (this neighbour is in range)
                    if ((!tt.IsOccupied || tt._character == Character) && (possibleTiles.ContainsKey(tt) && possibleTiles[tt] <= movementRange))
                    {
                        //int cost = attack.GetDamage(t._character, tt);
                        float cost          = AttackReward(t._character, tt);
                        int   rangeDistance = possibleTiles[tt];

                        // if this tile would do more damage, set it as best tile
                        // TODO add more conditions, like damage received?
                        if (cost > highestCost)
                        {
                            bestTile      = tt;
                            highestCost   = cost;
                            enemyToAttack = t._character;
                        }
                    }
                }
            }
            return(bestTile);
        }
        return(null);
    }
Exemplo n.º 5
0
    public Tile CanKillInRange(Dictionary <Tile, int> possibleTiles)
    {
        // Get all possible tiles, including the ones where character can't move bu can attack to
        List <Tile> tilesWithEnemy = new List <Tile>();
        List <Unit> squadMembers   = GetComponentInParent <Squad>().Units;

        int movementRange = Stats.MovementRange;

        //get a list of the tiles in range that contain an enemy
        foreach (Tile t in possibleTiles.Keys)
        {
            if (t.HasPlayer && t._character.tag == "Human")
            {
                tilesWithEnemy.Add(t);
            }
        }

        //if there are at least one enemy in range
        // TODO add more conditions?
        if (tilesWithEnemy.Count > 0)
        {
            Tile            bestTile      = null;
            AttackAlgorithm attack        = GetComponentInChildren <AttackAlgorithm>();
            int             highestDamage = 0;
            //Find an initial empty best tile
            foreach (Tile t in tilesWithEnemy)
            {
                for (int i = 0; i < 4; i++)
                {
                    bestTile = t.neighbours[i];
                    // when no player on the tile, break
                    if (possibleTiles.ContainsKey(t) && possibleTiles[t] <= movementRange && !bestTile.HasPlayer)
                    {
                        highestDamage = attack.GetDamage(t._character, bestTile);
                        enemyToAttack = t._character;
                        if (bestTile._character.GetComponent <PokemonStats>()._currentHealth - highestDamage <= 0)
                        {
                            return(bestTile);
                        }
                        break;
                    }
                    else
                    {
                        bestTile = null;
                    }
                }
            }

            // for each tile t with an enemy in range
            foreach (Tile t in tilesWithEnemy)
            {
                // for each neighbour of t
                Dictionary <Tile, int> possibleAttackingTiles = t.GetTiles(0, Stats.AttackRange);
                foreach (Tile tt in possibleAttackingTiles.Keys)
                {
                    // if (neighbour is empty or neighbour is where we currently are) and (this neighbour is in range)
                    if ((!tt.HasPlayer || tt._character == Character) && (possibleTiles.ContainsKey(tt) && possibleTiles[tt] <= movementRange))
                    {
                        int damage        = attack.GetDamage(t._character, tt);
                        int rangeDistance = possibleTiles[tt];

                        // if this tile would do more damage, set it as best tile
                        // TODO add more conditions, like damage received?
                        if (t._character.GetComponent <PokemonStats>()._currentHealth - damage <= 0)
                        {
                            bestTile      = tt;
                            highestDamage = damage;
                            enemyToAttack = t._character;
                            return(bestTile);
                        }
                    }
                }
            }
            return(bestTile);
        }
        return(null);
    }