mirror of
https://github.com/Card-Forge/forge.git
synced 2025-11-19 12:18:00 +00:00
- Cleanup and Updates in ComputerUtil_Attack2 (AI will not waste attacks against creatures with wither or infect).
This commit is contained in:
@@ -20,7 +20,7 @@ public class ComputerUtil_Attack2 {
|
|||||||
private CardList humanList; //holds human player creatures
|
private CardList humanList; //holds human player creatures
|
||||||
private CardList computerList;//holds computer creatures
|
private CardList computerList;//holds computer creatures
|
||||||
|
|
||||||
private int aiAggression = 0; // added by me, how aggressive the ai attack will be depending on circumstances
|
private int aiAggression = 0; // added by Masher, how aggressive the ai attack will be depending on circumstances
|
||||||
|
|
||||||
public ComputerUtil_Attack2(Card[] possibleAttackers, Card[] possibleBlockers, int blockerLife)
|
public ComputerUtil_Attack2(Card[] possibleAttackers, Card[] possibleBlockers, int blockerLife)
|
||||||
{
|
{
|
||||||
@@ -332,7 +332,7 @@ public class ComputerUtil_Attack2 {
|
|||||||
boolean isUnblockableCreature = true;
|
boolean isUnblockableCreature = true;
|
||||||
// check blockers individually, as the bulk canBeBlocked doesn't check all circumstances
|
// check blockers individually, as the bulk canBeBlocked doesn't check all circumstances
|
||||||
for(Card blocker:blockers){
|
for(Card blocker:blockers){
|
||||||
if(!blocker.isTapped() && CombatUtil.canBlock(attacker, blocker)){
|
if(CombatUtil.canBlock(attacker, blocker)){
|
||||||
isUnblockableCreature = false;
|
isUnblockableCreature = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -352,18 +352,18 @@ public class ComputerUtil_Attack2 {
|
|||||||
aiAggression = 5; // attack at all costs
|
aiAggression = 5; // attack at all costs
|
||||||
}else if((playerLifeToDamageRatio < 2 && ratioDiff >= 0) || ratioDiff > 3 || (ratioDiff > 0 && outNumber > 0)){
|
}else if((playerLifeToDamageRatio < 2 && ratioDiff >= 0) || ratioDiff > 3 || (ratioDiff > 0 && outNumber > 0)){
|
||||||
aiAggression = 3; // attack expecting to kill creatures or damage player.
|
aiAggression = 3; // attack expecting to kill creatures or damage player.
|
||||||
} else if(ratioDiff >= 0 || ratioDiff + outNumber >= -1){ // at 0 ratio expect to potentially gain an advantage by attacking first
|
}else if(ratioDiff >= 0 || ratioDiff + outNumber >= -1){ // at 0 ratio expect to potentially gain an advantage by attacking first
|
||||||
// if the ai has a slight advantage
|
// if the ai has a slight advantage
|
||||||
// or the ai has a significant advantage numerically but only a slight disadvantage damage/life
|
// or the ai has a significant advantage numerically but only a slight disadvantage damage/life
|
||||||
aiAggression = 2; // attack expecting to destroy creatures/be unblockable
|
aiAggression = 2; // attack expecting to destroy creatures/be unblockable
|
||||||
}else if(doUnblockableAttack || ((ratioDiff * -1) < turnsUntilDeathByUnblockable)){
|
|
||||||
aiAggression = 4; // look for unblockable creatures that might be able to attack for a bit of
|
|
||||||
// fatal damage even if the player is significantly better
|
|
||||||
}else if(ratioDiff < 0 && aiLifeToPlayerDamageRatio > 1){
|
}else if(ratioDiff < 0 && aiLifeToPlayerDamageRatio > 1){
|
||||||
// the player is overmatched but there are a few turns before death
|
// the player is overmatched but there are a few turns before death
|
||||||
aiAggression = 2; // attack expecting to destroy creatures/be unblockable
|
aiAggression = 2; // attack expecting to destroy creatures/be unblockable
|
||||||
|
}else if(doUnblockableAttack || ((ratioDiff * -1) < turnsUntilDeathByUnblockable)){
|
||||||
|
aiAggression = 1; // look for unblockable creatures that might be able to attack for a bit of
|
||||||
|
// fatal damage even if the player is significantly better
|
||||||
}else if(ratioDiff < 0){
|
}else if(ratioDiff < 0){
|
||||||
aiAggression = 1;
|
aiAggression = 0;
|
||||||
} // stay at home to block
|
} // stay at home to block
|
||||||
System.out.println(String.valueOf(aiAggression) + " = ai aggression");
|
System.out.println(String.valueOf(aiAggression) + " = ai aggression");
|
||||||
|
|
||||||
@@ -457,19 +457,11 @@ public class ComputerUtil_Attack2 {
|
|||||||
|
|
||||||
public boolean shouldAttack(Card attacker, CardList defenders, Combat combat)
|
public boolean shouldAttack(Card attacker, CardList defenders, Combat combat)
|
||||||
{
|
{
|
||||||
boolean canBeKilledByOne = false;
|
boolean canBeKilledByOne = false; // indicates if the attacker can be killed by a single blockers
|
||||||
boolean canKillOne = false;
|
boolean canKillAll = true; // indicates if the attacker can kill all single blockers
|
||||||
boolean canKillAllDangerous = true; // indicates if the attacker can kill all creatures that are currently capable of dealing damage to it or the player
|
boolean canKillAllDangerous = true; // indicates if the attacker can kill all single blockers with wither or infect
|
||||||
boolean isWorthLessThanAllKillers = true;
|
boolean isWorthLessThanAllKillers = true;
|
||||||
CardList blockers = new CardList(); //all creatures that can block the attacker
|
|
||||||
CardList killingBlockers = new CardList(); //all creatures that can kill the attacker alone
|
|
||||||
boolean canBeBlocked = false;
|
boolean canBeBlocked = false;
|
||||||
boolean canCauseDamage = true;
|
|
||||||
|
|
||||||
// ensure that this attacker can actually cause some damage
|
|
||||||
if(attacker.getNetCombatDamage() <= 0){
|
|
||||||
canCauseDamage = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// look at the attacker in relation to the blockers to establish a number of factors about the attacking
|
// look at the attacker in relation to the blockers to establish a number of factors about the attacking
|
||||||
// context that will be relevant to the attackers decision according to the selected strategy
|
// context that will be relevant to the attackers decision according to the selected strategy
|
||||||
@@ -478,7 +470,6 @@ public class ComputerUtil_Attack2 {
|
|||||||
canBeBlocked = true;
|
canBeBlocked = true;
|
||||||
if(CombatUtil.canDestroyAttacker(attacker, defender)) {
|
if(CombatUtil.canDestroyAttacker(attacker, defender)) {
|
||||||
canBeKilledByOne = true; // there is a single creature on the battlefield that can kill the creature
|
canBeKilledByOne = true; // there is a single creature on the battlefield that can kill the creature
|
||||||
killingBlockers.add(defender);
|
|
||||||
// see if the defending creature is of higher or lower value. We don't want to attack only to lose value
|
// see if the defending creature is of higher or lower value. We don't want to attack only to lose value
|
||||||
if(CardFactoryUtil.evaluateCreature(defender) <= CardFactoryUtil.evaluateCreature(attacker)){
|
if(CardFactoryUtil.evaluateCreature(defender) <= CardFactoryUtil.evaluateCreature(attacker)){
|
||||||
isWorthLessThanAllKillers = false;
|
isWorthLessThanAllKillers = false;
|
||||||
@@ -486,20 +477,16 @@ public class ComputerUtil_Attack2 {
|
|||||||
}
|
}
|
||||||
// see if this attacking creature can destroy this defender, if not record that it can't kill everything
|
// see if this attacking creature can destroy this defender, if not record that it can't kill everything
|
||||||
if(!CombatUtil.canDestroyBlocker(defender, attacker)){
|
if(!CombatUtil.canDestroyBlocker(defender, attacker)){
|
||||||
// make exception for walls, they are usually extra tough but not dangerous unless they have
|
canKillAll = false;
|
||||||
// high power, so check for walls that can kill but ignore others
|
if(defender.getKeyword().contains("Wither") || defender.getKeyword().contains("Infect")){
|
||||||
if(!(defender.isWall() && defender.getNetCombatDamage() <= 0)){
|
|
||||||
canKillAllDangerous = false; // there is a dangerous creature that can survive an attack from this creature
|
canKillAllDangerous = false; // there is a dangerous creature that can survive an attack from this creature
|
||||||
}
|
}
|
||||||
} else {
|
|
||||||
canKillOne = true; // there is at least one opposition creature on the battlefield the creature can kill
|
|
||||||
}
|
}
|
||||||
blockers.add(defender);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// if the creature cannot block and can kill all opponents they might as well attack, they do nothing staying back
|
// if the creature cannot block and can kill all opponents they might as well attack, they do nothing staying back
|
||||||
if(canKillAllDangerous && !CombatUtil.canBlock(attacker) && isWorthLessThanAllKillers){
|
if(canKillAll && !CombatUtil.canBlock(attacker) && isWorthLessThanAllKillers){
|
||||||
System.out.println(attacker.getName() + " = attacking because they can't block, expecting to kill or damage player");
|
System.out.println(attacker.getName() + " = attacking because they can't block, expecting to kill or damage player");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -507,25 +494,28 @@ public class ComputerUtil_Attack2 {
|
|||||||
// decide if the creature should attack based on the prevailing strategy choice in aiAggression
|
// decide if the creature should attack based on the prevailing strategy choice in aiAggression
|
||||||
switch(aiAggression){
|
switch(aiAggression){
|
||||||
case 5: // all out attacking
|
case 5: // all out attacking
|
||||||
if(canCauseDamage){
|
|
||||||
System.out.println(attacker.getName() + " = all out attacking");
|
System.out.println(attacker.getName() + " = all out attacking");
|
||||||
return true;
|
return true;
|
||||||
}
|
case 4: // expecting to at least trade with something
|
||||||
case 4: // unblockable creatures only
|
if(canKillAll || (canKillAllDangerous && !canBeKilledByOne) || !canBeBlocked){
|
||||||
if(!canBeBlocked && canCauseDamage){
|
System.out.println(attacker.getName() + " = attacking expecting to at least trade with something");
|
||||||
System.out.println(attacker.getName() + " = attacking expecting not to be blocked");
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
case 3: // expecting to at least kill a creature of equal value, not be blocked or to attract a group block. A standard attacking strategy
|
case 3: // expecting to at least kill a creature of equal value, not be blocked
|
||||||
if(((canKillAllDangerous && isWorthLessThanAllKillers) || !canBeBlocked || !canBeKilledByOne) && canCauseDamage){
|
if((canKillAll && isWorthLessThanAllKillers) || (canKillAllDangerous && !canBeKilledByOne) || !canBeBlocked){
|
||||||
System.out.println(attacker.getName() + " = attacking expecting to kill creature or cause damage, or is unblockable");
|
System.out.println(attacker.getName() + " = attacking expecting to kill creature or cause damage, or is unblockable");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
case 2: // attack expecting to attract even a group block or destroying single blockers and surviving
|
case 2: // attack expecting to attract a group block or destroying a single blocker and surviving
|
||||||
if(((canKillAllDangerous && !canBeKilledByOne) || !canBeBlocked) && canCauseDamage){
|
if((canKillAll && !canBeKilledByOne) || !canBeBlocked){
|
||||||
System.out.println(attacker.getName() + " = attacking expecting to survive or attract group block");
|
System.out.println(attacker.getName() + " = attacking expecting to survive or attract group block");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
case 1: // unblockable creatures only
|
||||||
|
if(!canBeBlocked){
|
||||||
|
System.out.println(attacker.getName() + " = attacking expecting not to be blocked");
|
||||||
|
return true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return false; // don't attack
|
return false; // don't attack
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user