Server/Management-Server/src/main/java/ms/system/communication/CommunicationInfo.java
2021-07-26 07:33:07 -05:00

658 lines
No EOL
18 KiB
Java

package ms.system.communication;
import ms.ServerConstants;
import ms.net.packet.WorldPacketRepository;
import ms.system.util.ByteBufferUtils;
import ms.system.util.StringUtils;
import ms.world.GameServer;
import ms.world.PlayerSession;
import ms.world.WorldDatabase;
import java.nio.ByteBuffer;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
/**
* Holds communication information.
* @author Emperor
*
*/
public final class CommunicationInfo {
/**
* The maximum list size.
*/
public static final int MAX_LIST_SIZE = 200;
/**
* The clan ranks.
*/
private final Map<String, ClanRank> contacts = new HashMap<>();
/**
* The list of blocked players.
*/
private final List<String> blocked = new ArrayList<>(20);
/**
* The player's clan name.
*/
private String clanName = "";
/**
* The current clan this player is in.
*/
private String currentClan = "2009scape";
/**
* The rank required for joining.
*/
private ClanRank joinRequirement = ClanRank.FRIEND;
/**
* The rank required for messaging.
*/
private ClanRank messageRequirement = ClanRank.NONE;
/**
* The rank required for kicking members.
*/
private ClanRank kickRequirement = ClanRank.OWNER;
/**
* The rank required for loot-share.
*/
private ClanRank lootRequirement = ClanRank.ADMINISTRATOR;
/**
* The public chat setting.
*/
private int publicChatSetting = 0;
/**
* The private chat setting.
*/
private int privateChatSetting = 0;
/**
* The trade setting.
*/
private int tradeSetting = 0;
/**
* The player session.
*/
private PlayerSession player;
/**
* Constructs a new {@code CommunicationInfo} {@code Object}.
* @param player The player.
*/
public CommunicationInfo(PlayerSession player) {
this.setPlayer(player);
}
/**
* Called when the player logs in.
*/
public void sync() {
if (privateChatSetting != 2) {
for (GameServer server : WorldDatabase.getWorlds()) {
if (server != null && server.isActive()) {
List<String> names = new ArrayList<>(20);
for (PlayerSession p : server.getPlayers().values()) {
if (p.isActive() && p.getCommunication().contacts.containsKey(player.getUsername())) {
if (privateChatSetting == 0 || contacts.containsKey(p.getUsername())) {
names.add(p.getUsername());
}
}
}
WorldPacketRepository.notifyPlayers(server, player, names);
}
}
}
}
/**
* Called when the player logs out.
*/
public void clear() {
for (GameServer server : WorldDatabase.getWorlds()) {
if (server != null && server.isActive()) {
WorldPacketRepository.notifyLogout(server, player);
}
}
if (player.getClan() != null) {
player.getClan().leave(player, true);
}
}
/**
* Saves the communication info.
* @param statement The buffer.
* @throws SQLException The exception if thrown.
*/
public void save(PreparedStatement statement) throws SQLException {
String contacts = "";
String blocked = "";
StringBuilder blockedBuilder = new StringBuilder();
for (int i = 0; i < this.blocked.size(); i++) {
String blockline = (i == 0 ? "" : ",") + this.blocked.get(i);
blockedBuilder.append(blockline);
}
blocked = blockedBuilder.toString();
int count = 0;
StringBuilder contactBuilder = new StringBuilder();
for (Entry<String, ClanRank> entry : this.contacts.entrySet()) {
String contactLine = "{" + entry.getKey() + "," + entry.getValue().ordinal() + "}" + (count == this.contacts.size() - 1 ? "" : "~");
contactBuilder.append(contactLine);
count++;
}
contacts = contactBuilder.toString();
statement.setString(3, contacts);
statement.setString(4, blocked);
statement.setString(5, clanName);
statement.setString(6, currentClan);
statement.setString(7, joinRequirement.ordinal() + "," + messageRequirement.ordinal() + "," + kickRequirement.ordinal() + "," + lootRequirement.ordinal());
statement.setString(8, publicChatSetting + "," + privateChatSetting + "," + tradeSetting);
}
/**
* Parses the communication info from the database.
* @param set The result set.
* @throws SQLException The exception if thrown.
*/
public void parse(ResultSet set) throws SQLException {
String contacts = set.getString("contacts");
String[] tokens;
if (contacts != null && !contacts.isEmpty()) {
String[] datas = contacts.split("~");
for (String d : datas) {
tokens = d.replace("{", "").replace("}", "").split(",");
if (tokens.length < 2) {
continue;
}
this.contacts.put(tokens[0], ClanRank.values()[Integer.parseInt(tokens[1])]);
}
}
String bl = set.getString("blocked");
if (bl != null && !bl.isEmpty()) {
tokens = bl.split(",");
for (String name : tokens) {
blocked.add(name);
}
}
clanName = set.getString("clanName");
currentClan = set.getString("currentClan");
String clanReqs = set.getString("clanReqs");
if (!clanReqs.isEmpty()) {
tokens = clanReqs.split(",");
ClanRank rank = null;
int ordinal = 0;
for (int i = 0; i < tokens.length; i++) {
ordinal = Integer.parseInt(tokens[i]);
if (ordinal < 0 || ordinal > ClanRank.values().length -1) {
continue;
}
rank = ClanRank.values()[ordinal];
switch (i) {
case 0:
joinRequirement = rank;
break;
case 1:
messageRequirement = rank;
break;
case 2:
if (ordinal < 3 || ordinal > 8) {
break;
}
kickRequirement = rank;
break;
case 3:
lootRequirement = rank;
break;
default:
break;
}
}
}
String chatSettings = set.getString("chatSettings");
if (!chatSettings.isEmpty()) {
tokens = chatSettings.split(",");
for (int i = 0; i < tokens.length; i++) {
switch (i) {
case 0:
publicChatSetting = Integer.parseInt(tokens[0]);
break;
case 1:
privateChatSetting = Integer.parseInt(tokens[1]);
break;
case 2:
tradeSetting = Integer.parseInt(tokens[2]);
break;
}
}
}
}
/**
* Saves the communication info.
* @param buffer The buffer.
*/
public void save(ByteBuffer buffer) {
buffer.put((byte) contacts.size());
for(Entry<String,ClanRank> contact : contacts.entrySet()){
ByteBufferUtils.putString(contact.getKey(), buffer);
buffer.put((byte) contact.getValue().ordinal());
}
buffer.put((byte) blocked.size());
for (String name : blocked) {
ByteBufferUtils.putString(name, buffer);
}
ByteBufferUtils.putString(clanName, buffer);
if (currentClan != null) {
ByteBufferUtils.putString(currentClan, buffer.put((byte) 1));
} else {
buffer.put((byte) 0);
}
buffer.put((byte) joinRequirement.ordinal());
buffer.put((byte) messageRequirement.ordinal());
buffer.put((byte) kickRequirement.ordinal());
buffer.put((byte) lootRequirement.ordinal());
buffer.put((byte) publicChatSetting);
buffer.put((byte) privateChatSetting);
buffer.put((byte) tradeSetting);
}
/**
* Parses the communication info from the buffer.
* @param buffer The buffer.
*/
public void parse(ByteBuffer buffer) {
int length = buffer.get() & 0xFF;
for (int i = 0; i < length; i++) {
contacts.put(ByteBufferUtils.getString(buffer), ClanRank.values()[buffer.get() & 0xFF]);
}
length = buffer.get() & 0xFF;
for (int i = 0; i < length; i++) {
blocked.add(ByteBufferUtils.getString(buffer));
}
clanName = ByteBufferUtils.getString(buffer);
if (buffer.get() == 1) {
currentClan = ByteBufferUtils.getString(buffer);
}
joinRequirement = ClanRank.values()[buffer.get()];
messageRequirement = ClanRank.values()[buffer.get()];
kickRequirement = ClanRank.values()[buffer.get()];
lootRequirement = ClanRank.values()[buffer.get()];
publicChatSetting = buffer.get();
privateChatSetting = buffer.get();
tradeSetting = buffer.get();
}
/**
* Sends a message to the target.
* @param target The target.
* @param message The message to send.
*/
public void sendMessage(String target, String message) {
PlayerSession receiver = WorldDatabase.getPlayer(target);
if (receiver == null || !receiver.isActive()) {
WorldPacketRepository.sendPlayerMessage(player, "That player is currently offline.");
return;
}
WorldPacketRepository.sendMessage(player, receiver, 0, message);
WorldPacketRepository.sendMessage(receiver, player, 1, message);
}
/**
* Adds a contact.
* @param contact The contact to add.
*/
public void add(String contact) {
if (contacts.size() >= MAX_LIST_SIZE) {
WorldPacketRepository.sendPlayerMessage(player, "Your friend list is full.");
return;
}
if (blocked.contains(contact)) {
WorldPacketRepository.sendPlayerMessage(player, "Please remove " + StringUtils.formatDisplayName(contact) + " from your ignored list first.");
return;
}
if (contacts.containsKey(contact)) {
WorldPacketRepository.sendPlayerMessage(player, StringUtils.formatDisplayName(contact) + " is already on your friend list.");
return;
}
contacts.put(contact, ClanRank.FRIEND);
WorldPacketRepository.sendContactUpdate(player, contact, false, false, getWorldId(player, contact), null);
ClanRepository clan = ClanRepository.getClans().get(player.getUsername());
if (clan != null) {
clan.update();
}
if (privateChatSetting == 1) {
PlayerSession other = WorldDatabase.getPlayer(contact);
if (other != null && other.isActive() && other.getCommunication().getContacts().containsKey(player.getUsername())) {
WorldPacketRepository.sendContactUpdate(other, player.getUsername(), false, false, getWorldId(other, player.getUsername()), null);
}
}
}
/**
* Gets the world id for the given contact.
* @param player The player.
* @param contact The contact.
* @return The world id to display.
*/
public static int getWorldId(PlayerSession player, String contact) {
PlayerSession p = WorldDatabase.getPlayer(contact);
if (p == null || !p.isActive() || p.getCommunication().getPrivateChatSetting() == 2) {
return 0;
}
if (p.getCommunication().getBlocked().contains(player.getUsername())) {
return 0;
}
if (p.getCommunication().getPrivateChatSetting() == 1) {
if (p.getCommunication().getContacts().containsKey(player.getUsername())) {
return p.getWorldId();
}
return 0;
}
return p.getWorldId();
}
/**
* Removes a contact.
* @param contact The contact to remove.
* @param block If the contact should be removed from the block list.
*/
public void remove(String contact, boolean block) {
PlayerSession other = WorldDatabase.getPlayer(contact);
if (block) {
blocked.remove(contact);
if (other != null && other.isActive() && other.getCommunication().getContacts().containsKey(player.getUsername())) {
WorldPacketRepository.sendContactUpdate(other, player.getUsername(), false, false, getWorldId(other, player.getUsername()), null);
}
} else {
contacts.remove(contact);
ClanRepository clan = ClanRepository.getClans().get(player.getUsername());
if (clan != null) {
clan.update();
}
if (privateChatSetting == 1 && other != null && other.isActive() && other.getCommunication().getContacts().containsKey(player.getUsername())) {
WorldPacketRepository.sendContactUpdate(other, player.getUsername(), false, false, getWorldId(other, player.getUsername()), null);
}
}
WorldPacketRepository.sendContactUpdate(player, contact, block, true, 0, null);
}
/**
* Adds a blocked contact.
* @param contact The contact to block.
*/
public void block(String contact) {
if (blocked.size() >= MAX_LIST_SIZE) {
WorldPacketRepository.sendPlayerMessage(player, "Your ignore list is full.");
return;
}
if (contacts.containsKey(contact)) {
WorldPacketRepository.sendPlayerMessage(player, "Please remove " + StringUtils.formatDisplayName(contact) + " from your friends list first.");
return;
}
if (blocked.contains(contact)) {
WorldPacketRepository.sendPlayerMessage(player, StringUtils.formatDisplayName(contact) + " is already on your friend list.");
return;
}
blocked.add(contact);
WorldPacketRepository.sendContactUpdate(player, contact, true, false, 0, null);
PlayerSession other = WorldDatabase.getPlayer(contact);
if (other != null && other.isActive() && other.getCommunication().getContacts().containsKey(player.getUsername())) {
WorldPacketRepository.sendContactUpdate(other, player.getUsername(), false, false, 0, null);
}
}
/**
* Updates the clan rank of a certain contact.
* @param contact The contact.
* @param clanRank The clan rank to set.
*/
public void updateClanRank(String contact, ClanRank clanRank) {
if (!contacts.containsKey(contact)) {
System.err.println("Could not find contact " + contact + " to update clan rank!");
return;
}
contacts.put(contact, clanRank);
ClanRepository clan = ClanRepository.getClans().get(player.getUsername());
if (clan != null) {
clan.update();
}
WorldPacketRepository.sendContactUpdate(player, contact, false, false, 0, clanRank);
}
/**
* Updates the settings.
* @param publicSetting The public chat setting.
* @param privateSetting The private chat setting.
* @param tradeSetting The trade setting.
*/
public void updateSettings(int publicSetting, int privateSetting, int tradeSetting) {
this.publicChatSetting = publicSetting;
this.tradeSetting = tradeSetting;
if (this.privateChatSetting != privateSetting) {
updatePrivateSetting(privateSetting);
}
}
/**
* Updates the private chat setting.
* @param privateSetting The private chat setting.
*/
private void updatePrivateSetting(int privateSetting) {
this.privateChatSetting = privateSetting;
for (GameServer server : WorldDatabase.getWorlds()) {
if (server != null && server.isActive()) {
if (privateSetting == 2) {
WorldPacketRepository.notifyLogout(server, player);
continue;
}
for (PlayerSession p : server.getPlayers().values()) {
if (p.isActive() && p.getCommunication().contacts.containsKey(player.getUsername())) {
WorldPacketRepository.sendContactUpdate(p, player.getUsername(), false, false, getWorldId(p, player.getUsername()), null);
}
}
}
}
}
/**
* Gets the contacts value.
* @return The contacts.
*/
public Map<String, ClanRank> getContacts() {
return contacts;
}
/**
* Gets the clan rank for the given contact.
* @param contact The contact.
* @return The rank.
*/
public ClanRank getRank(String contact) {
return contacts.get(contact);
}
/**
* Gets the blocked value.
* @return The blocked.
*/
public List<String> getBlocked() {
return blocked;
}
/**
* Gets the clanName value.
* @return The clanName.
*/
public String getClanName() {
return clanName;
}
/**
* Sets the clanName value.
* @param clanName The clanName to set.
*/
public void setClanName(String clanName) {
this.clanName = clanName;
}
/**
* Gets the currentClan value.
* @return The currentClan.
*/
public String getCurrentClan() {
return currentClan;
}
/**
* Sets the currentClan value.
* @param currentClan The currentClan to set.
*/
public void setCurrentClan(String currentClan) {
this.currentClan = currentClan;
}
/**
* Gets the player value.
* @return The player.
*/
public PlayerSession getPlayer() {
return player;
}
/**
* Sets the player value.
* @param player The player to set.
*/
public void setPlayer(PlayerSession player) {
this.player = player;
}
/**
* Gets the joinRequirement value.
* @return The joinRequirement.
*/
public ClanRank getJoinRequirement() {
return joinRequirement;
}
/**
* Sets the joinRequirement value.
* @param joinRequirement The joinRequirement to set.
*/
public void setJoinRequirement(ClanRank joinRequirement) {
this.joinRequirement = joinRequirement;
}
/**
* Gets the messageRequirement value.
* @return The messageRequirement.
*/
public ClanRank getMessageRequirement() {
return messageRequirement;
}
/**
* Sets the messageRequirement value.
* @param messageRequirement The messageRequirement to set.
*/
public void setMessageRequirement(ClanRank messageRequirement) {
this.messageRequirement = messageRequirement;
}
/**
* Gets the kickRequirement value.
* @return The kickRequirement.
*/
public ClanRank getKickRequirement() {
return kickRequirement;
}
/**
* Sets the kickRequirement value.
* @param kickRequirement The kickRequirement to set.
*/
public void setKickRequirement(ClanRank kickRequirement) {
this.kickRequirement = kickRequirement;
}
/**
* Gets the lootRequirement value.
* @return The lootRequirement.
*/
public ClanRank getLootRequirement() {
return lootRequirement;
}
/**
* Sets the lootRequirement value.
* @param lootRequirement The lootRequirement to set.
*/
public void setLootRequirement(ClanRank lootRequirement) {
this.lootRequirement = lootRequirement;
}
/**
* Gets the publicChatSetting value.
* @return The publicChatSetting.
*/
public int getPublicChatSetting() {
return publicChatSetting;
}
/**
* Sets the publicChatSetting value.
* @param publicChatSetting The publicChatSetting to set.
*/
public void setPublicChatSetting(int publicChatSetting) {
this.publicChatSetting = publicChatSetting;
}
/**
* Gets the privateChatSetting value.
* @return The privateChatSetting.
*/
public int getPrivateChatSetting() {
return privateChatSetting;
}
/**
* Sets the privateChatSetting value.
* @param privateChatSetting The privateChatSetting to set.
*/
public void setPrivateChatSetting(int privateChatSetting) {
this.privateChatSetting = privateChatSetting;
}
/**
* Gets the tradeSetting value.
* @return The tradeSetting.
*/
public int getTradeSetting() {
return tradeSetting;
}
/**
* Sets the tradeSetting value.
* @param tradeSetting The tradeSetting to set.
*/
public void setTradeSetting(int tradeSetting) {
this.tradeSetting = tradeSetting;
}
}