mirror of
https://github.com/2006-Scape/apollo.git
synced 2026-07-03 00:38:21 +00:00
Add GroupableEntity.
This commit is contained in:
@@ -14,6 +14,7 @@ import org.apollo.game.message.impl.RegionUpdateMessage;
|
||||
import org.apollo.game.model.Direction;
|
||||
import org.apollo.game.model.Position;
|
||||
import org.apollo.game.model.area.collision.CollisionMatrix;
|
||||
import org.apollo.game.model.area.update.GroupableEntity;
|
||||
import org.apollo.game.model.area.update.UpdateOperation;
|
||||
import org.apollo.game.model.entity.Entity;
|
||||
import org.apollo.game.model.entity.EntityType;
|
||||
@@ -40,8 +41,8 @@ public final class Region {
|
||||
@Override
|
||||
public void execute(Region region, Entity entity, EntityUpdateType update) {
|
||||
EntityType type = entity.getEntityType();
|
||||
if (type != EntityType.PLAYER && type != EntityType.NPC) {
|
||||
region.record(entity, update);
|
||||
if (!type.isMob()) {
|
||||
region.record((Entity & GroupableEntity) entity, update);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -53,9 +54,9 @@ public final class Region {
|
||||
public static final int SIZE = 8;
|
||||
|
||||
/**
|
||||
* The default size of newly-created sets, to reduce memory usage.
|
||||
* The default size of newly-created Lists, to reduce memory usage.
|
||||
*/
|
||||
private static final int DEFAULT_SET_SIZE = 2;
|
||||
private static final int DEFAULT_LIST_SIZE = 2;
|
||||
|
||||
/**
|
||||
* The RegionCoordinates of this Region.
|
||||
@@ -108,7 +109,7 @@ public final class Region {
|
||||
|
||||
for (int height = 0; height < Position.HEIGHT_LEVELS; height++) {
|
||||
snapshots.add(new HashMap<>());
|
||||
updates.add(new ArrayList<>(DEFAULT_SET_SIZE));
|
||||
updates.add(new ArrayList<>(DEFAULT_LIST_SIZE));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -124,7 +125,7 @@ public final class Region {
|
||||
Position position = entity.getPosition();
|
||||
checkPosition(position);
|
||||
|
||||
Set<Entity> local = entities.computeIfAbsent(position, key -> new HashSet<>(DEFAULT_SET_SIZE));
|
||||
Set<Entity> local = entities.computeIfAbsent(position, key -> new HashSet<>(DEFAULT_LIST_SIZE));
|
||||
local.add(entity);
|
||||
|
||||
if (notify) {
|
||||
@@ -212,7 +213,7 @@ public final class Region {
|
||||
*/
|
||||
public CollisionMatrix getMatrix(int height) {
|
||||
Preconditions.checkElementIndex(height, matrices.length, "Matrix height level must be [0, " + matrices.length
|
||||
+ ").");
|
||||
+ "), received " + height + ".");
|
||||
return matrices[height];
|
||||
}
|
||||
|
||||
@@ -307,22 +308,23 @@ public final class Region {
|
||||
}
|
||||
|
||||
/**
|
||||
* Records the specified {@link Entity} as being updated this pulse.
|
||||
* Records the specified {@link GroupableEntity} as being updated this pulse.
|
||||
*
|
||||
* @param entity The Entity.
|
||||
* @param entity The GroupableEntity.
|
||||
* @param type The {@link EntityUpdateType}.
|
||||
* @throws UnsupportedOperationException If the specified Entity cannot be operated on in this manner.
|
||||
*/
|
||||
private void record(Entity entity, EntityUpdateType type) {
|
||||
private <T extends Entity & GroupableEntity> void record(T entity, EntityUpdateType type) {
|
||||
RegionUpdateMessage message = entity.toUpdateOperation(this, type).toMessage();
|
||||
int height = entity.getPosition().getHeight();
|
||||
|
||||
Map<Entity, RegionUpdateMessage> snapshot = snapshots.get(height);
|
||||
updates.get(height).add(message);
|
||||
snapshots.get(height).remove(entity);
|
||||
|
||||
snapshot.remove(entity);
|
||||
if ((entity.getEntityType() == EntityType.STATIC_OBJECT && type == EntityUpdateType.REMOVE)
|
||||
|| (entity.getEntityType() != EntityType.STATIC_OBJECT && type == EntityUpdateType.ADD)) {
|
||||
snapshots.get(height).put(entity, message);
|
||||
snapshot.put(entity, message);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,24 @@
|
||||
package org.apollo.game.model.area.update;
|
||||
|
||||
import org.apollo.game.model.area.EntityUpdateType;
|
||||
import org.apollo.game.model.area.Region;
|
||||
|
||||
/**
|
||||
* An entity that can be sent as part of a grouped region update message.
|
||||
* <p>
|
||||
* Only {@link org.apollo.game.model.entity.Entity} extensions may implement this interface.
|
||||
*
|
||||
* @author Major
|
||||
*/
|
||||
public interface GroupableEntity {
|
||||
|
||||
/**
|
||||
* Gets this Entity, as an {@link UpdateOperation} of a {@link Region}.
|
||||
*
|
||||
* @param region The Region.
|
||||
* @param type The EntityUpdateType.
|
||||
* @return The UpdateOperation.
|
||||
*/
|
||||
public UpdateOperation<?> toUpdateOperation(Region region, EntityUpdateType type);
|
||||
|
||||
}
|
||||
@@ -2,9 +2,6 @@ package org.apollo.game.model.entity;
|
||||
|
||||
import org.apollo.game.model.Position;
|
||||
import org.apollo.game.model.World;
|
||||
import org.apollo.game.model.area.EntityUpdateType;
|
||||
import org.apollo.game.model.area.Region;
|
||||
import org.apollo.game.model.area.update.UpdateOperation;
|
||||
|
||||
/**
|
||||
* Represents an in-game entity, such as a mob, object, projectile, etc.
|
||||
@@ -65,13 +62,4 @@ public abstract class Entity {
|
||||
@Override
|
||||
public abstract int hashCode();
|
||||
|
||||
/**
|
||||
* Gets this Entity, as an {@link UpdateOperation} of a {@link Region}.
|
||||
*
|
||||
* @param region The Region.
|
||||
* @param type The EntityUpdateType.
|
||||
* @return The UpdateOperation.
|
||||
*/
|
||||
public abstract UpdateOperation<?> toUpdateOperation(Region region, EntityUpdateType type);
|
||||
|
||||
}
|
||||
@@ -5,6 +5,7 @@ import org.apollo.game.model.Position;
|
||||
import org.apollo.game.model.World;
|
||||
import org.apollo.game.model.area.EntityUpdateType;
|
||||
import org.apollo.game.model.area.Region;
|
||||
import org.apollo.game.model.area.update.GroupableEntity;
|
||||
import org.apollo.game.model.area.update.ItemUpdateOperation;
|
||||
import org.apollo.game.model.area.update.UpdateOperation;
|
||||
|
||||
@@ -13,7 +14,7 @@ import org.apollo.game.model.area.update.UpdateOperation;
|
||||
*
|
||||
* @author Major
|
||||
*/
|
||||
public final class GroundItem extends Entity {
|
||||
public final class GroundItem extends Entity implements GroupableEntity {
|
||||
|
||||
/**
|
||||
* Creates a new GroundItem.
|
||||
|
||||
@@ -12,10 +12,8 @@ import org.apollo.game.model.Direction;
|
||||
import org.apollo.game.model.Graphic;
|
||||
import org.apollo.game.model.Position;
|
||||
import org.apollo.game.model.World;
|
||||
import org.apollo.game.model.area.EntityUpdateType;
|
||||
import org.apollo.game.model.area.Region;
|
||||
import org.apollo.game.model.area.RegionRepository;
|
||||
import org.apollo.game.model.area.update.UpdateOperation;
|
||||
import org.apollo.game.model.entity.attr.Attribute;
|
||||
import org.apollo.game.model.entity.attr.AttributeMap;
|
||||
import org.apollo.game.model.event.impl.MobPositionUpdateEvent;
|
||||
@@ -53,7 +51,8 @@ public abstract class Mob extends Entity {
|
||||
/**
|
||||
* This mob's equipment.
|
||||
*/
|
||||
protected final Inventory equipment = new Inventory(InventoryConstants.EQUIPMENT_CAPACITY, StackMode.STACK_ALWAYS);
|
||||
protected final Inventory equipment = new Inventory(InventoryConstants.EQUIPMENT_CAPACITY,
|
||||
StackMode.STACK_ALWAYS);
|
||||
|
||||
/**
|
||||
* The index of this mob.
|
||||
@@ -198,8 +197,8 @@ public abstract class Mob extends Entity {
|
||||
*/
|
||||
public final Direction[] getDirections() {
|
||||
if (firstDirection != Direction.NONE) {
|
||||
return secondDirection == Direction.NONE ? new Direction[] { firstDirection } : new Direction[] {
|
||||
firstDirection, secondDirection };
|
||||
return secondDirection == Direction.NONE ? new Direction[] { firstDirection }
|
||||
: new Direction[] { firstDirection, secondDirection };
|
||||
}
|
||||
|
||||
return Direction.EMPTY_DIRECTION_ARRAY;
|
||||
@@ -430,14 +429,14 @@ public abstract class Mob extends Entity {
|
||||
/**
|
||||
* Sets the {@link Position} of this mob.
|
||||
* <p>
|
||||
* This method may be intercepted using a {@link MobPositionUpdateEvent}, which can be terminated like any other.
|
||||
* Plugins that intercept this Event <strong>must</strong> be cautious, because movement will not be possible (even
|
||||
* through mechanisms such as teleporting) if the Event is terminated.
|
||||
* This method may be intercepted using a {@link MobPositionUpdateEvent}, which can be terminated like any
|
||||
* other. Plugins that intercept this Event <strong>must</strong> be cautious, because movement will not be
|
||||
* possible (even through mechanisms such as teleporting) if the Event is terminated.
|
||||
*
|
||||
* @param position The Position.
|
||||
*/
|
||||
public final void setPosition(Position position) {
|
||||
if (world.submit(new MobPositionUpdateEvent(this, position))) {
|
||||
if (!position.equals(this.position) && world.submit(new MobPositionUpdateEvent(this, position))) {
|
||||
Position old = this.position;
|
||||
RegionRepository repository = world.getRegionRepository();
|
||||
Region current = repository.fromPosition(old), next = repository.fromPosition(position);
|
||||
@@ -524,11 +523,6 @@ public abstract class Mob extends Entity {
|
||||
stopAction();
|
||||
}
|
||||
|
||||
@Override
|
||||
public final UpdateOperation<Entity> toUpdateOperation(Region region, EntityUpdateType operation) {
|
||||
throw new UnsupportedOperationException("Mobs cannot be recorded as a Region update.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Turns this mob to face the specified {@link Position}.
|
||||
*
|
||||
|
||||
@@ -46,7 +46,8 @@ public final class WalkingQueue {
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return MoreObjects.toStringHelper(this).add("direction", direction).add("position", position).toString();
|
||||
return MoreObjects.toStringHelper(this).add("direction", direction).add("position", position)
|
||||
.toString();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -86,8 +87,8 @@ public final class WalkingQueue {
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds the first step to the queue, attempting to connect the server and client position by looking at the previous
|
||||
* queue.
|
||||
* Adds the first step to the queue, attempting to connect the server and client position by looking at the
|
||||
* previous queue.
|
||||
*
|
||||
* @param clientPosition The first step.
|
||||
* @return {@code true} if the queues could be connected correctly, {@code false} if not.
|
||||
@@ -202,11 +203,7 @@ public final class WalkingQueue {
|
||||
* @return The last point.
|
||||
*/
|
||||
private Point getLast() {
|
||||
Point last = points.peekLast();
|
||||
if (last == null) {
|
||||
return new Point(mob.getPosition(), Direction.NONE);
|
||||
}
|
||||
return last;
|
||||
return points.isEmpty() ? new Point(mob.getPosition(), Direction.NONE) : points.peekLast();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -223,13 +220,16 @@ public final class WalkingQueue {
|
||||
|
||||
if (runningQueue /* and enough energy */) {
|
||||
next = points.poll();
|
||||
|
||||
if (next != null) {
|
||||
second = next.direction;
|
||||
position = next.position;
|
||||
}
|
||||
}
|
||||
|
||||
mob.setPosition(position);
|
||||
}
|
||||
|
||||
mob.setDirections(first, second);
|
||||
}
|
||||
|
||||
|
||||
@@ -39,7 +39,8 @@ public final class DynamicGameObject extends GameObject {
|
||||
* @param orientation The orientation of the DynamicGameObject.
|
||||
* @return The DynamicGameObject.
|
||||
*/
|
||||
public static DynamicGameObject createPublic(World world, int id, Position position, int type, int orientation) {
|
||||
public static DynamicGameObject createPublic(World world, int id, Position position, int type,
|
||||
int orientation) {
|
||||
return new DynamicGameObject(world, id, position, type, orientation, true);
|
||||
}
|
||||
|
||||
@@ -49,9 +50,9 @@ public final class DynamicGameObject extends GameObject {
|
||||
private final boolean alwaysVisible;
|
||||
|
||||
/**
|
||||
* The Set of Players that can view this DynamicGameObject.
|
||||
* The Set of Player usernames that can view this DynamicGameObject.
|
||||
*/
|
||||
private final Set<Player> players = new HashSet<>();
|
||||
private final Set<String> players = new HashSet<>(); // TODO more appropriate type?
|
||||
|
||||
/**
|
||||
* Creates the DynamicGameObject.
|
||||
@@ -63,7 +64,8 @@ public final class DynamicGameObject extends GameObject {
|
||||
* @param orientation The orientation of the DynamicGameObject.
|
||||
* @param alwaysVisible The flag indicates whether or not this DynamicGameObject is visible to every player.
|
||||
*/
|
||||
private DynamicGameObject(World world, int id, Position position, int type, int orientation, boolean alwaysVisible) {
|
||||
private DynamicGameObject(World world, int id, Position position, int type, int orientation,
|
||||
boolean alwaysVisible) {
|
||||
super(world, id, position, type, orientation);
|
||||
this.alwaysVisible = alwaysVisible;
|
||||
}
|
||||
@@ -72,10 +74,10 @@ public final class DynamicGameObject extends GameObject {
|
||||
* Adds this DynamicGameObject to the view of the specified {@link Player}.
|
||||
*
|
||||
* @param player The Player.
|
||||
* @return {@code true} if this GameObject was not already visible to the specified Player.
|
||||
* @return {@code true} if this DynamicGameObject was not already visible to the specified Player.
|
||||
*/
|
||||
public boolean addTo(Player player) {
|
||||
return players.add(player);
|
||||
return players.add(player.getUsername());
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -87,15 +89,15 @@ public final class DynamicGameObject extends GameObject {
|
||||
* Removes this DynamicGameObject from the view of the specified {@link Player}.
|
||||
*
|
||||
* @param player The Player.
|
||||
* @return {@code true} if this GameObject was visible to the specified Player.
|
||||
* @return {@code true} if this DynamicGameObject was visible to the specified Player.
|
||||
*/
|
||||
public boolean removeFrom(Player player) {
|
||||
return players.remove(player);
|
||||
return players.remove(player.getUsername());
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean viewableBy(Player player, World world) {
|
||||
return alwaysVisible || players.contains(player);
|
||||
return alwaysVisible || players.contains(player.getUsername());
|
||||
}
|
||||
|
||||
}
|
||||
@@ -5,6 +5,7 @@ import org.apollo.game.model.Position;
|
||||
import org.apollo.game.model.World;
|
||||
import org.apollo.game.model.area.EntityUpdateType;
|
||||
import org.apollo.game.model.area.Region;
|
||||
import org.apollo.game.model.area.update.GroupableEntity;
|
||||
import org.apollo.game.model.area.update.ObjectUpdateOperation;
|
||||
import org.apollo.game.model.entity.Entity;
|
||||
import org.apollo.game.model.entity.Player;
|
||||
@@ -17,7 +18,7 @@ import com.google.common.base.MoreObjects;
|
||||
* @author Chris Fletcher
|
||||
* @author Major
|
||||
*/
|
||||
public abstract class GameObject extends Entity {
|
||||
public abstract class GameObject extends Entity implements GroupableEntity {
|
||||
|
||||
/**
|
||||
* The packed value that stores this object's id, type, and orientation.
|
||||
@@ -91,7 +92,8 @@ public abstract class GameObject extends Entity {
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return MoreObjects.toStringHelper(this).add("id", getId()).add("type", getType()).add("orientation", getOrientation()).toString();
|
||||
return MoreObjects.toStringHelper(this).add("id", getId()).add("type", getType())
|
||||
.add("orientation", getOrientation()).toString();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -26,7 +26,8 @@ public final class GroupedRegionUpdateMessageEncoder extends MessageEncoder<Grou
|
||||
/**
|
||||
* Creates the GroupedRegionUpdateMessageEncoder.
|
||||
*
|
||||
* @param release The {@link Release} containing the {@link MessageEncoder}s for the {@link RegionUpdateMessage}s.
|
||||
* @param release The {@link Release} containing the {@link MessageEncoder}s for the {@link RegionUpdateMessage}
|
||||
* s.
|
||||
*/
|
||||
public GroupedRegionUpdateMessageEncoder(Release release) {
|
||||
this.release = release;
|
||||
@@ -39,11 +40,8 @@ public final class GroupedRegionUpdateMessageEncoder extends MessageEncoder<Grou
|
||||
|
||||
builder.put(DataType.BYTE, region.getLocalY(lastKnownRegion));
|
||||
builder.put(DataType.BYTE, DataTransformation.NEGATE, region.getLocalX(lastKnownRegion));
|
||||
System.out.println("Grum: local x: " + lastKnownRegion.getLocalX(region) + ", local y: "
|
||||
+ lastKnownRegion.getLocalY(region));
|
||||
|
||||
for (RegionUpdateMessage update : message.getMessages()) {
|
||||
System.out.println("==== Sending " + update + " as part of grum");
|
||||
@SuppressWarnings("unchecked")
|
||||
MessageEncoder<RegionUpdateMessage> encoder = (MessageEncoder<RegionUpdateMessage>) release
|
||||
.getMessageEncoder(update.getClass());
|
||||
|
||||
@@ -94,7 +94,7 @@ public final class NpcMovementTask extends ScheduledTask {
|
||||
|
||||
Position first = positions.pollFirst();
|
||||
if (first != null && queue.addFirstStep(first)) {
|
||||
positions.forEach(npc.getWalkingQueue()::addStep);
|
||||
positions.forEach(queue::addStep);
|
||||
}
|
||||
|
||||
npcs.offer(npc);
|
||||
|
||||
Reference in New Issue
Block a user