Add support for archer AI
This commit is contained in:
53
src/main/java/com/bartlomiejpluta/demo/ai/ArcherAI.java
Normal file
53
src/main/java/com/bartlomiejpluta/demo/ai/ArcherAI.java
Normal file
@@ -0,0 +1,53 @@
|
|||||||
|
package com.bartlomiejpluta.demo.ai;
|
||||||
|
|
||||||
|
import com.bartlomiejpluta.base.api.ai.AI;
|
||||||
|
import com.bartlomiejpluta.base.api.ai.NPC;
|
||||||
|
import com.bartlomiejpluta.base.api.entity.Entity;
|
||||||
|
import com.bartlomiejpluta.base.api.map.layer.object.ObjectLayer;
|
||||||
|
import com.bartlomiejpluta.base.api.move.MoveEvent;
|
||||||
|
import com.bartlomiejpluta.base.lib.ai.KeepStraightDistanceAI;
|
||||||
|
import com.bartlomiejpluta.base.lib.ai.RandomMovementAI;
|
||||||
|
import com.bartlomiejpluta.base.util.path.MovementPath;
|
||||||
|
import com.bartlomiejpluta.base.util.path.PathExecutor;
|
||||||
|
import com.bartlomiejpluta.base.util.pathfinder.AstarPathFinder;
|
||||||
|
import com.bartlomiejpluta.base.util.pathfinder.PathFinder;
|
||||||
|
import lombok.NonNull;
|
||||||
|
import lombok.RequiredArgsConstructor;
|
||||||
|
import org.joml.Vector2i;
|
||||||
|
import org.joml.Vector2ic;
|
||||||
|
|
||||||
|
import com.bartlomiejpluta.demo.entity.Enemy;
|
||||||
|
import com.bartlomiejpluta.demo.entity.Character;
|
||||||
|
|
||||||
|
public class ArcherAI extends KeepStraightDistanceAI<Enemy, Character> {
|
||||||
|
private static final int ASTAR_MAX_NODES = 100;
|
||||||
|
private static final int IDLE_MOVEMENT_INTERVAL = 4;
|
||||||
|
private final int range;
|
||||||
|
private final AI idle;
|
||||||
|
|
||||||
|
public ArcherAI(Enemy enemy, Character target, int minRange, int maxRange, int range) {
|
||||||
|
super(new AstarPathFinder(ASTAR_MAX_NODES), enemy, target, minRange, maxRange);
|
||||||
|
this.range = range;
|
||||||
|
this.idle = new RandomMovementAI<>(enemy, IDLE_MOVEMENT_INTERVAL);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected boolean sees(Enemy enemy, Character target, ObjectLayer layer) {
|
||||||
|
return enemy.manhattanDistance(target) < range;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void interact(Enemy enemy, Character target, ObjectLayer layer, float dt) {
|
||||||
|
enemy.attack();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void follow(Enemy enemy, Character target, ObjectLayer layer, float dt) {
|
||||||
|
// noop
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void idle(Enemy enemy, Character target, ObjectLayer layer, float dt) {
|
||||||
|
idle.nextActivity(layer, dt);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -17,6 +17,7 @@ import com.bartlomiejpluta.base.generated.db.model.EnemyModel;
|
|||||||
import com.bartlomiejpluta.demo.world.weapon.*;
|
import com.bartlomiejpluta.demo.world.weapon.*;
|
||||||
import com.bartlomiejpluta.demo.event.EnemyDiedEvent;
|
import com.bartlomiejpluta.demo.event.EnemyDiedEvent;
|
||||||
import com.bartlomiejpluta.demo.ai.*;
|
import com.bartlomiejpluta.demo.ai.*;
|
||||||
|
import com.bartlomiejpluta.demo.ai.ArcherAI;
|
||||||
|
|
||||||
|
|
||||||
public class Enemy extends Character implements NPC {
|
public class Enemy extends Character implements NPC {
|
||||||
@@ -72,7 +73,7 @@ public class Enemy extends Character implements NPC {
|
|||||||
public Enemy followAndAttack(Character target, int range) {
|
public Enemy followAndAttack(Character target, int range) {
|
||||||
var ai = new SimpleEnemyAI(this, target, range);
|
var ai = new SimpleEnemyAI(this, target, range);
|
||||||
|
|
||||||
addEventListener(MoveEvent.TYPE, e -> ai.recomputePath());
|
addEventListener(MoveEvent.TYPE, ai::recomputePath);
|
||||||
addEventListener(EnemyDiedEvent.TYPE, e -> ai.recomputePath());
|
addEventListener(EnemyDiedEvent.TYPE, e -> ai.recomputePath());
|
||||||
|
|
||||||
this.ai = ai;
|
this.ai = ai;
|
||||||
@@ -91,4 +92,15 @@ public class Enemy extends Character implements NPC {
|
|||||||
|
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Enemy archer(Character target, int minRange, int maxRange, int range) {
|
||||||
|
var ai = new ArcherAI(this, target, minRange, maxRange, range);
|
||||||
|
|
||||||
|
addEventListener(MoveEvent.TYPE, ai::recomputePath);
|
||||||
|
addEventListener(EnemyDiedEvent.TYPE, e -> ai.recomputePath());
|
||||||
|
|
||||||
|
this.ai = ai;
|
||||||
|
|
||||||
|
return this;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
Reference in New Issue
Block a user