Browse Source

pet AI implemented

master
FatBoy-DOTC 2 years ago
parent
commit
cfa59d8012
  1. 132
      src/engine/ai/MobileFSM.java
  2. 20
      src/engine/devcmd/cmds/aiInfoCmd.java
  3. 1
      src/engine/net/client/ClientMessagePump.java
  4. 10
      src/engine/objects/Mob.java

132
src/engine/ai/MobileFSM.java

@ -56,7 +56,7 @@ public class MobileFSM {
SpellAggroGrouperWimpy(Spell, true, false, true, false, false), SpellAggroGrouperWimpy(Spell, true, false, true, false, false),
//Independent Types //Independent Types
SimpleStandingGuard(null, false, false, false, false, false), SimpleStandingGuard(null, false, false, false, false, false),
Pet1(null, false, false, false, false, false), Pet1(null, false, false, true, false, false),
Simple(null, false, false, true, false, false), Simple(null, false, false, true, false, false),
Helpee(null, false, true, true, false, true), Helpee(null, false, true, true, false, true),
HelpeeWimpy(null, true, false, true, false, false), HelpeeWimpy(null, true, false, true, false, false),
@ -566,34 +566,43 @@ public class MobileFSM {
} }
} }
public static void run(Mob mob) { public static void run(Mob mob) {
if (mob == null || mob.BehaviourType == MobBehaviourType.None) { if (mob == null) {
return; return;
} }
if (mob.isAlive() == false) { if (mob.isPet() == false && mob.isSummonedPet() == false && mob.isNecroPet() == false) {
//no need to continue if mob is dead, check for respawn and move on if (mob.BehaviourType != null && mob.BehaviourType == MobBehaviourType.None) {
CheckForRespawn(mob); return;
return; }
} if (mob.isAlive() == false) {
//check to see if mob has wandered too far from his bind loc //no need to continue if mob is dead, check for respawn and move on
CheckToSendMobHome(mob); CheckForRespawn(mob);
//check to see if players have mob loaded return;
if (mob.playerAgroMap.isEmpty()) { }
//no players loaded, no need to proceed //check to see if mob has wandered too far from his bind loc
return; CheckToSendMobHome(mob);
} //check to see if players have mob loaded
//check for players that can be aggroed if mob is agressive and has no target if (mob.playerAgroMap.isEmpty()) {
if (mob.BehaviourType.isAgressive && mob.getCombatTarget() == null) { //no players loaded, no need to proceed
CheckForAggro(mob); return;
} }
//check if mob can move for patrol or moving to target //check for players that can be aggroed if mob is agressive and has no target
if (mob.BehaviourType.canRoam) { if (mob.BehaviourType.isAgressive && mob.getCombatTarget() == null) {
CheckForAggro(mob);
}
//check if mob can move for patrol or moving to target
if (mob.BehaviourType.canRoam) {
CheckMobMovement(mob);
}
//check if mob can attack if it isn't wimpy
if (!mob.BehaviourType.isWimpy && !mob.isMoving() && mob.combatTarget != null) {
CheckForAttack(mob);
}
} else {
CheckMobMovement(mob); CheckMobMovement(mob);
}
//check if mob can attack if it isn't wimpy
if (!mob.BehaviourType.isWimpy && !mob.isMoving() && mob.combatTarget != null) {
CheckForAttack(mob); CheckForAttack(mob);
} }
} }
private static void CheckForAggro(Mob aiAgent) { private static void CheckForAggro(Mob aiAgent) {
//looks for and sets mobs combatTarget //looks for and sets mobs combatTarget
if (!aiAgent.isAlive()) { if (!aiAgent.isAlive()) {
@ -629,36 +638,59 @@ public class MobileFSM {
} }
private static void CheckMobMovement(Mob mob) { private static void CheckMobMovement(Mob mob) {
mob.updateLocation(); mob.updateLocation();
if (mob.getCombatTarget() == null) { if (mob.isPet() == false && mob.isSummonedPet() == false && mob.isNecroPet() == false) {
//patrol if (mob.getCombatTarget() == null) {
int patrolRandom = ThreadLocalRandom.current().nextInt(1000); //patrol
if (patrolRandom <= MBServerStatics.AI_PATROL_DIVISOR) { int patrolRandom = ThreadLocalRandom.current().nextInt(1000);
if (MovementUtilities.canMove(mob) && !mob.isMoving()) { if (patrolRandom <= MBServerStatics.AI_PATROL_DIVISOR) {
if (mob.isPlayerGuard()) { if (MovementUtilities.canMove(mob) && !mob.isMoving()) {
guardPatrol(mob); if (mob.isPlayerGuard()) {
return; guardPatrol(mob);
return;
}
float patrolRadius = mob.getSpawnRadius();
if (patrolRadius > 256)
patrolRadius = 256;
if (patrolRadius < 60)
patrolRadius = 60;
MovementUtilities.aiMove(mob, Vector3fImmutable.getRandomPointInCircle(mob.getBindLoc(), patrolRadius), true);
}
}
} else {
//chase target
mob.updateMovementState();
if (CombatUtilities.inRange2D(mob, mob.getCombatTarget(), mob.getRange()) == false) {
if (mob.getRange() > 15) {
mob.destination = mob.getCombatTarget().getLoc();
MovementUtilities.moveToLocation(mob, mob.destination, 0);
} else {
mob.destination = MovementUtilities.GetDestinationToCharacter(mob, (AbstractCharacter) mob.getCombatTarget());
MovementUtilities.moveToLocation(mob, mob.destination, mob.getRange());
} }
float patrolRadius = mob.getSpawnRadius();
if (patrolRadius > 256)
patrolRadius = 256;
if (patrolRadius < 60)
patrolRadius = 60;
MovementUtilities.aiMove(mob, Vector3fImmutable.getRandomPointInCircle(mob.getBindLoc(), patrolRadius), true);
} }
} }
}else { } else{
//chase target //pet logic
mob.updateMovementState(); if (mob.getCombatTarget() == null || mob.combatTarget.isAlive() == false) {
if (CombatUtilities.inRange2D(mob, mob.getCombatTarget(), mob.getRange()) == false) { //move back to owner
if (mob.getRange() > 15) { if (CombatUtilities.inRange2D(mob, mob.getOwner(), 5) == false) {
mob.destination = mob.getCombatTarget().getLoc(); mob.destination = mob.getOwner().getLoc();
MovementUtilities.moveToLocation(mob, mob.destination, 0); MovementUtilities.moveToLocation(mob, mob.destination, 5);
} else { }
mob.destination = MovementUtilities.GetDestinationToCharacter(mob, (AbstractCharacter) mob.getCombatTarget()); } else {
MovementUtilities.moveToLocation(mob, mob.destination, mob.getRange()); //chase target
mob.updateMovementState();
if (CombatUtilities.inRange2D(mob, mob.getCombatTarget(), mob.getRange()) == false) {
if (mob.getRange() > 15) {
mob.destination = mob.getCombatTarget().getLoc();
MovementUtilities.moveToLocation(mob, mob.destination, 0);
} else {
mob.destination = MovementUtilities.GetDestinationToCharacter(mob, (AbstractCharacter) mob.getCombatTarget());
MovementUtilities.moveToLocation(mob, mob.destination, mob.getRange());
}
} }
} }
} }

20
src/engine/devcmd/cmds/aiInfoCmd.java

@ -79,19 +79,23 @@ public class aiInfoCmd extends AbstractDevCmd {
Mob mob = (Mob) target; Mob mob = (Mob) target;
output = "Mob AI Information:" + newline; output = "Mob AI Information:" + newline;
output += mob.getName() + newline; output += mob.getName() + newline;
output += "BehaviourType: " + mob.BehaviourType.toString() + newline; if(mob.BehaviourType != null) {
output += "Behaviour Helper Type: " + mob.BehaviourType.BehaviourHelperType.toString() + newline; output += "BehaviourType: " + mob.BehaviourType.toString() + newline;
output += "Wimpy: " + mob.BehaviourType.isWimpy + newline; output += "Behaviour Helper Type: " + mob.BehaviourType.BehaviourHelperType.toString() + newline;
output += "Agressive: " + mob.BehaviourType.isAgressive + newline; output += "Wimpy: " + mob.BehaviourType.isWimpy + newline;
output += "Can Roam: " + mob.BehaviourType.canRoam + newline; output += "Agressive: " + mob.BehaviourType.isAgressive + newline;
output += "Calls For Help: " + mob.BehaviourType.callsForHelp + newline; output += "Can Roam: " + mob.BehaviourType.canRoam + newline;
output += "Responds To Call For Help: " + mob.BehaviourType.respondsToCallForHelp + newline; output += "Calls For Help: " + mob.BehaviourType.callsForHelp + newline;
output += "Responds To Call For Help: " + mob.BehaviourType.respondsToCallForHelp + newline;
} else{
output += "BehaviourType: NULL" + newline;
}
output += "Player Aggro Map Size: " + mob.playerAgroMap.size() + newline; output += "Player Aggro Map Size: " + mob.playerAgroMap.size() + newline;
if(mob.playerAgroMap.size() > 0){ if(mob.playerAgroMap.size() > 0){
output += "Players Loaded:" + newline; output += "Players Loaded:" + newline;
} }
for(Map.Entry<Integer,Boolean> entry : mob.playerAgroMap.entrySet()){ for(Map.Entry<Integer,Boolean> entry : mob.playerAgroMap.entrySet()){
output += "Player ID: " + entry.getKey() + "In Range To Aggro: " + entry.getValue() + newline; output += "Player ID: " + entry.getKey() + " In Range To Aggro: " + entry.getValue() + newline;
} }
} }
throwbackInfo(pc, output); throwbackInfo(pc, output);

1
src/engine/net/client/ClientMessagePump.java

@ -2022,7 +2022,6 @@ public class ClientMessagePump implements NetMsgHandler {
return; return;
CombatManager.setAttackTarget(msg, conn); CombatManager.setAttackTarget(msg, conn);
if (pet.getCombatTarget() == null) if (pet.getCombatTarget() == null)
return; return;
} }

10
src/engine/objects/Mob.java

@ -181,6 +181,7 @@ public class Mob extends AbstractIntelligenceAgent {
this.parentZone = parent; this.parentZone = parent;
this.parentZoneID = (parent != null) ? parent.getObjectUUID() : 0; this.parentZoneID = (parent != null) ? parent.getObjectUUID() : 0;
this.ownerUID = owner.getObjectUUID(); this.ownerUID = owner.getObjectUUID();
this.BehaviourType = MobileFSM.MobBehaviourType.Pet1;
initializeMob(true, false, false); initializeMob(true, false, false);
clearStatic(); clearStatic();
} }
@ -1955,10 +1956,13 @@ public class Mob extends AbstractIntelligenceAgent {
} }
// Combine mobbase and mob aggro arrays into one bitvector // Combine mobbase and mob aggro arrays into one bitvector
try {
this.notEnemy.addAll(this.getMobBase().notEnemy);
this.enemy.addAll(this.getMobBase().enemy);
}
catch(Exception ex){
this.notEnemy.addAll(this.getMobBase().notEnemy); }
this.enemy.addAll(this.getMobBase().enemy);
try { try {
NPCManager.applyRuneSetEffects(this); NPCManager.applyRuneSetEffects(this);
recalculateStats(); recalculateStats();

Loading…
Cancel
Save