Making progress on player data
This commit is contained in:
parent
4aa7cccb5c
commit
28fcb2f8d8
2 changed files with 86 additions and 15 deletions
|
@ -1,11 +1,8 @@
|
||||||
package buttondevteam.lib.player;
|
package buttondevteam.lib.player;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.util.Collections;
|
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Map;
|
|
||||||
import java.util.Map.Entry;
|
import java.util.Map.Entry;
|
||||||
import java.util.function.BiConsumer;
|
|
||||||
import java.util.function.Consumer;
|
import java.util.function.Consumer;
|
||||||
|
|
||||||
import org.bukkit.configuration.file.YamlConfiguration;
|
import org.bukkit.configuration.file.YamlConfiguration;
|
||||||
|
@ -17,12 +14,30 @@ public abstract class ChromaGamerBase implements AutoCloseable {
|
||||||
|
|
||||||
private static final HashMap<Class<?>, String> playerTypes = new HashMap<>();
|
private static final HashMap<Class<?>, String> playerTypes = new HashMap<>();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Use only if outside Minecraft, and use it to register your plugin's class.
|
||||||
|
*
|
||||||
|
* @param cl
|
||||||
|
* The custom player class
|
||||||
|
* @param folder
|
||||||
|
* The folder to store the data in (like "discord")
|
||||||
|
*/
|
||||||
public static <T extends ChromaGamerBase> void addPlayerType(Class<T> cl, String folder) {
|
public static <T extends ChromaGamerBase> void addPlayerType(Class<T> cl, String folder) {
|
||||||
playerTypes.put(cl, folder);
|
playerTypes.put(cl, folder);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the folder name for the given player class. If a direct match is not found, it'll look for superclasses.
|
||||||
|
*
|
||||||
|
* @param cl
|
||||||
|
* The class to get the folder from (like {@link TBMCPlayerBase} or one of it's subclasses
|
||||||
|
* @return The folder name for the given type
|
||||||
|
*/
|
||||||
public static <T extends ChromaGamerBase> String getFolderForType(Class<T> cl) {
|
public static <T extends ChromaGamerBase> String getFolderForType(Class<T> cl) {
|
||||||
return playerTypes.get(cl);
|
if (playerTypes.containsKey(cl))
|
||||||
|
return playerTypes.get(cl);
|
||||||
|
return playerTypes.entrySet().stream().filter(e -> e.getKey().isAssignableFrom(cl)).findAny()
|
||||||
|
.orElseThrow(() -> new RuntimeException("Type not registered as a player type!")).getValue();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -35,10 +50,6 @@ public abstract class ChromaGamerBase implements AutoCloseable {
|
||||||
*/
|
*/
|
||||||
protected YamlConfiguration plugindata;
|
protected YamlConfiguration plugindata;
|
||||||
|
|
||||||
public YamlConfiguration getData() {
|
|
||||||
return plugindata;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getID() {
|
public String getID() {
|
||||||
return plugindata != null ? plugindata.getString("id") : null;
|
return plugindata != null ? plugindata.getString("id") : null;
|
||||||
}
|
}
|
||||||
|
@ -47,7 +58,7 @@ public abstract class ChromaGamerBase implements AutoCloseable {
|
||||||
try {
|
try {
|
||||||
T obj = cl.newInstance();
|
T obj = cl.newInstance();
|
||||||
obj.plugindata = YamlConfiguration
|
obj.plugindata = YamlConfiguration
|
||||||
.loadConfiguration(new File(TBMC_PLAYERS_DIR + playerTypes.get(cl), fname));
|
.loadConfiguration(new File(TBMC_PLAYERS_DIR + getFolderForType(cl), fname));
|
||||||
return obj;
|
return obj;
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
TBMCCoreAPI.SendException("An error occured while loading a " + cl.getSimpleName() + "!", e);
|
TBMCCoreAPI.SendException("An error occured while loading a " + cl.getSimpleName() + "!", e);
|
||||||
|
@ -60,15 +71,54 @@ public abstract class ChromaGamerBase implements AutoCloseable {
|
||||||
plugindata.save(new File(TBMC_PLAYERS_DIR + getFolderForType(getClass()), getFileName()));
|
plugindata.save(new File(TBMC_PLAYERS_DIR + getFolderForType(getClass()), getFileName()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Connect two accounts. Do not use for connecting two Minecraft accounts or similar. Also make sure you have the "id" tag set
|
||||||
|
*
|
||||||
|
* @param user
|
||||||
|
* The account to connect with
|
||||||
|
*/
|
||||||
public <T extends ChromaGamerBase> void connectWith(T user) {
|
public <T extends ChromaGamerBase> void connectWith(T user) {
|
||||||
// Set the ID, go through all linked files and connect them as well
|
// Set the ID, go through all linked files and connect them as well
|
||||||
plugindata.set(playerTypes.get(user.getClass()) + "_id", user.plugindata.getString("id"));
|
plugindata.set(getFolderForType(user.getClass()) + "_id", user.plugindata.getString("id"));
|
||||||
final String ownFolder = getFolderForType(getClass());
|
final String ownFolder = getFolderForType(getClass());
|
||||||
user.plugindata.set(ownFolder + "_id", plugindata.getString("id"));
|
user.plugindata.set(ownFolder + "_id", plugindata.getString("id"));
|
||||||
BiConsumer<YamlConfiguration, YamlConfiguration> sync = (pdata1, pdata2) -> {
|
Consumer<YamlConfiguration> sync = sourcedata -> {
|
||||||
for (Entry<Class<?>, String> entry : playerTypes.entrySet())
|
final String sourcefolder = sourcedata == plugindata ? ownFolder : getFolderForType(user.getClass());
|
||||||
if (pdata1.contains(entry.getValue() + "_id", false))
|
final String id = sourcedata.getString("id");
|
||||||
pdata2.set(entry.getValue() + "_id", pdata1.getString(entry.getValue() + "_id"));
|
for (Entry<Class<?>, String> entry : playerTypes.entrySet()) { // Set our ID in all files we can find, both from our connections and the new ones
|
||||||
}; // ...
|
final String otherid = sourcedata.getString(entry.getValue() + "_id");
|
||||||
|
if (otherid == null)
|
||||||
|
continue;
|
||||||
|
try (@SuppressWarnings("unchecked")
|
||||||
|
ChromaGamerBase cg = getUser(otherid, (Class<T>) entry.getKey())) {
|
||||||
|
cg.plugindata.set(sourcefolder + "_id", id); // Set new IDs
|
||||||
|
for (Entry<Class<?>, String> item : playerTypes.entrySet())
|
||||||
|
if (sourcedata.contains(item.getValue() + "_id"))
|
||||||
|
cg.plugindata.set(item.getValue() + "_id", sourcedata.getString(item.getValue() + "_id")); // Set all existing IDs
|
||||||
|
} catch (Exception e) {
|
||||||
|
TBMCCoreAPI.SendException("Failed to update " + sourcefolder + " ID in player files for " + id
|
||||||
|
+ " in folder with " + entry.getValue() + " id " + otherid + "!", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
sync.accept(plugindata);
|
||||||
|
sync.accept(user.plugindata);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns this player as a plugin player. This will return a new instance unless the player is online.<br>
|
||||||
|
* Make sure to close both the returned and this object. A try-with-resources block or two can help.<br>
|
||||||
|
*
|
||||||
|
* @param cl
|
||||||
|
* The target player class
|
||||||
|
* @return The player as a {@link T} object or null if not having an account there
|
||||||
|
*/
|
||||||
|
public <T extends ChromaGamerBase> T getAs(Class<T> cl) {
|
||||||
|
String newfolder = getFolderForType(cl);
|
||||||
|
if (newfolder == null)
|
||||||
|
throw new RuntimeException("The specified class " + cl.getSimpleName() + " isn't registered!");
|
||||||
|
if (!plugindata.contains(newfolder + "_id"))
|
||||||
|
return null;
|
||||||
|
return getUser(plugindata.getString(newfolder + "_id"), cl);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
package buttondevteam.lib.player;
|
package buttondevteam.lib.player;
|
||||||
|
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
import java.util.concurrent.ConcurrentHashMap;
|
||||||
|
|
||||||
public abstract class TBMCPlayerBase extends ChromaGamerBase {
|
public abstract class TBMCPlayerBase extends ChromaGamerBase {
|
||||||
private static final String FOLDER_NAME = "minecraft";
|
private static final String FOLDER_NAME = "minecraft";
|
||||||
|
@ -28,9 +29,29 @@ public abstract class TBMCPlayerBase extends ChromaGamerBase {
|
||||||
addPlayerType(TBMCPlayerBase.class, FOLDER_NAME);
|
addPlayerType(TBMCPlayerBase.class, FOLDER_NAME);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
public static <T extends TBMCPlayerBase> T getPlayer(UUID uuid, Class<T> cl) {
|
public static <T extends TBMCPlayerBase> T getPlayer(UUID uuid, Class<T> cl) {
|
||||||
|
if (playermap.containsKey(uuid + "-" + cl.getSimpleName()))
|
||||||
|
return (T) playermap.get(uuid + "-" + cl.getSimpleName());
|
||||||
T obj = ChromaGamerBase.getUser(uuid.toString(), cl);
|
T obj = ChromaGamerBase.getUser(uuid.toString(), cl);
|
||||||
obj.uuid = uuid;
|
obj.uuid = uuid;
|
||||||
return obj;
|
return obj;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Key: UUID-Class
|
||||||
|
*/
|
||||||
|
static final ConcurrentHashMap<String, TBMCPlayerBase> playermap = new ConcurrentHashMap<>();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the TBMCPlayer object as a specific plugin player, keeping it's data *
|
||||||
|
*
|
||||||
|
* @param p
|
||||||
|
* Player to get
|
||||||
|
* @param cl
|
||||||
|
* The TBMCPlayer subclass
|
||||||
|
*/
|
||||||
|
public <T extends TBMCPlayerBase> T asPluginPlayer(Class<T> cl) {
|
||||||
|
return getPlayer(uuid, cl);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue