mirror of
https://github.com/2006-Scape/apollo.git
synced 2026-07-03 08:39:11 +00:00
Merge branch 'master' into resource.
This commit is contained in:
@@ -1,7 +1,7 @@
|
||||
package org.apollo.game.command;
|
||||
|
||||
import org.apollo.game.model.entity.Player;
|
||||
import org.apollo.game.model.setting.PrivilegeLevel;
|
||||
import org.apollo.game.model.entity.setting.PrivilegeLevel;
|
||||
|
||||
/**
|
||||
* An interface which should be implemented to listen to {@link Command}s.
|
||||
|
||||
@@ -5,7 +5,7 @@ import org.apollo.game.message.handler.MessageHandlerContext;
|
||||
import org.apollo.game.message.impl.PlayerDesignMessage;
|
||||
import org.apollo.game.model.Appearance;
|
||||
import org.apollo.game.model.entity.Player;
|
||||
import org.apollo.game.model.setting.Gender;
|
||||
import org.apollo.game.model.entity.setting.Gender;
|
||||
|
||||
/**
|
||||
* A {@link MessageHandler} that verifies {@link PlayerDesignMessage}s.
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
package org.apollo.game.message.impl;
|
||||
|
||||
import org.apollo.game.message.Message;
|
||||
import org.apollo.game.model.setting.PrivilegeLevel;
|
||||
import org.apollo.game.model.entity.setting.PrivilegeLevel;
|
||||
|
||||
/**
|
||||
* A {@link Message} sent to the client that forwards a private chat.
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
package org.apollo.game.message.impl;
|
||||
|
||||
import org.apollo.game.message.Message;
|
||||
import org.apollo.game.model.setting.ServerStatus;
|
||||
import org.apollo.game.model.entity.setting.ServerStatus;
|
||||
|
||||
/**
|
||||
* A {@link Message} sent to the client to update the friend server status.
|
||||
|
||||
@@ -13,7 +13,7 @@ import org.apollo.game.model.Position;
|
||||
*/
|
||||
public final class HintIconMessage extends Message {
|
||||
|
||||
// TODO identify the other types and use an enum.
|
||||
// TODO identify the other types.
|
||||
|
||||
/**
|
||||
* The type of a HintIcon.
|
||||
@@ -75,6 +75,24 @@ public final class HintIconMessage extends Message {
|
||||
return new HintIconMessage(Type.PLAYER, Optional.of(index), Optional.empty());
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a HintIconMessage that removes the current Npc hint icon.
|
||||
*
|
||||
* @return The HintIconMessage.
|
||||
*/
|
||||
public static HintIconMessage resetNpc() {
|
||||
return forNpc(-1);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a HintIconMessage that removes the current Player hint icon.
|
||||
*
|
||||
* @return The HintIconMessage.
|
||||
*/
|
||||
public static HintIconMessage resetPlayer() {
|
||||
return forPlayer(-1);
|
||||
}
|
||||
|
||||
/**
|
||||
* The index of the Mob, if applicable.
|
||||
*/
|
||||
|
||||
@@ -0,0 +1,35 @@
|
||||
package org.apollo.game.message.impl;
|
||||
|
||||
import org.apollo.game.message.Message;
|
||||
|
||||
/**
|
||||
* A {@link Message} sent to the client that opens a dialogue interface (an interface that appears in the chat box).
|
||||
*
|
||||
* @author Chris Fletcher
|
||||
*/
|
||||
public final class OpenDialogueOverlayMessage extends Message {
|
||||
|
||||
/**
|
||||
* The interface id.
|
||||
*/
|
||||
private final int interfaceId;
|
||||
|
||||
/**
|
||||
* Creates a new message with the specified interface id.
|
||||
*
|
||||
* @param interfaceId The interface id.
|
||||
*/
|
||||
public OpenDialogueOverlayMessage(int interfaceId) {
|
||||
this.interfaceId = interfaceId;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the interface id.
|
||||
*
|
||||
* @return The interface id.
|
||||
*/
|
||||
public int getInterfaceId() {
|
||||
return interfaceId;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,7 +1,7 @@
|
||||
package org.apollo.game.message.impl;
|
||||
|
||||
import org.apollo.game.message.Message;
|
||||
import org.apollo.game.model.setting.PrivacyState;
|
||||
import org.apollo.game.model.entity.setting.PrivacyState;
|
||||
|
||||
/**
|
||||
* A {@link Message} sent both by and to the client to update the public chat, private (friend) chat, and trade chat
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
package org.apollo.game.model;
|
||||
|
||||
import org.apollo.game.model.setting.Gender;
|
||||
import org.apollo.game.model.entity.setting.Gender;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
|
||||
|
||||
@@ -8,7 +8,9 @@ import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
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.entity.Entity;
|
||||
import org.apollo.game.model.entity.Entity.EntityType;
|
||||
|
||||
@@ -23,7 +25,7 @@ import com.google.common.collect.ImmutableSet;
|
||||
public final class Sector {
|
||||
|
||||
/**
|
||||
* The width and length of a sector, in tiles.
|
||||
* The width and length of a Sector, in tiles.
|
||||
*/
|
||||
public static final int SECTOR_SIZE = 8;
|
||||
|
||||
@@ -33,20 +35,25 @@ public final class Sector {
|
||||
private static final int DEFAULT_SET_SIZE = 2;
|
||||
|
||||
/**
|
||||
* The sector coordinates of this sector.
|
||||
* The SectorCoordinates of this Sector.
|
||||
*/
|
||||
private final SectorCoordinates coordinates;
|
||||
|
||||
/**
|
||||
* A map of positions to entities in that position.
|
||||
* The Map of Positions to Entities in that Position.
|
||||
*/
|
||||
private final Map<Position, Set<Entity>> entities = new HashMap<>();
|
||||
|
||||
/**
|
||||
* A list of listeners registered to this sector.
|
||||
* A List of SectorListeners registered to this Sector.
|
||||
*/
|
||||
private final List<SectorListener> listeners = new ArrayList<>();
|
||||
|
||||
/**
|
||||
* The CollisionMatrix.
|
||||
*/
|
||||
private final CollisionMatrix matrix = new CollisionMatrix(SECTOR_SIZE, SECTOR_SIZE);
|
||||
|
||||
/**
|
||||
* Creates a new sector.
|
||||
*
|
||||
@@ -67,28 +74,29 @@ public final class Sector {
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds a {@link Entity} from to sector. Note that this does not spawn the entity, or do any other action other than
|
||||
* Adds a {@link Entity} from to sector. Note that this does not spawn the Entity, or do any other action other than
|
||||
* register it to this sector.
|
||||
*
|
||||
* @param entity The entity.
|
||||
* @throws IllegalArgumentException If the entity does not belong in this sector.
|
||||
* @param entity The Entity.
|
||||
* @throws IllegalArgumentException If the Entity does not belong in this sector.
|
||||
*/
|
||||
public void addEntity(Entity entity) {
|
||||
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_SET_SIZE));
|
||||
local.add(entity);
|
||||
|
||||
notifyListeners(entity, SectorOperation.ADD);
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if this sector contains the specified entity.
|
||||
* Checks if this sector contains the specified Entity.
|
||||
* <p>
|
||||
* This method operates in constant time.
|
||||
*
|
||||
* @param entity The entity.
|
||||
* @return {@code true} if this sector contains the entity, otherwise {@code false}.
|
||||
* @param entity The Entity.
|
||||
* @return {@code true} if this sector contains the Entity, otherwise {@code false}.
|
||||
*/
|
||||
public boolean contains(Entity entity) {
|
||||
Position position = entity.getPosition();
|
||||
@@ -114,12 +122,13 @@ public final class Sector {
|
||||
* @return The list.
|
||||
*/
|
||||
public Set<Entity> getEntities(Position position) {
|
||||
return ImmutableSet.copyOf(entities.computeIfAbsent(position, key -> new HashSet<>(DEFAULT_SET_SIZE)));
|
||||
Set<Entity> set = entities.get(position);
|
||||
return (set == null) ? ImmutableSet.of() : ImmutableSet.copyOf(set);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets a shallow copy of the {@link Set} of {@link Entity}s with the specified {@link EntityType}. The returned
|
||||
* type will be immutable. Type will be inferred from the call, so ensure that the entity type and the reference
|
||||
* type will be immutable. Type will be inferred from the call, so ensure that the Entity type and the reference
|
||||
* correspond, or this method will fail at runtime.
|
||||
*
|
||||
* @param position The {@link Position} containing the entities.
|
||||
@@ -127,21 +136,24 @@ public final class Sector {
|
||||
* @return The set of entities.
|
||||
*/
|
||||
public <T extends Entity> Set<T> getEntities(Position position, EntityType type) {
|
||||
Set<Entity> local = entities.computeIfAbsent(position, key -> new HashSet<>(DEFAULT_SET_SIZE));
|
||||
Set<Entity> local = entities.get(position);
|
||||
if (local == null) {
|
||||
return ImmutableSet.of();
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
Set<T> filtered = (Set<T>) local.stream().filter(entity -> entity.getEntityType() == type).collect(Collectors.toSet());
|
||||
Set<T> filtered = (Set<T>) local.stream().filter(Entity -> Entity.getEntityType() == type).collect(Collectors.toSet());
|
||||
return ImmutableSet.copyOf(filtered);
|
||||
}
|
||||
|
||||
/**
|
||||
* Moves the {@link Entity} that was in the specified {@code old} {@link Position}, to the current position of the
|
||||
* entity.
|
||||
* Entity.
|
||||
* <p>
|
||||
* Both the {@code old} and current positions of the entity must belong to this sector.
|
||||
* Both the {@code old} and current positions of the Entity must belong to this sector.
|
||||
*
|
||||
* @param old The old position of the entity.
|
||||
* @param entity The entity to move.
|
||||
* @param old The old position of the Entity.
|
||||
* @param entity The Entity to move.
|
||||
* @throws IllegalArgumentException If either of the positions do not belong to this sector.
|
||||
*/
|
||||
public void moveEntity(Position old, Entity entity) {
|
||||
@@ -175,8 +187,8 @@ public final class Sector {
|
||||
/**
|
||||
* Removes a {@link Entity} from this sector.
|
||||
*
|
||||
* @param entity The entity.
|
||||
* @throws IllegalArgumentException If the entity does not belong in this sector, or if it was never added.
|
||||
* @param entity The Entity.
|
||||
* @throws IllegalArgumentException If the Entity does not belong in this sector, or if it was never added.
|
||||
*/
|
||||
public void removeEntity(Entity entity) {
|
||||
Position position = entity.getPosition();
|
||||
@@ -191,6 +203,20 @@ public final class Sector {
|
||||
notifyListeners(entity, SectorOperation.REMOVE);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns whether or not an Entity of the specified {@link EntityType type} can traverse the tile at the specified
|
||||
* coordinate pair.
|
||||
*
|
||||
* @param x The x coordinate.
|
||||
* @param y The y coordinate.
|
||||
* @param entity The {@link EntityType}.
|
||||
* @param direction The {@link Direction} the Entity is approaching from.
|
||||
* @return {@code true} if the tile at the specified coordinate pair is traversable, {@code false} if not.
|
||||
*/
|
||||
public boolean traversable(int x, int y, EntityType entity, Direction direction) {
|
||||
return matrix.traversable(x, y, entity, direction);
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks that the specified {@link Position} is included in this sector.
|
||||
*
|
||||
|
||||
@@ -0,0 +1,100 @@
|
||||
package org.apollo.game.model.area.collision;
|
||||
|
||||
/**
|
||||
* A type of flag in a {@link CollisionMatrix}.
|
||||
*
|
||||
* @author Major
|
||||
*/
|
||||
public enum CollisionFlag {
|
||||
|
||||
/**
|
||||
* The walk north flag.
|
||||
*/
|
||||
MOB_NORTH(0),
|
||||
|
||||
/**
|
||||
* The walk east flag.
|
||||
*/
|
||||
MOB_EAST(1),
|
||||
|
||||
/**
|
||||
* The walk south flag.
|
||||
*/
|
||||
MOB_SOUTH(2),
|
||||
|
||||
/**
|
||||
* The walk west flag.
|
||||
*/
|
||||
MOB_WEST(3),
|
||||
|
||||
/**
|
||||
* The projectile north flag.
|
||||
*/
|
||||
PROJECTILE_NORTH(4),
|
||||
|
||||
/**
|
||||
* The projectile east flag.
|
||||
*/
|
||||
PROJECTILE_EAST(5),
|
||||
|
||||
/**
|
||||
* The projectile south flag.
|
||||
*/
|
||||
PROJECTILE_SOUTH(6),
|
||||
|
||||
/**
|
||||
* The projectile west flag.
|
||||
*/
|
||||
PROJECTILE_WEST(7);
|
||||
|
||||
/**
|
||||
* Returns an array of CollisionFlags that indicate if a Mob can traverse over a tile.
|
||||
*
|
||||
* @return The array of CollisionFlags.
|
||||
*/
|
||||
public static CollisionFlag[] mobs() {
|
||||
return new CollisionFlag[] { MOB_NORTH, MOB_EAST, MOB_SOUTH, MOB_WEST };
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns an array of CollisionFlags that indicate if a Projectile can traverse over a tile.
|
||||
*
|
||||
* @return The array of CollisionFlags.
|
||||
*/
|
||||
public static CollisionFlag[] projectiles() {
|
||||
return new CollisionFlag[] { PROJECTILE_NORTH, PROJECTILE_EAST, PROJECTILE_SOUTH, PROJECTILE_WEST };
|
||||
}
|
||||
|
||||
/**
|
||||
* The index of the bit this flag is stored in.
|
||||
*/
|
||||
private final int bit;
|
||||
|
||||
/**
|
||||
* Creates the CollisionFlag.
|
||||
*
|
||||
* @param bit The index of the bit this flag is stored in.
|
||||
*/
|
||||
private CollisionFlag(int bit) {
|
||||
this.bit = bit;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets this CollisionFlag, as a {@code byte}.
|
||||
*
|
||||
* @return The value, as a {@code byte}.
|
||||
*/
|
||||
public byte asByte() {
|
||||
return (byte) (1 << bit);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the index of the bit this flag is stored in.
|
||||
*
|
||||
* @return The index of the bit.
|
||||
*/
|
||||
public int getBit() {
|
||||
return bit;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,227 @@
|
||||
package org.apollo.game.model.area.collision;
|
||||
|
||||
import java.util.Arrays;
|
||||
|
||||
import org.apollo.game.model.Direction;
|
||||
import org.apollo.game.model.entity.Entity.EntityType;
|
||||
|
||||
import com.google.common.base.MoreObjects;
|
||||
import com.google.common.base.Preconditions;
|
||||
|
||||
/**
|
||||
* A 2-dimensional adjacency matrix containing tile collision data.
|
||||
*
|
||||
* @author Major
|
||||
*/
|
||||
public final class CollisionMatrix {
|
||||
|
||||
/**
|
||||
* Indicates that all types of traversal are allowed.
|
||||
*/
|
||||
private static final byte ALL_ALLOWED = 0b0000_0000;
|
||||
|
||||
/**
|
||||
* Indicates that no types of traversal are allowed.
|
||||
*/
|
||||
private static final byte ALL_BLOCKED = (byte) 0b1111_1111;
|
||||
|
||||
/**
|
||||
* The length of the matrix.
|
||||
*/
|
||||
private final int length;
|
||||
|
||||
/**
|
||||
* The collision matrix, as a {@code byte} array.
|
||||
*/
|
||||
private final byte[] matrix;
|
||||
|
||||
/**
|
||||
* The width of the matrix.
|
||||
*/
|
||||
private final int width;
|
||||
|
||||
/**
|
||||
* Creates the CollisionMatrix.
|
||||
*
|
||||
* @param width The width of the matrix.
|
||||
* @param length The length of the matrix.
|
||||
*/
|
||||
public CollisionMatrix(int width, int length) {
|
||||
this.width = width;
|
||||
this.length = length;
|
||||
matrix = new byte[width * length];
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns whether or not <strong>all</strong> of the specified {@link CollisionFlag}s are set for the specified
|
||||
* coordinate pair.
|
||||
*
|
||||
* @param x The x coordinate.
|
||||
* @param y The y coordinate.
|
||||
* @param flags The CollisionFlags.
|
||||
* @return {@code true} if all of the CollisionFlags are set, otherwise {@code false}.
|
||||
*/
|
||||
public boolean all(int x, int y, CollisionFlag... flags) {
|
||||
for (CollisionFlag flag : flags) {
|
||||
if ((get(x, y) & flag.asByte()) == 0) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns whether or not <strong>any</strong> of the specified {@link CollisionFlag}s are set for the specified
|
||||
* coordinate pair.
|
||||
*
|
||||
* @param x The x coordinate.
|
||||
* @param y The y coordinate.
|
||||
* @param flags The CollisionFlags.
|
||||
* @return {@code true} if any of the CollisionFlags are set, otherwise {@code false}.
|
||||
*/
|
||||
public boolean any(int x, int y, CollisionFlag... flags) {
|
||||
for (CollisionFlag flag : flags) {
|
||||
if ((get(x, y) & flag.asByte()) != 0) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Completely blocks the tile at the specified coordinate pair.
|
||||
*
|
||||
* @param x The x coordinate.
|
||||
* @param y The y coordinate.
|
||||
*/
|
||||
public void block(int x, int y) {
|
||||
set(x, y, ALL_BLOCKED);
|
||||
}
|
||||
|
||||
/**
|
||||
* Clears (i.e. sets to {@code false}) the value of the specified {@link CollisionFlag} for the specified coordinate
|
||||
* pair.
|
||||
*
|
||||
* @param x The x coordinate.
|
||||
* @param y The y coordinate.
|
||||
* @param flag The CollisionFlag.
|
||||
*/
|
||||
public void clear(int x, int y, CollisionFlag flag) {
|
||||
set(x, y, (byte) ~flag.asByte());
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns whether or not the specified {@link CollisionFlag} is set for the specified coordinate pair.
|
||||
*
|
||||
* @param x The x coordinate.
|
||||
* @param y The y coordinate.
|
||||
* @param flag The CollisionFlag.
|
||||
* @return {@code true} if the CollisionFlag is set, {@code false} if not.
|
||||
*/
|
||||
public boolean flagged(int x, int y, CollisionFlag flag) {
|
||||
return (get(x, y) & flag.asByte()) != 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the value of the specified tile.
|
||||
*
|
||||
* @param x The x coordinate of the tile.
|
||||
* @param y The y coordinate of the tile.
|
||||
* @return The value.
|
||||
*/
|
||||
public int get(int x, int y) {
|
||||
return matrix[indexOf(x, y)] & 0xFF;
|
||||
}
|
||||
|
||||
/**
|
||||
* Resets the cell of the specified coordinate pair.
|
||||
*
|
||||
* @param x The x coordinate.
|
||||
* @param y The y coordinate.
|
||||
*/
|
||||
public void reset(int x, int y) {
|
||||
set(x, y, ALL_ALLOWED);
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets (i.e. sets to {@code true}) the value of the specified {@link CollisionFlag} for the specified coordinate
|
||||
* pair.
|
||||
*
|
||||
* @param x The x coordinate.
|
||||
* @param y The y coordinate.
|
||||
* @param flag The CollisionFlag.
|
||||
*/
|
||||
public void set(int x, int y, CollisionFlag flag) {
|
||||
set(x, y, flag.asByte());
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return MoreObjects.toStringHelper(this).add("width", width).add("length", length).add("matrix", Arrays.toString(matrix))
|
||||
.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns whether or not an Entity of the specified {@link EntityType type} can traverse the tile at the specified
|
||||
* coordinate pair.
|
||||
*
|
||||
* @param x The x coordinate.
|
||||
* @param y The y coordinate.
|
||||
* @param entity The {@link EntityType}.
|
||||
* @param direction The {@link Direction} the Entity is approaching from.
|
||||
* @return {@code true} if the tile at the specified coordinate pair is traversable, {@code false} if not.
|
||||
*/
|
||||
public boolean traversable(int x, int y, EntityType entity, Direction direction) {
|
||||
CollisionFlag[] flags = (entity == EntityType.PROJECTILE) ? CollisionFlag.projectiles() : CollisionFlag.mobs();
|
||||
int north = 0, east = 1, south = 2, west = 3;
|
||||
|
||||
switch (direction) {
|
||||
case NORTH_WEST:
|
||||
return any(x, y, flags[south], flags[east]);
|
||||
case NORTH:
|
||||
return flagged(x, y, flags[south]);
|
||||
case NORTH_EAST:
|
||||
return any(x, y, flags[south], flags[west]);
|
||||
case EAST:
|
||||
return flagged(x, y, flags[west]);
|
||||
case SOUTH_EAST:
|
||||
return any(x, y, flags[north], flags[west]);
|
||||
case SOUTH:
|
||||
return flagged(x, y, flags[north]);
|
||||
case SOUTH_WEST:
|
||||
return any(x, y, flags[north], flags[east]);
|
||||
case WEST:
|
||||
return flagged(x, y, flags[east]);
|
||||
}
|
||||
|
||||
throw new IllegalArgumentException("Unrecognised direction " + direction + ".");
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the index in the matrix for the specified coordinate pair.
|
||||
*
|
||||
* @param x The x coordinate.
|
||||
* @param y The y coordinate.
|
||||
* @return The index.
|
||||
* @throws ArrayIndexOutOfBoundsException If the specified coordinate pair does not fit in this matrix.
|
||||
*/
|
||||
private int indexOf(int x, int y) {
|
||||
int index = y * width + x;
|
||||
Preconditions.checkElementIndex(index, matrix.length, "Index out of bounds.");
|
||||
return index;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the appropriate index for the specified coordinate pair to the specified value.
|
||||
*
|
||||
* @param x The x coordinate.
|
||||
* @param y The y coordinate.
|
||||
* @param value The value.
|
||||
*/
|
||||
private void set(int x, int y, byte value) {
|
||||
matrix[indexOf(x, y)] = value;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,4 @@
|
||||
/**
|
||||
* Contains classes related to tile collision data.
|
||||
*/
|
||||
package org.apollo.game.model.area.collision;
|
||||
@@ -16,6 +16,7 @@ import org.apollo.game.model.area.SectorRepository;
|
||||
import org.apollo.game.model.def.NpcDefinition;
|
||||
import org.apollo.game.model.entity.attr.Attribute;
|
||||
import org.apollo.game.model.entity.attr.AttributeMap;
|
||||
import org.apollo.game.model.event.impl.MobPositionUpdateEvent;
|
||||
import org.apollo.game.model.inv.Inventory;
|
||||
import org.apollo.game.model.inv.Inventory.StackMode;
|
||||
import org.apollo.game.model.inv.InventoryConstants;
|
||||
@@ -402,7 +403,7 @@ public abstract class Mob extends Entity {
|
||||
this.index = index;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Returns this mobs interacting index.
|
||||
*
|
||||
@@ -428,6 +429,9 @@ public abstract class Mob extends Entity {
|
||||
* @param position The position.
|
||||
*/
|
||||
public final void setPosition(Position position) {
|
||||
World.getWorld().submit(new MobPositionUpdateEvent(this, position));
|
||||
// Intentionally ignore the Event result - accidentally terminating this method would break the entire server.
|
||||
|
||||
Position old = this.position;
|
||||
SectorRepository repository = World.getWorld().getSectorRepository();
|
||||
Sector current = repository.fromPosition(old);
|
||||
|
||||
@@ -19,6 +19,9 @@ import org.apollo.game.model.Appearance;
|
||||
import org.apollo.game.model.Position;
|
||||
import org.apollo.game.model.World;
|
||||
import org.apollo.game.model.area.Sector;
|
||||
import org.apollo.game.model.entity.setting.PrivacyState;
|
||||
import org.apollo.game.model.entity.setting.PrivilegeLevel;
|
||||
import org.apollo.game.model.entity.setting.ScreenBrightness;
|
||||
import org.apollo.game.model.event.impl.LoginEvent;
|
||||
import org.apollo.game.model.event.impl.LogoutEvent;
|
||||
import org.apollo.game.model.inter.InterfaceConstants;
|
||||
@@ -33,9 +36,6 @@ import org.apollo.game.model.inv.Inventory.StackMode;
|
||||
import org.apollo.game.model.inv.InventoryConstants;
|
||||
import org.apollo.game.model.inv.InventoryListener;
|
||||
import org.apollo.game.model.inv.SynchronizationInventoryListener;
|
||||
import org.apollo.game.model.setting.PrivacyState;
|
||||
import org.apollo.game.model.setting.PrivilegeLevel;
|
||||
import org.apollo.game.model.setting.ScreenBrightness;
|
||||
import org.apollo.game.model.skill.LevelUpSkillListener;
|
||||
import org.apollo.game.model.skill.SynchronizationSkillListener;
|
||||
import org.apollo.game.sync.block.SynchronizationBlock;
|
||||
|
||||
+1
-1
@@ -1,4 +1,4 @@
|
||||
package org.apollo.game.model.setting;
|
||||
package org.apollo.game.model.entity.setting;
|
||||
|
||||
/**
|
||||
* An enumeration containing the two genders (male and female). This enumeration relies on the ordering of the elements
|
||||
+1
-1
@@ -1,4 +1,4 @@
|
||||
package org.apollo.game.model.setting;
|
||||
package org.apollo.game.model.entity.setting;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
|
||||
+1
-1
@@ -1,4 +1,4 @@
|
||||
package org.apollo.game.model.setting;
|
||||
package org.apollo.game.model.entity.setting;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
|
||||
+1
-1
@@ -1,4 +1,4 @@
|
||||
package org.apollo.game.model.setting;
|
||||
package org.apollo.game.model.entity.setting;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
|
||||
+1
-1
@@ -1,4 +1,4 @@
|
||||
package org.apollo.game.model.setting;
|
||||
package org.apollo.game.model.entity.setting;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
|
||||
+1
-1
@@ -1,4 +1,4 @@
|
||||
/**
|
||||
* Contains player setting or customisation-related classes.
|
||||
*/
|
||||
package org.apollo.game.model.setting;
|
||||
package org.apollo.game.model.entity.setting;
|
||||
@@ -0,0 +1,56 @@
|
||||
package org.apollo.game.model.event.impl;
|
||||
|
||||
import org.apollo.game.model.Position;
|
||||
import org.apollo.game.model.entity.Mob;
|
||||
import org.apollo.game.model.event.Event;
|
||||
|
||||
/**
|
||||
* An {@link Event} created when a Mob's Position is being updated.
|
||||
* <p>
|
||||
* This Event intentionally ignores the result of execution - it should not be possible for a plugin to prevent this
|
||||
* Event from happening, only to listen for it.
|
||||
*
|
||||
* @author Major
|
||||
*/
|
||||
public final class MobPositionUpdateEvent extends Event {
|
||||
|
||||
/**
|
||||
* The Mob whose position is being updated.
|
||||
*/
|
||||
private final Mob mob;
|
||||
|
||||
/**
|
||||
* The next Position of the Mob.
|
||||
*/
|
||||
private final Position next;
|
||||
|
||||
/**
|
||||
* Creates the MobPositionUpdateEvent.
|
||||
*
|
||||
* @param mob The {@link Mob} whose Position is being updated.
|
||||
* @param next The next {@link Position} of the Mob.
|
||||
*/
|
||||
public MobPositionUpdateEvent(Mob mob, Position next) {
|
||||
this.mob = mob;
|
||||
this.next = next;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the {@link Mob} being moved.
|
||||
*
|
||||
* @return The Mob.
|
||||
*/
|
||||
public Mob getMob() {
|
||||
return mob;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the {@link Position} this {@link Mob} is being moved to.
|
||||
*
|
||||
* @return The Position.
|
||||
*/
|
||||
public Position getNext() {
|
||||
return next;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -7,6 +7,7 @@ import java.util.Optional;
|
||||
import org.apollo.game.message.impl.CloseInterfaceMessage;
|
||||
import org.apollo.game.message.impl.EnterAmountMessage;
|
||||
import org.apollo.game.message.impl.OpenDialogueInterfaceMessage;
|
||||
import org.apollo.game.message.impl.OpenDialogueOverlayMessage;
|
||||
import org.apollo.game.message.impl.OpenInterfaceMessage;
|
||||
import org.apollo.game.message.impl.OpenInterfaceSidebarMessage;
|
||||
import org.apollo.game.message.impl.OpenOverlayMessage;
|
||||
@@ -144,10 +145,10 @@ public final class InterfaceSet {
|
||||
}
|
||||
|
||||
/**
|
||||
* Opens a chat box dialogue.
|
||||
* Opens a dialogue interface.
|
||||
*
|
||||
* @param listener The listener for the dialogue.
|
||||
* @param dialogueId The dialogue's id.
|
||||
* @param listener The {@link DialogueListener}.
|
||||
* @param dialogueId The dialogue id.
|
||||
*/
|
||||
public void openDialogue(DialogueListener listener, int dialogueId) {
|
||||
closeAndNotify();
|
||||
@@ -160,14 +161,39 @@ public final class InterfaceSet {
|
||||
}
|
||||
|
||||
/**
|
||||
* Opens a chat box dialogue.
|
||||
* Opens a dialogue.
|
||||
*
|
||||
* @param dialogueId The dialogue's id.
|
||||
* @param dialogueId The dialogue id.
|
||||
*/
|
||||
public void openDialogue(int dialogueId) {
|
||||
openDialogue(null, dialogueId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Opens a dialogue overlay interface.
|
||||
*
|
||||
* @param listener The {@link DialogueListener}.
|
||||
* @param dialogueId The dialogue id.
|
||||
*/
|
||||
public void openDialogueOverlay(DialogueListener listener, int dialogueId) {
|
||||
closeAndNotify();
|
||||
|
||||
this.dialogueListener = Optional.ofNullable(listener);
|
||||
this.listener = Optional.ofNullable(listener);
|
||||
|
||||
interfaces.put(InterfaceType.DIALOGUE, dialogueId);
|
||||
player.send(new OpenDialogueOverlayMessage(dialogueId));
|
||||
}
|
||||
|
||||
/**
|
||||
* Opens a dialogue overlay.
|
||||
*
|
||||
* @param dialogueId The dialogue id.
|
||||
*/
|
||||
public void openDialogueOverlay(int dialogueId) {
|
||||
openDialogueOverlay(null, dialogueId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Opens the enter amount dialogue.
|
||||
*
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
package org.apollo.game.sync.block;
|
||||
|
||||
import org.apollo.game.message.impl.ChatMessage;
|
||||
import org.apollo.game.model.setting.PrivilegeLevel;
|
||||
import org.apollo.game.model.entity.setting.PrivilegeLevel;
|
||||
|
||||
/**
|
||||
* The chat {@link SynchronizationBlock}. Only players can utilise this block.
|
||||
|
||||
@@ -20,11 +20,11 @@ import org.apollo.game.model.entity.attr.AttributeType;
|
||||
import org.apollo.game.model.entity.attr.BooleanAttribute;
|
||||
import org.apollo.game.model.entity.attr.NumericalAttribute;
|
||||
import org.apollo.game.model.entity.attr.StringAttribute;
|
||||
import org.apollo.game.model.entity.setting.Gender;
|
||||
import org.apollo.game.model.entity.setting.PrivacyState;
|
||||
import org.apollo.game.model.entity.setting.PrivilegeLevel;
|
||||
import org.apollo.game.model.entity.setting.ScreenBrightness;
|
||||
import org.apollo.game.model.inv.Inventory;
|
||||
import org.apollo.game.model.setting.Gender;
|
||||
import org.apollo.game.model.setting.PrivacyState;
|
||||
import org.apollo.game.model.setting.PrivilegeLevel;
|
||||
import org.apollo.game.model.setting.ScreenBrightness;
|
||||
import org.apollo.io.player.PlayerLoader;
|
||||
import org.apollo.io.player.PlayerLoaderResponse;
|
||||
import org.apollo.net.codec.login.LoginConstants;
|
||||
|
||||
@@ -2,7 +2,7 @@ package org.apollo.io.player.impl;
|
||||
|
||||
import org.apollo.game.model.Position;
|
||||
import org.apollo.game.model.entity.Player;
|
||||
import org.apollo.game.model.setting.PrivilegeLevel;
|
||||
import org.apollo.game.model.entity.setting.PrivilegeLevel;
|
||||
import org.apollo.io.player.PlayerLoader;
|
||||
import org.apollo.io.player.PlayerLoaderResponse;
|
||||
import org.apollo.net.codec.login.LoginConstants;
|
||||
|
||||
@@ -5,6 +5,8 @@ import io.netty.channel.ChannelHandler.Sharable;
|
||||
import io.netty.channel.ChannelHandlerContext;
|
||||
import io.netty.channel.ChannelInboundHandlerAdapter;
|
||||
import io.netty.handler.codec.http.HttpRequest;
|
||||
import io.netty.util.Attribute;
|
||||
import io.netty.util.ReferenceCountUtil;
|
||||
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
@@ -65,25 +67,36 @@ public final class ApolloHandler extends ChannelInboundHandlerAdapter {
|
||||
|
||||
@Override
|
||||
public void channelRead(ChannelHandlerContext ctx, Object message) {
|
||||
if (ctx.attr(NetworkConstants.SESSION_KEY).get() == null) {
|
||||
try {
|
||||
Attribute<Session> attribute = ctx.attr(NetworkConstants.SESSION_KEY);
|
||||
Session session = attribute.get();
|
||||
|
||||
if (message instanceof HttpRequest || message instanceof JagGrabRequest) {
|
||||
new UpdateSession(ctx.channel(), serverContext).messageReceived(message);
|
||||
} else {
|
||||
session = new UpdateSession(ctx.channel(), serverContext);
|
||||
}
|
||||
|
||||
if (session != null) {
|
||||
session.messageReceived(message);
|
||||
return;
|
||||
}
|
||||
|
||||
// TODO: Perhaps let HandshakeMessage implement Message to remove this explicit check
|
||||
if (message instanceof HandshakeMessage) {
|
||||
HandshakeMessage handshakeMessage = (HandshakeMessage) message;
|
||||
|
||||
switch (handshakeMessage.getServiceId()) {
|
||||
case HandshakeConstants.SERVICE_GAME:
|
||||
ctx.attr(NetworkConstants.SESSION_KEY).set(new LoginSession(ctx, serverContext));
|
||||
attribute.set(new LoginSession(ctx, serverContext));
|
||||
break;
|
||||
|
||||
case HandshakeConstants.SERVICE_UPDATE:
|
||||
ctx.attr(NetworkConstants.SESSION_KEY).set(new UpdateSession(ctx.channel(), serverContext));
|
||||
attribute.set(new UpdateSession(ctx.channel(), serverContext));
|
||||
break;
|
||||
default:
|
||||
throw new IllegalStateException("Invalid service id.");
|
||||
}
|
||||
}
|
||||
} else {
|
||||
ctx.attr(NetworkConstants.SESSION_KEY).get().messageReceived(message);
|
||||
|
||||
} finally {
|
||||
ReferenceCountUtil.release(message);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -5,6 +5,7 @@ import io.netty.channel.ChannelHandlerContext;
|
||||
import io.netty.handler.codec.ByteToMessageDecoder;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
import org.apollo.net.codec.login.LoginDecoder;
|
||||
import org.apollo.net.codec.login.LoginEncoder;
|
||||
@@ -19,35 +20,41 @@ import org.apollo.net.codec.update.UpdateEncoder;
|
||||
*/
|
||||
public final class HandshakeDecoder extends ByteToMessageDecoder {
|
||||
|
||||
/**
|
||||
* The logger for this class.
|
||||
*/
|
||||
private static final Logger logger = Logger.getLogger(HandshakeDecoder.class.getName());
|
||||
|
||||
@Override
|
||||
protected void decode(ChannelHandlerContext ctx, ByteBuf buffer, List<Object> out) {
|
||||
if (buffer.isReadable()) {
|
||||
int id = buffer.readUnsignedByte();
|
||||
|
||||
switch (id) {
|
||||
case HandshakeConstants.SERVICE_GAME:
|
||||
ctx.pipeline().addFirst("loginEncoder", new LoginEncoder());
|
||||
ctx.pipeline().addAfter("handshakeDecoder", "loginDecoder", new LoginDecoder());
|
||||
break;
|
||||
case HandshakeConstants.SERVICE_UPDATE:
|
||||
ctx.pipeline().addFirst("updateEncoder", new UpdateEncoder());
|
||||
ctx.pipeline().addBefore("handler", "updateDecoder", new UpdateDecoder());
|
||||
ByteBuf buf = ctx.alloc().buffer(8);
|
||||
buf.writeLong(0);
|
||||
ctx.channel().writeAndFlush(buf);
|
||||
break;
|
||||
default:
|
||||
throw new IllegalArgumentException("Invalid service id.");
|
||||
}
|
||||
|
||||
ctx.pipeline().remove(this);
|
||||
HandshakeMessage message = new HandshakeMessage(id);
|
||||
|
||||
out.add(message);
|
||||
if (buffer.isReadable()) {
|
||||
out.add(buffer.readBytes(buffer.readableBytes()));
|
||||
}
|
||||
if (!buffer.isReadable()) {
|
||||
return;
|
||||
}
|
||||
|
||||
int id = buffer.readUnsignedByte();
|
||||
|
||||
switch (id) {
|
||||
case HandshakeConstants.SERVICE_GAME:
|
||||
ctx.pipeline().addFirst("loginEncoder", new LoginEncoder());
|
||||
ctx.pipeline().addAfter("handshakeDecoder", "loginDecoder", new LoginDecoder());
|
||||
break;
|
||||
|
||||
case HandshakeConstants.SERVICE_UPDATE:
|
||||
ctx.pipeline().addFirst("updateEncoder", new UpdateEncoder());
|
||||
ctx.pipeline().addBefore("handler", "updateDecoder", new UpdateDecoder());
|
||||
|
||||
ByteBuf buf = ctx.alloc().buffer(8).writeLong(0);
|
||||
ctx.channel().writeAndFlush(buf);
|
||||
break;
|
||||
|
||||
default:
|
||||
ByteBuf data = buffer.readBytes(buffer.readableBytes());
|
||||
logger.info(String.format("Unexpected handshake request received: %d data: %s", id, data.toString()));
|
||||
return;
|
||||
}
|
||||
|
||||
ctx.pipeline().remove(this);
|
||||
out.add(new HandshakeMessage(id));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
package org.apollo.net.release.r317;
|
||||
|
||||
import org.apollo.game.message.impl.OpenDialogueOverlayMessage;
|
||||
import org.apollo.net.codec.game.DataOrder;
|
||||
import org.apollo.net.codec.game.DataTransformation;
|
||||
import org.apollo.net.codec.game.DataType;
|
||||
import org.apollo.net.codec.game.GamePacket;
|
||||
import org.apollo.net.codec.game.GamePacketBuilder;
|
||||
import org.apollo.net.release.MessageEncoder;
|
||||
|
||||
/**
|
||||
* A {@link MessageEncoder} for the {@link OpenDialogueOverlayMessage}.
|
||||
*
|
||||
* @author Major
|
||||
*/
|
||||
public final class OpenDialogueOverlayMessageEncoder extends MessageEncoder<OpenDialogueOverlayMessage> {
|
||||
|
||||
@Override
|
||||
public GamePacket encode(OpenDialogueOverlayMessage message) {
|
||||
GamePacketBuilder builder = new GamePacketBuilder(218);
|
||||
builder.put(DataType.SHORT, DataOrder.LITTLE, DataTransformation.ADD, message.getInterfaceId());
|
||||
return builder.toGamePacket();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -2,7 +2,7 @@ package org.apollo.net.release.r317;
|
||||
|
||||
import org.apollo.game.message.impl.PlayerDesignMessage;
|
||||
import org.apollo.game.model.Appearance;
|
||||
import org.apollo.game.model.setting.Gender;
|
||||
import org.apollo.game.model.entity.setting.Gender;
|
||||
import org.apollo.net.codec.game.DataType;
|
||||
import org.apollo.net.codec.game.GamePacket;
|
||||
import org.apollo.net.codec.game.GamePacketReader;
|
||||
|
||||
@@ -9,8 +9,8 @@ import org.apollo.game.model.Item;
|
||||
import org.apollo.game.model.Position;
|
||||
import org.apollo.game.model.def.EquipmentDefinition;
|
||||
import org.apollo.game.model.entity.EquipmentConstants;
|
||||
import org.apollo.game.model.entity.setting.Gender;
|
||||
import org.apollo.game.model.inv.Inventory;
|
||||
import org.apollo.game.model.setting.Gender;
|
||||
import org.apollo.game.sync.block.AnimationBlock;
|
||||
import org.apollo.game.sync.block.AppearanceBlock;
|
||||
import org.apollo.game.sync.block.ChatBlock;
|
||||
|
||||
@@ -16,6 +16,7 @@ import org.apollo.game.message.impl.IgnoreListMessage;
|
||||
import org.apollo.game.message.impl.LogoutMessage;
|
||||
import org.apollo.game.message.impl.NpcSynchronizationMessage;
|
||||
import org.apollo.game.message.impl.OpenDialogueInterfaceMessage;
|
||||
import org.apollo.game.message.impl.OpenDialogueOverlayMessage;
|
||||
import org.apollo.game.message.impl.OpenInterfaceMessage;
|
||||
import org.apollo.game.message.impl.OpenInterfaceSidebarMessage;
|
||||
import org.apollo.game.message.impl.OpenOverlayMessage;
|
||||
@@ -214,5 +215,7 @@ public final class Release317 extends Release {
|
||||
register(FlashTabInterfaceMessage.class, new FlashTabInterfaceMessageEncoder());
|
||||
register(OpenSidebarMessage.class, new OpenSidebarMessageEncoder());
|
||||
register(OpenOverlayMessage.class, new OpenOverlayMessageEncoder());
|
||||
register(OpenDialogueOverlayMessage.class, new OpenDialogueOverlayMessageEncoder());
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,24 @@
|
||||
package org.apollo.net.release.r377;
|
||||
|
||||
import org.apollo.game.message.impl.OpenDialogueOverlayMessage;
|
||||
import org.apollo.net.codec.game.DataOrder;
|
||||
import org.apollo.net.codec.game.DataType;
|
||||
import org.apollo.net.codec.game.GamePacket;
|
||||
import org.apollo.net.codec.game.GamePacketBuilder;
|
||||
import org.apollo.net.release.MessageEncoder;
|
||||
|
||||
/**
|
||||
* A {@link MessageEncoder} for the {@link OpenDialogueOverlayMessage}.
|
||||
*
|
||||
* @author Major
|
||||
*/
|
||||
public final class OpenDialogueOverlayMessageEncoder extends MessageEncoder<OpenDialogueOverlayMessage> {
|
||||
|
||||
@Override
|
||||
public GamePacket encode(OpenDialogueOverlayMessage message) {
|
||||
GamePacketBuilder builder = new GamePacketBuilder(158);
|
||||
builder.put(DataType.SHORT, DataOrder.LITTLE, message.getInterfaceId());
|
||||
return builder.toGamePacket();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -2,7 +2,7 @@ package org.apollo.net.release.r377;
|
||||
|
||||
import org.apollo.game.message.impl.PlayerDesignMessage;
|
||||
import org.apollo.game.model.Appearance;
|
||||
import org.apollo.game.model.setting.Gender;
|
||||
import org.apollo.game.model.entity.setting.Gender;
|
||||
import org.apollo.net.codec.game.DataType;
|
||||
import org.apollo.net.codec.game.GamePacket;
|
||||
import org.apollo.net.codec.game.GamePacketReader;
|
||||
|
||||
@@ -9,8 +9,8 @@ import org.apollo.game.model.Item;
|
||||
import org.apollo.game.model.Position;
|
||||
import org.apollo.game.model.def.EquipmentDefinition;
|
||||
import org.apollo.game.model.entity.EquipmentConstants;
|
||||
import org.apollo.game.model.entity.setting.Gender;
|
||||
import org.apollo.game.model.inv.Inventory;
|
||||
import org.apollo.game.model.setting.Gender;
|
||||
import org.apollo.game.sync.block.AnimationBlock;
|
||||
import org.apollo.game.sync.block.AppearanceBlock;
|
||||
import org.apollo.game.sync.block.ChatBlock;
|
||||
|
||||
@@ -16,6 +16,7 @@ import org.apollo.game.message.impl.IgnoreListMessage;
|
||||
import org.apollo.game.message.impl.LogoutMessage;
|
||||
import org.apollo.game.message.impl.NpcSynchronizationMessage;
|
||||
import org.apollo.game.message.impl.OpenDialogueInterfaceMessage;
|
||||
import org.apollo.game.message.impl.OpenDialogueOverlayMessage;
|
||||
import org.apollo.game.message.impl.OpenInterfaceMessage;
|
||||
import org.apollo.game.message.impl.OpenInterfaceSidebarMessage;
|
||||
import org.apollo.game.message.impl.OpenOverlayMessage;
|
||||
@@ -210,6 +211,7 @@ public final class Release377 extends Release {
|
||||
register(FlashTabInterfaceMessage.class, new FlashTabInterfaceMessageEncoder());
|
||||
register(OpenSidebarMessage.class, new OpenSidebarMessageEncoder());
|
||||
register(OpenOverlayMessage.class, new OpenOverlayMessageEncoder());
|
||||
register(OpenDialogueOverlayMessage.class, new OpenDialogueOverlayMessageEncoder());
|
||||
}
|
||||
|
||||
}
|
||||
@@ -131,7 +131,7 @@ public final class LoginSession extends Session {
|
||||
future.addListener(ChannelFutureListener.CLOSE);
|
||||
}
|
||||
|
||||
if (optional.isPresent()) {
|
||||
if (optional.isPresent() && request.isReconnecting()) {
|
||||
optional.get().sendInitialMessages();
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user