9
0
mirror of https://github.com/Xiao-MoMi/craft-engine.git synced 2025-12-27 10:59:07 +00:00

优化实现

This commit is contained in:
XiaoMoMi
2025-04-12 15:53:35 +08:00
parent 970b49305c
commit 1e417cf6b4
7 changed files with 77 additions and 93 deletions

View File

@@ -6,6 +6,7 @@ import net.luckperms.api.event.EventSubscription;
import net.luckperms.api.event.group.GroupDataRecalculateEvent;
import net.luckperms.api.event.user.UserDataRecalculateEvent;
import net.luckperms.api.model.user.User;
import net.momirealms.craftengine.core.plugin.CraftEngine;
import net.momirealms.craftengine.core.plugin.scheduler.SchedulerAdapter;
import org.bukkit.Bukkit;
import org.bukkit.World;
@@ -17,25 +18,24 @@ import java.util.List;
import java.util.UUID;
import java.util.concurrent.TimeUnit;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import java.util.logging.Level;
public class LuckPermsEventListeners {
private final JavaPlugin plugin;
private final LuckPerms luckPerms;
private final BiConsumer<UUID, Boolean> consumer;
private final SchedulerAdapter<World> scheduler;
private final Consumer<UUID> playerCallback;
private final List<EventSubscription<?>> subscriptions = new ArrayList<>();
public LuckPermsEventListeners(JavaPlugin plugin, BiConsumer<UUID, Boolean> consumer, SchedulerAdapter<World> scheduler) {
public LuckPermsEventListeners(JavaPlugin plugin, Consumer<UUID> playerCallback) {
this.plugin = plugin;
this.consumer = consumer;
this.scheduler = scheduler;
this.playerCallback = playerCallback;
RegisteredServiceProvider<LuckPerms> provider = Bukkit.getServicesManager().getRegistration(LuckPerms.class);
if (provider != null) {
this.luckPerms = provider.getProvider();
this.registerEventListeners();
} else {
throw new IllegalStateException("Unable to hook into LuckPerms");
throw new IllegalStateException("Unable to hook LuckPerms");
}
}
@@ -57,11 +57,13 @@ public class LuckPermsEventListeners {
}
private void onUserPermissionChange(UserDataRecalculateEvent event) {
this.consumer.accept(event.getUser().getUniqueId(), true);
CraftEngine.instance().scheduler().async().execute(() -> {
this.playerCallback.accept(event.getUser().getUniqueId());
});
}
private void onGroupPermissionChange(GroupDataRecalculateEvent event) {
this.scheduler.asyncLater(() -> {
CraftEngine.instance().scheduler().asyncLater(() -> {
String groupName = event.getGroup().getName();
Bukkit.getOnlinePlayers().forEach(player -> {
UUID uuid = player.getUniqueId();
@@ -70,7 +72,7 @@ public class LuckPermsEventListeners {
boolean inGroup = user.getInheritedGroups(user.getQueryOptions()).stream()
.anyMatch(g -> g.getName().equals(groupName));
if (inGroup) {
this.consumer.accept(uuid, false);
this.playerCallback.accept(uuid);
}
});
}, 1L, TimeUnit.SECONDS);

View File

@@ -31,8 +31,7 @@ import org.bukkit.inventory.meta.BookMeta;
import org.bukkit.inventory.view.AnvilView;
import java.lang.reflect.InvocationTargetException;
import java.util.List;
import java.util.UUID;
import java.util.*;
import java.util.stream.Collectors;
public class BukkitFontManager extends AbstractFontManager implements Listener {
@@ -47,9 +46,7 @@ public class BukkitFontManager extends AbstractFontManager implements Listener {
@Override
public void delayedInit() {
if (this.plugin.isPluginEnabled("LuckPerms")) {
luckPermsEventListeners = new LuckPermsEventListeners(
plugin.bootstrap(), this::refreshEmojiSuggestions, plugin.scheduler()
);
luckPermsEventListeners = new LuckPermsEventListeners(plugin.bootstrap(), this::refreshEmojiSuggestions);
}
Bukkit.getPluginManager().registerEvents(this, plugin.bootstrap());
}
@@ -65,49 +62,46 @@ public class BukkitFontManager extends AbstractFontManager implements Listener {
@Override
public void delayedLoad() {
List<String> oldCachedEmojiSuggestions = this.oldCachedEmojiSuggestions();
Collection<? extends Player> players = Bukkit.getOnlinePlayers();
for (Player player : players) {
removeEmojiSuggestions(player);
}
super.delayedLoad();
this.oldCachedEmojiSuggestions.addAll(this.cachedEmojiSuggestions());
Bukkit.getOnlinePlayers().forEach(player -> {
player.removeCustomChatCompletions(oldCachedEmojiSuggestions);
this.addEmojiSuggestions(player);
});
for (Player player : players) {
this.addEmojiSuggestions(player, getEmojiSuggestion(player));
}
}
@EventHandler(priority = EventPriority.LOWEST)
public void onPlayerJoin(PlayerJoinEvent event) {
plugin.scheduler().async().execute(() -> {
Player player = event.getPlayer();
this.addEmojiSuggestions(player);
});
plugin.scheduler().async().execute(() -> this.addEmojiSuggestions(event.getPlayer(), getEmojiSuggestion(event.getPlayer())));
}
public void refreshEmojiSuggestions(UUID playerUUID, boolean isAsync) {
if (isAsync) {
plugin.scheduler().async().execute(() -> {
Player player = Bukkit.getPlayer(playerUUID);
if (player == null) return;
player.removeCustomChatCompletions(oldCachedEmojiSuggestions);
this.addEmojiSuggestions(player);
});
} else {
Player player = Bukkit.getPlayer(playerUUID);
if (player == null) return;
player.removeCustomChatCompletions(oldCachedEmojiSuggestions);
this.addEmojiSuggestions(player);
private void refreshEmojiSuggestions(UUID uuid) {
Player player = Bukkit.getPlayer(uuid);
if (player == null) return;
removeEmojiSuggestions(player);
addEmojiSuggestions(player, getEmojiSuggestion(player));
}
private List<String> getEmojiSuggestion(Player player) {
List<String> suggestions = new ArrayList<>();
for (Emoji emoji : super.emojiList) {
if (emoji.permission() == null || player.hasPermission(Objects.requireNonNull(emoji.permission()))) {
suggestions.addAll(emoji.keywords());
}
}
return suggestions;
}
private void addEmojiSuggestions(Player player) {
List<String> hasPermissions = cachedEmojiSuggestions().stream()
.filter(keyword -> {
Emoji emoji = super.emojiMapper.get(keyword);
if (emoji == null) return false;
String permission = emoji.permission();
return permission == null || player.hasPermission(permission);
})
.collect(Collectors.toList());
player.addCustomChatCompletions(hasPermissions);
private void addEmojiSuggestions(Player player, List<String> suggestions) {
player.addCustomChatCompletions(suggestions);
}
private void removeEmojiSuggestions(Player player) {
if (super.allEmojiSuggestions != null) {
player.removeCustomChatCompletions(super.allEmojiSuggestions);
}
}
@EventHandler(priority = EventPriority.LOWEST, ignoreCancelled = true)

View File

@@ -443,10 +443,10 @@ public class BukkitNetworkManager implements NetworkManager, Listener, PluginMes
NMSPacketEvent event = new NMSPacketEvent(packet);
onNMSPacketSend(player, event, packet);
if (event.isCancelled()) return;
if (!event.hasNewPacket()) {
super.write(context, packet, channelPromise);
if (event.isUsingNewPacket()) {
super.write(context, event.optionalNewPacket(), channelPromise);
} else {
super.write(context, event.getNewPacket(), channelPromise);
super.write(context, packet, channelPromise);
}
channelPromise.addListener((p) -> {
for (Runnable task : event.getDelayedTasks()) {
@@ -464,10 +464,10 @@ public class BukkitNetworkManager implements NetworkManager, Listener, PluginMes
NMSPacketEvent event = new NMSPacketEvent(packet);
onNMSPacketReceive(player, event, packet);
if (event.isCancelled()) return;
if (!event.hasNewPacket()) {
super.channelRead(context, packet);
if (event.isUsingNewPacket()) {
super.channelRead(context, event.optionalNewPacket());
} else {
super.channelRead(context, event.getNewPacket());
super.channelRead(context, packet);
}
}
}

View File

@@ -1,19 +1,18 @@
package net.momirealms.craftengine.bukkit.plugin.network;
import net.momirealms.craftengine.core.util.Cancellable;
import org.jetbrains.annotations.NotNull;
import javax.annotation.Nullable;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Optional;
public class NMSPacketEvent implements Cancellable {
private boolean cancelled;
private boolean hasNewPacket;
private List<Runnable> delayedTasks = null;
private final Object packet;
private Object newPacket;
private boolean cancelled;
private List<Runnable> delayedTasks = null;
private Object newPacket = null;
public NMSPacketEvent(Object packet) {
this.packet = packet;
@@ -23,17 +22,15 @@ public class NMSPacketEvent implements Cancellable {
return packet;
}
public void setNewPacket(Object newPacket) {
hasNewPacket = true;
public void replacePacket(@NotNull Object newPacket) {
this.newPacket = newPacket;
}
public boolean hasNewPacket() {
return hasNewPacket;
public boolean isUsingNewPacket() {
return newPacket != null;
}
@Nullable
public Object getNewPacket() {
public Object optionalNewPacket() {
return newPacket;
}

View File

@@ -362,7 +362,7 @@ public class PacketConsumers {
isChanged = true;
}
if (isChanged) {
event.setNewPacket(FastNMS.INSTANCE.constructor$ClientboundPlayerInfoUpdatePacket(enums, newEntries));
event.replacePacket(FastNMS.INSTANCE.constructor$ClientboundPlayerInfoUpdatePacket(enums, newEntries));
}
} catch (Exception e) {
CraftEngine.instance().logger().warn("Failed to handle ClientboundPlayerInfoUpdatePacket", e);
@@ -1778,7 +1778,7 @@ public class PacketConsumers {
newPages,
newTitle
);
event.setNewPacket(newPacket);
event.replacePacket(newPacket);
}
} catch (Exception e) {
CraftEngine.instance().logger().warn("Failed to handle ServerboundEditBookPacket", e);

View File

@@ -41,9 +41,9 @@ public abstract class AbstractFontManager implements FontManager {
protected Trie emojiKeywordTrie;
protected Map<String, Component> tagMapper;
protected Map<String, Emoji> emojiMapper;
// tab补全
protected final List<String> cachedEmojiSuggestions = new ArrayList<>();
protected final List<String> oldCachedEmojiSuggestions = new ArrayList<>();
protected List<Emoji> emojiList;
protected List<String> allEmojiSuggestions;
public AbstractFontManager(CraftEngine plugin) {
this.plugin = plugin;
@@ -64,17 +64,27 @@ public abstract class AbstractFontManager implements FontManager {
this.images.clear();
this.illegalChars.clear();
this.emojis.clear();
this.cachedEmojiSuggestions.clear();
}
@Override
public List<String> cachedEmojiSuggestions() {
return List.copyOf(this.cachedEmojiSuggestions);
public void disable() {
this.unload();
}
@Override
public List<String> oldCachedEmojiSuggestions() {
return List.copyOf(this.oldCachedEmojiSuggestions);
public ConfigSectionParser[] parsers() {
return new ConfigSectionParser[] {this.imageParser, this.emojiParser};
}
@Override
public void delayedLoad() {
Optional.ofNullable(this.fonts.get(DEFAULT_FONT)).ifPresent(font -> this.illegalChars.addAll(font.codepointsInUse()));
this.buildImageTagTrie();
this.buildEmojiKeywordsTrie();
this.emojiList = new ArrayList<>(this.emojis.values());
this.allEmojiSuggestions = this.emojis.values().stream()
.flatMap(emoji -> emoji.keywords().stream())
.collect(Collectors.toList());
}
@Override
@@ -242,19 +252,6 @@ public abstract class AbstractFontManager implements FontManager {
return IllegalCharacterProcessResult.not();
}
@Override
public ConfigSectionParser[] parsers() {
return new ConfigSectionParser[] {this.imageParser, this.emojiParser};
}
@Override
public void delayedLoad() {
this.oldCachedEmojiSuggestions.clear();
Optional.ofNullable(this.fonts.get(DEFAULT_FONT)).ifPresent(font -> this.illegalChars.addAll(font.codepointsInUse()));
this.buildImageTagTrie();
this.buildEmojiKeywordsTrie();
}
private void buildEmojiKeywordsTrie() {
this.emojiMapper = new HashMap<>();
for (Emoji emoji : this.emojis.values()) {
@@ -371,8 +368,6 @@ public abstract class AbstractFontManager implements FontManager {
TranslationManager.instance().log("warning.config.emoji.lack_keywords", path.toString(), id.toString());
return;
}
String keyword = keywords.get(0);
cachedEmojiSuggestions.add(keyword);
String content = section.getOrDefault("content", "<arg:emoji>").toString();
String image = null;
if (section.containsKey("image")) {

View File

@@ -101,8 +101,4 @@ public interface FontManager extends Manageable {
}
Map<String, Component> matchTags(String json);
List<String> cachedEmojiSuggestions();
List<String> oldCachedEmojiSuggestions();
}