Merge pull request #8 from iXanadu13/v2.3.0

V2.3.0
This commit is contained in:
Xanadu13
2023-12-07 11:10:10 +08:00
committed by GitHub
34 changed files with 716 additions and 284 deletions
@@ -45,7 +45,6 @@ public final class EnderDragon extends JavaPlugin {
public static FileConfiguration data; public static FileConfiguration data;
public static FileConfiguration lang; public static FileConfiguration lang;
private WorldManager worldManager; private WorldManager worldManager;
private DragonManager dragonManager;
private NMSUtil nmsManager; private NMSUtil nmsManager;
private I_BossBarManager i_bossBarManager; private I_BossBarManager i_bossBarManager;
private I_NMSItemManager i_nmsItemManager; private I_NMSItemManager i_nmsItemManager;
@@ -65,7 +64,6 @@ public final class EnderDragon extends JavaPlugin {
Lang.info("Enabling plugin..."); Lang.info("Enabling plugin...");
Lang.info("Author: Xanadu13"); Lang.info("Author: Xanadu13");
Version.init(); Version.init();
dragonManager = new DragonManager();
worldManager = new WorldManager(); worldManager = new WorldManager();
nmsManager = new NMSUtil(); nmsManager = new NMSUtil();
nmsManager.init(); nmsManager.init();
@@ -77,7 +75,7 @@ public final class EnderDragon extends JavaPlugin {
getInstance().getWorldManager().fixWorldEnvironment(); getInstance().getWorldManager().fixWorldEnvironment();
Lang.info(Lang.world_env_fix_enable); Lang.info(Lang.world_env_fix_enable);
} }
if(Version.mcMainVersion == 12 || Version.mcMainVersion == 13){ if(Config.advanced_setting_save_bossbar){
fixWorldBossBar(); fixWorldBossBar();
} }
TimerManager.enable(); TimerManager.enable();
@@ -139,7 +137,7 @@ public final class EnderDragon extends JavaPlugin {
Bukkit.getWorlds().forEach(world -> { Bukkit.getWorlds().forEach(world -> {
if(!Config.blacklist_worlds.contains(world.getName())){ if(!Config.blacklist_worlds.contains(world.getName())){
char split = data.options().pathSeparator(); char split = data.options().pathSeparator();
if(EnderDragon.getInstance().getDragonManager().isRespawnRunning(world)){ if(DragonManager.isRespawnRunning(world)){
data.set("respawn_fix"+split+world.getName(),true); data.set("respawn_fix"+split+world.getName(),true);
} }
else data.set("respawn_fix"+split+world.getName(),false); else data.set("respawn_fix"+split+world.getName(),false);
@@ -153,7 +151,7 @@ public final class EnderDragon extends JavaPlugin {
Lang.error(Lang.plugin_file_save_error.replaceAll("\\{file_name}",dataF.getName())); Lang.error(Lang.plugin_file_save_error.replaceAll("\\{file_name}",dataF.getName()));
} }
} }
if(Version.mcMainVersion == 12 || Version.mcMainVersion == 13){ if(Config.advanced_setting_save_bossbar){
List<World> worlds = new ArrayList<>(); List<World> worlds = new ArrayList<>();
Bukkit.getWorlds().forEach(world -> { Bukkit.getWorlds().forEach(world -> {
if(world.getEnvironment()==World.Environment.THE_END&&!Config.blacklist_worlds.contains(world.getName())){ if(world.getEnvironment()==World.Environment.THE_END&&!Config.blacklist_worlds.contains(world.getName())){
@@ -290,7 +288,7 @@ public final class EnderDragon extends JavaPlugin {
if(section != null){ if(section != null){
section.getKeys(false).forEach(key->{ section.getKeys(false).forEach(key->{
if(section.getBoolean(key)){ if(section.getBoolean(key)){
EnderDragon.getInstance().getDragonManager().refresh_respawn(Bukkit.getWorld(key)); DragonManager.refresh_respawn(Bukkit.getWorld(key));
Lang.info("DragonRespawn continues!"); Lang.info("DragonRespawn continues!");
} }
}); });
@@ -299,9 +297,6 @@ public final class EnderDragon extends JavaPlugin {
}.runTaskLater(plugin,100L); }.runTaskLater(plugin,100L);
} }
public DragonManager getDragonManager(){
return dragonManager;
}
public WorldManager getWorldManager(){ public WorldManager getWorldManager(){
return worldManager; return worldManager;
} }
@@ -11,7 +11,6 @@ import org.bukkit.inventory.ItemStack;
import pers.xanadu.enderdragon.config.Config; import pers.xanadu.enderdragon.config.Config;
import pers.xanadu.enderdragon.config.Lang; import pers.xanadu.enderdragon.config.Lang;
import pers.xanadu.enderdragon.manager.*; import pers.xanadu.enderdragon.manager.*;
import pers.xanadu.enderdragon.EnderDragon;
import pers.xanadu.enderdragon.maven.DependencyManager; import pers.xanadu.enderdragon.maven.DependencyManager;
import pers.xanadu.enderdragon.reward.Chance; import pers.xanadu.enderdragon.reward.Chance;
import pers.xanadu.enderdragon.config.FileUpdater; import pers.xanadu.enderdragon.config.FileUpdater;
@@ -33,7 +32,6 @@ public class MainCommand implements CommandExecutor {
switch(args[0].toLowerCase()){ switch(args[0].toLowerCase()){
// case "parse" : { // case "parse" : {
// if(!sender.isOp()) return false; // if(!sender.isOp()) return false;
//
// if(args.length == 2) GroovyManager.invoke("test.groovy", args[1]); // if(args.length == 2) GroovyManager.invoke("test.groovy", args[1]);
// else if(args.length == 3) GroovyManager.invoke("test.groovy",args[1],Bukkit.getPlayer(args[2])); // else if(args.length == 3) GroovyManager.invoke("test.groovy",args[1],Bukkit.getPlayer(args[2]));
//// List<Entity> entities = p.getNearbyEntities(50,50,50); //// List<Entity> entities = p.getNearbyEntities(50,50,50);
@@ -46,15 +44,15 @@ public class MainCommand implements CommandExecutor {
//// } //// }
//// ////
//// ////
////// if(entity instanceof org.bukkit.entity.EnderDragon){ //// if(entity instanceof org.bukkit.entity.EnderDragon){
////// Bukkit.broadcastMessage(entity.getName());//1 Special Ender Dragon //// Bukkit.broadcastMessage(entity.getName());//1 Special Ender Dragon
////// } //// }
////// if(entity instanceof ComplexEntityPart){ //// if(entity instanceof ComplexEntityPart){
////// Bukkit.broadcastMessage(entity.getName());//1 Special Ender Dragon //// Bukkit.broadcastMessage(entity.getName());//1 Special Ender Dragon
////// } //// }
////// if(entity instanceof ComplexLivingEntity){ //// if(entity instanceof ComplexLivingEntity){
////// Bukkit.broadcastMessage(entity.getName());//8 EnderDragon //// Bukkit.broadcastMessage(entity.getName());//8 EnderDragon
////// } //// }
//// }); //// });
// //
// return true; // return true;
@@ -109,7 +107,34 @@ public class MainCommand implements CommandExecutor {
} }
break; break;
} }
case "respawn" : {//ed respawn [world_name] case "spawn" : {//ed spawn [dragon] (world_name)
if(!sender.hasPermission("ed.respawn")){
Lang.sendFeedback(sender,Lang.command_no_permission);
return false;
}
if(args.length == 2){
if(!(sender instanceof Player)){
Lang.sendFeedback(sender,"§cConsole usage: /ed spawn [dragon] [world_name]");
return false;
}
Player player = (Player) sender;
DragonManager.initiateRespawn(player,args[1]);
return true;
}
else if(args.length == 3){
String world_name = args[2];
DragonManager.initiateRespawn(sender,world_name,args[1]);
return true;
}
else if(args.length > 3){//if world_name contains " "
int size = args.length;
StringBuilder builder = new StringBuilder(args[2]);
for(int i=3;i<size;i++) builder.append(" ").append(args[i]);
DragonManager.initiateRespawn(sender,builder.toString(),args[1]);
return true;
}
}
case "respawn" : {//ed respawn (world_name)
if(!sender.hasPermission("ed.respawn")){ if(!sender.hasPermission("ed.respawn")){
Lang.sendFeedback(sender,Lang.command_no_permission); Lang.sendFeedback(sender,Lang.command_no_permission);
return false; return false;
@@ -120,19 +145,19 @@ public class MainCommand implements CommandExecutor {
return false; return false;
} }
Player player = (Player) sender; Player player = (Player) sender;
EnderDragon.getInstance().getDragonManager().initiateRespawn(player); DragonManager.initiateRespawn(player);
return true; return true;
} }
else if(args.length == 2){ else if(args.length == 2){
String world_name = args[1]; String world_name = args[1];
EnderDragon.getInstance().getDragonManager().initiateRespawn(sender,world_name); DragonManager.initiateRespawn(sender,world_name);
return true; return true;
} }
else { else {//if world_name contains " "
int size = args.length; int size = args.length;
StringBuilder builder = new StringBuilder(args[1]); StringBuilder builder = new StringBuilder(args[1]);
for(int i=2;i<size;i++) builder.append(" ").append(args[i]); for(int i=2;i<size;i++) builder.append(" ").append(args[i]);
EnderDragon.getInstance().getDragonManager().initiateRespawn(sender,builder.toString()); DragonManager.initiateRespawn(sender,builder.toString());
return true; return true;
} }
} }
@@ -17,7 +17,7 @@ import java.util.stream.Stream;
public class TabCompleter implements org.bukkit.command.TabCompleter { public class TabCompleter implements org.bukkit.command.TabCompleter {
private static final List<String> arguments_ed = Arrays.asList("action", "drop", "reload", "respawn", "respawn_cd", "update"); private static final List<String> arguments_ed = Arrays.asList("action", "drop", "reload", "respawn", "respawn_cd", "spawn", "update");
private static final List<String> arguments_drop = Arrays.asList("add", "clear", "edit", "remove", "gui"); private static final List<String> arguments_drop = Arrays.asList("add", "clear", "edit", "remove", "gui");
private static final List<String> arguments_action = Arrays.asList("tell:","tell-colorless:","tell-raw:","groovy:"); private static final List<String> arguments_action = Arrays.asList("tell:","tell-colorless:","tell-raw:","groovy:");
private static final List<String> arguments_respawn_cd = Arrays.asList("get","remove","removeAll","set","start"); private static final List<String> arguments_respawn_cd = Arrays.asList("get","remove","removeAll","set","start");
@@ -42,6 +42,9 @@ public class TabCompleter implements org.bukkit.command.TabCompleter {
else if(args[0].equalsIgnoreCase("reload")){ else if(args[0].equalsIgnoreCase("reload")){
result.addAll(arguments_reload); result.addAll(arguments_reload);
} }
else if(args[0].equalsIgnoreCase("spawn")){
result.addAll(DragonManager.dragon_names);
}
else if(args[0].equalsIgnoreCase("action")){ else if(args[0].equalsIgnoreCase("action")){
Stream<String> stream = Bukkit.getOnlinePlayers().stream().map(Player::getName); Stream<String> stream = Bukkit.getOnlinePlayers().stream().map(Player::getName);
return filterResult(stream,Arrays.asList("me"),args[args.length-1]); return filterResult(stream,Arrays.asList("me"),args[args.length-1]);
@@ -60,6 +63,9 @@ public class TabCompleter implements org.bukkit.command.TabCompleter {
result.addAll(WorldManager.worlds); result.addAll(WorldManager.worlds);
} }
} }
else if("spawn".equals(args[0])){
result.addAll(WorldManager.worlds);
}
else if("action".equals(args[0])){ else if("action".equals(args[0])){
result.addAll(arguments_action); result.addAll(arguments_action);
} }
@@ -19,6 +19,7 @@ public class Config {
public static boolean debug; public static boolean debug;
public static boolean advanced_setting_world_env_fix; public static boolean advanced_setting_world_env_fix;
public static boolean advanced_setting_save_respawn_status; public static boolean advanced_setting_save_respawn_status;
public static boolean advanced_setting_save_bossbar;
public static boolean advanced_setting_glowing_fix; public static boolean advanced_setting_glowing_fix;
public static boolean advanced_setting_backslash_split_reward; public static boolean advanced_setting_backslash_split_reward;
public static String damage_visible_mode; public static String damage_visible_mode;
@@ -34,6 +35,7 @@ public class Config {
public static String item_format_reward; public static String item_format_reward;
public static List<String> dragon_setting_file; public static List<String> dragon_setting_file;
public static List<String> blacklist_worlds; public static List<String> blacklist_worlds;
public static List<String> blacklist_spawn_reason;
private static final String pluginFilePath; private static final String pluginFilePath;
public static void reload(FileConfiguration file){ public static void reload(FileConfiguration file){
@@ -2,7 +2,6 @@ package pers.xanadu.enderdragon.config;
import org.bukkit.configuration.file.FileConfiguration; import org.bukkit.configuration.file.FileConfiguration;
import org.bukkit.configuration.file.YamlConfiguration; import org.bukkit.configuration.file.YamlConfiguration;
import pers.xanadu.enderdragon.EnderDragon;
import java.io.*; import java.io.*;
@@ -10,9 +9,9 @@ import static pers.xanadu.enderdragon.EnderDragon.*;
public class FileUpdater { public class FileUpdater {
public static void update() throws IOException { public static void update() throws IOException {
String respawn_world_name = null;
FileConfiguration config_old = plugin.getConfig(); FileConfiguration config_old = plugin.getConfig();
if("2.1.0".equals(config_old.getString("version"))){ if("2.2.0".equals(config_old.getString("version"))){
Config.saveResource("config.yml","new/config.yml",true); Config.saveResource("config.yml","new/config.yml",true);
File config_new_F = new File(plugin.getDataFolder(),"new/config.yml"); File config_new_F = new File(plugin.getDataFolder(),"new/config.yml");
FileConfiguration config_new = YamlConfiguration.loadConfiguration(config_new_F); FileConfiguration config_new = YamlConfiguration.loadConfiguration(config_new_F);
@@ -24,111 +23,26 @@ public class FileUpdater {
config_new.set("special_dragon_jude_mode",judge_mode); config_new.set("special_dragon_jude_mode",judge_mode);
config_new.set("dragon_setting_file",config_old.getStringList("dragon_setting_file")); config_new.set("dragon_setting_file",config_old.getStringList("dragon_setting_file"));
// auto_respawn // auto_respawn
config_new.set("auto_respawn.task1.enable",config_old.getBoolean("auto_respawn.enable")); config_new.set("auto_respawn",config_old.getConfigurationSection("auto_respawn"));
respawn_world_name = config_old.getString("auto_respawn.world_the_end_name");
config_new.set("auto_respawn.task1.world_name",respawn_world_name);
config_new.set("auto_respawn.task1.respawn_time",config_old.getString("auto_respawn.respawn_time"));
config_new.set("crystal_invulnerable",config_old.getBoolean("auto_respawn.invulnerable"));
config_new.set("respawn_cd.enable",config_old.getBoolean("respawn_cd.enable")); config_new.set("respawn_cd.enable",config_old.getBoolean("respawn_cd.enable"));
config_new.set("crystal_invulnerable",config_old.getBoolean("crystal_invulnerable"));
config_new.set("resist_player_respawn",config_old.getBoolean("resist_player_respawn")); config_new.set("resist_player_respawn",config_old.getBoolean("resist_player_respawn"));
config_new.set("resist_dragon_breath_gather",config_old.getBoolean("resist_dragon_breath_gather")); config_new.set("resist_dragon_breath_gather",config_old.getBoolean("resist_dragon_breath_gather"));
config_new.set("main_gui",config_old.getString("main_gui")); config_new.set("main_gui",config_old.getString("main_gui"));
config_new.set("blacklist_worlds",config_old.getStringList("blacklist_worlds")); config_new.set("blacklist_worlds",config_old.getStringList("blacklist_worlds"));
//item_format.data -> item_format.reward config_new.set("item_format.reward",config_old.getString("item_format.reward"));
config_new.set("item_format.reward",config_old.getString("item_format.data"));
config_new.set("hook_plugins.MythicLib",config_old.getBoolean("hook_plugins.MythicLib")); config_new.set("hook_plugins.MythicLib",config_old.getBoolean("hook_plugins.MythicLib"));
config_new.set("expansion.groovy",config_old.getBoolean("expansion.groovy"));
config_new.set("debug",config_old.getBoolean("debug")); config_new.set("debug",config_old.getBoolean("debug"));
config_new.set("advanced_setting.world_env_fix",config_old.getBoolean("advanced_setting.world_env_fix")); config_new.set("advanced_setting.world_env_fix",config_old.getBoolean("advanced_setting.world_env_fix"));
config_new.set("advanced_setting.save_respawn_status",config_old.getBoolean("advanced_setting.save_respawn_status")); config_new.set("advanced_setting.save_respawn_status",config_old.getBoolean("advanced_setting.save_respawn_status"));
config_new.set("save_bossbar",config_old.getBoolean("save_bossbar"));
config_new.set("backslash_split.reward",config_old.getBoolean("backslash_split.reward"));
config_new.save(config_new_F); config_new.save(config_new_F);
} }
else Lang.error("The version of config.yml is not supported!"); else Lang.error("The version of config.yml is not supported!");
File folder = new File(plugin.getDataFolder(),"setting");
if(folder.exists()){
File[] files = folder.listFiles();
if(files != null){
for(File file : files){
FileConfiguration config = YamlConfiguration.loadConfiguration(file);
String ver = config.getString("version");
if(!"2.1.0".equals(ver)) {
Lang.error("The version of setting/"+file.getName()+" is not supported!");
continue;
}
String name = file.getName();
Config.copyFile("setting/"+name,"new/setting/"+name,true);
}
File new_folder = new File(plugin.getDataFolder(),"new/setting/");
files = new_folder.listFiles();
if(files != null){
for(File file : files){
FileOutputStream out = new FileOutputStream(file,true);
out.write(("\n\n" +
"# the least interval time between injuries (unit:tick, 1tick=0.05s)\n" +
"# only supports integer value\n" +
"no_damage_tick: 10\n" +
"\n" +
"attack:\n" +
" #the damage modify when this dragon attacks player with body or limb (allow double and negative value)\n" +
" damage_modify: 0\n" +
"\n" +
" #the effect give to player when this ender dragon attacks player with body or limb\n" +
" #the format is the same as effect_cloud.potion\n" +
" potion_effect:\n" +
" - ''\n" +
" - ''\n" +
" - ''\n" +
"\n" +
" # the effect give to player when this ender dragon attacks player with body or limb\n" +
" # format: (<type>: seconds)\n" +
" extra_effect:\n" +
" fire: 0\n" +
" # \"freeze\" can only be used in server greater than or equal to version 1.17\n" +
" freeze: 0\n" +
"\n"
).getBytes());
out.close();
FileConfiguration fc = YamlConfiguration.loadConfiguration(file);
fc.set("version","2.2.0");
fc.set("attack.damage_modify",fc.getDouble("attack_damage_modify"));
fc.set("attack_damage_modify",null);
fc.get("attack.potion_effect",fc.getStringList("attack_potion_effect"));
fc.set("attack_potion_effect",null);
fc.save(file);
}
}
}
}
String lang_name = config_old.getString("lang","English") + ".yml";
FileConfiguration lang_old = lang;
if("2.1.0".equals(lang_old.getString("version"))){
Config.saveResource("lang/"+lang_name,"new/lang/"+lang_name,true);
File lang_new_F = new File(plugin.getDataFolder(),"new/lang/"+lang_name);
FileConfiguration lang_new = YamlConfiguration.loadConfiguration(lang_new_F);
lang_old.getKeys(true).forEach(key->{
Object obj = lang_old.get(key);
lang_new.set(key,obj);
});
lang_new.set("version","2.2.0");
lang_new.save(lang_new_F);
}
else Lang.error("The version of "+lang_name+" is not supported!");
FileConfiguration data_old = EnderDragon.data;
if("2.1.0".equals(data_old.getString("version"))){
Config.copyFile("data.yml","new/data.yml",true);
File new_data_file = new File(plugin.getDataFolder(),"new/data.yml");
FileConfiguration new_data = YamlConfiguration.loadConfiguration(new_data_file);
String next_time = new_data.getString("auto_respawn.next_respawn_time");
new_data.set("version","2.2.0");
if(next_time!=null && respawn_world_name!=null){
new_data.set("auto_respawn.task1.world_name",respawn_world_name);
new_data.set("auto_respawn.task1.next_respawn_time",next_time);
}
new_data.save(new_data_file);
}
else Lang.error("The version of data.yml is not supported!");
Lang.info("New config files are generated in plugins/EnderDragon/new."); Lang.info("New config files are generated in plugins/EnderDragon/new.");
Lang.warn("Attention: Please confirm the accuracy before using new config!"); Lang.warn("Attention: Please confirm the accuracy before using new config!");
} }
@@ -4,20 +4,20 @@ import org.bukkit.entity.EnderDragon;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import org.bukkit.event.HandlerList; import org.bukkit.event.HandlerList;
import org.bukkit.event.entity.EntityDamageByEntityEvent; import org.bukkit.event.entity.EntityDamageByEntityEvent;
/**
* Called when a dragon is damaged by a player, including block_explosion.
*/
public final class DragonDamageByPlayerEvent extends EntityDamageByEntityEvent { public final class DragonDamageByPlayerEvent extends EntityDamageByEntityEvent {
private static final HandlerList handlers = new HandlerList(); private static final HandlerList handlers = new HandlerList();
private boolean cancel = false; private boolean cancel = false;
private final Player damager; private final Player damager;
private final EnderDragon dragon; private final EnderDragon dragon;
private final DamageCause cause;
private final double finalDamage; private final double finalDamage;
public DragonDamageByPlayerEvent(final Player damager, final EnderDragon dragon, final DamageCause cause, final double finalDamage) { public DragonDamageByPlayerEvent(final Player damager, final EnderDragon dragon, final DamageCause cause, final double finalDamage) {
super(damager, dragon, cause, finalDamage); super(damager, dragon, cause, finalDamage);
this.damager = damager; this.damager = damager;
this.dragon = dragon; this.dragon = dragon;
this.cause = cause;
this.finalDamage = finalDamage; this.finalDamage = finalDamage;
} }
@@ -29,15 +29,15 @@ public final class DragonDamageByPlayerEvent extends EntityDamageByEntityEvent {
public HandlerList getHandlers() { public HandlerList getHandlers() {
return handlers; return handlers;
} }
@Override
public void setCancelled(final boolean cancel) { public void setCancelled(final boolean cancel) {
this.cancel = cancel; this.cancel = cancel;
} }
@Override
public boolean isCancelled() { public boolean isCancelled() {
return cancel; return cancel;
} }
@Override
public Player getDamager() { public Player getDamager() {
return damager; return damager;
} }
@@ -46,9 +46,6 @@ public final class DragonDamageByPlayerEvent extends EntityDamageByEntityEvent {
return dragon; return dragon;
} }
public DamageCause getDamagerCause() {
return cause;
}
@Override @Override
public double getDamage() { public double getDamage() {
return finalDamage; return finalDamage;
@@ -0,0 +1,55 @@
package pers.xanadu.enderdragon.event;
import org.bukkit.Location;
import org.bukkit.World;
import org.bukkit.entity.EnderDragon;
import org.bukkit.event.HandlerList;
import org.bukkit.event.entity.CreatureSpawnEvent;
import pers.xanadu.enderdragon.manager.DragonManager;
import pers.xanadu.enderdragon.util.MyDragon;
/**
* Called when a dragon is spawned, filtered through blacklist.
* <p>
* Cancelling this event make no changes.
*/
public final class DragonRespawnPostEvent extends CreatureSpawnEvent {
private static final HandlerList handlers = new HandlerList();
private boolean cancel = false;
private final World world;
private final MyDragon myDragon;
public DragonRespawnPostEvent(final EnderDragon dragon, final SpawnReason reason, final MyDragon myDragon) {
super(dragon,reason);
world = dragon.getWorld();
this.myDragon = myDragon;
}
public EnderDragon getEnderDragon(){
return (EnderDragon) getEntity();
}
public Location getEndPortalLocation(){
return DragonManager.getEndPortalLocation(world);
}
public MyDragon getDragonConfiguration(){
return myDragon;
}
public String getDragonUniqueId(){
return myDragon.unique_name;
}
public static HandlerList getHandlerList() {
return handlers;
}
@Override
public HandlerList getHandlers() {
return handlers;
}
@Override
public void setCancelled(final boolean cancel) {
this.cancel = cancel;
}
@Override
public boolean isCancelled() {
return cancel;
}
}
@@ -7,6 +7,7 @@ import org.bukkit.World;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import pers.xanadu.enderdragon.EnderDragon; import pers.xanadu.enderdragon.EnderDragon;
import pers.xanadu.enderdragon.manager.DragonManager;
import pers.xanadu.enderdragon.manager.TimerManager; import pers.xanadu.enderdragon.manager.TimerManager;
import pers.xanadu.enderdragon.task.DragonRespawnTimer; import pers.xanadu.enderdragon.task.DragonRespawnTimer;
import pers.xanadu.enderdragon.util.MathUtil; import pers.xanadu.enderdragon.util.MathUtil;
@@ -46,8 +47,7 @@ public class Papi extends PlaceholderExpansion {
public String onPlaceholderRequest(final Player player, final @NotNull String params){ public String onPlaceholderRequest(final Player player, final @NotNull String params){
if(params.equals("can_respawn")){ if(params.equals("can_respawn")){
if(player == null) return String.valueOf(false); if(player == null) return String.valueOf(false);
boolean res = EnderDragon.getInstance().getDragonManager().canRespawn(player.getWorld()); return String.valueOf(DragonManager.canRespawn(player.getWorld()));
return String.valueOf(res);
} }
if(params.equals("respawn_cd_progress")){ if(params.equals("respawn_cd_progress")){
if(player == null) return null; if(player == null) return null;
@@ -73,8 +73,7 @@ public class Papi extends PlaceholderExpansion {
if(params.startsWith("can_respawn_")){ if(params.startsWith("can_respawn_")){
String name = params.substring("can_respawn_".length()); String name = params.substring("can_respawn_".length());
World world = Bukkit.getWorld(name); World world = Bukkit.getWorld(name);
boolean res = EnderDragon.getInstance().getDragonManager().canRespawn(world); return String.valueOf(DragonManager.canRespawn(world));
return String.valueOf(res);
} }
if(params.startsWith("respawn_cd_progress_")){ if(params.startsWith("respawn_cd_progress_")){
String name = params.substring("respawn_cd_progress_".length()); String name = params.substring("respawn_cd_progress_".length());
@@ -20,13 +20,17 @@ public class DragonBaseHurtListener implements Listener {
EnderDragon dragon = (EnderDragon) victim; EnderDragon dragon = (EnderDragon) victim;
if(entity instanceof Player){ if(entity instanceof Player){
Player player = (Player) entity; Player player = (Player) entity;
pm.callEvent(new DragonDamageByPlayerEvent(player,dragon,e.getCause(),e.getFinalDamage())); DragonDamageByPlayerEvent event = new DragonDamageByPlayerEvent(player,dragon,e.getCause(),e.getFinalDamage());
pm.callEvent(event);
if(event.isCancelled()) e.setCancelled(true);
} }
else if(entity instanceof Projectile){ else if(entity instanceof Projectile){
Projectile projectile = (Projectile) entity; Projectile projectile = (Projectile) entity;
if(!(projectile.getShooter() instanceof Player)) return; if(!(projectile.getShooter() instanceof Player)) return;
Player damager = (Player) projectile.getShooter(); Player damager = (Player) projectile.getShooter();
pm.callEvent(new DragonDamageByPlayerEvent(damager,dragon,e.getCause(),e.getFinalDamage())); DragonDamageByPlayerEvent event = new DragonDamageByPlayerEvent(damager,dragon,e.getCause(),e.getFinalDamage());
pm.callEvent(event);
if(event.isCancelled()) e.setCancelled(true);
} }
} }
} }
@@ -19,6 +19,7 @@ public class DragonDamageByPlayerListener implements Listener {
@EventHandler(priority = EventPriority.HIGHEST) @EventHandler(priority = EventPriority.HIGHEST)
public void OnDragonDamageByPlayer(final DragonDamageByPlayerEvent e){ public void OnDragonDamageByPlayer(final DragonDamageByPlayerEvent e){
if(e.isCancelled()) return;
Player p = e.getDamager(); Player p = e.getDamager();
EnderDragon dragon = e.getDragon(); EnderDragon dragon = e.getDragon();
double health = dragon.getHealth(); double health = dragon.getHealth();
@@ -39,7 +39,9 @@ public class DragonExplosionHurtListener implements Listener {
TNTPrimed tnt = (TNTPrimed) entity; TNTPrimed tnt = (TNTPrimed) entity;
if(!(tnt.getSource() instanceof Player)) return; if(!(tnt.getSource() instanceof Player)) return;
Player damager = (Player) tnt.getSource(); Player damager = (Player) tnt.getSource();
pers.xanadu.enderdragon.EnderDragon.pm.callEvent(new DragonDamageByPlayerEvent(damager,dragon,e.getCause(),e.getFinalDamage())); DragonDamageByPlayerEvent event = new DragonDamageByPlayerEvent(damager,dragon,e.getCause(),e.getFinalDamage());
pm.callEvent(event);
if(event.isCancelled()) e.setCancelled(true);
} }
} }
} }
@@ -54,16 +56,15 @@ public class DragonExplosionHurtListener implements Listener {
if(e.getCause() != EntityDamageEvent.DamageCause.BLOCK_EXPLOSION) return; if(e.getCause() != EntityDamageEvent.DamageCause.BLOCK_EXPLOSION) return;
Entity entity = e.getEntity(); Entity entity = e.getEntity();
if(entity instanceof EnderDragon){ if(entity instanceof EnderDragon){
//Bukkit.broadcastMessage(e.getFinalDamage()+"awa");
EnderDragon dragon = (EnderDragon) entity; EnderDragon dragon = (EnderDragon) entity;
for(UUID uuid : mp.keySet()){ for(UUID uuid : mp.keySet()){
PlayerExplodeDragonEvent ped = mp.get(uuid); PlayerExplodeDragonEvent ped = mp.get(uuid);
if(ped == null) continue; if(ped == null) continue;
if(ped.getTime() != time) continue; if(ped.getTime() != time) continue;
if(ped.getEnderDragon().getUniqueId() != dragon.getUniqueId()) continue; if(ped.getEnderDragon().getUniqueId() != dragon.getUniqueId()) continue;
//mp.remove(uuid); DragonDamageByPlayerEvent event = new DragonDamageByPlayerEvent(ped.getPlayer(),dragon,cause,e.getFinalDamage());
pm.callEvent(new DragonDamageByPlayerEvent(ped.getPlayer(),dragon,cause,e.getFinalDamage())); pm.callEvent(event);
//Bukkit.broadcastMessage("final: "+e.getFinalDamage()); if(event.isCancelled()) e.setCancelled(true);
break; break;
} }
} }
@@ -82,7 +83,6 @@ public class DragonExplosionHurtListener implements Listener {
} }
} }
public static void clearUID(final UUID uuid){ public static void clearUID(final UUID uuid){
mp.remove(uuid); mp.remove(uuid);
} }
@@ -1,5 +1,6 @@
package pers.xanadu.enderdragon.listener; package pers.xanadu.enderdragon.listener;
import org.bukkit.Bukkit;
import org.bukkit.attribute.Attribute; import org.bukkit.attribute.Attribute;
import org.bukkit.boss.BarColor; import org.bukkit.boss.BarColor;
import org.bukkit.boss.BarStyle; import org.bukkit.boss.BarStyle;
@@ -11,10 +12,12 @@ import org.bukkit.event.Listener;
import org.bukkit.event.entity.CreatureSpawnEvent; import org.bukkit.event.entity.CreatureSpawnEvent;
import pers.xanadu.enderdragon.config.Config; import pers.xanadu.enderdragon.config.Config;
import pers.xanadu.enderdragon.config.Lang; import pers.xanadu.enderdragon.config.Lang;
import pers.xanadu.enderdragon.event.DragonRespawnPostEvent;
import pers.xanadu.enderdragon.manager.DamageManager; import pers.xanadu.enderdragon.manager.DamageManager;
import pers.xanadu.enderdragon.util.MyDragon; import pers.xanadu.enderdragon.util.MyDragon;
import pers.xanadu.enderdragon.util.Version; import pers.xanadu.enderdragon.util.Version;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.ConcurrentHashMap;
import static pers.xanadu.enderdragon.EnderDragon.*; import static pers.xanadu.enderdragon.EnderDragon.*;
@@ -26,8 +29,13 @@ public class DragonSpawnListener implements Listener {
public void OnDragonSpawn(final CreatureSpawnEvent e){ public void OnDragonSpawn(final CreatureSpawnEvent e){
if(!(e.getEntity() instanceof EnderDragon)) return; if(!(e.getEntity() instanceof EnderDragon)) return;
if(Config.blacklist_worlds.contains(e.getEntity().getWorld().getName())) return; if(Config.blacklist_worlds.contains(e.getEntity().getWorld().getName())) return;
if(Config.blacklist_spawn_reason.contains(e.getSpawnReason().name())) return;
EnderDragon dragon = (EnderDragon) e.getEntity(); EnderDragon dragon = (EnderDragon) e.getEntity();
MyDragon myDragon = judge(); MyDragon myDragon = null;
if(e.getSpawnReason() == CreatureSpawnEvent.SpawnReason.DEFAULT){
myDragon = getDesignatedDragon(dragon.getWorld());
}
if(myDragon == null) myDragon = judge();
if(myDragon == null) { if(myDragon == null) {
Lang.warn("special_dragon_jude_mode setting error!"); Lang.warn("special_dragon_jude_mode setting error!");
return; return;
@@ -50,8 +58,8 @@ public class DragonSpawnListener implements Listener {
modifyAttribute(dragon, Attribute.GENERIC_ARMOR_TOUGHNESS, myDragon.armor_toughness_modify); modifyAttribute(dragon, Attribute.GENERIC_ARMOR_TOUGHNESS, myDragon.armor_toughness_modify);
String color = myDragon.glow_color.toUpperCase(); String color = myDragon.glow_color.toUpperCase();
if(!color.equals("NONE")) setGlowingColor(dragon,getGlowColor(color)); if(color.equals("NONE")) dragon.setGlowing(false);
else dragon.setGlowing(false); else setGlowingColor(dragon,getGlowColor(color));
String bossBar_color = myDragon.bossbar_color.toUpperCase(); String bossBar_color = myDragon.bossbar_color.toUpperCase();
String bossBar_style = myDragon.bossbar_style.toUpperCase(); String bossBar_style = myDragon.bossbar_style.toUpperCase();
@@ -65,7 +73,10 @@ public class DragonSpawnListener implements Listener {
else if(Version.mcMainVersion >= 12){ else if(Version.mcMainVersion >= 12){
getInstance().getBossBarManager().setBossBar(dragon.getWorld(),myDragon.display_name,bossBar_color,bossBar_style); getInstance().getBossBarManager().setBossBar(dragon.getWorld(),myDragon.display_name,bossBar_color,bossBar_style);
} }
//dragon.getMetadata(); Bukkit.getPluginManager().callEvent(new DragonRespawnPostEvent(dragon,e.getSpawnReason(),myDragon));
if(Config.advanced_setting_save_bossbar){
getInstance().getBossBarManager().saveBossBarData(Collections.singletonList(dragon.getWorld()));
}
} }
} }
@@ -49,6 +49,7 @@ public class PlayerListener implements Listener {
Location cen = block.getLocation().clone().add(0.5,1,0.5); Location cen = block.getLocation().clone().add(0.5,1,0.5);
Collection<Entity> list = world.getNearbyEntities(cen,0.5,1,0.5); Collection<Entity> list = world.getNearbyEntities(cen,0.5,1,0.5);
if(!list.isEmpty()) return; if(!list.isEmpty()) return;
if(e.getPlayer().getGameMode() == GameMode.ADVENTURE) return;
e.setCancelled(true); e.setCancelled(true);
if(e.getPlayer().getGameMode() != GameMode.CREATIVE){ if(e.getPlayer().getGameMode() != GameMode.CREATIVE){
ItemStack item = e.getItem(); ItemStack item = e.getItem();
@@ -21,6 +21,7 @@ public class PlayerAttackListener implements Listener {
if(final_damage > 0.0d){ if(final_damage > 0.0d){
DragonDamageByPlayerEvent event = new DragonDamageByPlayerEvent(e.getAttacker().getPlayer(),dragon, e.toBukkit().getCause(), final_damage); DragonDamageByPlayerEvent event = new DragonDamageByPlayerEvent(e.getAttacker().getPlayer(),dragon, e.toBukkit().getCause(), final_damage);
pm.callEvent(event); pm.callEvent(event);
if(event.isCancelled()) e.setCancelled(true);
} }
} }
@@ -33,10 +33,15 @@ public class DragonManager {
public static List<String> dragon_names = new ArrayList<>(); public static List<String> dragon_names = new ArrayList<>();
private static int sum = 0; private static int sum = 0;
private static final int[][] nxt = {{3,0},{0,3},{-3,0},{0,-3}}; private static final int[][] nxt = {{3,0},{0,3},{-3,0},{0,-3}};
private Method DragonBattle_e; private static final int[][] nxt_2 = {{2,0},{0,2},{-2,0},{0,-2}};
private Method getX; private static final String getEDB_base;
private Method getY; private static Class<?> CraftWorldClass;
private Method getZ; private static Class<?> WorldProviderTheEndClass;
private static Class<?> EnderDragonBattleClass;
private static Method DragonBattle_e;
private static Method getX;
private static Method getY;
private static Method getZ;
public static void reload(){ public static void reload(){
new BukkitRunnable(){ new BukkitRunnable(){
@@ -278,25 +283,77 @@ public class DragonManager {
instance.addModifier(new AttributeModifier("EnderDragon",amount,AttributeModifier.Operation.ADD_NUMBER)); instance.addModifier(new AttributeModifier("EnderDragon",amount,AttributeModifier.Operation.ADD_NUMBER));
} }
public void initiateRespawn(final Player p){ public static void initiateRespawn(final Player p,final String uniqueId){
DragonRespawnResult res = initiateRespawn(p.getWorld()); DragonRespawnResult res = initiateRespawn(p.getWorld(),uniqueId);
if(res == DragonRespawnResult.success) Lang.broadcastMSG(Lang.dragon_auto_respawn); if(res == DragonRespawnResult.success) Lang.broadcastMSG(Lang.dragon_auto_respawn);
else Lang.sendFeedback(p,"§c"+res.getMessage()); else Lang.sendFeedback(p,"§c"+res.getMessage());
} }
public void initiateRespawn(final CommandSender sender,final String world_name){ public static void initiateRespawn(final CommandSender sender,final String world_name,final String uniqueId){
DragonRespawnResult res = initiateRespawn(Bukkit.getWorld(world_name)); DragonRespawnResult res = initiateRespawn(Bukkit.getWorld(world_name),uniqueId);
if(res == DragonRespawnResult.success) Lang.broadcastMSG(Lang.dragon_auto_respawn); if(res == DragonRespawnResult.success) Lang.broadcastMSG(Lang.dragon_auto_respawn);
else Lang.sendFeedback(sender,"§c"+res.getMessage()); else Lang.sendFeedback(sender,"§c"+res.getMessage());
} }
public void initiateRespawn(final String world_name){ public static void initiateRespawn(final String world_name,final String uniqueId){
DragonRespawnResult res = initiateRespawn(Bukkit.getWorld(world_name)); DragonRespawnResult res = initiateRespawn(Bukkit.getWorld(world_name),uniqueId);
if(res == DragonRespawnResult.success) Lang.broadcastMSG(Lang.dragon_auto_respawn); if(res == DragonRespawnResult.success) Lang.broadcastMSG(Lang.dragon_auto_respawn);
else Lang.error(res.getMessage()); else Lang.error(res.getMessage());
} }
public boolean canRespawn(final String world_name){ public static DragonRespawnResult initiateRespawn(final World world,final String uniqueId){
if(world == null) return DragonRespawnResult.world_not_found;
if(world.getEnvironment() != World.Environment.THE_END) return DragonRespawnResult.world_wrong_env;
if(Version.mcMainVersion >= 16){
DragonBattle battle = world.getEnderDragonBattle();
assert battle != null;
if(battle.getEnderDragon() != null) return DragonRespawnResult.dragon_has_existed;
if(battle.getRespawnPhase() != DragonBattle.RespawnPhase.NONE) return DragonRespawnResult.respawn_has_started;
Location cen = battle.getEndPortalLocation();
if(cen == null) {
battle.initiateRespawn();
cen = battle.getEndPortalLocation();
if(cen == null){
return DragonRespawnResult.world_unloaded;//也可尝试chunk.load()
}
}
if(uniqueId == null) placeEndCrystals(cen);
else placeEndCrystals(cen,uniqueId);
battle.initiateRespawn();
return DragonRespawnResult.success;
}
try {
Object battle = getEnderDragonBattle(world);
assert battle != null;
Field k = EnderDragonBattleClass.getDeclaredField("k");
k.setAccessible(true);
Object dragonKilled = k.get(battle);
if(!((boolean) dragonKilled)) return DragonRespawnResult.dragon_has_existed;
Field p = EnderDragonBattleClass.getDeclaredField("p");
p.setAccessible(true);
Object phase = p.get(battle);
if(phase != null) return DragonRespawnResult.respawn_has_started;
Field field = EnderDragonBattleClass.getDeclaredField("o");
field.setAccessible(true);
Object BlockPosition = field.get(battle);
if(BlockPosition == null){
DragonBattle_e.invoke(battle);
BlockPosition = field.get(battle);
if(BlockPosition == null) return DragonRespawnResult.world_unloaded;
}
if(getX == null) getX = BlockPosition.getClass().getMethod("getX");
if(getY == null) getY = BlockPosition.getClass().getMethod("getY");
if(getZ == null) getZ = BlockPosition.getClass().getMethod("getZ");
Location loc = new Location(world,(int)getX.invoke(BlockPosition),(int)getY.invoke(BlockPosition),(int)getZ.invoke(BlockPosition));
if(uniqueId == null) placeEndCrystals(loc);
else placeEndCrystals(loc,uniqueId);
DragonBattle_e.invoke(battle);
return DragonRespawnResult.success;
} catch (ReflectiveOperationException e) {
return DragonRespawnResult.version_not_support;
}
}
public static boolean canRespawn(final String world_name){
return canRespawn(Bukkit.getWorld(world_name)); return canRespawn(Bukkit.getWorld(world_name));
} }
public boolean canRespawn(final World world){ public static boolean canRespawn(final World world){
if(world == null) return false; if(world == null) return false;
if(world.getEnvironment() != World.Environment.THE_END) return false; if(world.getEnvironment() != World.Environment.THE_END) return false;
if(Version.mcMainVersion >= 16){//executes 1e5 times within 27ms if(Version.mcMainVersion >= 16){//executes 1e5 times within 27ms
@@ -315,22 +372,21 @@ public class DragonManager {
return true; return true;
} }
try {//executes 1e5 times within 76ms try {//executes 1e5 times within 76ms
Object battle = getInstance().getNMSManager().getEnderDragonBattle(world); Object battle = getEnderDragonBattle(world);
if(battle == null) return false; if(battle == null) return false;
Field k = battle.getClass().getDeclaredField("k"); Field k = EnderDragonBattleClass.getDeclaredField("k");
k.setAccessible(true); k.setAccessible(true);
Object isAlive = k.get(battle); Object dragonKilled = k.get(battle);
if(!((boolean) isAlive)) return false; if(!((boolean) dragonKilled)) return false;
Field p = battle.getClass().getDeclaredField("p"); Field p = EnderDragonBattleClass.getDeclaredField("p");
p.setAccessible(true); p.setAccessible(true);
Object phase = p.get(battle); Object phase = p.get(battle);
if(phase != null) return false; if(phase != null) return false;
Field field = battle.getClass().getDeclaredField("o"); Field field = EnderDragonBattleClass.getDeclaredField("o");
field.setAccessible(true); field.setAccessible(true);
Object BlockPosition = field.get(battle); Object BlockPosition = field.get(battle);
if(BlockPosition == null){ if(BlockPosition == null){
if (this.DragonBattle_e == null) this.DragonBattle_e = battle.getClass().getMethod("e"); DragonBattle_e.invoke(battle);
this.DragonBattle_e.invoke(battle);
BlockPosition = field.get(battle); BlockPosition = field.get(battle);
if(BlockPosition == null) return false; if(BlockPosition == null) return false;
} }
@@ -339,7 +395,39 @@ public class DragonManager {
return false; return false;
} }
} }
public boolean isRespawnRunning(final World world){ public static Location getEndPortalLocation(final World world){
if(world == null) return null;
if(world.getEnvironment() != World.Environment.THE_END) return null;
if(Version.mcMainVersion >= 16){
DragonBattle battle = world.getEnderDragonBattle();
if(battle == null) return null;
Location cen = battle.getEndPortalLocation();
if(cen == null) {
battle.initiateRespawn();
cen = battle.getEndPortalLocation();
}
return cen;
}
try {
Object battle = getEnderDragonBattle(world);
if(battle == null) return null;
Field field = EnderDragonBattleClass.getDeclaredField("o");
field.setAccessible(true);
Object BlockPosition = field.get(battle);
if(BlockPosition == null){
DragonBattle_e.invoke(battle);
BlockPosition = field.get(battle);
if(BlockPosition == null) return null;
}
if(getX == null) getX = BlockPosition.getClass().getMethod("getX");
if(getY == null) getY = BlockPosition.getClass().getMethod("getY");
if(getZ == null) getZ = BlockPosition.getClass().getMethod("getZ");
return new Location(world,(int)getX.invoke(BlockPosition),(int)getY.invoke(BlockPosition),(int)getZ.invoke(BlockPosition));
} catch (ReflectiveOperationException e) {
return null;
}
}
public static boolean isRespawnRunning(final World world){
if(world == null) return false; if(world == null) return false;
if(world.getEnvironment() != World.Environment.THE_END) return false; if(world.getEnvironment() != World.Environment.THE_END) return false;
if(Version.mcMainVersion >= 16){ if(Version.mcMainVersion >= 16){
@@ -348,9 +436,9 @@ public class DragonManager {
return battle.getRespawnPhase() != DragonBattle.RespawnPhase.NONE; return battle.getRespawnPhase() != DragonBattle.RespawnPhase.NONE;
} }
try { try {
Object battle = getInstance().getNMSManager().getEnderDragonBattle(world); Object battle = getEnderDragonBattle(world);
assert battle != null; assert battle != null;
Field p = battle.getClass().getDeclaredField("p"); Field p = EnderDragonBattleClass.getDeclaredField("p");
p.setAccessible(true); p.setAccessible(true);
Object phase = p.get(battle); Object phase = p.get(battle);
return phase != null; return phase != null;
@@ -359,7 +447,7 @@ public class DragonManager {
return false; return false;
} }
} }
public void refresh_respawn(final World world){ public static void refresh_respawn(final World world){
if(world == null) return; if(world == null) return;
if(world.getEnvironment() != World.Environment.THE_END) return; if(world.getEnvironment() != World.Environment.THE_END) return;
if(Version.mcMainVersion >= 16){ if(Version.mcMainVersion >= 16){
@@ -369,16 +457,113 @@ public class DragonManager {
return; return;
} }
try { try {
Object battle = getInstance().getNMSManager().getEnderDragonBattle(world); Object battle = getEnderDragonBattle(world);
assert battle != null; assert battle != null;
if (this.DragonBattle_e == null) this.DragonBattle_e = battle.getClass().getMethod("e"); DragonBattle_e.invoke(battle);
this.DragonBattle_e.invoke(battle);
} catch (ReflectiveOperationException e) { } catch (ReflectiveOperationException e) {
e.printStackTrace(); e.printStackTrace();
} }
} }
private static void placeEndCrystals(final Location cen){
private DragonRespawnResult initiateRespawn(final World world){ World world = cen.getWorld();
if(world == null) return;
cen.add(0.5,1,0.5);
for(int i = 0; i < 4; i++){
EnderCrystal crystal = (EnderCrystal) world.spawnEntity(cen.clone().add(nxt[i][0],0,nxt[i][1]), EntityType.ENDER_CRYSTAL);
if(Config.crystal_invulnerable) crystal.setInvulnerable(true);
crystal.setShowingBottom(false);
}
}
private static void placeEndCrystals(final Location cen,final String uniqueId){
World world = cen.getWorld();
if(world == null) return;
cen.add(0.5,1,0.5);
for(int i=0;i<4;i++){
Location loc = cen.clone().add(nxt_2[i][0],0,nxt_2[i][1]);
world.getNearbyEntities(loc,0.5,0.5,0.5).forEach(entity -> {
if(entity instanceof EnderCrystal) entity.remove();
});
}
for(int i = 0; i < 4; i++){
EnderCrystal crystal = (EnderCrystal) world.spawnEntity(cen.clone().add(nxt[i][0],0,nxt[i][1]), EntityType.ENDER_CRYSTAL);
if(Config.crystal_invulnerable) crystal.setInvulnerable(true);
crystal.setShowingBottom(false);
crystal.addScoreboardTag("ed_spe_"+uniqueId);
}
}
public static MyDragon getDesignatedDragon(final World world){
List<EnderCrystal> list = new ArrayList<>();
Location cen = DragonManager.getEndPortalLocation(world).add(0.5,1,0.5);
for(int i=0;i<4;i++){
Location loc = cen.clone().add(nxt_2[i][0],0,nxt_2[i][1]);
world.getNearbyEntities(loc,0.5,0.5,0.5).forEach(entity -> {
if(entity instanceof EnderCrystal) list.add((EnderCrystal) entity);
});
}
for(EnderCrystal crystal : list) {
Set<String> tags = crystal.getScoreboardTags();
for(MyDragon a : dragons){
if(tags.contains("ed_spe_"+a.unique_name)) {
return a;
}
}
}
return null;
}
public static Object getEnderDragonBattle(final World world){
String version = Version.getVersion();
if (Version.mcMainVersion>=12 && Version.mcMainVersion<16) {
try {
Object worldServer = getWorldServer(world);
assert worldServer != null;
Field field = worldServer.getClass().getField("worldProvider");
Object worldProvider = field.get(worldServer);
Object WorldProviderTheEnd = WorldProviderTheEndClass.cast(worldProvider);
String method_name = getEDB_base;
if(method_name == null) return null;
Method method = WorldProviderTheEnd.getClass().getDeclaredMethod(method_name);
return method.invoke(WorldProviderTheEnd);
} catch (ReflectiveOperationException e) {
Lang.warn("Your server version (" + version + ") is not supported!");
e.printStackTrace();
}
}
Lang.warn("Your server version (" + version + ") is not supported!");
return null;
}
private static Object getWorldServer(final World world) {
try {
Object castClass = getCraftWorld(world);
return CraftWorldClass.getDeclaredMethod("getHandle").invoke(castClass);
} catch (ReflectiveOperationException e) {
e.printStackTrace();
}
return null;
}
private static Object getCraftWorld(final World world) {
if (CraftWorldClass.isInstance(world)) return CraftWorldClass.cast(world);
return null;
}
@Deprecated
public static void initiateRespawn(final Player p){
DragonRespawnResult res = initiateRespawn(p.getWorld());
if(res == DragonRespawnResult.success) Lang.broadcastMSG(Lang.dragon_auto_respawn);
else Lang.sendFeedback(p,"§c"+res.getMessage());
}
@Deprecated
public static void initiateRespawn(final CommandSender sender,final String world_name){
DragonRespawnResult res = initiateRespawn(Bukkit.getWorld(world_name));
if(res == DragonRespawnResult.success) Lang.broadcastMSG(Lang.dragon_auto_respawn);
else Lang.sendFeedback(sender,"§c"+res.getMessage());
}
@Deprecated
public static void initiateRespawn(final String world_name){
DragonRespawnResult res = initiateRespawn(Bukkit.getWorld(world_name));
if(res == DragonRespawnResult.success) Lang.broadcastMSG(Lang.dragon_auto_respawn);
else Lang.error(res.getMessage());
}
@Deprecated
public static DragonRespawnResult initiateRespawn(final World world){
if(world == null) return DragonRespawnResult.world_not_found; if(world == null) return DragonRespawnResult.world_not_found;
if(world.getEnvironment() != World.Environment.THE_END) return DragonRespawnResult.world_wrong_env; if(world.getEnvironment() != World.Environment.THE_END) return DragonRespawnResult.world_wrong_env;
if(Version.mcMainVersion >= 16){ if(Version.mcMainVersion >= 16){
@@ -391,53 +576,42 @@ public class DragonManager {
battle.initiateRespawn(); battle.initiateRespawn();
cen = battle.getEndPortalLocation(); cen = battle.getEndPortalLocation();
if(cen == null){ if(cen == null){
return DragonRespawnResult.world_unloaded;//也可尝试chunk.load() return DragonRespawnResult.world_unloaded;
} }
} }
placeEndCrystals(world,cen); placeEndCrystals(cen);
battle.initiateRespawn(); battle.initiateRespawn();
return DragonRespawnResult.success; return DragonRespawnResult.success;
} }
try { try {
Object battle = getInstance().getNMSManager().getEnderDragonBattle(world); Object battle = getEnderDragonBattle(world);
assert battle != null; assert battle != null;
Field k = battle.getClass().getDeclaredField("k"); Field k = EnderDragonBattleClass.getDeclaredField("k");
k.setAccessible(true); k.setAccessible(true);
Object isAlive = k.get(battle); Object dragonKilled = k.get(battle);
if(!((boolean) isAlive)) return DragonRespawnResult.dragon_has_existed; if(!((boolean) dragonKilled)) return DragonRespawnResult.dragon_has_existed;
Field p = battle.getClass().getDeclaredField("p"); Field p = EnderDragonBattleClass.getDeclaredField("p");
p.setAccessible(true); p.setAccessible(true);
Object phase = p.get(battle); Object phase = p.get(battle);
if(phase != null) return DragonRespawnResult.respawn_has_started; if(phase != null) return DragonRespawnResult.respawn_has_started;
Field field = battle.getClass().getDeclaredField("o"); Field field = EnderDragonBattleClass.getDeclaredField("o");
field.setAccessible(true); field.setAccessible(true);
Object BlockPosition = field.get(battle); Object BlockPosition = field.get(battle);
if(BlockPosition == null){ if(BlockPosition == null){
if (this.DragonBattle_e == null) this.DragonBattle_e = battle.getClass().getMethod("e"); DragonBattle_e.invoke(battle);
this.DragonBattle_e.invoke(battle);
BlockPosition = field.get(battle); BlockPosition = field.get(battle);
if(BlockPosition == null) return DragonRespawnResult.world_unloaded; if(BlockPosition == null) return DragonRespawnResult.world_unloaded;
} }
if(this.getX == null) this.getX = BlockPosition.getClass().getMethod("getX"); if(getX == null) getX = BlockPosition.getClass().getMethod("getX");
if(this.getY == null) this.getY = BlockPosition.getClass().getMethod("getY"); if(getY == null) getY = BlockPosition.getClass().getMethod("getY");
if(this.getZ == null) this.getZ = BlockPosition.getClass().getMethod("getZ"); if(getZ == null) getZ = BlockPosition.getClass().getMethod("getZ");
Location loc = new Location(world,(int)getX.invoke(BlockPosition),(int)this.getY.invoke(BlockPosition),(int)this.getZ.invoke(BlockPosition)); Location loc = new Location(world,(int)getX.invoke(BlockPosition),(int)getY.invoke(BlockPosition),(int)getZ.invoke(BlockPosition));
placeEndCrystals(world, loc); placeEndCrystals(loc);
if (this.DragonBattle_e == null) this.DragonBattle_e = battle.getClass().getMethod("e"); DragonBattle_e.invoke(battle);
this.DragonBattle_e.invoke(battle);
return DragonRespawnResult.success; return DragonRespawnResult.success;
} catch (ReflectiveOperationException e) { } catch (ReflectiveOperationException e) {
return DragonRespawnResult.version_not_support; return DragonRespawnResult.version_not_support;
} }
}
private void placeEndCrystals(final World world,final Location cen){
cen.add(0.5,1,0.5);
for(int i = 0; i < 4; i++){
EnderCrystal crystal = (EnderCrystal) world.spawnEntity(cen.clone().add(nxt[i][0],0,nxt[i][1]), EntityType.ENDER_CRYSTAL);
if(Config.crystal_invulnerable) crystal.setInvulnerable(true);
crystal.setShowingBottom(false);
}
} }
public enum DragonRespawnResult{ public enum DragonRespawnResult{
success, success,
@@ -461,4 +635,37 @@ public class DragonManager {
} }
} }
static{
String version = Version.getVersion();
switch (version) {
case "v1_12_R1" : {
getEDB_base = "t";
break;
}
case "v1_13_R1" :
case "v1_13_R2" : {
getEDB_base = "r";
break;
}
case "v1_14_R1" : {
getEDB_base = "q";
break;
}
case "v1_15_R1" : {
getEDB_base = "o";
break;
}
default : getEDB_base = null;
}
if(Version.mcMainVersion>=12 && Version.mcMainVersion<16){
try{
CraftWorldClass = Class.forName("org.bukkit.craftbukkit." + version + ".CraftWorld");
WorldProviderTheEndClass = Class.forName("net.minecraft.server."+version+".WorldProviderTheEnd");
EnderDragonBattleClass = Class.forName("net.minecraft.server."+version+".EnderDragonBattle");
DragonBattle_e = EnderDragonBattleClass.getMethod("e");
}catch (ReflectiveOperationException e){
e.printStackTrace();
}
}
}
} }
@@ -7,6 +7,7 @@ import org.bukkit.configuration.InvalidConfigurationException;
import org.bukkit.configuration.file.YamlConfiguration; import org.bukkit.configuration.file.YamlConfiguration;
import org.bukkit.craftbukkit.v1_12_R1.util.CraftChatMessage; import org.bukkit.craftbukkit.v1_12_R1.util.CraftChatMessage;
import pers.xanadu.enderdragon.config.Lang; import pers.xanadu.enderdragon.config.Lang;
import pers.xanadu.enderdragon.manager.DragonManager;
import pers.xanadu.enderdragon.nms.BossBar.I_BossBarManager; import pers.xanadu.enderdragon.nms.BossBar.I_BossBarManager;
import java.io.File; import java.io.File;
@@ -14,7 +15,6 @@ import java.io.IOException;
import java.lang.reflect.Field; import java.lang.reflect.Field;
import java.util.List; import java.util.List;
import static pers.xanadu.enderdragon.EnderDragon.getInstance;
import static pers.xanadu.enderdragon.EnderDragon.plugin; import static pers.xanadu.enderdragon.EnderDragon.plugin;
public class BossBarManager implements I_BossBarManager { public class BossBarManager implements I_BossBarManager {
@@ -24,7 +24,8 @@ public class BossBarManager implements I_BossBarManager {
YamlConfiguration yml = new YamlConfiguration(); YamlConfiguration yml = new YamlConfiguration();
worlds.forEach(world -> { worlds.forEach(world -> {
try{ try{
Object edb = getInstance().getNMSManager().getEnderDragonBattle(world); Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("c"); if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("c");
BossBattleServer.setAccessible(true); BossBattleServer.setAccessible(true);
BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb); BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb);
@@ -56,7 +57,8 @@ public class BossBarManager implements I_BossBarManager {
} }
worlds.forEach(world -> { worlds.forEach(world -> {
try{ try{
Object edb = getInstance().getNMSManager().getEnderDragonBattle(world); Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("c"); if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("c");
BossBattleServer.setAccessible(true); BossBattleServer.setAccessible(true);
BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb); BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb);
@@ -79,7 +81,8 @@ public class BossBarManager implements I_BossBarManager {
bbs.setDarkenSky(true); bbs.setDarkenSky(true);
bbs.setPlayMusic(true); bbs.setPlayMusic(true);
try{ try{
Object edb = getInstance().getNMSManager().getEnderDragonBattle(world); Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("c"); if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("c");
BossBattleServer.setAccessible(true); BossBattleServer.setAccessible(true);
BossBattleServer.set(edb,bbs); BossBattleServer.set(edb,bbs);
@@ -7,6 +7,7 @@ import org.bukkit.configuration.InvalidConfigurationException;
import org.bukkit.configuration.file.YamlConfiguration; import org.bukkit.configuration.file.YamlConfiguration;
import org.bukkit.craftbukkit.v1_13_R1.util.CraftChatMessage; import org.bukkit.craftbukkit.v1_13_R1.util.CraftChatMessage;
import pers.xanadu.enderdragon.config.Lang; import pers.xanadu.enderdragon.config.Lang;
import pers.xanadu.enderdragon.manager.DragonManager;
import pers.xanadu.enderdragon.nms.BossBar.I_BossBarManager; import pers.xanadu.enderdragon.nms.BossBar.I_BossBarManager;
import java.io.File; import java.io.File;
@@ -14,7 +15,6 @@ import java.io.IOException;
import java.lang.reflect.Field; import java.lang.reflect.Field;
import java.util.List; import java.util.List;
import static pers.xanadu.enderdragon.EnderDragon.getInstance;
import static pers.xanadu.enderdragon.EnderDragon.plugin; import static pers.xanadu.enderdragon.EnderDragon.plugin;
public class BossBarManager implements I_BossBarManager { public class BossBarManager implements I_BossBarManager {
@@ -24,7 +24,8 @@ public class BossBarManager implements I_BossBarManager {
YamlConfiguration yml = new YamlConfiguration(); YamlConfiguration yml = new YamlConfiguration();
worlds.forEach(world -> { worlds.forEach(world -> {
try{ try{
Object edb = getInstance().getNMSManager().getEnderDragonBattle(world); Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("c"); if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("c");
BossBattleServer.setAccessible(true); BossBattleServer.setAccessible(true);
BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb); BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb);
@@ -56,7 +57,8 @@ public class BossBarManager implements I_BossBarManager {
} }
worlds.forEach(world -> { worlds.forEach(world -> {
try{ try{
Object edb = getInstance().getNMSManager().getEnderDragonBattle(world); Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("c"); if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("c");
BossBattleServer.setAccessible(true); BossBattleServer.setAccessible(true);
BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb); BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb);
@@ -79,7 +81,8 @@ public class BossBarManager implements I_BossBarManager {
bbs.setDarkenSky(true); bbs.setDarkenSky(true);
bbs.setPlayMusic(true); bbs.setPlayMusic(true);
try{ try{
Object edb = getInstance().getNMSManager().getEnderDragonBattle(world); Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("c"); if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("c");
BossBattleServer.setAccessible(true); BossBattleServer.setAccessible(true);
BossBattleServer.set(edb,bbs); BossBattleServer.set(edb,bbs);
@@ -7,6 +7,7 @@ import org.bukkit.configuration.InvalidConfigurationException;
import org.bukkit.configuration.file.YamlConfiguration; import org.bukkit.configuration.file.YamlConfiguration;
import org.bukkit.craftbukkit.v1_13_R2.util.CraftChatMessage; import org.bukkit.craftbukkit.v1_13_R2.util.CraftChatMessage;
import pers.xanadu.enderdragon.config.Lang; import pers.xanadu.enderdragon.config.Lang;
import pers.xanadu.enderdragon.manager.DragonManager;
import pers.xanadu.enderdragon.nms.BossBar.I_BossBarManager; import pers.xanadu.enderdragon.nms.BossBar.I_BossBarManager;
import java.io.File; import java.io.File;
@@ -14,7 +15,6 @@ import java.io.IOException;
import java.lang.reflect.Field; import java.lang.reflect.Field;
import java.util.List; import java.util.List;
import static pers.xanadu.enderdragon.EnderDragon.getInstance;
import static pers.xanadu.enderdragon.EnderDragon.plugin; import static pers.xanadu.enderdragon.EnderDragon.plugin;
public class BossBarManager implements I_BossBarManager { public class BossBarManager implements I_BossBarManager {
@@ -24,7 +24,8 @@ public class BossBarManager implements I_BossBarManager {
YamlConfiguration yml = new YamlConfiguration(); YamlConfiguration yml = new YamlConfiguration();
worlds.forEach(world -> { worlds.forEach(world -> {
try{ try{
Object edb = getInstance().getNMSManager().getEnderDragonBattle(world); Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("bossBattle"); if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("bossBattle");
BossBattleServer.setAccessible(true); BossBattleServer.setAccessible(true);
BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb); BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb);
@@ -56,7 +57,8 @@ public class BossBarManager implements I_BossBarManager {
} }
worlds.forEach(world -> { worlds.forEach(world -> {
try{ try{
Object edb = getInstance().getNMSManager().getEnderDragonBattle(world); Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("bossBattle"); if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("bossBattle");
BossBattleServer.setAccessible(true); BossBattleServer.setAccessible(true);
BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb); BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb);
@@ -79,7 +81,8 @@ public class BossBarManager implements I_BossBarManager {
bbs.setDarkenSky(true); bbs.setDarkenSky(true);
bbs.setPlayMusic(true); bbs.setPlayMusic(true);
try{ try{
Object edb = getInstance().getNMSManager().getEnderDragonBattle(world); Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getField("bossBattle"); if(BossBattleServer == null) BossBattleServer = edb.getClass().getField("bossBattle");
BossBattleServer.setAccessible(true); BossBattleServer.setAccessible(true);
BossBattleServer.set(edb,bbs); BossBattleServer.set(edb,bbs);
@@ -0,0 +1,76 @@
package pers.xanadu.enderdragon.nms.BossBar.v1_14_R1;
import net.minecraft.server.v1_14_R1.BossBattle;
import net.minecraft.server.v1_14_R1.BossBattleServer;
import org.bukkit.World;
import org.bukkit.configuration.InvalidConfigurationException;
import org.bukkit.configuration.file.YamlConfiguration;
import org.bukkit.craftbukkit.v1_14_R1.util.CraftChatMessage;
import pers.xanadu.enderdragon.config.Lang;
import pers.xanadu.enderdragon.manager.DragonManager;
import pers.xanadu.enderdragon.nms.BossBar.I_BossBarManager;
import java.io.File;
import java.io.IOException;
import java.lang.reflect.Field;
import java.util.List;
import static pers.xanadu.enderdragon.EnderDragon.plugin;
public class BossBarManager implements I_BossBarManager {
private Field BossBattleServer = null;
public void saveBossBarData(List<World> worlds){
File file = new File(plugin.getDataFolder(),"world_data.yml");
YamlConfiguration yml = new YamlConfiguration();
worlds.forEach(world -> {
try{
Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("bossBattle");
BossBattleServer.setAccessible(true);
BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb);
String path = world.getName() + yml.options().pathSeparator();
yml.set(path+"title",bbs.title.getText());
yml.set(path+"color",bbs.color.name());
yml.set(path+"style",bbs.style.name());
}catch (ReflectiveOperationException e){
e.printStackTrace();
}
});
try{
yml.save(file);
Lang.info("BossBar data has been saved!");
}catch (IOException e){
Lang.error("Failed to save world_data!");
}
}
public void loadBossBarData(List<World> worlds){
File file = new File(plugin.getDataFolder(),"world_data.yml");
if(!file.exists()) return;
Lang.info("Enabling BossBar fix...");
YamlConfiguration yml = new YamlConfiguration();
try{
yml.load(file);
}catch (InvalidConfigurationException | IOException e) {
Lang.error("Failed to load world_data!");
return;
}
worlds.forEach(world -> {
try{
Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("bossBattle");
BossBattleServer.setAccessible(true);
BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb);
String path = world.getName() + yml.options().pathSeparator();
bbs.title = CraftChatMessage.fromString(yml.getString(path+"title"), true)[0];
bbs.color = BossBattle.BarColor.valueOf(yml.getString(path+"color"));
bbs.style = BossBattle.BarStyle.valueOf(yml.getString(path+"style"));
}catch (ReflectiveOperationException e){
e.printStackTrace();
}
});
}
public void setBossBar(World world,String title,String color,String style){
}
}
@@ -0,0 +1,77 @@
package pers.xanadu.enderdragon.nms.BossBar.v1_15_R1;
import net.minecraft.server.v1_15_R1.BossBattle;
import net.minecraft.server.v1_15_R1.BossBattleServer;
import org.bukkit.World;
import org.bukkit.configuration.InvalidConfigurationException;
import org.bukkit.configuration.file.YamlConfiguration;
import org.bukkit.craftbukkit.v1_15_R1.util.CraftChatMessage;
import pers.xanadu.enderdragon.config.Lang;
import pers.xanadu.enderdragon.manager.DragonManager;
import pers.xanadu.enderdragon.nms.BossBar.I_BossBarManager;
import java.io.File;
import java.io.IOException;
import java.lang.reflect.Field;
import java.util.List;
import static pers.xanadu.enderdragon.EnderDragon.plugin;
public class BossBarManager implements I_BossBarManager {
private Field BossBattleServer = null;
public void saveBossBarData(List<World> worlds){
File file = new File(plugin.getDataFolder(),"world_data.yml");
YamlConfiguration yml = new YamlConfiguration();
worlds.forEach(world -> {
try{
Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("bossBattle");
BossBattleServer.setAccessible(true);
BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb);
String path = world.getName() + yml.options().pathSeparator();
yml.set(path+"title",bbs.title.getText());
yml.set(path+"color",bbs.color.name());
yml.set(path+"style",bbs.style.name());
}catch (ReflectiveOperationException e){
e.printStackTrace();
}
});
try{
yml.save(file);
Lang.info("BossBar data has been saved!");
}catch (IOException e){
Lang.error("Failed to save world_data!");
}
}
public void loadBossBarData(List<World> worlds){
File file = new File(plugin.getDataFolder(),"world_data.yml");
if(!file.exists()) return;
Lang.info("Enabling BossBar fix...");
YamlConfiguration yml = new YamlConfiguration();
try{
yml.load(file);
}catch (InvalidConfigurationException | IOException e) {
Lang.error("Failed to load world_data!");
return;
}
worlds.forEach(world -> {
try{
Object edb = DragonManager.getEnderDragonBattle(world);
assert edb != null;
if(BossBattleServer == null) BossBattleServer = edb.getClass().getDeclaredField("bossBattle");
BossBattleServer.setAccessible(true);
BossBattleServer bbs = (BossBattleServer) BossBattleServer.get(edb);
String path = world.getName() + yml.options().pathSeparator();
bbs.title = CraftChatMessage.fromString(yml.getString(path+"title"), true)[0];
bbs.color = BossBattle.BarColor.valueOf(yml.getString(path+"color"));
bbs.style = BossBattle.BarStyle.valueOf(yml.getString(path+"style"));
}catch (ReflectiveOperationException e){
e.printStackTrace();
}
});
}
public void setBossBar(World world,String title,String color,String style){
}
}
@@ -0,0 +1,62 @@
package pers.xanadu.enderdragon.nms.BossBar.v1_16_R1_above;
import org.bukkit.World;
import org.bukkit.boss.BarColor;
import org.bukkit.boss.BarStyle;
import org.bukkit.boss.BossBar;
import org.bukkit.boss.DragonBattle;
import org.bukkit.configuration.InvalidConfigurationException;
import org.bukkit.configuration.file.YamlConfiguration;
import pers.xanadu.enderdragon.config.Lang;
import pers.xanadu.enderdragon.nms.BossBar.I_BossBarManager;
import java.io.File;
import java.io.IOException;
import java.util.List;
import static pers.xanadu.enderdragon.EnderDragon.plugin;
public class BossBarManager implements I_BossBarManager {
public void saveBossBarData(List<World> worlds){
File file = new File(plugin.getDataFolder(),"world_data.yml");
YamlConfiguration yml = new YamlConfiguration();
worlds.forEach(world -> {
DragonBattle battle = world.getEnderDragonBattle();
if(battle == null) return;
BossBar bossBar = battle.getBossBar();
String path = world.getName() + yml.options().pathSeparator();
yml.set(path+"title",bossBar.getTitle());
yml.set(path+"color",bossBar.getColor().name());
yml.set(path+"style",bossBar.getStyle().name());
});
try{
yml.save(file);
Lang.info("BossBar data has been saved!");
}catch (IOException e){
Lang.error("Failed to save world_data!");
}
}
public void loadBossBarData(List<World> worlds){
File file = new File(plugin.getDataFolder(),"world_data.yml");
if(!file.exists()) return;
Lang.info("Enabling BossBar fix...");
YamlConfiguration yml = new YamlConfiguration();
try{
yml.load(file);
}catch (InvalidConfigurationException | IOException e) {
Lang.error("Failed to load world_data!");
return;
}
worlds.forEach(world -> {
DragonBattle battle = world.getEnderDragonBattle();
if(battle == null) return;
BossBar bossBar = battle.getBossBar();
String path = world.getName() + yml.options().pathSeparator();
bossBar.setTitle(yml.getString(path+"title"));
bossBar.setColor(BarColor.valueOf(yml.getString(path+"color")));
bossBar.setStyle(BarStyle.valueOf(yml.getString(path+"style")));
});
}
public void setBossBar(World world,String title,String color,String style){
}
}
@@ -1,11 +1,15 @@
package pers.xanadu.enderdragon.nms.NMSItem; package pers.xanadu.enderdragon.nms.NMSItem;
import org.bukkit.inventory.ItemStack; import org.bukkit.inventory.ItemStack;
import org.jetbrains.annotations.TestOnly;
public interface I_NMSItemManager { public interface I_NMSItemManager {
ItemStack readAsItem(String nbt); ItemStack readAsItem(String nbt);
ItemStack cpdToItem(Object cpd); ItemStack cpdToItem(Object cpd);
@TestOnly
Object parseNBT(Object nbt_base); Object parseNBT(Object nbt_base);
@TestOnly
Object readAsNBTBase(String raw); Object readAsNBTBase(String raw);
@TestOnly
Object getNBTBase(Object obj); Object getNBTBase(Object obj);
} }
@@ -70,9 +70,6 @@ public class Events<T extends Event> implements Listener, EventExecutor {
GroovyManager.event_set.add(tmp); GroovyManager.event_set.add(tmp);
return tmp; return tmp;
} }
// private static <T extends Event> void register(Class<T> clazz, Events<T> event, EventPriority priority, boolean ignoreCancelled) {
// Bukkit.getPluginManager().registerEvent(clazz,event,priority,event,plugin,ignoreCancelled);
// }
@Override @Override
public void execute(@NotNull Listener listener, @NotNull Event event) { public void execute(@NotNull Listener listener, @NotNull Event event) {
@@ -3,6 +3,7 @@ package pers.xanadu.enderdragon.task;
import org.bukkit.scheduler.BukkitRunnable; import org.bukkit.scheduler.BukkitRunnable;
import pers.xanadu.enderdragon.config.Lang; import pers.xanadu.enderdragon.config.Lang;
import pers.xanadu.enderdragon.EnderDragon; import pers.xanadu.enderdragon.EnderDragon;
import pers.xanadu.enderdragon.manager.DragonManager;
import static pers.xanadu.enderdragon.EnderDragon.*; import static pers.xanadu.enderdragon.EnderDragon.*;
@@ -22,7 +23,7 @@ public class DragonRespawnRunnable extends BukkitRunnable {
new BukkitRunnable(){ new BukkitRunnable(){
@Override @Override
public void run(){ public void run(){
EnderDragon.getInstance().getDragonManager().initiateRespawn(task.world_name); DragonManager.initiateRespawn(task.world_name);
task.updateTime(); task.updateTime();
task.saveFile(); task.saveFile();
} }
@@ -4,6 +4,7 @@ import org.bukkit.Bukkit;
import org.bukkit.scheduler.BukkitRunnable; import org.bukkit.scheduler.BukkitRunnable;
import pers.xanadu.enderdragon.EnderDragon; import pers.xanadu.enderdragon.EnderDragon;
import pers.xanadu.enderdragon.config.Lang; import pers.xanadu.enderdragon.config.Lang;
import pers.xanadu.enderdragon.manager.DragonManager;
import pers.xanadu.enderdragon.util.MathUtil; import pers.xanadu.enderdragon.util.MathUtil;
import static pers.xanadu.enderdragon.EnderDragon.plugin; import static pers.xanadu.enderdragon.EnderDragon.plugin;
@@ -65,8 +66,8 @@ public class DragonRespawnTimer {
remainSecond--; remainSecond--;
if(remainSecond <= 0){ if(remainSecond <= 0){
Bukkit.getScheduler().runTask(plugin,() -> { Bukkit.getScheduler().runTask(plugin,() -> {
if(EnderDragon.getInstance().getDragonManager().canRespawn(world_name)){ if(DragonManager.canRespawn(world_name)){
EnderDragon.getInstance().getDragonManager().initiateRespawn(world_name); DragonManager.initiateRespawn(world_name);
update(); update();
} }
else { else {
@@ -49,8 +49,8 @@ public class ColorUtil {
} }
private static int[] gradient(String start,String end,int length){ private static int[] gradient(String start,String end,int length){
int[] color = new int[length]; int[] color = new int[length];
int[] rgb1 = MathUtil.hexToInt(start); int[] rgb1 = MathUtil.hex2Int(start);
int[] rgb2 = MathUtil.hexToInt(end); int[] rgb2 = MathUtil.hex2Int(end);
if(length==0){return color;} if(length==0){return color;}
if(length==1){ if(length==1){
for(int j=0;j<3;j++){ for(int j=0;j<3;j++){
@@ -28,7 +28,7 @@ public class MathUtil {
BigDecimal b2 = new BigDecimal(d2); BigDecimal b2 = new BigDecimal(d2);
return b1.divide(b2,len, RoundingMode.HALF_UP).doubleValue(); return b1.divide(b2,len, RoundingMode.HALF_UP).doubleValue();
} }
public static int[] hexToInt(final String hex){ public static int[] hex2Int(final String hex){
int[] result = new int[3]; int[] result = new int[3];
String s1 = hex.substring(0,2); String s1 = hex.substring(0,2);
String s2 = hex.substring(2,4); String s2 = hex.substring(2,4);
@@ -38,11 +38,11 @@ public class MathUtil {
result[2] = Integer.parseInt(s3,16); result[2] = Integer.parseInt(s3,16);
return result; return result;
} }
public static String locationToString(final Location loc){ public static String location2String(final Location loc){
if (loc.getWorld() == null) return ""; if (loc.getWorld() == null) return "";
return loc.getWorld().getName()+";"+loc.getX()+";"+loc.getY()+";"+loc.getZ(); return loc.getWorld().getName()+";"+loc.getX()+";"+loc.getY()+";"+loc.getZ();
} }
public static Location stringToLocation(final String str){ public static Location string2Location(final String str){
final String[] parts = str.split(";"); final String[] parts = str.split(";");
if(parts.length != 4) return null; if(parts.length != 4) return null;
final World world = Bukkit.getWorld(parts[0]); final World world = Bukkit.getWorld(parts[0]);
@@ -6,23 +6,24 @@ import org.bukkit.World;
import org.bukkit.inventory.ItemStack; import org.bukkit.inventory.ItemStack;
import org.bukkit.inventory.meta.ItemMeta; import org.bukkit.inventory.meta.ItemMeta;
import org.bukkit.persistence.PersistentDataContainer; import org.bukkit.persistence.PersistentDataContainer;
import org.jetbrains.annotations.TestOnly;
import pers.xanadu.enderdragon.EnderDragon; import pers.xanadu.enderdragon.EnderDragon;
import pers.xanadu.enderdragon.config.Config; import pers.xanadu.enderdragon.config.Config;
import pers.xanadu.enderdragon.config.Lang;
import java.lang.reflect.Field; import java.lang.reflect.Field;
import java.lang.reflect.Method; import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map; import java.util.Map;
import static pers.xanadu.enderdragon.EnderDragon.getInstance;
public class NMSUtil { public class NMSUtil {
private String getEDB_base;
private Method getNMSWord; private Method getNMSWord;
private Method asNMSCopy; private Method asNMSCopy;
private Method copyNMSStack; private Method copyNMSStack;
private Method asBukkitCopy; private Method asBukkitCopy;
private Method asCraftMirror; private Method asCraftMirror;
/**
* 浅拷贝unhandledTags
*/
private Method asCraftCopy; private Method asCraftCopy;
private Method NMSItemStack_save; private Method NMSItemStack_save;
private Method NMSItemStack_setTag; private Method NMSItemStack_setTag;
@@ -42,7 +43,7 @@ public class NMSUtil {
private Class<?> WorldClass; private Class<?> WorldClass;
private Class<?> CraftWorldClass; private Class<?> CraftWorldClass;
private Class<?> WorldProviderClass; private Class<?> WorldProviderClass;
private Class<?> WorldProviderTheEndClass; //private Class<?> WorldProviderTheEndClass;
private Class<?> CraftItemStackClass; private Class<?> CraftItemStackClass;
private Class<?> CraftMetaItemClass; private Class<?> CraftMetaItemClass;
private Class<?> NMSItemStackClass; private Class<?> NMSItemStackClass;
@@ -63,7 +64,7 @@ public class NMSUtil {
this.world_c_environment.setAccessible(true); this.world_c_environment.setAccessible(true);
if(Version.mcMainVersion>=12 && Version.mcMainVersion<16){ if(Version.mcMainVersion>=12 && Version.mcMainVersion<16){
this.WorldProviderClass = Class.forName("net.minecraft.server."+version+".WorldProvider"); this.WorldProviderClass = Class.forName("net.minecraft.server."+version+".WorldProvider");
this.WorldProviderTheEndClass = Class.forName("net.minecraft.server."+version+".WorldProviderTheEnd"); //this.WorldProviderTheEndClass = Class.forName("net.minecraft.server."+version+".WorldProviderTheEnd");
} }
this.CraftItemStackClass = Class.forName("org.bukkit.craftbukkit." + version + ".inventory.CraftItemStack"); this.CraftItemStackClass = Class.forName("org.bukkit.craftbukkit." + version + ".inventory.CraftItemStack");
this.CraftMetaItemClass = Class.forName("org.bukkit.craftbukkit." + version + ".inventory.CraftMetaItem"); this.CraftMetaItemClass = Class.forName("org.bukkit.craftbukkit." + version + ".inventory.CraftMetaItem");
@@ -110,26 +111,6 @@ public class NMSUtil {
}catch(ReflectiveOperationException e){ }catch(ReflectiveOperationException e){
e.printStackTrace(); e.printStackTrace();
} }
switch (version) {
case "v1_12_R1" : {
getEDB_base = "t";
break;
}
case "v1_13_R1" :
case "v1_13_R2" : {
getEDB_base = "r";
break;
}
case "v1_14_R1" : {
getEDB_base = "q";
break;
}
case "v1_15_R1" : {
getEDB_base = "o";
break;
}
default : getEDB_base = null;
}
if(Config.debug) check(); if(Config.debug) check();
} }
public void check(){ public void check(){
@@ -236,6 +217,7 @@ public class NMSUtil {
return null; return null;
} }
} }
@TestOnly
public void setUnhandledTags(final ItemMeta meta, Map<String,?> unhandledTags){ public void setUnhandledTags(final ItemMeta meta, Map<String,?> unhandledTags){
try{ try{
Object craft_meta = CraftMetaItemClass.cast(meta); Object craft_meta = CraftMetaItemClass.cast(meta);
@@ -244,6 +226,10 @@ public class NMSUtil {
e.printStackTrace(); e.printStackTrace();
} }
} }
/**
* @return meta中unhandledTags的引用
*/
@TestOnly
public Map<String,Object> getUnhandledTags(final ItemMeta meta){ public Map<String,Object> getUnhandledTags(final ItemMeta meta){
try{ try{
Object craft_meta = CraftMetaItemClass.cast(meta); Object craft_meta = CraftMetaItemClass.cast(meta);
@@ -266,7 +252,7 @@ public class NMSUtil {
} }
public String getNBT(final ItemStack item){ public String getNBT(final ItemStack item){
try{ try{
Object ci = CraftItemStackClass.isInstance(item)?CraftItemStackClass.cast(item):asCraftCopy.invoke(null,item); Object ci = CraftItemStackClass.isInstance(item)?CraftItemStackClass.cast(item):asCraftCopy.invoke(null,item);//浅拷贝unhandledTags
Object ei = asNMSCopy.invoke(null, ci); Object ei = asNMSCopy.invoke(null, ci);
Object cpd = NMSItemStack_save.invoke(ei, NBTTagCompoundClass.newInstance()); Object cpd = NMSItemStack_save.invoke(ei, NBTTagCompoundClass.newInstance());
return cpd.toString(); return cpd.toString();
@@ -277,7 +263,7 @@ public class NMSUtil {
} }
public Object getCPD(final ItemStack item){ public Object getCPD(final ItemStack item){
try{ try{
Object ci = CraftItemStackClass.isInstance(item)?CraftItemStackClass.cast(item):asCraftCopy.invoke(null,item); Object ci = CraftItemStackClass.isInstance(item)?CraftItemStackClass.cast(item):asCraftCopy.invoke(null,item);//浅拷贝unhandledTags
Object ei = asNMSCopy.invoke(null, ci); Object ei = asNMSCopy.invoke(null, ci);
return NMSItemStack_save.invoke(ei, NBTTagCompoundClass.newInstance()); return NMSItemStack_save.invoke(ei, NBTTagCompoundClass.newInstance());
}catch (ReflectiveOperationException e){ }catch (ReflectiveOperationException e){
@@ -329,27 +315,7 @@ public class NMSUtil {
e.printStackTrace(); e.printStackTrace();
} }
} }
public Object getEnderDragonBattle(final World world){
String version = Version.getVersion();
if (Version.mcMainVersion>=12 && Version.mcMainVersion<16) {
try {
Object worldServer = getInstance().getNMSManager().getWorldServer(world);
assert worldServer != null;
Field field = worldServer.getClass().getField("worldProvider");
Object worldProvider = field.get(worldServer);
Object WorldProviderTheEnd = WorldProviderTheEndClass.cast(worldProvider);
String method_name = getInstance().getNMSManager().getEDB_base;
if(method_name == null) return null;
Method method = WorldProviderTheEnd.getClass().getDeclaredMethod(method_name);
return method.invoke(WorldProviderTheEnd);
} catch (ReflectiveOperationException e) {
Lang.warn("Your server version (" + version + ") is not supported!");
e.printStackTrace();
}
}
Lang.warn("Your server version (" + version + ") is not supported!");
return null;
}
public Object getWorldServer(final World ThisWorld) { public Object getWorldServer(final World ThisWorld) {
try { try {
Object castClass = getCraftWorld(ThisWorld); Object castClass = getCraftWorld(ThisWorld);
@@ -12,7 +12,7 @@ import java.io.InputStreamReader;
import java.net.URL; import java.net.URL;
import java.net.URLConnection; import java.net.URLConnection;
public class UpdateChecker { public final class UpdateChecker {
public static void checkUpdate(){ public static void checkUpdate(){
Lang.info(Lang.plugin_checking_update); Lang.info(Lang.plugin_checking_update);
new BukkitRunnable(){ new BukkitRunnable(){
@@ -11,7 +11,7 @@ import static org.bukkit.Bukkit.getServer;
public class Version { public class Version {
public static final String setting_dragon = "2.2.0"; public static final String setting_dragon = "2.2.0";
public static final String lang = "2.2.0"; public static final String lang = "2.2.0";
public static final String config = "2.2.0"; public static final String config = "2.3.0";
public static final String data = "2.2.0"; public static final String data = "2.2.0";
public static int mcMainVersion; public static int mcMainVersion;
public static int mcPatchVersion; public static int mcPatchVersion;
@@ -47,7 +47,9 @@ public class Version {
case "v1_12_R1" : return new pers.xanadu.enderdragon.nms.BossBar.v1_12_R1.BossBarManager(); case "v1_12_R1" : return new pers.xanadu.enderdragon.nms.BossBar.v1_12_R1.BossBarManager();
case "v1_13_R1" : return new pers.xanadu.enderdragon.nms.BossBar.v1_13_R1.BossBarManager(); case "v1_13_R1" : return new pers.xanadu.enderdragon.nms.BossBar.v1_13_R1.BossBarManager();
case "v1_13_R2" : return new pers.xanadu.enderdragon.nms.BossBar.v1_13_R2.BossBarManager(); case "v1_13_R2" : return new pers.xanadu.enderdragon.nms.BossBar.v1_13_R2.BossBarManager();
default: return null; case "v1_14_R1" : return new pers.xanadu.enderdragon.nms.BossBar.v1_14_R1.BossBarManager();
case "v1_15_R1" : return new pers.xanadu.enderdragon.nms.BossBar.v1_15_R1.BossBarManager();
default: return new pers.xanadu.enderdragon.nms.BossBar.v1_16_R1_above.BossBarManager();
} }
} }
public static I_WorldDataManager getWorldDataManager(){ public static I_WorldDataManager getWorldDataManager(){
+9 -1
View File
@@ -1,5 +1,5 @@
#配置文件版本,请勿修改 #配置文件版本,请勿修改
version: 2.2.0 version: 2.3.0
#可选: 'Chinese','English' #可选: 'Chinese','English'
lang: 'English' lang: 'English'
@@ -67,6 +67,13 @@ blacklist_worlds:
- 'world' - 'world'
- 'world_nether' - 'world_nether'
#由以下原因生成的末影龙不被插件监听
#常用选项:COMMAND(原版summon指令生成),CUSTOM(别的插件生成的),DEFAULT(自然生成,包括玩家放置水晶复活的)
#你可以在这里找到所有生成原因:
#https://bukkit.windit.net/javadoc/org/bukkit/event/entity/CreatureSpawnEvent.SpawnReason.html
#写法示例: [COMMAND,CUSTOM]
blacklist_spawn_reason: []
#可选: [default/nbt/advanced] #可选: [default/nbt/advanced]
item_format: item_format:
reward: default reward: default
@@ -89,5 +96,6 @@ advanced_setting:
# 设置该项为true并重启服务器将尝试修复 # 设置该项为true并重启服务器将尝试修复
world_env_fix: false world_env_fix: false
save_respawn_status: false save_respawn_status: false
save_bossbar: false
backslash_split: backslash_split:
reward: false reward: false
+9 -1
View File
@@ -1,5 +1,5 @@
#You don't need to edit it. #You don't need to edit it.
version: 2.2.0 version: 2.3.0
#Enabled: 'Chinese','English' #Enabled: 'Chinese','English'
lang: 'English' lang: 'English'
@@ -66,6 +66,13 @@ blacklist_worlds:
- 'world' - 'world'
- 'world_nether' - 'world_nether'
# Ender_dragon spawns with these reasons will be ignored by this plugin.
# common options: COMMAND(spawn with /summon), CUSTOM(generate by other plugins), DEFAULT(by nature, including end_crystal)
# You can find all spawn reasons here:
# https://hub.spigotmc.org/javadocs/bukkit/org/bukkit/event/entity/CreatureSpawnEvent.SpawnReason.html
# example: [COMMAND,CUSTOM]
blacklist_spawn_reason: []
#optional: [default/nbt/advanced] #optional: [default/nbt/advanced]
item_format: item_format:
reward: default reward: default
@@ -88,5 +95,6 @@ advanced_setting:
# You can set this to "true" and reload server to fix it. # You can set this to "true" and reload server to fix it.
world_env_fix: false world_env_fix: false
save_respawn_status: false save_respawn_status: false
save_bossbar: false
backslash_split: backslash_split:
reward: false reward: false
@@ -1,15 +1,15 @@
package expansion.groovy package expansion.groovy
import groovy.transform.Field
import org.bukkit.Bukkit import org.bukkit.Bukkit
import pers.xanadu.enderdragon.config.Lang
import static pers.xanadu.enderdragon.EnderDragon.plugin
@Field static def x=5
static void enable(){ static void enable(){
// Lang.info("I am a test script written in groovy.") //Bukkit.getLogger().info("static variable test: x="+x)
}
static void test(){
Bukkit.broadcastMessage("you runs test()")
} }
@@ -17,3 +17,6 @@ static void test(){
+1 -1
View File
@@ -1,5 +1,5 @@
name: EnderDragon name: EnderDragon
version: 2.2.0 version: 2.3.0
main: pers.xanadu.enderdragon.EnderDragon main: pers.xanadu.enderdragon.EnderDragon
author: Xanadu13 author: Xanadu13
api-version: 1.13 api-version: 1.13