Chimaera Wing exploit fix

This commit is contained in:
nossr50 2019-01-10 23:52:11 -08:00
parent 00a14ccb17
commit 626890ed95
7 changed files with 69 additions and 13 deletions

View File

@ -25,6 +25,7 @@ Version 2.1.0
+ (API) Added many missing SubSkills to SubSkillType class + (API) Added many missing SubSkills to SubSkillType class
+ (Permissions) Added permission node mcmmo.commands.mcchatspy & mcmmo.commands.mcchatspy.others + (Permissions) Added permission node mcmmo.commands.mcchatspy & mcmmo.commands.mcchatspy.others
+ (Permissions) Added permission nodes for Harvest Lumber, Splinter, Nature's Bounty, and Bark Surgeon + (Permissions) Added permission nodes for Harvest Lumber, Splinter, Nature's Bounty, and Bark Surgeon
+ (Permissions) Added mcmmo.commands.mmoinfo for the new mmoinfo/mcinfo command
+ (Locale) Added locale strings for new Woodcutting abilities + (Locale) Added locale strings for new Woodcutting abilities
+ (Locale) Added locale strings for mcchatspy command + (Locale) Added locale strings for mcchatspy command
+ (Locale) Added locale strings for JSON integration + (Locale) Added locale strings for JSON integration
@ -33,6 +34,7 @@ Version 2.1.0
- (Locale) Removed localizations with the following codes for being almost empty: id, HR_hr, et_EE, lv, lt, no, pl_PL, pt_PT, tr_TR - (Locale) Removed localizations with the following codes for being almost empty: id, HR_hr, et_EE, lv, lt, no, pl_PL, pt_PT, tr_TR
- (Config) Removed SkillShot's IncreaseLevel & IncreasePercentage (replaced by RankDamageMultiplier) - (Config) Removed SkillShot's IncreaseLevel & IncreasePercentage (replaced by RankDamageMultiplier)
- (Config) Removed AxeMastery's MaxBonus & MaxBonusLevel (replaced by RankDamageMultiplier) - (Config) Removed AxeMastery's MaxBonus & MaxBonusLevel (replaced by RankDamageMultiplier)
= (Items) Chimaera Wing now tracks cooldowns between sessions for players (no more disconnect abuse)
= (Skills) Added missing mushroom blocks to experience.yml defaults = (Skills) Added missing mushroom blocks to experience.yml defaults
= (Skills) Tridents will no longer be considered unarmed = (Skills) Tridents will no longer be considered unarmed
= (MySQL) You can now inspect offline players = (MySQL) You can now inspect offline players
@ -51,7 +53,6 @@ Version 2.1.0
! (Config) Axes.CriticalHit in advanced.yml is now Axes.CriticalStrikes ! (Config) Axes.CriticalHit in advanced.yml is now Axes.CriticalStrikes
! (Config) Archery's Skill Shot now uses RankDamageMultiplier for its damage bonus calculations ! (Config) Archery's Skill Shot now uses RankDamageMultiplier for its damage bonus calculations
! (Config) Axe's Axe mastery now uses RankDamageMultiplier for its damage bonus calculations ! (Config) Axe's Axe mastery now uses RankDamageMultiplier for its damage bonus calculations
+ (Permissions) Added mcmmo.commands.mmoinfo for the new mmoinfo/mcinfo command
! (Permissions) Replaced the old Double Drop permission node for woodcutting with a new Harvest Lumber permission node ! (Permissions) Replaced the old Double Drop permission node for woodcutting with a new Harvest Lumber permission node
! (Permissions) Fast Food Service permission node renamed to mcmmo.ability.taming.fastfoodservice ! (Permissions) Fast Food Service permission node renamed to mcmmo.ability.taming.fastfoodservice
! (Permissions) Counter Attack permission node renamed to mcmmo.ability.swords.counterattack ! (Permissions) Counter Attack permission node renamed to mcmmo.ability.swords.counterattack

View File

@ -17,6 +17,7 @@ import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.UUID; import java.util.UUID;
import com.gmail.nossr50.datatypes.player.UniqueDataType;
import com.gmail.nossr50.datatypes.skills.PrimarySkill; import com.gmail.nossr50.datatypes.skills.PrimarySkill;
import com.gmail.nossr50.datatypes.skills.SuperAbility; import com.gmail.nossr50.datatypes.skills.SuperAbility;
import org.bukkit.OfflinePlayer; import org.bukkit.OfflinePlayer;
@ -320,6 +321,7 @@ public final class FlatfileDatabaseManager implements DatabaseManager {
writer.append(profile.getSkillXpLevel(PrimarySkill.ALCHEMY)).append(":"); writer.append(profile.getSkillXpLevel(PrimarySkill.ALCHEMY)).append(":");
writer.append(uuid != null ? uuid.toString() : "NULL").append(":"); writer.append(uuid != null ? uuid.toString() : "NULL").append(":");
writer.append(profile.getScoreboardTipsShown()).append(":"); writer.append(profile.getScoreboardTipsShown()).append(":");
writer.append(profile.getUniqueData(UniqueDataType.CHIMAERA_WING_DATS)).append(":");
writer.append("\r\n"); writer.append("\r\n");
} }
} }
@ -1130,6 +1132,7 @@ public final class FlatfileDatabaseManager implements DatabaseManager {
Map<PrimarySkill, Integer> skills = getSkillMapFromLine(character); // Skill levels Map<PrimarySkill, Integer> skills = getSkillMapFromLine(character); // Skill levels
Map<PrimarySkill, Float> skillsXp = new EnumMap<PrimarySkill, Float>(PrimarySkill.class); // Skill & XP Map<PrimarySkill, Float> skillsXp = new EnumMap<PrimarySkill, Float>(PrimarySkill.class); // Skill & XP
Map<SuperAbility, Integer> skillsDATS = new EnumMap<SuperAbility, Integer>(SuperAbility.class); // Ability & Cooldown Map<SuperAbility, Integer> skillsDATS = new EnumMap<SuperAbility, Integer>(SuperAbility.class); // Ability & Cooldown
Map<UniqueDataType, Integer> uniquePlayerDataMap = new EnumMap<UniqueDataType, Integer>(UniqueDataType.class);
MobHealthbarType mobHealthbarType; MobHealthbarType mobHealthbarType;
int scoreboardTipsShown; int scoreboardTipsShown;
@ -1184,7 +1187,14 @@ public final class FlatfileDatabaseManager implements DatabaseManager {
scoreboardTipsShown = 0; scoreboardTipsShown = 0;
} }
return new PlayerProfile(character[USERNAME], uuid, skills, skillsXp, skillsDATS, mobHealthbarType, scoreboardTipsShown); try {
uniquePlayerDataMap.put(UniqueDataType.CHIMAERA_WING_DATS, Integer.valueOf(character[COOLDOWN_CHIMAERA_WING]));
}
catch (Exception e) {
uniquePlayerDataMap.put(UniqueDataType.CHIMAERA_WING_DATS, 0);
}
return new PlayerProfile(character[USERNAME], uuid, skills, skillsXp, skillsDATS, mobHealthbarType, scoreboardTipsShown, uniquePlayerDataMap);
} }
private Map<PrimarySkill, Integer> getSkillMapFromLine(String[] character) { private Map<PrimarySkill, Integer> getSkillMapFromLine(String[] character) {
@ -1287,6 +1297,7 @@ public final class FlatfileDatabaseManager implements DatabaseManager {
public static int EXP_ALCHEMY = 40; public static int EXP_ALCHEMY = 40;
public static int UUID_INDEX = 41; public static int UUID_INDEX = 41;
public static int SCOREBOARD_TIPS = 42; public static int SCOREBOARD_TIPS = 42;
public static int COOLDOWN_CHIMAERA_WING = 43;
public void resetMobHealthSettings() { public void resetMobHealthSettings() {
BufferedReader in = null; BufferedReader in = null;

View File

@ -6,6 +6,7 @@ import com.gmail.nossr50.datatypes.database.DatabaseType;
import com.gmail.nossr50.datatypes.database.PlayerStat; import com.gmail.nossr50.datatypes.database.PlayerStat;
import com.gmail.nossr50.datatypes.database.UpgradeType; import com.gmail.nossr50.datatypes.database.UpgradeType;
import com.gmail.nossr50.datatypes.player.PlayerProfile; import com.gmail.nossr50.datatypes.player.PlayerProfile;
import com.gmail.nossr50.datatypes.player.UniqueDataType;
import com.gmail.nossr50.datatypes.skills.SuperAbility; import com.gmail.nossr50.datatypes.skills.SuperAbility;
import com.gmail.nossr50.datatypes.skills.PrimarySkill; import com.gmail.nossr50.datatypes.skills.PrimarySkill;
import com.gmail.nossr50.mcMMO; import com.gmail.nossr50.mcMMO;
@ -280,7 +281,7 @@ public final class SQLDatabaseManager implements DatabaseManager {
statement = connection.prepareStatement("UPDATE " + tablePrefix + "cooldowns SET " statement = connection.prepareStatement("UPDATE " + tablePrefix + "cooldowns SET "
+ " mining = ?, woodcutting = ?, unarmed = ?" + " mining = ?, woodcutting = ?, unarmed = ?"
+ ", herbalism = ?, excavation = ?, swords = ?" + ", herbalism = ?, excavation = ?, swords = ?"
+ ", axes = ?, blast_mining = ? WHERE user_id = ?"); + ", axes = ?, blast_mining = ?, chimaera_wing = ? WHERE user_id = ?");
statement.setLong(1, profile.getAbilityDATS(SuperAbility.SUPER_BREAKER)); statement.setLong(1, profile.getAbilityDATS(SuperAbility.SUPER_BREAKER));
statement.setLong(2, profile.getAbilityDATS(SuperAbility.TREE_FELLER)); statement.setLong(2, profile.getAbilityDATS(SuperAbility.TREE_FELLER));
statement.setLong(3, profile.getAbilityDATS(SuperAbility.BERSERK)); statement.setLong(3, profile.getAbilityDATS(SuperAbility.BERSERK));
@ -289,7 +290,8 @@ public final class SQLDatabaseManager implements DatabaseManager {
statement.setLong(6, profile.getAbilityDATS(SuperAbility.SERRATED_STRIKES)); statement.setLong(6, profile.getAbilityDATS(SuperAbility.SERRATED_STRIKES));
statement.setLong(7, profile.getAbilityDATS(SuperAbility.SKULL_SPLITTER)); statement.setLong(7, profile.getAbilityDATS(SuperAbility.SKULL_SPLITTER));
statement.setLong(8, profile.getAbilityDATS(SuperAbility.BLAST_MINING)); statement.setLong(8, profile.getAbilityDATS(SuperAbility.BLAST_MINING));
statement.setInt(9, id); statement.setLong(9, profile.getUniqueData(UniqueDataType.CHIMAERA_WING_DATS));
statement.setInt(10, id);
success = (statement.executeUpdate() != 0); success = (statement.executeUpdate() != 0);
statement.close(); statement.close();
if (!success) { if (!success) {
@ -546,7 +548,7 @@ public final class SQLDatabaseManager implements DatabaseManager {
"SELECT " "SELECT "
+ "s.taming, s.mining, s.repair, s.woodcutting, s.unarmed, s.herbalism, s.excavation, s.archery, s.swords, s.axes, s.acrobatics, s.fishing, s.alchemy, " + "s.taming, s.mining, s.repair, s.woodcutting, s.unarmed, s.herbalism, s.excavation, s.archery, s.swords, s.axes, s.acrobatics, s.fishing, s.alchemy, "
+ "e.taming, e.mining, e.repair, e.woodcutting, e.unarmed, e.herbalism, e.excavation, e.archery, e.swords, e.axes, e.acrobatics, e.fishing, e.alchemy, " + "e.taming, e.mining, e.repair, e.woodcutting, e.unarmed, e.herbalism, e.excavation, e.archery, e.swords, e.axes, e.acrobatics, e.fishing, e.alchemy, "
+ "c.taming, c.mining, c.repair, c.woodcutting, c.unarmed, c.herbalism, c.excavation, c.archery, c.swords, c.axes, c.acrobatics, c.blast_mining, " + "c.taming, c.mining, c.repair, c.woodcutting, c.unarmed, c.herbalism, c.excavation, c.archery, c.swords, c.axes, c.acrobatics, c.blast_mining, c.chimaera_wing, "
+ "h.mobhealthbar, h.scoreboardtips, u.uuid, u.user " + "h.mobhealthbar, h.scoreboardtips, u.uuid, u.user "
+ "FROM " + tablePrefix + "users u " + "FROM " + tablePrefix + "users u "
+ "JOIN " + tablePrefix + "skills s ON (u.id = s.user_id) " + "JOIN " + tablePrefix + "skills s ON (u.id = s.user_id) "
@ -624,7 +626,7 @@ public final class SQLDatabaseManager implements DatabaseManager {
"SELECT " "SELECT "
+ "s.taming, s.mining, s.repair, s.woodcutting, s.unarmed, s.herbalism, s.excavation, s.archery, s.swords, s.axes, s.acrobatics, s.fishing, s.alchemy, " + "s.taming, s.mining, s.repair, s.woodcutting, s.unarmed, s.herbalism, s.excavation, s.archery, s.swords, s.axes, s.acrobatics, s.fishing, s.alchemy, "
+ "e.taming, e.mining, e.repair, e.woodcutting, e.unarmed, e.herbalism, e.excavation, e.archery, e.swords, e.axes, e.acrobatics, e.fishing, e.alchemy, " + "e.taming, e.mining, e.repair, e.woodcutting, e.unarmed, e.herbalism, e.excavation, e.archery, e.swords, e.axes, e.acrobatics, e.fishing, e.alchemy, "
+ "c.taming, c.mining, c.repair, c.woodcutting, c.unarmed, c.herbalism, c.excavation, c.archery, c.swords, c.axes, c.acrobatics, c.blast_mining, " + "c.taming, c.mining, c.repair, c.woodcutting, c.unarmed, c.herbalism, c.excavation, c.archery, c.swords, c.axes, c.acrobatics, c.blast_mining, c.chimaera_wing, "
+ "h.mobhealthbar, h.scoreboardtips, u.uuid " + "h.mobhealthbar, h.scoreboardtips, u.uuid "
+ "FROM " + tablePrefix + "users u " + "FROM " + tablePrefix + "users u "
+ "JOIN " + tablePrefix + "skills s ON (u.id = s.user_id) " + "JOIN " + tablePrefix + "skills s ON (u.id = s.user_id) "
@ -817,6 +819,7 @@ public final class SQLDatabaseManager implements DatabaseManager {
+ "`axes` int(32) unsigned NOT NULL DEFAULT '0'," + "`axes` int(32) unsigned NOT NULL DEFAULT '0',"
+ "`acrobatics` int(32) unsigned NOT NULL DEFAULT '0'," + "`acrobatics` int(32) unsigned NOT NULL DEFAULT '0',"
+ "`blast_mining` int(32) unsigned NOT NULL DEFAULT '0'," + "`blast_mining` int(32) unsigned NOT NULL DEFAULT '0',"
+ "`chimaera_wing` int(32) unsigned NOT NULL DEFAULT '0',"
+ "PRIMARY KEY (`user_id`)) " + "PRIMARY KEY (`user_id`)) "
+ "DEFAULT CHARSET=latin1;"); + "DEFAULT CHARSET=latin1;");
tryClose(createStatement); tryClose(createStatement);
@ -988,6 +991,9 @@ public final class SQLDatabaseManager implements DatabaseManager {
case ADD_SKILL_TOTAL: case ADD_SKILL_TOTAL:
checkUpgradeSkillTotal(connection); checkUpgradeSkillTotal(connection);
break; break;
case ADD_UNIQUE_PLAYER_DATA:
checkUpgradeAddUniqueChimaeraWing(statement);
break;
default: default:
break; break;
@ -1042,6 +1048,7 @@ public final class SQLDatabaseManager implements DatabaseManager {
Map<PrimarySkill, Integer> skills = new EnumMap<PrimarySkill, Integer>(PrimarySkill.class); // Skill & Level Map<PrimarySkill, Integer> skills = new EnumMap<PrimarySkill, Integer>(PrimarySkill.class); // Skill & Level
Map<PrimarySkill, Float> skillsXp = new EnumMap<PrimarySkill, Float>(PrimarySkill.class); // Skill & XP Map<PrimarySkill, Float> skillsXp = new EnumMap<PrimarySkill, Float>(PrimarySkill.class); // Skill & XP
Map<SuperAbility, Integer> skillsDATS = new EnumMap<SuperAbility, Integer>(SuperAbility.class); // Ability & Cooldown Map<SuperAbility, Integer> skillsDATS = new EnumMap<SuperAbility, Integer>(SuperAbility.class); // Ability & Cooldown
Map<UniqueDataType, Integer> uniqueData = new EnumMap<UniqueDataType, Integer>(UniqueDataType.class); //Chimaera wing cooldown and other misc info
MobHealthbarType mobHealthbarType; MobHealthbarType mobHealthbarType;
UUID uuid; UUID uuid;
int scoreboardTipsShown; int scoreboardTipsShown;
@ -1050,7 +1057,7 @@ public final class SQLDatabaseManager implements DatabaseManager {
// changes (a new skill is added) // changes (a new skill is added)
final int OFFSET_XP = 13; final int OFFSET_XP = 13;
final int OFFSET_DATS = 26; final int OFFSET_DATS = 26;
final int OFFSET_OTHER = 38; final int OFFSET_OTHER = 39;
skills.put(PrimarySkill.TAMING, result.getInt(OFFSET_SKILLS + 1)); skills.put(PrimarySkill.TAMING, result.getInt(OFFSET_SKILLS + 1));
skills.put(PrimarySkill.MINING, result.getInt(OFFSET_SKILLS + 2)); skills.put(PrimarySkill.MINING, result.getInt(OFFSET_SKILLS + 2));
@ -1092,6 +1099,8 @@ public final class SQLDatabaseManager implements DatabaseManager {
skillsDATS.put(SuperAbility.SKULL_SPLITTER, result.getInt(OFFSET_DATS + 10)); skillsDATS.put(SuperAbility.SKULL_SPLITTER, result.getInt(OFFSET_DATS + 10));
// Acrobatics - Unused - result.getInt(OFFSET_DATS + 11) // Acrobatics - Unused - result.getInt(OFFSET_DATS + 11)
skillsDATS.put(SuperAbility.BLAST_MINING, result.getInt(OFFSET_DATS + 12)); skillsDATS.put(SuperAbility.BLAST_MINING, result.getInt(OFFSET_DATS + 12));
uniqueData.put(UniqueDataType.CHIMAERA_WING_DATS, result.getInt(OFFSET_DATS + 13));
try { try {
mobHealthbarType = MobHealthbarType.valueOf(result.getString(OFFSET_OTHER + 1)); mobHealthbarType = MobHealthbarType.valueOf(result.getString(OFFSET_OTHER + 1));
@ -1114,7 +1123,7 @@ public final class SQLDatabaseManager implements DatabaseManager {
uuid = null; uuid = null;
} }
return new PlayerProfile(playerName, uuid, skills, skillsXp, skillsDATS, mobHealthbarType, scoreboardTipsShown); return new PlayerProfile(playerName, uuid, skills, skillsXp, skillsDATS, mobHealthbarType, scoreboardTipsShown, uniqueData);
} }
private void printErrors(SQLException ex) { private void printErrors(SQLException ex) {
@ -1171,6 +1180,16 @@ public final class SQLDatabaseManager implements DatabaseManager {
} }
} }
private void checkUpgradeAddUniqueChimaeraWing(final Statement statement) throws SQLException {
try {
statement.executeQuery("SELECT `chimaera_wing` FROM `" + tablePrefix + "cooldowns` LIMIT 1");
}
catch (SQLException ex) {
mcMMO.p.getLogger().info("Updating mcMMO MySQL tables for Chimaera Wing...");
statement.executeUpdate("ALTER TABLE `" + tablePrefix + "cooldowns` ADD `chimaera_wing` int(32) NOT NULL DEFAULT '0'");
}
}
private void checkUpgradeAddFishing(final Statement statement) throws SQLException { private void checkUpgradeAddFishing(final Statement statement) throws SQLException {
try { try {
statement.executeQuery("SELECT `fishing` FROM `" + tablePrefix + "skills` LIMIT 1"); statement.executeQuery("SELECT `fishing` FROM `" + tablePrefix + "skills` LIMIT 1");

View File

@ -13,4 +13,5 @@ public enum UpgradeType {
ADD_SCOREBOARD_TIPS, ADD_SCOREBOARD_TIPS,
DROP_NAME_UNIQUENESS, DROP_NAME_UNIQUENESS,
ADD_SKILL_TOTAL, ADD_SKILL_TOTAL,
ADD_UNIQUE_PLAYER_DATA,
} }

View File

@ -87,7 +87,7 @@ public class McMMOPlayer {
private int respawnATS; private int respawnATS;
private int teleportATS; private int teleportATS;
private long databaseATS; private long databaseATS;
private int chimeraWingLastUse; //private int chimeraWingLastUse;
private Location teleportCommence; private Location teleportCommence;
private boolean isUsingUnarmed; private boolean isUsingUnarmed;
@ -306,11 +306,11 @@ public class McMMOPlayer {
*/ */
public int getChimeraWingLastUse() { public int getChimeraWingLastUse() {
return chimeraWingLastUse; return profile.getChimaerWingDATS();
} }
public void actualizeChimeraWingLastUse() { public void actualizeChimeraWingLastUse() {
chimeraWingLastUse = (int) (System.currentTimeMillis() / Misc.TIME_CONVERSION_FACTOR); profile.setChimaeraWingDATS((int) (System.currentTimeMillis() / Misc.TIME_CONVERSION_FACTOR));
} }
public Location getTeleportCommenceLocation() { public Location getTeleportCommenceLocation() {

View File

@ -34,6 +34,7 @@ public class PlayerProfile {
private final Map<PrimarySkill, Integer> skills = new HashMap<PrimarySkill, Integer>(); // Skill & Level private final Map<PrimarySkill, Integer> skills = new HashMap<PrimarySkill, Integer>(); // Skill & Level
private final Map<PrimarySkill, Float> skillsXp = new HashMap<PrimarySkill, Float>(); // Skill & XP private final Map<PrimarySkill, Float> skillsXp = new HashMap<PrimarySkill, Float>(); // Skill & XP
private final Map<SuperAbility, Integer> abilityDATS = new HashMap<SuperAbility, Integer>(); // Ability & Cooldown private final Map<SuperAbility, Integer> abilityDATS = new HashMap<SuperAbility, Integer>(); // Ability & Cooldown
private final Map<UniqueDataType, Integer> uniquePlayerData = new HashMap<>(); //Misc data that doesn't fit into other categories (chimaera wing, etc..)
// Store previous XP gains for deminished returns // Store previous XP gains for deminished returns
private DelayQueue<SkillXpGain> gainedSkillsXp = new DelayQueue<SkillXpGain>(); private DelayQueue<SkillXpGain> gainedSkillsXp = new DelayQueue<SkillXpGain>();
@ -59,6 +60,9 @@ public class PlayerProfile {
skills.put(primarySkill, 0); skills.put(primarySkill, 0);
skillsXp.put(primarySkill, 0F); skillsXp.put(primarySkill, 0F);
} }
//Misc Cooldowns
uniquePlayerData.put(UniqueDataType.CHIMAERA_WING_DATS, 0); //Chimaera wing
} }
@Deprecated @Deprecated
@ -72,7 +76,7 @@ public class PlayerProfile {
this.loaded = isLoaded; this.loaded = isLoaded;
} }
public PlayerProfile(String playerName, UUID uuid, Map<PrimarySkill, Integer> levelData, Map<PrimarySkill, Float> xpData, Map<SuperAbility, Integer> cooldownData, MobHealthbarType mobHealthbarType, int scoreboardTipsShown) { public PlayerProfile(String playerName, UUID uuid, Map<PrimarySkill, Integer> levelData, Map<PrimarySkill, Float> xpData, Map<SuperAbility, Integer> cooldownData, MobHealthbarType mobHealthbarType, int scoreboardTipsShown, Map<UniqueDataType, Integer> uniqueProfileData) {
this.playerName = playerName; this.playerName = playerName;
this.uuid = uuid; this.uuid = uuid;
this.mobHealthbarType = mobHealthbarType; this.mobHealthbarType = mobHealthbarType;
@ -81,6 +85,7 @@ public class PlayerProfile {
skills.putAll(levelData); skills.putAll(levelData);
skillsXp.putAll(xpData); skillsXp.putAll(xpData);
abilityDATS.putAll(cooldownData); abilityDATS.putAll(cooldownData);
uniquePlayerData.putAll(uniqueProfileData);
loaded = true; loaded = true;
} }
@ -95,7 +100,7 @@ public class PlayerProfile {
} }
// TODO should this part be synchronized? // TODO should this part be synchronized?
PlayerProfile profileCopy = new PlayerProfile(playerName, uuid, ImmutableMap.copyOf(skills), ImmutableMap.copyOf(skillsXp), ImmutableMap.copyOf(abilityDATS), mobHealthbarType, scoreboardTipsShown); PlayerProfile profileCopy = new PlayerProfile(playerName, uuid, ImmutableMap.copyOf(skills), ImmutableMap.copyOf(skillsXp), ImmutableMap.copyOf(abilityDATS), mobHealthbarType, scoreboardTipsShown, ImmutableMap.copyOf(uniquePlayerData));
changed = !mcMMO.getDatabaseManager().saveUser(profileCopy); changed = !mcMMO.getDatabaseManager().saveUser(profileCopy);
if (changed) { if (changed) {
@ -153,6 +158,20 @@ public class PlayerProfile {
* Cooldowns * Cooldowns
*/ */
public int getChimaerWingDATS() { return uniquePlayerData.get(UniqueDataType.CHIMAERA_WING_DATS);}
protected void setChimaeraWingDATS(int DATS) {
changed = true;
uniquePlayerData.put(UniqueDataType.CHIMAERA_WING_DATS, DATS);
}
public void setUniqueData(UniqueDataType uniqueDataType, int newData) {
changed = true;
uniquePlayerData.put(uniqueDataType, newData);
}
public long getUniqueData(UniqueDataType uniqueDataType) { return uniquePlayerData.get(uniqueDataType); }
/** /**
* Get the current deactivation timestamp of an ability. * Get the current deactivation timestamp of an ability.
* *

View File

@ -0,0 +1,5 @@
package com.gmail.nossr50.datatypes.player;
public enum UniqueDataType {
CHIMAERA_WING_DATS
}