diff --git a/README.md b/README.md
index 8031631..5ff24bb 100644
--- a/README.md
+++ b/README.md
@@ -8,25 +8,17 @@
[![](https://img.shields.io/github/stars/Bkm016/TabooLib.svg?style=flat-square&label=Stars)](https://github.com/Bkm016/TabooLib)
[![](https://jitpack.io/v/Bkm016/TabooLib.svg)](https://jitpack.io/#Bkm016/TabooLib)
-## 安装 TabooLib
-
-#### 服务器有网络:
-1. 在[这里](https://github.com/bkm016/TabooLib/releases)下载最新版的 **TabooLib**
-2. 正常步骤安装
-
-#### 服务器无网络:
-1. 重复上面步骤
-2. 在[这里](https://skymc.oss-cn-shanghai.aliyuncs.com/plugins/libs.rar)下载 **TabooLib** 所需要的第三方库
-3. 解压后覆盖 **"plugins"** 文件夹(注意不是丢到 **"plugins"** 文件夹里)
-
-#### 服务端为 1.7.10 版本
-1. 重复上面步骤
-2. 查阅[文档](https://blog.yumc.pw/posts/Fix-Thermos-Load-Plugin-Class-Not-Found/), 获取解决办法
-
## 插件文档
[TabooLib 文档](https://bkm016.github.io/TabooLib/#/)
+## 下载 TabooLib 插件
+
+在 [这里](https://github.com/bkm016/TabooLib/releases) 根据您服务器的网络状态下载**在线**或**离线**版本
+离线版为 **offline** 结尾的 **jar** 文件
+
+如果你的服务器是 **1.7.10** 版本,在 [这里](https://pcd.ac.cn/2018/05/19/71/) 修复因 **SpecialSource** 版本过低导致插件无法载入的问题
+
## 添加 TabooLib 为库
### Maven
diff --git a/pom.xml b/pom.xml
index b76f6a9..0ecda19 100644
--- a/pom.xml
+++ b/pom.xml
@@ -6,7 +6,7 @@
me.skymc
TabooLib
- 4.02
+ 4.09
UTF-8
@@ -175,6 +175,13 @@
system
${basedir}/libs/Vault.jar
+
+ bossbar
+ bossbar
+ 1
+ system
+ ${basedir}/libs/BossBarAPI.jar
+
\ No newline at end of file
diff --git a/src/main/java/com/ilummc/tlib/TLib.java b/src/main/java/com/ilummc/tlib/TLib.java
index a4643ee..9c64381 100644
--- a/src/main/java/com/ilummc/tlib/TLib.java
+++ b/src/main/java/com/ilummc/tlib/TLib.java
@@ -13,6 +13,7 @@ import com.ilummc.tlib.resources.TLocale;
import com.ilummc.tlib.resources.TLocaleLoader;
import com.ilummc.tlib.util.IO;
import me.skymc.taboolib.Main;
+import me.skymc.taboolib.fileutils.FileUtils;
import org.bukkit.Bukkit;
import org.bukkit.configuration.InvalidConfigurationException;
import org.bukkit.configuration.file.YamlConfiguration;
@@ -49,7 +50,7 @@ public class TLib {
libsFolder.mkdirs();
}
try {
- String yamlText = new String(IO.readFully(TLib.class.getResourceAsStream("/lang/internal.yml")), Charset.forName("utf-8"));
+ String yamlText = new String(IO.readFully(FileUtils.getResource("lang/internal.yml")), Charset.forName("utf-8"));
internalLanguage = new YamlConfiguration();
internalLanguage.loadFromString(yamlText);
} catch (IOException | InvalidConfigurationException ignored) {
@@ -71,13 +72,14 @@ public class TLib {
TLocaleLoader.init();
PlaceholderHook.init();
TLocaleLoader.load(Main.getInst(), false);
- TDependencyInjector.inject(Main.getInst(), tLib);
+ }
+ public static void initPost() {
+ TDependencyInjector.inject(Main.getInst(), TLib.getTLib());
try {
Pool.init();
} catch (Throwable ignored) {
}
-
}
public static void unload() {
diff --git a/src/main/java/com/ilummc/tlib/bungee/chat/ComponentSerializer.java b/src/main/java/com/ilummc/tlib/bungee/chat/ComponentSerializer.java
index b6165db..6d19961 100644
--- a/src/main/java/com/ilummc/tlib/bungee/chat/ComponentSerializer.java
+++ b/src/main/java/com/ilummc/tlib/bungee/chat/ComponentSerializer.java
@@ -6,6 +6,7 @@ import com.ilummc.tlib.bungee.api.chat.TextComponent;
import com.ilummc.tlib.bungee.api.chat.TranslatableComponent;
import java.lang.reflect.Type;
+import java.util.Arrays;
import java.util.HashSet;
/**
diff --git a/src/main/java/com/ilummc/tlib/dependency/TDependency.java b/src/main/java/com/ilummc/tlib/dependency/TDependency.java
index 193f115..50d7494 100644
--- a/src/main/java/com/ilummc/tlib/dependency/TDependency.java
+++ b/src/main/java/com/ilummc/tlib/dependency/TDependency.java
@@ -52,8 +52,8 @@ public class TDependency {
}
private static boolean downloadMaven(String url, String groupId, String artifactId, String version, File target, String dl) {
- if (Main.getInst().getConfig().getBoolean("OFFLINE-MODE")) {
- TLocale.Logger.warn("DEPENDENCY.OFFLINE-DEPENDENCY-WARN");
+ if (Main.isOfflineVersion()) {
+ TLocale.Logger.warn("DEPENDENCY.DOWNLOAD-OFFLINE");
return false;
}
AtomicBoolean failed = new AtomicBoolean(false);
@@ -84,4 +84,4 @@ public class TDependency {
private static int getDownloadPoolSize() {
return Main.getInst().getConfig().getInt("DOWNLOAD-POOL-SIZE", 4);
}
-}
+}
\ No newline at end of file
diff --git a/src/main/java/com/ilummc/tlib/inject/TDependencyInjector.java b/src/main/java/com/ilummc/tlib/inject/TDependencyInjector.java
index def8e07..d8298a9 100644
--- a/src/main/java/com/ilummc/tlib/inject/TDependencyInjector.java
+++ b/src/main/java/com/ilummc/tlib/inject/TDependencyInjector.java
@@ -13,9 +13,23 @@ import org.bukkit.plugin.java.JavaPlugin;
import java.io.File;
import java.lang.reflect.Field;
+import java.util.HashMap;
public class TDependencyInjector {
+ public static Dependency[] getDependencies(Object o) {
+ Dependency[] dependencies = new Dependency[0];
+ Dependencies d = o.getClass().getAnnotation(Dependencies.class);
+ if (d != null) {
+ dependencies = d.value();
+ }
+ Dependency d2 = o.getClass().getAnnotation(Dependency.class);
+ if (d2 != null) {
+ dependencies = new Dependency[]{d2};
+ }
+ return dependencies;
+ }
+
public static void inject(Plugin plugin, Object o) {
TLocaleLoader.load(plugin, true);
injectDependencies(plugin, o);
@@ -135,17 +149,7 @@ public class TDependencyInjector {
}
private static void injectDependencies(Plugin plugin, Object o) {
- Dependency[] dependencies = new Dependency[0];
- {
- Dependencies d = o.getClass().getAnnotation(Dependencies.class);
- if (d != null) {
- dependencies = d.value();
- }
- Dependency d2 = o.getClass().getAnnotation(Dependency.class);
- if (d2 != null) {
- dependencies = new Dependency[]{d2};
- }
- }
+ Dependency[] dependencies = getDependencies(o);
if (dependencies.length != 0) {
TLocale.Logger.info("DEPENDENCY.LOADING-START", plugin.getName());
for (Dependency dependency : dependencies) {
@@ -167,5 +171,4 @@ public class TDependencyInjector {
TLocale.Logger.info("DEPENDENCY.LOAD-COMPLETE");
}
}
-
}
diff --git a/src/main/java/com/ilummc/tlib/resources/TLocale.java b/src/main/java/com/ilummc/tlib/resources/TLocale.java
index b2dc858..c696a4d 100644
--- a/src/main/java/com/ilummc/tlib/resources/TLocale.java
+++ b/src/main/java/com/ilummc/tlib/resources/TLocale.java
@@ -2,20 +2,30 @@ package com.ilummc.tlib.resources;
import com.ilummc.tlib.TLib;
import com.ilummc.tlib.bungee.api.ChatColor;
+import com.ilummc.tlib.bungee.api.chat.BaseComponent;
+import com.ilummc.tlib.bungee.api.chat.TextComponent;
+import com.ilummc.tlib.bungee.chat.ComponentSerializer;
import com.ilummc.tlib.inject.TLoggerManager;
import com.ilummc.tlib.util.Ref;
import com.ilummc.tlib.util.Strings;
import me.clip.placeholderapi.PlaceholderAPI;
import me.skymc.taboolib.Main;
-import me.skymc.taboolib.TabooLib;
+import me.skymc.taboolib.nms.NMSUtil19;
+import me.skymc.taboolib.nms.NMSUtils;
import org.bukkit.Bukkit;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Field;
+import java.lang.reflect.Method;
import java.util.Collections;
import java.util.List;
import java.util.stream.Collectors;
+/**
+ * @author IzzelAliz
+ */
public class TLocale {
private TLocale() {
@@ -128,4 +138,23 @@ public class TLocale {
}
}
+ public static class Tellraw extends TLocale {
+
+ private static final Field playerConnection = NMSUtils.getFieldSilent(NMSUtil19.class_EntityPlayer, "playerConnection");
+ private static final Method sendPacket = NMSUtils.getMethodSilent(NMSUtil19.class_PlayerConnection, "sendPacket", NMSUtil19.class_Packet);
+ private static final Constructor> PacketPlayOutChat = NMSUtils.getConstructorSilent(NMSUtil19.class_PacketPlayOutChat, NMSUtil19.class_IChatBaseComponent);
+
+ public static void send(CommandSender sender, String rawMessage) {
+ if (sender instanceof Player) {
+ try {
+ sendPacket.invoke(playerConnection.get(NMSUtils.getHandle(sender)), PacketPlayOutChat.newInstance(rawMessage));
+ } catch (Exception e) {
+ Bukkit.getServer().dispatchCommand(Bukkit.getConsoleSender(), "tellraw " + sender.getName() + " " + rawMessage);
+ }
+ } else {
+ sender.sendMessage(TextComponent.toLegacyText(ComponentSerializer.parse(rawMessage)));
+ }
+ }
+
+ }
}
diff --git a/src/main/java/com/ilummc/tlib/resources/TLocaleLoader.java b/src/main/java/com/ilummc/tlib/resources/TLocaleLoader.java
index 31ddcad..98f9a99 100644
--- a/src/main/java/com/ilummc/tlib/resources/TLocaleLoader.java
+++ b/src/main/java/com/ilummc/tlib/resources/TLocaleLoader.java
@@ -10,6 +10,7 @@ import me.skymc.taboocode.TabooCodeLang;
import me.skymc.taboolib.Main;
import me.skymc.taboolib.TabooLib;
import me.skymc.taboolib.fileutils.ConfigUtils;
+import me.skymc.taboolib.fileutils.FileUtils;
import org.bukkit.Bukkit;
import org.bukkit.command.CommandSender;
import org.bukkit.configuration.file.YamlConfiguration;
@@ -29,8 +30,10 @@ public class TLocaleLoader {
public static void init() {
ConfigurationSerialization.registerClass(TLocaleText.class, "TEXT");
ConfigurationSerialization.registerClass(TLocaleJson.class, "JSON");
+ ConfigurationSerialization.registerClass(TLocaleBook.class, "BOOK");
ConfigurationSerialization.registerClass(TLocaleSound.class, "SOUND");
ConfigurationSerialization.registerClass(TLocaleTitle.class, "TITLE");
+ ConfigurationSerialization.registerClass(TLocaleBossBar.class, "BAR");
ConfigurationSerialization.registerClass(TLocaleActionBar.class, "ACTION");
}
@@ -140,7 +143,7 @@ public class TLocaleLoader {
}
private static YamlConfiguration getLocaleAtStream(Plugin plugin, File localeFile) {
- InputStream localeInputSteam = plugin.getClass().getResourceAsStream("/lang/" + localeFile.getName());
+ InputStream localeInputSteam = FileUtils.getResource(plugin, "lang/" + localeFile.getName());
try {
String yamlText = new String(IO.readFully(localeInputSteam), Charset.forName("utf-8"));
YamlConfiguration yaml = new YamlConfiguration();
diff --git a/src/main/java/com/ilummc/tlib/resources/type/TLocaleBook.java b/src/main/java/com/ilummc/tlib/resources/type/TLocaleBook.java
new file mode 100644
index 0000000..978eb27
--- /dev/null
+++ b/src/main/java/com/ilummc/tlib/resources/type/TLocaleBook.java
@@ -0,0 +1,91 @@
+package com.ilummc.tlib.resources.type;
+
+import com.google.common.collect.Maps;
+import com.ilummc.tlib.bungee.chat.ComponentSerializer;
+import com.ilummc.tlib.resources.TLocale;
+import com.ilummc.tlib.resources.TLocaleSerialize;
+import com.ilummc.tlib.util.Strings;
+import me.skymc.taboolib.Main;
+import me.skymc.taboolib.bookformatter.BookFormatter;
+import me.skymc.taboolib.bookformatter.builder.BookBuilder;
+import me.skymc.taboolib.json.tellraw.TellrawJson;
+import org.bukkit.command.CommandSender;
+import org.bukkit.configuration.serialization.SerializableAs;
+import org.bukkit.entity.Player;
+import org.bukkit.scheduler.BukkitRunnable;
+
+import javax.annotation.concurrent.ThreadSafe;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.stream.Collectors;
+
+/**
+ * @Author sky
+ * @Since 2018-05-27 0:05
+ */
+@ThreadSafe
+@SerializableAs("BOOK")
+public class TLocaleBook extends TLocaleSerialize {
+
+ /*
+ BookTest:
+ - ==: BOOK
+ pages:
+ 0:
+ - '第一页内容'
+ - '[ <变量1@page-1> ]'
+ 1:
+ - '第二页内容'
+ - '[ <变量2@page-2> ]'
+ args:
+ page-1:
+ hover: '展示内容1'
+ command: '/say %player_name% NB1'
+ page-2:
+ hover: '展示内容2'
+ suggest: '/say %player_name% NB2'
+ */
+
+ private final List pages;
+ private final Map map;
+ private final boolean papi;
+
+ public TLocaleBook(List pages, Map map, boolean papi) {
+ this.pages = pages;
+ this.map = map;
+ this.papi = papi;
+ }
+
+ @Override
+ public Map serialize() {
+ return Maps.newHashMap(map);
+ }
+
+ @Override
+ public void sendTo(CommandSender sender, String... args) {
+ if (!(sender instanceof Player)) {
+ return;
+ }
+ new BukkitRunnable() {
+ @Override
+ public void run() {
+ BookBuilder bookBuilder = BookFormatter.writtenBook();
+ pages.stream().map(jsonPage -> papi ? TLocale.Translate.setPlaceholders(sender, Strings.replaceWithOrder(jsonPage.toRawMessage(), args)) : TLocale.Translate.setColored(Strings.replaceWithOrder(jsonPage.toRawMessage(), args))).map(ComponentSerializer::parse).forEach(bookBuilder::addPages);
+ new BukkitRunnable() {
+ @Override
+ public void run() {
+ BookFormatter.forceOpen((Player) sender, bookBuilder.build());
+ }
+ }.runTask(Main.getInst());
+ }
+ }.runTaskAsynchronously(Main.getInst());
+ }
+
+ public static TLocaleBook valueOf(Map map) {
+ Map pages = map.containsKey("pages") ? (Map) map.get("pages") : new HashMap<>();
+ Map section = map.containsKey("args") ? (Map) map.get("args") : new HashMap<>();
+ List pageJsonList = pages.values().stream().map(page -> TLocaleJson.formatJson(section, page, TellrawJson.create())).collect(Collectors.toList());
+ return new TLocaleBook(pageJsonList, map, isPlaceholderEnabled(map));
+ }
+}
diff --git a/src/main/java/com/ilummc/tlib/resources/type/TLocaleBossBar.java b/src/main/java/com/ilummc/tlib/resources/type/TLocaleBossBar.java
new file mode 100644
index 0000000..62261ca
--- /dev/null
+++ b/src/main/java/com/ilummc/tlib/resources/type/TLocaleBossBar.java
@@ -0,0 +1,95 @@
+package com.ilummc.tlib.resources.type;
+
+import com.ilummc.tlib.resources.TLocale;
+import com.ilummc.tlib.resources.TLocaleSerialize;
+import com.ilummc.tlib.util.Strings;
+import me.skymc.taboolib.other.NumberUtils;
+import net.md_5.bungee.api.chat.TextComponent;
+import org.bukkit.Bukkit;
+import org.bukkit.command.CommandSender;
+import org.bukkit.configuration.serialization.SerializableAs;
+import org.bukkit.entity.Player;
+import org.inventivetalent.bossbar.BossBar;
+import org.inventivetalent.bossbar.BossBarAPI;
+
+import javax.annotation.concurrent.ThreadSafe;
+import java.util.Map;
+
+/**
+ * @Author sky
+ * @Since 2018-05-27 18:52
+ */
+@ThreadSafe
+@SerializableAs("BAR")
+public class TLocaleBossBar extends TLocaleSerialize {
+
+ /*
+ BossBar:
+ - ==: BAR
+ text: 'BossBar 血条公告'
+ color: BLUE
+ style: NOTCHED_20
+ progress: 1.0
+ timeout: 20
+ timeout-interval: 2
+ */
+
+ private final String text;
+ private final BossBarAPI.Color color;
+ private final BossBarAPI.Style style;
+ private final float progress;
+ private final int timeout;
+ private final int timeoutInterval;
+ private final boolean papi;
+
+ public TLocaleBossBar(String text, BossBarAPI.Color color, BossBarAPI.Style style, float progress, int timeout, int timeoutInterval, boolean papi) {
+ this.text = text;
+ this.color = color;
+ this.style = style;
+ this.progress = progress;
+ this.timeout = timeout;
+ this.timeoutInterval = timeoutInterval;
+ this.papi = papi;
+ }
+
+ @Override
+ public void sendTo(CommandSender sender, String... args) {
+ if (Bukkit.getPluginManager().getPlugin("BossBarAPI") == null) {
+ TLocale.Logger.error("LOCALE.BAR-PLUGIN-NOT-FOUND");
+ return;
+ }
+ if (sender instanceof Player) {
+ TextComponent textComponent = new TextComponent(papi ? TLocale.Translate.setPlaceholders(sender, Strings.replaceWithOrder(text, args)) : TLocale.Translate.setColored(Strings.replaceWithOrder(text, args)));
+ BossBar bossBar = BossBarAPI.addBar((Player) sender, textComponent, color, style, progress, timeout, timeoutInterval);
+ } else {
+ sender.sendMessage(text);
+ }
+ }
+
+ @Override
+ public Map serialize() {
+ return null;
+ }
+
+ public static TLocaleBossBar valueOf(Map map) {
+ return new TLocaleBossBar(map.getOrDefault("text", "§4* Invalid Text*").toString(), getColor(String.valueOf(map.get("color"))), getStyle(String.valueOf(map.get("style"))), (float) NumberUtils.getDouble(String.valueOf(map.getOrDefault("progress", 1))), NumberUtils.getInteger(String.valueOf(map.getOrDefault("timeout", 20))), NumberUtils.getInteger(String.valueOf(map.getOrDefault("timeout-interval", 2))), isPlaceholderEnabled(map));
+ }
+
+ private static BossBarAPI.Color getColor(String color) {
+ try {
+ return BossBarAPI.Color.valueOf(color);
+ } catch (Exception e) {
+ TLocale.Logger.error("LOCALE.BAR-STYLE-IDENTIFICATION-FAILED", e.toString());
+ return BossBarAPI.Color.WHITE;
+ }
+ }
+
+ private static BossBarAPI.Style getStyle(String style) {
+ try {
+ return BossBarAPI.Style.valueOf(style);
+ } catch (Exception e) {
+ TLocale.Logger.error("LOCALE.BAR-COLOR-IDENTIFICATION-FAILED", e.toString());
+ return BossBarAPI.Style.NOTCHED_20;
+ }
+ }
+}
diff --git a/src/main/java/com/ilummc/tlib/resources/type/TLocaleJson.java b/src/main/java/com/ilummc/tlib/resources/type/TLocaleJson.java
index 4cc689b..2a14974 100644
--- a/src/main/java/com/ilummc/tlib/resources/type/TLocaleJson.java
+++ b/src/main/java/com/ilummc/tlib/resources/type/TLocaleJson.java
@@ -10,10 +10,12 @@ import com.ilummc.tlib.compat.PlaceholderHook;
import com.ilummc.tlib.resources.TLocale;
import com.ilummc.tlib.resources.TLocaleSerialize;
import com.ilummc.tlib.util.Strings;
-import me.skymc.taboolib.jsonformatter.JSONFormatter;
+import me.skymc.taboolib.inventory.ItemUtils;
+import me.skymc.taboolib.json.tellraw.TellrawJson;
+import me.skymc.taboolib.other.NumberUtils;
+import me.skymc.taboolib.string.VariableFormatter;
import org.bukkit.command.CommandSender;
import org.bukkit.configuration.serialization.SerializableAs;
-import org.bukkit.entity.Player;
import javax.annotation.concurrent.ThreadSafe;
import java.util.*;
@@ -21,6 +23,7 @@ import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;
+
@ThreadSafe
@SerializableAs("JSON")
public class TLocaleJson extends TLocaleSerialize {
@@ -72,11 +75,11 @@ public class TLocaleJson extends TLocaleSerialize {
// 可能有很多个 BaseComponent,于是为每个 component 单独设置各种事件
BaseComponent[] component = TextComponent.fromLegacyText(text);
arg.forEach((key, value) -> {
- if ("suggest".equalsIgnoreCase(key)) {
+ if (key.equalsIgnoreCase("suggest")) {
Arrays.stream(component).forEach(baseComponent -> baseComponent.setClickEvent(new ClickEvent(ClickEvent.Action.SUGGEST_COMMAND, String.valueOf(value))));
- } else if ("command".equalsIgnoreCase(key) || "commands".equalsIgnoreCase(key)) {
+ } else if (key.equalsIgnoreCase("command") || "commands".equalsIgnoreCase(key)) {
Arrays.stream(component).forEach(baseComponent -> baseComponent.setClickEvent(new ClickEvent(ClickEvent.Action.RUN_COMMAND, String.valueOf(value))));
- } else if ("hover".equalsIgnoreCase(key)) {
+ } else if (key.equalsIgnoreCase("hover")) {
Arrays.stream(component).forEach(baseComponent -> baseComponent.setHoverEvent(new HoverEvent(HoverEvent.Action.SHOW_TEXT, new ComponentBuilder(TLocale.Translate.setColored(String.valueOf(value))).create())));
}
});
@@ -101,7 +104,7 @@ public class TLocaleJson extends TLocaleSerialize {
private static List getTextList(Object textObj) {
if (textObj instanceof List) {
- return ((List>) textObj).stream().map(Object::toString).map(s -> TLocale.Translate.setColored(s)).collect(Collectors.toList());
+ return ((List>) textObj).stream().map(Object::toString).map(TLocale.Translate::setColored).collect(Collectors.toList());
} else if (textObj instanceof String) {
return Lists.newArrayList(TLocale.Translate.setColored((String) textObj));
} else {
@@ -125,11 +128,11 @@ public class TLocaleJson extends TLocaleSerialize {
}
private void sendRawMessage(CommandSender sender, BaseComponent[] components) {
- if (sender instanceof Player) {
- JSONFormatter.sendRawMessage((Player) sender, ComponentSerializer.toString(components));
- } else {
- sender.sendMessage(TextComponent.toLegacyText(components));
- }
+ TLocale.Tellraw.send(sender, ComponentSerializer.toString(components));
+ }
+
+ private List replace(List component, CommandSender sender, String... args) {
+ return component.stream().map(c -> replace(c, sender, args)).collect(Collectors.toList());
}
private BaseComponent[] replace(BaseComponent[] component, CommandSender sender, String... args) {
@@ -140,10 +143,6 @@ public class TLocaleJson extends TLocaleSerialize {
return components;
}
- private List replace(List component, CommandSender sender, String... args) {
- return component.stream().map(c -> replace(c, sender, args)).collect(Collectors.toList());
- }
-
private BaseComponent replace(BaseComponent component, CommandSender sender, String... args) {
if (component.getClickEvent() != null) {
ClickEvent clickEvent = new ClickEvent(component.getClickEvent().getAction(), replace(sender, component.getClickEvent().getValue(), args));
@@ -166,4 +165,63 @@ public class TLocaleJson extends TLocaleSerialize {
String s = Strings.replaceWithOrder(text, args);
return papi ? PlaceholderHook.replace(sender, s) : s;
}
+
+ public static TellrawJson formatJson(Map section, Object textObject, TellrawJson pageJson) {
+ List textList = textObject instanceof List ? (List) textObject : Collections.singletonList(String.valueOf(textObject));
+ // 遍历本页文本
+ for (int i = 0; i < textList.size(); i++) {
+ // 捕捉变量
+ for (VariableFormatter.Variable variable : new VariableFormatter(textList.get(i), pattern).find().getVariableList()) {
+ // 如果是变量
+ if (variable.isVariable()) {
+ String[] split = variable.getText().split("@");
+ // @ 前面的字符串
+ String text = split.length > 1 ? split[0] : "§4* Invalid Text *";
+ // @ 后面的节点名
+ String node = split.length > 1 ? split[1] : null;
+ // 处理变量
+ formatNode(section, pageJson, text, node);
+ } else {
+ pageJson.append(variable.getText());
+ }
+ }
+ if (i + 1 < textList.size()) {
+ pageJson.newLine();
+ }
+ }
+ return pageJson;
+ }
+
+ private static void formatNode(Map section, TellrawJson pageJson, String text, String node) {
+ if (section.containsKey(node)) {
+ try {
+ Map args = (Map) section.get(node);
+ // 文本
+ pageJson.append(args.getOrDefault("text", text).toString());
+ // 功能
+ if (args.containsKey("item")) {
+ pageJson.hoverItem(ItemUtils.getCacheItem(args.get("item").toString()));
+ }
+ if (args.containsKey("hover")) {
+ pageJson.hoverText(args.get("hover").toString());
+ }
+ if (args.containsKey("suggest")) {
+ pageJson.clickSuggest(args.get("suggest").toString());
+ }
+ if (args.containsKey("command")) {
+ pageJson.clickCommand(args.get("command").toString());
+ }
+ if (args.containsKey("page")) {
+ pageJson.clickChangePage(NumberUtils.getInteger(args.get("page").toString()));
+ }
+ if (args.containsKey("url")) {
+ pageJson.clickOpenURL(args.get("url").toString());
+ }
+ } catch (Exception e) {
+ TLocale.Logger.error("LOCALE.BOOK-ARGUMENTS-IDENTIFICATION-FAILED", e.toString());
+ }
+ } else {
+ pageJson.append("§4* Invalid Argument *");
+ }
+ }
}
diff --git a/src/main/java/com/ilummc/tlib/util/Strings.java b/src/main/java/com/ilummc/tlib/util/Strings.java
index e454212..40207d0 100644
--- a/src/main/java/com/ilummc/tlib/util/Strings.java
+++ b/src/main/java/com/ilummc/tlib/util/Strings.java
@@ -2,6 +2,14 @@ package com.ilummc.tlib.util;
public class Strings {
+ public static boolean isBlank(String var) {
+ return var == null || var.trim().isEmpty();
+ }
+
+ public static boolean isEmpty(CharSequence var) {
+ return var == null || var.length() == 0;
+ }
+
/**
* 优化过的 String#replace,比默认快了大概 5 倍
*
@@ -28,15 +36,13 @@ public class Strings {
return stringBuilder.toString();
}
+ // *********************************
+ //
+ // Deprecated
+ //
+ // *********************************
+
public static String replaceWithOrder(String template, String... args) {
return replaceWithOrder(template, (Object[]) args);
}
-
- public static boolean isBlank(String var) {
- return var == null || var.trim().isEmpty();
- }
-
- public static boolean isEmpty(CharSequence var) {
- return var == null || var.length() == 0;
- }
}
diff --git a/src/main/java/me/skymc/taboolib/Main.java b/src/main/java/me/skymc/taboolib/Main.java
index 5eefd71..731b886 100644
--- a/src/main/java/me/skymc/taboolib/Main.java
+++ b/src/main/java/me/skymc/taboolib/Main.java
@@ -1,12 +1,13 @@
package me.skymc.taboolib;
import com.ilummc.tlib.TLib;
-import com.ilummc.tlib.inject.TConfigWatcher;
+import com.ilummc.tlib.annotations.Dependency;
+import com.ilummc.tlib.inject.TDependencyInjector;
import com.ilummc.tlib.resources.TLocale;
import me.skymc.taboolib.anvil.AnvilContainerAPI;
import me.skymc.taboolib.bstats.Metrics;
import me.skymc.taboolib.commands.TabooLibMainCommand;
-import me.skymc.taboolib.commands.internal.BaseMainCommand;
+import me.skymc.taboolib.commands.internal.TBaseCommand;
import me.skymc.taboolib.commands.language.Language2Command;
import me.skymc.taboolib.commands.locale.TabooLibLocaleCommand;
import me.skymc.taboolib.commands.plugin.TabooLibPluginMainCommand;
@@ -17,17 +18,17 @@ import me.skymc.taboolib.database.PlayerDataManager;
import me.skymc.taboolib.economy.EcoUtils;
import me.skymc.taboolib.entity.EntityUtils;
import me.skymc.taboolib.fileutils.ConfigUtils;
+import me.skymc.taboolib.fileutils.FileUtils;
import me.skymc.taboolib.inventory.ItemUtils;
import me.skymc.taboolib.inventory.speciaitem.SpecialItem;
+import me.skymc.taboolib.itagapi.TagDataHandler;
import me.skymc.taboolib.javashell.JavaShell;
import me.skymc.taboolib.listener.*;
import me.skymc.taboolib.message.ChatCatcher;
-import me.skymc.taboolib.message.MsgUtils;
import me.skymc.taboolib.mysql.hikari.HikariHandler;
import me.skymc.taboolib.mysql.protect.MySQLConnection;
import me.skymc.taboolib.nms.item.DabItemUtils;
import me.skymc.taboolib.other.NumberUtils;
-import me.skymc.taboolib.packet.PacketUtils;
import me.skymc.taboolib.permission.PermissionUtils;
import me.skymc.taboolib.playerdata.DataUtils;
import me.skymc.taboolib.sign.SignUtils;
@@ -35,8 +36,6 @@ import me.skymc.taboolib.skript.SkriptHandler;
import me.skymc.taboolib.string.StringUtils;
import me.skymc.taboolib.string.language2.Language2;
import me.skymc.taboolib.support.SupportPlaceholder;
-import me.skymc.taboolib.team.TagAPI;
-import me.skymc.taboolib.team.TagUtils;
import me.skymc.taboolib.timecycle.TimeCycleManager;
import me.skymc.taboolib.update.UpdateTask;
import me.skymc.tlm.TLM;
@@ -50,6 +49,8 @@ import org.bukkit.plugin.java.JavaPlugin;
import org.bukkit.scheduler.BukkitRunnable;
import java.io.File;
+import java.io.InputStream;
+import java.net.InetAddress;
import java.util.Random;
/**
@@ -57,6 +58,14 @@ import java.util.Random;
*/
public class Main extends JavaPlugin implements Listener {
+ public Main() {
+ inst = this;
+ }
+
+ public enum StorageType {
+ LOCAL, SQL
+ }
+
private static Plugin inst;
private static net.milkbowl.vault.economy.Economy Economy;
@@ -65,7 +74,7 @@ public class Main extends JavaPlugin implements Listener {
private static File serverDataFolder;
- private static StorageType storageType;
+ private static StorageType storageType = StorageType.LOCAL;
private static boolean disable = false;
@@ -75,60 +84,10 @@ public class Main extends JavaPlugin implements Listener {
private static boolean started;
+ private static boolean isInternetOnline = false;
+
private FileConfiguration config = null;
- public static Plugin getInst() {
- return inst;
- }
-
- public static String getPrefix() {
- return "§8[§3§lTabooLib§8] §7";
- }
-
- public static net.milkbowl.vault.economy.Economy getEconomy() {
- return Economy;
- }
-
- public static void setEconomy(net.milkbowl.vault.economy.Economy economy) {
- Economy = economy;
- }
-
- public static File getPlayerDataFolder() {
- return playerDataFolder;
- }
-
- public static File getServerDataFolder() {
- return serverDataFolder;
- }
-
- public static StorageType getStorageType() {
- return storageType;
- }
-
- public static boolean isDisable() {
- return disable;
- }
-
- public static MySQLConnection getConnection() {
- return connection;
- }
-
- public static Language2 getExampleLanguage2() {
- return exampleLanguage2;
- }
-
- public static boolean isStarted() {
- return started;
- }
-
- public static Random getRandom() {
- return NumberUtils.getRandom();
- }
-
- public static String getTablePrefix() {
- return inst.getConfig().getString("MYSQL.PREFIX");
- }
-
@Override
public FileConfiguration getConfig() {
return config;
@@ -150,71 +109,31 @@ public class Main extends JavaPlugin implements Listener {
@Override
public void onLoad() {
- inst = this;
disable = false;
-
// 载入配置
saveDefaultConfig();
-
- // 加载依赖
+ // 载入牛逼玩意儿
TLib.init();
TLib.injectPluginManager();
-
- // 载入目录
+ // 网络检测
+ testInternet();
+ // 创建文件夹
setupDataFolder();
- // 注册配置
- DataUtils.addPluginData("TabooLibrary", null);
-
- // 启用数据库
- if (getConfig().getBoolean("MYSQL.ENABLE")) {
- // 连接数据库
- connection = new MySQLConnection(getConfig().getString("MYSQL.HOST"), getConfig().getString("MYSQL.USER"), getConfig().getString("MYSQL.POST"), getConfig().getString("MYSQL.PASSWORD"), getConfig().getString("MYSQL.DATABASE"), 30, this);
- // 连接成功
- if (connection.isConnection()) {
- // 创建表
- connection.createTable(getTablePrefix() + "_playerdata", "username", "configuration");
- connection.createTable(getTablePrefix() + "_plugindata", "name", "variable", "upgrade");
- connection.createTable(getTablePrefix() + "_serveruuid", "uuid", "hash");
-
- // 如果没有数据
- if (!connection.isExists(getTablePrefix() + "_serveruuid", "uuid", TabooLib.getServerUID())) {
- connection.intoValue(getTablePrefix() + "_serveruuid", TabooLib.getServerUID(), StringUtils.hashKeyForDisk(getDataFolder().getPath()));
- } else {
- String hash = connection.getValue(getTablePrefix() + "_serveruuid", "uuid", TabooLib.getServerUID(), "hash").toString();
- // 如果这个值和我的值不同
- if (!hash.equals(StringUtils.hashKeyForDisk(getDataFolder().getPath()))) {
- TLocale.Logger.error("NOTIFY.ERROR-SERVER-KEY");
- // 重新生成序列号
- TabooLib.resetServerUID();
- // 关服
- Bukkit.shutdown();
- }
- }
- } else {
- // 提示
- TLocale.Logger.error("NOTIFY.ERROR-CONNECTION-FAIL");
- // 关服
- Bukkit.shutdown();
- }
- // 储存方式
- storageType = StorageType.SQL;
- } else {
- // 储存方式
- storageType = StorageType.LOCAL;
- }
+ // 创建数据库
+ setupDatabase();
+ // 载入离线库文件
+ setupLibraries();
+ // 载入牛逼玩意儿
+ TLib.initPost();
}
@Override
public void onEnable() {
- // 注册指令
- getCommand("language2").setExecutor(new Language2Command());
- getCommand("taboolibrarymodule").setExecutor(new TLMCommands());
- getCommand("tabooliblocale").setExecutor(new TabooLibLocaleCommand());
- BaseMainCommand.createCommandExecutor("taboolib", new TabooLibMainCommand());
- BaseMainCommand.createCommandExecutor("taboolibplugin", new TabooLibPluginMainCommand());
-
+ // 注册命令
+ registerCommands();
// 注册监听
registerListener();
+
// 载入经济
EcoUtils.setupEconomy();
// 载入权限
@@ -229,6 +148,8 @@ public class Main extends JavaPlugin implements Listener {
JavaShell.javaShellSetup();
// 注册脚本
SkriptHandler.getInst();
+ // 注册头衔
+ TagDataHandler.init(this);
// 载入语言文件
exampleLanguage2 = new Language2("Language2", this);
@@ -243,6 +164,7 @@ public class Main extends JavaPlugin implements Listener {
// 文件保存
Bukkit.getScheduler().runTaskTimerAsynchronously(this, DataUtils::saveAllCaches, 20, 20 * 120);
Bukkit.getScheduler().runTaskTimerAsynchronously(this, () -> PlayerDataManager.saveAllCaches(true, false), 20, 20 * 60);
+
// 文件监控
TLib.getTLib().getConfigWatcher().addListener(new File(getDataFolder(), "config.yml"), null, obj -> {
reloadConfig();
@@ -254,12 +176,10 @@ public class Main extends JavaPlugin implements Listener {
@Override
public void run() {
+ // 载入 PlaceholderAPI 扩展
if (Bukkit.getPluginManager().getPlugin("PlaceholderAPI") != null) {
new SupportPlaceholder(getInst(), "taboolib").hook();
}
- if (PacketUtils.isProtocolLibEnabled()) {
- TagAPI.inst();
- }
// 载入 SpecialItem 接口
SpecialItem.getInst().loadItems();
// 载入 TLM 接口
@@ -320,20 +240,34 @@ public class Main extends JavaPlugin implements Listener {
// 提示信息
TLocale.Logger.error("NOTIFY.SUCCESS-DISABLE");
- // 清理头衔
- TagUtils.delete();
-
// 结束连接
if (connection != null && connection.isConnection()) {
connection.closeConnection();
}
+ // 卸载牛逼玩意儿
TLib.unload();
// 关闭服务器
Bukkit.shutdown();
}
+ private void testInternet() {
+ try {
+ InetAddress inetAddress = InetAddress.getByName(getConfig().getString("TEST-URL", "aliyun.com"));
+ isInternetOnline = inetAddress.isReachable(10000);
+ } catch (Exception ignored) {
+ }
+ if (!isInternetOnline() && !isOfflineVersion() && !isLibrariesExists()) {
+ TLocale.Logger.error("TLIB.LOAD-FAIL-OFFLINE", getDescription().getVersion());
+ // 死锁
+ try {
+ Thread.sleep(Long.MAX_VALUE);
+ } catch (Exception ignored) {
+ }
+ }
+ }
+
private void setupDataFolder() {
playerDataFolder = new File(getConfig().getString("DATAURL.PLAYER-DATA"));
if (!playerDataFolder.exists()) {
@@ -345,11 +279,61 @@ public class Main extends JavaPlugin implements Listener {
}
}
+ private void setupLibraries() {
+ if (!isOfflineVersion()) {
+ return;
+ }
+ for (Dependency dependency : TDependencyInjector.getDependencies(TLib.getTLib())) {
+ if (dependency.type() == Dependency.Type.LIBRARY && dependency.maven().matches(".*:.*:.*")) {
+ String fileName = String.join("-", dependency.maven().split(":")) + ".jar";
+ File targetFile = FileUtils.file(TLib.getTLib().getLibsFolder(), fileName);
+ InputStream inputStream = FileUtils.getResource("libs/" + fileName);
+ if (!targetFile.exists() && inputStream != null) {
+ FileUtils.inputStreamToFile(inputStream, FileUtils.file(TLib.getTLib().getLibsFolder(), fileName));
+ }
+ }
+ }
+ }
+
+ private void setupDatabase() {
+ DataUtils.addPluginData("TabooLibrary", null);
+ if (getConfig().getBoolean("MYSQL.ENABLE")) {
+ connection = new MySQLConnection(getConfig().getString("MYSQL.HOST"), getConfig().getString("MYSQL.USER"), getConfig().getString("MYSQL.POST"), getConfig().getString("MYSQL.PASSWORD"), getConfig().getString("MYSQL.DATABASE"), 30, this);
+ if (connection.isConnection()) {
+ connection.createTable(getTablePrefix() + "_playerdata", "username", "configuration");
+ connection.createTable(getTablePrefix() + "_plugindata", "name", "variable", "upgrade");
+ connection.createTable(getTablePrefix() + "_serveruuid", "uuid", "hash");
+ if (!connection.isExists(getTablePrefix() + "_serveruuid", "uuid", TabooLib.getServerUID())) {
+ connection.intoValue(getTablePrefix() + "_serveruuid", TabooLib.getServerUID(), StringUtils.hashKeyForDisk(getDataFolder().getPath()));
+ } else {
+ String hash = connection.getValue(getTablePrefix() + "_serveruuid", "uuid", TabooLib.getServerUID(), "hash").toString();
+ if (!hash.equals(StringUtils.hashKeyForDisk(getDataFolder().getPath()))) {
+ TLocale.Logger.error("NOTIFY.ERROR-SERVER-KEY");
+ TabooLib.resetServerUID();
+ Bukkit.shutdown();
+ }
+ }
+ } else {
+ TLocale.Logger.error("NOTIFY.ERROR-CONNECTION-FAIL");
+ Bukkit.shutdown();
+ }
+ storageType = StorageType.SQL;
+ }
+ }
+
+ private void registerCommands() {
+ getCommand("language2").setExecutor(new Language2Command());
+ getCommand("taboolibrarymodule").setExecutor(new TLMCommands());
+ getCommand("tabooliblocale").setExecutor(new TabooLibLocaleCommand());
+ TBaseCommand.registerCommand("taboolib", new TabooLibMainCommand());
+ TBaseCommand.registerCommand("taboolibplugin", new TabooLibPluginMainCommand());
+ }
+
private void registerListener() {
getServer().getPluginManager().registerEvents(this, this);
getServer().getPluginManager().registerEvents(new ListenerPlayerCommand(), this);
getServer().getPluginManager().registerEvents(new ListenerPlayerJump(), this);
- getServer().getPluginManager().registerEvents(new ListenerPlayerQuit(), this);
+ getServer().getPluginManager().registerEvents(new ListenerPlayerJoinAndQuit(), this);
getServer().getPluginManager().registerEvents(new ChatCatcher(), this);
getServer().getPluginManager().registerEvents(new DataUtils(), this);
getServer().getPluginManager().registerEvents(new AnvilContainerAPI(), this);
@@ -368,7 +352,73 @@ public class Main extends JavaPlugin implements Listener {
}
}
- public enum StorageType {
- LOCAL, SQL
+ // *********************************
+ //
+ // Getter and Setter
+ //
+ // *********************************
+
+ public static Plugin getInst() {
+ return inst;
+ }
+
+ public static String getPrefix() {
+ return "§8[§3§lTabooLib§8] §7";
+ }
+
+ public static net.milkbowl.vault.economy.Economy getEconomy() {
+ return Economy;
+ }
+
+ public static void setEconomy(net.milkbowl.vault.economy.Economy economy) {
+ Economy = economy;
+ }
+
+ public static File getPlayerDataFolder() {
+ return playerDataFolder;
+ }
+
+ public static File getServerDataFolder() {
+ return serverDataFolder;
+ }
+
+ public static StorageType getStorageType() {
+ return storageType;
+ }
+
+ public static boolean isDisable() {
+ return disable;
+ }
+
+ public static MySQLConnection getConnection() {
+ return connection;
+ }
+
+ public static Language2 getExampleLanguage2() {
+ return exampleLanguage2;
+ }
+
+ public static boolean isStarted() {
+ return started;
+ }
+
+ public static Random getRandom() {
+ return NumberUtils.getRandom();
+ }
+
+ public static String getTablePrefix() {
+ return inst.getConfig().getString("MYSQL.PREFIX");
+ }
+
+ public static boolean isInternetOnline() {
+ return isInternetOnline;
+ }
+
+ public static boolean isOfflineVersion() {
+ return inst.getResource("libs") != null;
+ }
+
+ public static boolean isLibrariesExists() {
+ return TLib.getTLib().getLibsFolder().listFiles().length > 0;
}
}
diff --git a/src/main/java/me/skymc/taboolib/TabooLib.java b/src/main/java/me/skymc/taboolib/TabooLib.java
index beceeff..9ae1e60 100644
--- a/src/main/java/me/skymc/taboolib/TabooLib.java
+++ b/src/main/java/me/skymc/taboolib/TabooLib.java
@@ -1,5 +1,6 @@
package me.skymc.taboolib;
+import me.skymc.taboolib.other.NumberUtils;
import me.skymc.taboolib.playerdata.DataUtils;
import net.md_5.bungee.api.ChatColor;
import org.bukkit.Bukkit;
@@ -37,17 +38,17 @@ public class TabooLib {
}
public static double getPluginVersion() {
- try {
- return Double.valueOf(Main.getInst().getDescription().getVersion());
- } catch (Exception e) {
- return 0D;
- }
+ return NumberUtils.getDouble(Main.getInst().getDescription().getVersion());
}
public static String getVersion() {
return Bukkit.getServer().getClass().getPackage().getName().replace(".", ",").split(",")[3];
}
+ public static int getVersionNumber() {
+ return getVerint();
+ }
+
public static String getServerUID() {
if (!DataUtils.getPluginData("TabooLibrary", null).contains("serverUID")) {
DataUtils.getPluginData("TabooLibrary", null).set("serverUID", UUID.randomUUID().toString());
@@ -59,20 +60,22 @@ public class TabooLib {
DataUtils.getPluginData("TabooLibrary", null).set("serverUID", UUID.randomUUID().toString());
}
+ @Deprecated
public static int getVerint() {
- if (getVersion().startsWith("v1_7")) {
+ String version = getVersion();
+ if (version.startsWith("v1_7")) {
return 10700;
- } else if (getVersion().startsWith("v1_8")) {
+ } else if (version.startsWith("v1_8")) {
return 10800;
- } else if (getVersion().startsWith("v1_9")) {
+ } else if (version.startsWith("v1_9")) {
return 10900;
- } else if (getVersion().startsWith("v1_10")) {
+ } else if (version.startsWith("v1_10")) {
return 11000;
- } else if (getVersion().startsWith("v1_11")) {
+ } else if (version.startsWith("v1_11")) {
return 11100;
- } else if (getVersion().startsWith("v1_12")) {
+ } else if (version.startsWith("v1_12")) {
return 11200;
- } else if (getVersion().startsWith("v1_13")) {
+ } else if (version.startsWith("v1_13")) {
return 11300;
}
return 0;
diff --git a/src/main/java/me/skymc/taboolib/bookformatter/BookReflection.java b/src/main/java/me/skymc/taboolib/bookformatter/BookReflection.java
index 5cbf36c..b090544 100644
--- a/src/main/java/me/skymc/taboolib/bookformatter/BookReflection.java
+++ b/src/main/java/me/skymc/taboolib/bookformatter/BookReflection.java
@@ -1,8 +1,10 @@
package me.skymc.taboolib.bookformatter;
-import net.md_5.bungee.api.chat.BaseComponent;
-import net.md_5.bungee.api.chat.TextComponent;
-import net.md_5.bungee.chat.ComponentSerializer;
+import com.ilummc.tlib.bungee.api.chat.BaseComponent;
+import com.ilummc.tlib.bungee.api.chat.TextComponent;
+import com.ilummc.tlib.bungee.chat.ComponentSerializer;
+import com.ilummc.tlib.logger.TLogger;
+import com.ilummc.tlib.resources.TLocale;
import org.bukkit.Bukkit;
import org.bukkit.entity.Player;
import org.bukkit.inventory.ItemStack;
@@ -12,6 +14,7 @@ import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
+import java.util.Arrays;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
@@ -31,11 +34,13 @@ public final class BookReflection {
private static final Method craftPlayerGetHandle;
- //This method takes an enum that represents the player's hand only in versions >= 1.9
- //In the other versions it only takes the nms item
+ /*
+ This method takes an enum that represents the player's hand only in versions >= 1.9
+ In the other versions it only takes the nms item
+ */
private static final Method entityPlayerOpenBook;
- //only version >= 1.9
+ // only version >= 1.9
private static final Object[] hands;
//Older versions
@@ -115,18 +120,22 @@ public final class BookReflection {
* @param meta the book meta to change
* @param components the pages of the book
*/
- @SuppressWarnings("unchecked")//reflections = unchecked warnings
- public static void setPages(BookMeta meta, BaseComponent[][] components) {
+ public static void setPages(BookMeta meta, BaseComponent[]... components) {
+ List