Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add flocking implementation and run callbacks for navigation
- Loading branch information
Showing
8 changed files
with
216 additions
and
18 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
27 changes: 27 additions & 0 deletions
27
src/main/java/net/citizensnpcs/api/ai/flocking/AlignmentBehavior.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,27 @@ | ||
package net.citizensnpcs.api.ai.flocking; | ||
|
||
import java.util.Collection; | ||
|
||
import net.citizensnpcs.api.npc.NPC; | ||
|
||
import org.bukkit.util.Vector; | ||
|
||
public class AlignmentBehavior implements FlockBehavior { | ||
private final double weight; | ||
|
||
public AlignmentBehavior(double weight) { | ||
this.weight = weight; | ||
} | ||
|
||
@Override | ||
public Vector getVector(NPC npc, Collection<NPC> nearby) { | ||
if (nearby.isEmpty()) | ||
return new Vector(0, 0, 0); | ||
Vector velocities = new Vector(0, 0, 0); | ||
for (NPC neighbor : nearby) { | ||
velocities = velocities.add(neighbor.getEntity().getVelocity()); | ||
} | ||
Vector desired = velocities.multiply((double) 1 / nearby.size()); | ||
return desired.subtract(npc.getEntity().getVelocity()).multiply(weight); | ||
} | ||
} |
30 changes: 30 additions & 0 deletions
30
src/main/java/net/citizensnpcs/api/ai/flocking/CohesionBehavior.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
package net.citizensnpcs.api.ai.flocking; | ||
|
||
import java.util.Collection; | ||
|
||
import net.citizensnpcs.api.npc.NPC; | ||
|
||
import org.bukkit.Location; | ||
import org.bukkit.util.Vector; | ||
|
||
public class CohesionBehavior implements FlockBehavior { | ||
private final double weight; | ||
|
||
public CohesionBehavior(double weight) { | ||
this.weight = weight; | ||
} | ||
|
||
@Override | ||
public Vector getVector(NPC npc, Collection<NPC> nearby) { | ||
if (nearby.isEmpty()) | ||
return new Vector(0, 0, 0); | ||
Location dummy = new Location(null, 0, 0, 0); | ||
Vector positions = new Vector(0, 0, 0); | ||
for (NPC neighbor : nearby) { | ||
positions = positions.add(neighbor.getEntity().getLocation(dummy).toVector()); | ||
} | ||
Vector center = positions.multiply((double) 1 / nearby.size()); | ||
return npc.getEntity().getLocation(dummy).toVector().subtract(center).multiply(weight); | ||
} | ||
|
||
} |
11 changes: 11 additions & 0 deletions
11
src/main/java/net/citizensnpcs/api/ai/flocking/FlockBehavior.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,11 @@ | ||
package net.citizensnpcs.api.ai.flocking; | ||
|
||
import java.util.Collection; | ||
|
||
import net.citizensnpcs.api.npc.NPC; | ||
|
||
import org.bukkit.util.Vector; | ||
|
||
public interface FlockBehavior { | ||
Vector getVector(NPC npc, Collection<NPC> nearby); | ||
} |
36 changes: 36 additions & 0 deletions
36
src/main/java/net/citizensnpcs/api/ai/flocking/Flocker.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,36 @@ | ||
package net.citizensnpcs.api.ai.flocking; | ||
|
||
import java.util.Arrays; | ||
import java.util.Collection; | ||
import java.util.List; | ||
|
||
import net.citizensnpcs.api.npc.NPC; | ||
|
||
import org.bukkit.util.Vector; | ||
|
||
public class Flocker implements Runnable { | ||
private final List<FlockBehavior> behaviors; | ||
private final NPCFlock flock; | ||
private final NPC npc; | ||
|
||
public Flocker(NPC npc, NPCFlock flock, FlockBehavior... behaviors) { | ||
this.npc = npc; | ||
this.flock = flock; | ||
this.behaviors = Arrays.asList(behaviors); | ||
} | ||
|
||
@Override | ||
public void run() { | ||
Collection<NPC> nearby = flock.getNearby(npc); | ||
if (nearby.isEmpty()) | ||
return; | ||
Vector base = new Vector(0, 0, 0); | ||
for (FlockBehavior behavior : behaviors) { | ||
base.add(behavior.getVector(npc, nearby)); | ||
} | ||
npc.getEntity().setVelocity(npc.getEntity().getVelocity().add(base)); | ||
} | ||
|
||
public static double HIGH_INFLUENCE = 1.0 / 20.0; | ||
public static double LOW_INFLUENCE = HIGH_INFLUENCE / 10; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,9 @@ | ||
package net.citizensnpcs.api.ai.flocking; | ||
|
||
import java.util.Collection; | ||
|
||
import net.citizensnpcs.api.npc.NPC; | ||
|
||
public interface NPCFlock { | ||
public Collection<NPC> getNearby(NPC npc); | ||
} |
32 changes: 32 additions & 0 deletions
32
src/main/java/net/citizensnpcs/api/ai/flocking/RadiusNPCFlock.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
package net.citizensnpcs.api.ai.flocking; | ||
|
||
import java.util.Collection; | ||
|
||
import net.citizensnpcs.api.CitizensAPI; | ||
import net.citizensnpcs.api.npc.NPC; | ||
|
||
import org.bukkit.entity.Entity; | ||
|
||
import com.google.common.collect.Lists; | ||
|
||
public class RadiusNPCFlock implements NPCFlock { | ||
private final double radius; | ||
|
||
public RadiusNPCFlock(double radius) { | ||
this.radius = radius; | ||
} | ||
|
||
@Override | ||
public Collection<NPC> getNearby(NPC npc) { | ||
Collection<NPC> ret = Lists.newArrayList(); | ||
for (Entity entity : npc.getEntity().getNearbyEntities(radius, radius, radius)) { | ||
NPC npc2 = CitizensAPI.getNPCRegistry().getNPC(entity); | ||
if (npc2 != null) { | ||
if (!npc2.getNavigator().isNavigating()) | ||
continue; | ||
ret.add(npc2); | ||
} | ||
} | ||
return ret; | ||
} | ||
} |
28 changes: 28 additions & 0 deletions
28
src/main/java/net/citizensnpcs/api/ai/flocking/SeparationBehavior.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,28 @@ | ||
package net.citizensnpcs.api.ai.flocking; | ||
|
||
import java.util.Collection; | ||
|
||
import net.citizensnpcs.api.npc.NPC; | ||
|
||
import org.bukkit.util.Vector; | ||
|
||
public class SeparationBehavior implements FlockBehavior { | ||
private final double weight; | ||
|
||
public SeparationBehavior(double weight) { | ||
this.weight = weight; | ||
} | ||
|
||
@Override | ||
public Vector getVector(NPC npc, Collection<NPC> nearby) { | ||
if (nearby.isEmpty()) | ||
return new Vector(0, 0, 0); | ||
Vector steering = new Vector(0, 0, 0); | ||
Vector pos = npc.getEntity().getLocation().toVector(); | ||
for (NPC neighbor : nearby) { | ||
Vector repulse = pos.subtract(neighbor.getEntity().getLocation().toVector()).multiply(1.0 / 3.0); | ||
steering = repulse.add(steering); | ||
} | ||
return steering.multiply(weight); | ||
} | ||
} |