1
mirror of https://github.com/CarmJos/UserPrefix.git synced 2026-06-04 15:28:21 +08:00

feat: folia support

This commit is contained in:
flowerinsnow
2025-05-05 22:17:40 +08:00
committed by Carm
parent 003884d772
commit eab9b2385c
10 changed files with 147 additions and 15 deletions
+16 -4
View File
@@ -5,7 +5,7 @@
<modelVersion>4.0.0</modelVersion> <modelVersion>4.0.0</modelVersion>
<properties> <properties>
<project.jdk.version>8</project.jdk.version> <project.jdk.version>21</project.jdk.version>
<project.package>cc.carm.plugin.userprefix</project.package> <project.package>cc.carm.plugin.userprefix</project.package>
<maven.compiler.source>${project.jdk.version}</maven.compiler.source> <maven.compiler.source>${project.jdk.version}</maven.compiler.source>
@@ -76,6 +76,11 @@
<url>https://hub.spigotmc.org/nexus/content/repositories/snapshots/</url> <url>https://hub.spigotmc.org/nexus/content/repositories/snapshots/</url>
</repository> </repository>
<repository>
<id>papermc</id>
<url>https://repo.papermc.io/repository/maven-public/</url>
</repository>
<repository> <repository>
<id>luck-repo</id> <id>luck-repo</id>
<url>https://repo.lucko.me/</url> <url>https://repo.lucko.me/</url>
@@ -185,10 +190,17 @@
<scope>provided</scope> <scope>provided</scope>
</dependency> </dependency>
<!-- <dependency>-->
<!-- <groupId>org.spigotmc</groupId>-->
<!-- <artifactId>spigot-api</artifactId>-->
<!-- <version>1.17-R0.1-SNAPSHOT</version>-->
<!-- <scope>provided</scope>-->
<!-- </dependency>-->
<dependency> <dependency>
<groupId>org.spigotmc</groupId> <groupId>dev.folia</groupId>
<artifactId>spigot-api</artifactId> <artifactId>folia-api</artifactId>
<version>1.17-R0.1-SNAPSHOT</version> <version>1.21.4-R0.1-SNAPSHOT</version>
<scope>provided</scope> <scope>provided</scope>
</dependency> </dependency>
@@ -8,6 +8,7 @@ import cc.carm.lib.easyplugin.utils.MessageUtils;
import cc.carm.plugin.userprefix.command.AdminCommand; import cc.carm.plugin.userprefix.command.AdminCommand;
import cc.carm.plugin.userprefix.command.UserCommand; import cc.carm.plugin.userprefix.command.UserCommand;
import cc.carm.plugin.userprefix.conf.PluginConfig; import cc.carm.plugin.userprefix.conf.PluginConfig;
import cc.carm.plugin.userprefix.folia.FoliaScheduler;
import cc.carm.plugin.userprefix.hooker.UserPrefixExpansion; import cc.carm.plugin.userprefix.hooker.UserPrefixExpansion;
import cc.carm.plugin.userprefix.listener.ChatListener; import cc.carm.plugin.userprefix.listener.ChatListener;
import cc.carm.plugin.userprefix.listener.UserListener; import cc.carm.plugin.userprefix.listener.UserListener;
@@ -28,6 +29,9 @@ public class Main extends EasyPlugin {
private static Main instance; private static Main instance;
protected FoliaScheduler foliaScheduler;
protected boolean onFolia;
protected ConfigManager configManager; protected ConfigManager configManager;
protected PrefixManager prefixManager; protected PrefixManager prefixManager;
protected UserManager userManager; protected UserManager userManager;
@@ -36,6 +40,14 @@ public class Main extends EasyPlugin {
protected boolean initialize() { protected boolean initialize() {
instance = this; instance = this;
try {
Class.forName("io.papermc.paper.threadedregions.RegionizedServerInitEvent");
this.onFolia = true;
} catch (ClassNotFoundException e) {
this.onFolia = false;
}
this.foliaScheduler = new FoliaScheduler(this, this.onFolia);
log("加载插件配置..."); log("加载插件配置...");
this.configManager = new ConfigManager(getDataFolder()); this.configManager = new ConfigManager(getDataFolder());
this.prefixManager = new PrefixManager(); this.prefixManager = new PrefixManager();
@@ -87,11 +99,14 @@ public class Main extends EasyPlugin {
if (PluginConfig.CHECK_UPDATE.getNotNull()) { if (PluginConfig.CHECK_UPDATE.getNotNull()) {
log("开始检查更新..."); log("开始检查更新...");
getScheduler().runAsync(GHUpdateChecker.runner(this)); this.foliaScheduler.runAsync(GHUpdateChecker.runner(this));
} else { } else {
log("已禁用检查更新,跳过。"); log("已禁用检查更新,跳过。");
} }
if (PluginConfig.FUNCTIONS.NAME_PREFIX.ENABLE.getNotNull() && this.isOnFolia()) {
log("插件正运行在 Folia 服务端上,头顶前缀功能不可用");
}
Bukkit.getOnlinePlayers().forEach(userManager::initPlayer); // 适配热重载 Bukkit.getOnlinePlayers().forEach(userManager::initPlayer); // 适配热重载
log("&7感谢您使用 &3&lUserPrefix " + getDescription().getVersion() + "&7!"); log("&7感谢您使用 &3&lUserPrefix " + getDescription().getVersion() + "&7!");
@@ -113,6 +128,14 @@ public class Main extends EasyPlugin {
log("&7本插件由 &b&lYourCraft &7提供长期支持与维护。"); log("&7本插件由 &b&lYourCraft &7提供长期支持与维护。");
} }
public boolean isOnFolia() {
return this.onFolia;
}
public FoliaScheduler getFoliaScheduler() {
return this.foliaScheduler;
}
@Override @Override
public boolean isDebugging() { public boolean isDebugging() {
return PluginConfig.DEBUG.getNotNull(); return PluginConfig.DEBUG.getNotNull();
@@ -163,7 +163,7 @@ public class PluginConfig implements Configuration {
@HeaderComments({"当选择了默认前缀时显示的物品"}) @HeaderComments({"当选择了默认前缀时显示的物品"})
public static final ConfiguredItem USING = ConfiguredItem.create() public static final ConfiguredItem USING = ConfiguredItem.create()
.defaultType(Material.NAME_TAG) .defaultType(Material.NAME_TAG)
.defaultEnchant(Enchantment.PROTECTION_ENVIRONMENTAL, 1) .defaultEnchant(Enchantment.PROTECTION, 1)
.defaultFlags(ItemFlag.HIDE_ENCHANTS) .defaultFlags(ItemFlag.HIDE_ENCHANTS)
.defaultName("&f默认玩家前缀") .defaultName("&f默认玩家前缀")
.defaultLore("", "&a✔ 您正在使用该前缀") .defaultLore("", "&a✔ 您正在使用该前缀")
@@ -1,8 +1,10 @@
package cc.carm.plugin.userprefix.conf.prefix; package cc.carm.plugin.userprefix.conf.prefix;
import cc.carm.lib.easyplugin.gui.configuration.GUIActionConfiguration; import cc.carm.lib.easyplugin.gui.configuration.GUIActionConfiguration;
import cc.carm.lib.easyplugin.gui.configuration.GUIActionType;
import cc.carm.lib.easyplugin.utils.MessageUtils; import cc.carm.lib.easyplugin.utils.MessageUtils;
import cc.carm.lib.mineconfiguration.bukkit.value.item.PreparedItem; import cc.carm.lib.mineconfiguration.bukkit.value.item.PreparedItem;
import cc.carm.plugin.userprefix.Main;
import cc.carm.plugin.userprefix.manager.ServiceManager; import cc.carm.plugin.userprefix.manager.ServiceManager;
import org.bukkit.command.CommandSender; import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
@@ -97,7 +99,13 @@ public class PrefixConfig {
} }
public void executeActions(@NotNull Player player) { public void executeActions(@NotNull Player player) {
this.actions.forEach(action -> action.executeAction(player)); this.actions.forEach(action -> {
if (action.getActionType() == GUIActionType.CONSOLE) { // 控制台执行命令必须在全局调度器中执行
Main.getInstance().getFoliaScheduler().runGlobal(false, () -> action.executeAction(player));
} else {
action.executeAction(player);
}
});
} }
public boolean isVisible(Player player) { public boolean isVisible(Player player) {
@@ -2,6 +2,7 @@ package cc.carm.plugin.userprefix.event;
import cc.carm.plugin.userprefix.Main; import cc.carm.plugin.userprefix.Main;
import cc.carm.plugin.userprefix.conf.prefix.PrefixConfig; import cc.carm.plugin.userprefix.conf.prefix.PrefixConfig;
import org.bukkit.Bukkit;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import org.bukkit.event.Cancellable; import org.bukkit.event.Cancellable;
import org.bukkit.event.HandlerList; import org.bukkit.event.HandlerList;
@@ -61,8 +62,11 @@ public class UserPrefixChangeEvent extends UserPrefixEvent implements Cancellabl
@Nullable PrefixConfig before, @Nullable PrefixConfig before,
@NotNull PrefixConfig after, @NotNull PrefixConfig after,
@Nullable Consumer<@Nullable PrefixConfig> finish) { @Nullable Consumer<@Nullable PrefixConfig> finish) {
Main.getInstance().callSync(new UserPrefixChangeEvent(who, before, after)) UserPrefixChangeEvent event = new UserPrefixChangeEvent(who, before, after);
.thenAccept((e) -> Optional.ofNullable(finish).ifPresent(f -> f.accept(e.getAfter()))); Main.getInstance().getFoliaScheduler().runGlobal(true, () -> {
Bukkit.getPluginManager().callEvent(event);
Optional.ofNullable(finish).ifPresent(f -> f.accept(event.getAfter()));
});
} }
} }
@@ -2,6 +2,7 @@ package cc.carm.plugin.userprefix.event;
import cc.carm.plugin.userprefix.Main; import cc.carm.plugin.userprefix.Main;
import cc.carm.plugin.userprefix.conf.prefix.PrefixConfig; import cc.carm.plugin.userprefix.conf.prefix.PrefixConfig;
import org.bukkit.Bukkit;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import org.bukkit.event.HandlerList; import org.bukkit.event.HandlerList;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
@@ -30,7 +31,7 @@ public class UserPrefixExpireEvent extends UserPrefixEvent {
} }
public static void call(@NotNull Player player, @NotNull PrefixConfig currentPrefix) { public static void call(@NotNull Player player, @NotNull PrefixConfig currentPrefix) {
Main.getInstance().callSync(new UserPrefixExpireEvent(player, currentPrefix)); Main.getInstance().getFoliaScheduler().runGlobal(true, () -> Bukkit.getPluginManager().callEvent(new UserPrefixExpireEvent(player, currentPrefix)));
} }
} }
@@ -0,0 +1,80 @@
package cc.carm.plugin.userprefix.folia;
import org.bukkit.Bukkit;
import org.bukkit.entity.Entity;
import org.bukkit.plugin.Plugin;
public class FoliaScheduler {
private final Plugin plugin;
private final boolean folia;
public FoliaScheduler(Plugin plugin, boolean folia) {
this.plugin = plugin;
this.folia = folia;
}
public void runAsync(Runnable task) {
if (this.folia) {
this.runAsyncFolia(task);
} else {
this.runAsyncBukkit(task);
}
}
private void runAsyncBukkit(Runnable task) {
Bukkit.getScheduler().runTaskAsynchronously(this.plugin, task);
}
private void runAsyncFolia(Runnable task) {
Bukkit.getAsyncScheduler().runNow(this.plugin, t -> task.run());
}
/**
* Folia 上在实体所在的调度器上执行任务,或在 Bukkit 上同步执行任务
*
* @param entity 实体
* @param forceSync 若为 trueBukkit 下强制同步运行;若为 false,Bukkit 下直接执行
* @param task 任务
* @see FoliaScheduler#runBukkit(boolean, Runnable)
* @see FoliaScheduler#runOnEntityFolia(Entity, Runnable)
*/
public void runOnEntity(Entity entity, boolean forceSync, Runnable task) {
if (this.folia) {
this.runOnEntityFolia(entity, task);
} else {
this.runBukkit(forceSync, task);
}
}
private void runOnEntityFolia(Entity entity, Runnable task) {
entity.getScheduler().run(this.plugin, t -> task.run(), null);
}
/**
* Folia 上在全局调度器上执行任务,或在 Bukkit 上同步执行任务
*
* @param forceSync 若为 trueBukkit 下强制同步运行;若为 false,Bukkit 下直接执行
* @param task 任务
* @see FoliaScheduler#runBukkit(boolean, Runnable)
* @see FoliaScheduler#runGlobalFolia(Runnable)
*/
public void runGlobal(boolean forceSync, Runnable task) {
if (this.folia) {
this.runGlobalFolia(task);
} else {
this.runBukkit(forceSync, task);
}
}
private void runGlobalFolia(Runnable task) {
Bukkit.getGlobalRegionScheduler().execute(this.plugin, task);
}
private void runBukkit(boolean forceSync, Runnable task) {
if (forceSync) {
Bukkit.getScheduler().runTask(this.plugin, task);
} else {
task.run();
}
}
}
@@ -14,7 +14,7 @@ public class UserPermListener {
if (player == null) return; if (player == null) return;
UserPrefixAPI.getUserManager().checkPrefix(player, true); UserPrefixAPI.getUserManager().checkPrefix(player, true);
if (PrefixSelectGUI.openingUsers.contains(player)) { if (PrefixSelectGUI.openingUsers.contains(player)) {
Main.getInstance().getScheduler().run(() -> { Main.getInstance().getFoliaScheduler().runOnEntity(player, true, () -> {
// 玩家权限更新,同步关闭其GUI,以令其重新打开刷新自己的前缀。 // 玩家权限更新,同步关闭其GUI,以令其重新打开刷新自己的前缀。
player.closeInventory(); player.closeInventory();
PrefixSelectGUI.removeOpening(player); PrefixSelectGUI.removeOpening(player);
@@ -32,7 +32,7 @@ public class UserManager {
@Nullable @Nullable
public UserNameTag getNameTag(Player player) { public UserNameTag getNameTag(Player player) {
if (PluginConfig.FUNCTIONS.NAME_PREFIX.ENABLE.getNotNull()) { if (this.isNamePrefixEnabled()) {
if (nameTags.containsKey(player.getUniqueId())) { if (nameTags.containsKey(player.getUniqueId())) {
return nameTags.get(player.getUniqueId()); return nameTags.get(player.getUniqueId());
} else { } else {
@@ -53,7 +53,7 @@ public class UserManager {
public void initPlayer(Player player) { public void initPlayer(Player player) {
checkPrefix(player, false); checkPrefix(player, false);
if (PluginConfig.FUNCTIONS.NAME_PREFIX.ENABLE.getNotNull()) { if (this.isNamePrefixEnabled()) {
createNameTag(player); createNameTag(player);
updatePrefixView(player, true); updatePrefixView(player, true);
} }
@@ -73,7 +73,7 @@ public class UserManager {
* @param loadOthers 是否为玩家更新其他人的前缀(一般用于加入游戏) * @param loadOthers 是否为玩家更新其他人的前缀(一般用于加入游戏)
*/ */
public void updatePrefixView(Player player, boolean loadOthers) { public void updatePrefixView(Player player, boolean loadOthers) {
if (!PluginConfig.FUNCTIONS.NAME_PREFIX.ENABLE.getNotNull()) return; //未启用的情况下,不需要进行任何操作。 if (!this.isNamePrefixEnabled()) return; //未启用的情况下,不需要进行任何操作。
UserNameTag tag = getNameTag(player); UserNameTag tag = getNameTag(player);
if (tag == null) return; //未启用的情况下,不需要进行任何操作。 if (tag == null) return; //未启用的情况下,不需要进行任何操作。
@@ -273,4 +273,7 @@ public class UserManager {
user.data().clear(NodeType.META.predicate(mn -> mn.getMetaKey().equals(META_KEY))); user.data().clear(NodeType.META.predicate(mn -> mn.getMetaKey().equals(META_KEY)));
} }
private boolean isNamePrefixEnabled() {
return PluginConfig.FUNCTIONS.NAME_PREFIX.ENABLE.getNotNull() && !Main.getInstance().isOnFolia();
}
} }
+2 -1
View File
@@ -7,7 +7,8 @@ authors:
- SakuraGame - SakuraGame
website: ${project.url} website: ${project.url}
description: ${project.description} description: ${project.description}
api-version: 1.13 api-version: 1.21.4
folia-supported: true
depend: depend:
- LuckPerms - LuckPerms