Compare commits

...
Author SHA1 Message Date
Rollczi e91248f22f Update Maven repository declarations and clean up version configurations 2023-11-14 13:22:40 +01:00
Dominik ea618cc734 Initial commit. 2023-11-02 18:05:39 +01:00
Dominik a46d0c67aa Initial commit. 2023-11-02 18:05:22 +01:00
27 changed files with 369 additions and 180 deletions

No files matched your search

@@ -18,12 +18,12 @@ checkstyle {
repositories {
mavenCentral()
maven { url = uri("https://hub.spigotmc.org/nexus/content/repositories/snapshots/") }
maven { url = uri("https://papermc.io/repo/repository/maven-public/") }
maven { url = uri("https://repo.eternalcode.pl/releases") }
maven { url = uri("https://storehouse.okaeri.eu/repository/maven-public/") }
maven { url = uri("https://repo.panda-lang.org/releases") }
maven { url = uri("https://maven.enginehub.org/repo/") }
maven("https://hub.spigotmc.org/nexus/content/repositories/snapshots/")
maven("https://papermc.io/repo/repository/maven-public/")
maven("https://repo.eternalcode.pl/releases")
maven("https://storehouse.okaeri.eu/repository/maven-public/")
maven("https://repo.panda-lang.org/releases")
maven("https://maven.enginehub.org/repo/")
}
java {
@@ -7,6 +7,7 @@ import com.eternalcode.combat.fight.event.CauseOfTag;
import com.eternalcode.combat.fight.event.CauseOfUnTag;
import com.eternalcode.combat.fight.event.FightTagEvent;
import com.eternalcode.combat.fight.event.FightUntagEvent;
import com.eternalcode.combat.notification.Notification;
import com.eternalcode.combat.notification.NotificationAnnouncer;
import dev.rollczi.litecommands.argument.Arg;
import dev.rollczi.litecommands.command.async.Async;
@@ -44,9 +45,11 @@ public class CombatCommand {
Formatter formatter = new Formatter()
.register("{PLAYER}", target.getName());
this.announcer.sendMessage(sender, this.fightManager.isInCombat(targetUniqueId)
? formatter.format(messages.admin.playerInCombat)
: formatter.format(messages.admin.playerNotInCombat));
Notification notification = this.fightManager.isInCombat(targetUniqueId)
? messages.admin.playerInCombat
: messages.admin.playerNotInCombat;
this.announcer.send(sender, notification, formatter);
}
@Execute(route = "tag", required = 1)
@@ -65,8 +68,7 @@ public class CombatCommand {
return;
}
String format = formatter.format(this.config.messages.admin.adminTagPlayer);
this.announcer.sendMessage(sender, format);
this.announcer.send(sender, this.config.messages.admin.adminTagPlayer, formatter);
}
@Execute(route = "tag", required = 2)
@@ -76,19 +78,13 @@ public class CombatCommand {
PluginConfig.Messages messages = this.config.messages;
if (sender.equals(firstTarget) || sender.equals(secondTarget)) {
this.announcer.sendMessage(sender, messages.admin.adminCannotTagSelf);
this.announcer.send(sender, messages.admin.adminCannotTagSelf);
return;
}
FightTagEvent firstTagEvent = this.fightManager.tag(firstTarget.getUniqueId(), combatTime, CauseOfTag.COMMAND);
FightTagEvent secondTagEvent = this.fightManager.tag(secondTarget.getUniqueId(), combatTime, CauseOfTag.COMMAND);
Formatter formatter = new Formatter()
.register("{FIRST_PLAYER}", firstTarget.getName())
.register("{SECOND_PLAYER}", secondTarget.getName());
String format = formatter.format(messages.admin.adminTagMultiplePlayers);
if (firstTagEvent.isCancelled()) {
this.announcer.sendMessage(sender, firstTagEvent.getCancelMessage());
}
@@ -101,7 +97,11 @@ public class CombatCommand {
return;
}
this.announcer.sendMessage(sender, format);
Formatter formatter = new Formatter()
.register("{FIRST_PLAYER}", firstTarget.getName())
.register("{SECOND_PLAYER}", secondTarget.getName());
this.announcer.send(sender, messages.admin.adminTagMultiplePlayers, formatter);
}
@Async
@@ -109,7 +109,7 @@ public class CombatCommand {
@Permission("eternalcombat.reload")
void execute(CommandSender player) {
this.configService.reload();
this.announcer.sendMessage(player, this.config.messages.admin.reload);
this.announcer.send(player, this.config.messages.admin.reload);
}
@Execute(route = "untag", required = 1)
@@ -118,7 +118,7 @@ public class CombatCommand {
UUID targetUniqueId = target.getUniqueId();
if (!this.fightManager.isInCombat(targetUniqueId)) {
this.announcer.sendMessage(sender, this.config.messages.admin.adminPlayerNotInCombat);
this.announcer.send(sender, this.config.messages.admin.adminPlayerNotInCombat);
return;
}
@@ -130,8 +130,6 @@ public class CombatCommand {
Formatter formatter = new Formatter()
.register("{PLAYER}", target.getName());
String format = formatter.format(this.config.messages.admin.adminUntagPlayer);
this.announcer.sendMessage(sender, format);
this.announcer.send(sender, this.config.messages.admin.adminUntagPlayer, formatter);
}
}
@@ -29,7 +29,7 @@ public class InvalidUsage implements InvalidUsageHandler<CommandSender> {
Formatter formatter = new Formatter()
.register("{USAGE}", schematic);
this.announcer.sendMessage(commandSender, formatter.format(this.config.messages.invalidCommandUsage));
this.announcer.send(commandSender, this.config.messages.invalidCommandUsage, formatter);
}
}
}
@@ -28,7 +28,7 @@ public class PermissionMessage implements PermissionHandler<CommandSender> {
Formatter formatter = new Formatter()
.register("{PERMISSION}", value);
this.announcer.sendMessage(commandSender, formatter.format(this.config.messages.noPermission));
this.announcer.send(commandSender, this.config.messages.noPermission, formatter);
}
}
@@ -1,6 +1,7 @@
package com.eternalcode.combat.config;
import com.eternalcode.combat.notification.serializer.NotificationSerializer;
import com.eternalcode.combat.notification.implementation.title.serializer.TitleTimesSerializer;
import eu.okaeri.configs.ConfigManager;
import eu.okaeri.configs.OkaeriConfig;
import eu.okaeri.configs.serdes.commons.SerdesCommons;
@@ -29,6 +30,7 @@ public class ConfigService {
configFile.withConfigurer(new YamlBukkitConfigurer(), new SerdesCommons(), new SerdesBukkit());
configFile.withSerdesPack(registry -> {
registry.register(new NotificationSerializer());
registry.register(new TitleTimesSerializer());
});
configFile.withBindFile(file);
@@ -5,9 +5,13 @@ import com.eternalcode.combat.drop.DropSettings;
import com.eternalcode.combat.fight.effect.FightEffectSettings;
import com.eternalcode.combat.fight.pearl.FightPearlSettings;
import com.eternalcode.combat.notification.Notification;
import com.eternalcode.combat.notification.implementation.ActionBarNotification;
import com.eternalcode.combat.notification.implementation.BossBarNotification;
import com.eternalcode.combat.notification.implementation.ChatNotification;
import com.eternalcode.combat.notification.implementation.title.TitleNotification;
import eu.okaeri.configs.OkaeriConfig;
import eu.okaeri.configs.annotation.Comment;
import net.kyori.adventure.bossbar.BossBar;
import net.kyori.adventure.title.Title;
import org.bukkit.Material;
import org.bukkit.entity.EntityType;
import org.bukkit.event.entity.EntityDamageEvent;
@@ -121,7 +125,15 @@ public class PluginConfig extends OkaeriConfig {
}
@Comment({" ", "# Do you want to change the plugin messages?"})
@Comment({
" ",
"# Do you want to change the plugin messages?",
"# Message types: CHAT, ACTION_BAR, TITLE, SUB_TITLE, BOSS_BAR",
" ",
"# BossBar progress: This is the value of the progress bar",
"# BossBar colors: https://javadoc.io/static/net.kyori/adventure-api/4.14.0/net/kyori/adventure/bossbar/BossBar.Color.html",
"# BossBar overlays: https://javadoc.io/static/net.kyori/adventure-api/4.14.0/net/kyori/adventure/bossbar/BossBar.Overlay.html"
})
public Messages messages = new Messages();
public static class Messages extends OkaeriConfig {
@@ -131,94 +143,91 @@ public class PluginConfig extends OkaeriConfig {
@Comment({
" ",
"# Combat log notification",
"# You can use {TIME} variable to display the time left in combat",
"# Notification types: CHAT, ACTION_BAR, TITLE, SUB_TITLE, BOSS_BAR",
"# Combat log message",
"# Use {TIME} to display the remaining fight time",
" ",
"# BossBar progress: This is the value of the progress bar. Set it to -1.0 to show the remaining combat time",
"# BossBar colors: https://javadoc.io/static/net.kyori/adventure-api/4.14.0/net/kyori/adventure/bossbar/BossBar.Color.html",
"# BossBar overlays: https://javadoc.io/static/net.kyori/adventure-api/4.14.0/net/kyori/adventure/bossbar/BossBar.Overlay.html"
"# BossBar progress: Set to -1.0 to have the bossbar progress show the remaining fight time"
})
public Notification combatNotification = new ActionBarNotification("&dCombat ends in: &f{TIME}");
public Notification combatLog = new BossBarNotification(-1.0F, BossBar.Color.RED, BossBar.Overlay.NOTCHED_6, "&dCombat ends in: &f{TIME}");
@Comment("# Message sent when the player does not have permission to perform a command")
public String noPermission = "&cYou don't have permission to perform this command!";
public Notification noPermission = new TitleNotification(Title.DEFAULT_TIMES, "&cYou don't have permission to perform this command!");
@Comment("# Message sent when the specified player could not be found")
public String playerNotFound = "&cThe specified player could not be found!";
public Notification playerNotFound = new ChatNotification("&cThe specified player could not be found!");
@Comment("# Message sent when the player enters combat")
public String playerTagged = "&cYou are in combat, do not leave the server!";
public Notification playerTagged = new ChatNotification("&cYou are in combat, do not leave the server!");
@Comment("# Message sent when the player leaves combat")
public String playerUntagged = "&aYou are no longer in combat! You can safely leave the server.";
public Notification playerUntagged = new ChatNotification("&aYou are no longer in combat! You can safely leave the server.");
@Comment("# This is broadcast when the player is in combat and logs out")
public String playerLoggedOutDuringCombat = "&c{PLAYER} logged off during the fight!";
public Notification playerLoggedOutDuringCombat = new ChatNotification("&c{PLAYER} logged off during the fight!");
@Comment({
"# Message sent when the player is in combat and tries to use a disabled command",
"# you can configure the list of disabled commands in the blockedCommands section of the config.yml file"
})
public String commandDisabledDuringCombat = "&cUsing this command during combat is prohibited!";
public Notification commandDisabledDuringCombat = new ChatNotification("&cUsing this command during combat is prohibited!");
@Comment("# Message sent when player tries to use a command with invalid arguments")
public String invalidCommandUsage = "&7Correct usage: &e{USAGE}";
public Notification invalidCommandUsage = new ChatNotification("&7Correct usage: &e{USAGE}");
@Comment("# Message sent when player tries to open inventory, but the inventory open is blocked")
public String inventoryBlockedDuringCombat = "&cYou cannot open this inventory during combat!";
public Notification inventoryBlockedDuringCombat = new ChatNotification("&cYou cannot open this inventory during combat!");
@Comment("# Message sent when player tries to place a block, but the block place is blocked")
public String blockPlacingBlockedDuringCombat = "&cYou cannot place above 40Y coordinate during combat!";
public Notification blockPlacingBlockedDuringCombat = new ChatNotification("&cYou cannot place above 40Y coordinate during combat!");
@Comment("# Message sent when player tries to enter a region")
public String cantEnterOnRegion = "&cYou can't enter on this region during combat!";
public Notification cantEnterOnRegion = new ChatNotification("&cYou can't enter on this region during combat!");
public static class AdminMessages extends OkaeriConfig {
@Comment("# Message sent when the configuration is reloaded")
public String reload = "&aConfiguration has been successfully reloaded!";
public Notification reload = new ChatNotification("&aConfiguration has been successfully reloaded!");
@Comment("# Message sent when console tries to use a command that is only for players")
public String onlyForPlayers = "&cThis command is only available to players!";
public Notification onlyForPlayers = new ChatNotification("&cThis command is only available to players!");
@Comment("# Message sent to admin when they tag a player")
public String adminTagPlayer = "&7You have tagged &e{PLAYER}";
public Notification adminTagPlayer = new ChatNotification("&7You have tagged &e{PLAYER}");
@Comment("# Message sent when a player is tagged by an admin")
public String adminTagMultiplePlayers = "&7You have tagged &e{FIRST_PLAYER}&7 and &e{SECOND_PLAYER}&7.";
public Notification adminTagMultiplePlayers = new ChatNotification("&7You have tagged &e{FIRST_PLAYER}&7 and &e{SECOND_PLAYER}&7.");
@Comment("# Message sent to admin when they remove a player from combat")
public String adminUntagPlayer = "&7You have removed &e{PLAYER}&7 from the fight.";
public Notification adminUntagPlayer = new ChatNotification("&7You have removed &e{PLAYER}&7 from the fight.");
@Comment("# Message sent when the player is not in combat")
public String adminPlayerNotInCombat = "&cThis player is not in combat!";
public Notification adminPlayerNotInCombat = new ChatNotification("&cThis player is not in combat!");
@Comment("# Message sent when the player is in combat")
public String playerInCombat = "&c{PLAYER} is currently in combat!";
public Notification playerInCombat = new ChatNotification("&c{PLAYER} is currently in combat!");
@Comment("# Message sent when a player is not in combat")
public String playerNotInCombat = "&a{PLAYER} is not currently in combat.";
public Notification playerNotInCombat = new ChatNotification("&a{PLAYER} is not currently in combat.");
@Comment("# Message sent when an admin tries to tag themselves")
public String adminCannotTagSelf = "&cYou cannot tag yourself!";
public Notification adminCannotTagSelf = new ChatNotification("&cYou cannot tag yourself!");
@Comment("# Message sent when an admin disables the ability to get tagged for some time")
public String adminTagOutSelf = "&7Successfully disabled tag for Yourself! You will be taggable after &e{TIME} ";
public Notification adminTagOutSelf = new ChatNotification("&7Successfully disabled tag for Yourself! You will be taggable after &e{TIME}");
@Comment("# Message sent when an admin disables the ability to get tagged for some time for other player")
public String adminTagOut = "&7Successfully disabled tag for &e{PLAYER}! They will be taggable after &e{TIME} ";
public Notification adminTagOut = new ChatNotification("&7Successfully disabled tag for &e{PLAYER}! They will be taggable after &e{TIME}");
@Comment("# Message sent to the player whom the ability to get tagged for some time has been disabled")
public String playerTagOut = "&7You will be taggable in &e{TIME} !";
public Notification playerTagOut = new ChatNotification("&7You will be taggable in &e{TIME}!");
@Comment("# Message sent when an admin reenables the ability to get tagged for the player")
public String adminTagOutOff = "&7Successfully enabled tag for &e{PLAYER}!";
public Notification adminTagOutOff = new ChatNotification("&7Successfully enabled tag for &e{PLAYER}!");
@Comment("# Message sent to the player whom the ability to get tagged has been reenabled")
public String playerTagOutOff = "&7You are now taggable!";
public Notification playerTagOutOff = new ChatNotification("&7You are now taggable!");
@Comment("# Message sent when player cannot be tagged because they have enabled tag-out")
public String adminTagOutCanceled = "&cCannot tag this player due to tag-out!";
public Notification adminTagOutCanceled = new ChatNotification("&cCannot tag this player due to tag-out!");
}
}
}
@@ -1,8 +1,8 @@
package com.eternalcode.combat.fight;
import com.eternalcode.combat.fight.event.CauseOfUnTag;
import com.eternalcode.combat.config.implementation.PluginConfig;
import com.eternalcode.combat.fight.bossbar.FightBossBarService;
import com.eternalcode.combat.fight.event.CauseOfUnTag;
import com.eternalcode.combat.notification.Notification;
import com.eternalcode.combat.notification.NotificationAnnouncer;
import com.eternalcode.combat.notification.implementation.BossBarNotification;
@@ -50,9 +50,9 @@ public class FightTask implements Runnable {
Formatter formatter = new Formatter()
.register("{TIME}", DurationUtil.format(remaining));
Notification combatNotification = this.config.messages.combatNotification;
Notification combatLog = this.config.messages.combatLog;
this.sendFightNotification(player, fightTag, combatNotification, formatter);
this.sendFightNotification(player, fightTag, combatLog, formatter);
}
}
@@ -51,14 +51,14 @@ public class FightActionBlockerController implements Listener {
boolean isBlockPlaceLevel = level > this.config.settings.minBlockPlacingLevel;
if (isBlockPlaceLevel && specificBlocksToPreventPlacing.isEmpty()) {
event.setCancelled(true);
this.announcer.sendMessage(player, this.config.messages.blockPlacingBlockedDuringCombat);
this.announcer.send(player, this.config.messages.blockPlacingBlockedDuringCombat);
}
Material blockMaterial = block.getType();
boolean isBlockInDisabledList = specificBlocksToPreventPlacing.contains(blockMaterial);
if (isBlockPlaceLevel && isBlockInDisabledList) {
event.setCancelled(true);
this.announcer.sendMessage(player, this.config.messages.blockPlacingBlockedDuringCombat);
this.announcer.send(player, this.config.messages.blockPlacingBlockedDuringCombat);
}
}
@@ -113,7 +113,7 @@ public class FightActionBlockerController implements Listener {
event.setCancelled(true);
this.announcer.sendMessage(player, this.config.messages.inventoryBlockedDuringCombat);
this.announcer.send(player, this.config.messages.inventoryBlockedDuringCombat);
}
@EventHandler
@@ -136,7 +136,7 @@ public class FightActionBlockerController implements Listener {
if (shouldCancel) {
event.setCancelled(true);
this.announcer.sendMessage(player, this.config.messages.commandDisabledDuringCombat);
this.announcer.send(player, this.config.messages.commandDisabledDuringCombat);
}
}
}
@@ -33,9 +33,7 @@ public class FightEscapeController implements Listener {
Formatter formatter = new Formatter()
.register("{PLAYER}", player.getName());
String format = formatter.format(this.config.messages.playerLoggedOutDuringCombat);
this.announcer.broadcast(format);
this.announcer.broadcast(this.config.messages.playerLoggedOutDuringCombat, formatter);
FightTag fightTag = this.fightManager.getTag(player.getUniqueId());
fightTag.setHealthBeforeDeath(player.getHealth());
@@ -39,7 +39,7 @@ public class FightMessageController implements Listener {
return;
}
this.announcer.sendMessage(player, this.config.messages.playerTagged);
this.announcer.send(player, this.config.messages.playerTagged);
}
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
@@ -54,7 +54,7 @@ public class FightMessageController implements Listener {
return;
}
this.announcer.sendMessage(player, this.config.messages.playerUntagged);
this.announcer.send(player, this.config.messages.playerUntagged);
this.bossBarService.hide(event.getPlayer());
}
@@ -1,10 +1,9 @@
package com.eternalcode.combat.fight.controller;
import com.eternalcode.combat.WhitelistBlacklistMode;
import com.eternalcode.combat.fight.event.CauseOfTag;
import com.eternalcode.combat.config.implementation.PluginConfig;
import com.eternalcode.combat.fight.FightManager;
import com.eternalcode.combat.notification.NotificationAnnouncer;
import com.eternalcode.combat.fight.event.CauseOfTag;
import org.bukkit.entity.EntityType;
import org.bukkit.entity.Player;
import org.bukkit.entity.Projectile;
@@ -23,12 +22,10 @@ public class FightTagController implements Listener {
private final FightManager fightManager;
private final PluginConfig config;
private final NotificationAnnouncer announcer;
public FightTagController(FightManager fightManager, PluginConfig config, NotificationAnnouncer announcer) {
public FightTagController(FightManager fightManager, PluginConfig config) {
this.fightManager = fightManager;
this.config = config;
this.announcer = announcer;
}
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
@@ -58,7 +58,7 @@ public class FightPearlController implements Listener {
if (this.settings.pearlThrowDelay.isZero()) {
event.setCancelled(true);
this.announcer.sendMessage(player, this.settings.pearlThrowBlockedDuringCombat);
this.announcer.send(player, this.settings.pearlThrowBlockedDuringCombat);
return;
}
@@ -70,8 +70,7 @@ public class FightPearlController implements Listener {
Formatter formatter = new Formatter()
.register("{TIME}", DurationUtil.format(remainingPearlDelay));
String format = formatter.format(this.settings.pearlThrowBlockedDelayDuringCombat);
this.announcer.sendMessage(player, format);
this.announcer.send(player, this.settings.pearlThrowBlockedDelayDuringCombat, formatter);
return;
}
@@ -1,5 +1,7 @@
package com.eternalcode.combat.fight.pearl;
import com.eternalcode.combat.notification.Notification;
import com.eternalcode.combat.notification.implementation.ChatNotification;
import eu.okaeri.configs.OkaeriConfig;
import eu.okaeri.configs.annotation.Comment;
@@ -21,9 +23,9 @@ public class FightPearlSettings extends OkaeriConfig {
public Duration pearlThrowDelay = Duration.ofSeconds(3);
@Comment("# Message sent when player tries to throw ender pearl, but are disabled")
public String pearlThrowBlockedDuringCombat = "&cThrowing ender pearls is prohibited during combat!";
public Notification pearlThrowBlockedDuringCombat = new ChatNotification("&cThrowing ender pearls is prohibited during combat!");
@Comment("# Message sent when player tries to throw ender pearl, but has delay")
public String pearlThrowBlockedDelayDuringCombat = "&cYou must wait {TIME} before next throw!";
public Notification pearlThrowBlockedDelayDuringCombat = new ChatNotification("&cYou must wait {TIME} before next throw!");
}
@@ -22,7 +22,7 @@ public class FightTagOutController implements Listener {
UUID uniqueId = event.getPlayer();
if (this.tagOutService.isTaggedOut(uniqueId)) {
event.cancel(this.config.messages.admin.adminTagOutCanceled);
event.cancel(this.config.messages.admin.adminTagOutCanceled.message());
}
}
@@ -38,8 +38,7 @@ public class TagOutCommand {
this.fightTagOutService.tagOut(targetUniqueId, time);
String format = formatter.format(this.config.messages.admin.adminTagOutSelf);
this.announcer.sendMessage(sender, format);
this.announcer.send(sender, this.config.messages.admin.adminTagOutSelf, formatter);
}
@Execute(required = 2)
@@ -56,11 +55,8 @@ public class TagOutCommand {
this.fightTagOutService.tagOut(targetUniqueId, time);
String adminTagOutFormat = formatter.format(this.config.messages.admin.adminTagOut);
this.announcer.sendMessage(sender, adminTagOutFormat);
String playerTagOutFormat = formatter.format(this.config.messages.admin.playerTagOut);
this.announcer.sendMessage(target, playerTagOutFormat);
this.announcer.send(sender, this.config.messages.admin.adminTagOut, formatter);
this.announcer.send(target, this.config.messages.admin.playerTagOut, formatter);
}
@Execute(route = "remove", required = 1)
@@ -74,11 +70,10 @@ public class TagOutCommand {
.register("{PLAYER}", target.getName());
if (!targetUniqueId.equals(sender.getUniqueId())) {
String adminUnTagOutFormat = formatter.format(this.config.messages.admin.adminTagOutOff);
this.announcer.sendMessage(sender, adminUnTagOutFormat);
this.announcer.send(sender, this.config.messages.admin.adminTagOutOff, formatter);
}
this.announcer.sendMessage(target, this.config.messages.admin.playerTagOutOff);
this.announcer.send(target, this.config.messages.admin.playerTagOutOff);
}
@Execute(route = "remove", required = 0)
@@ -88,7 +83,7 @@ public class TagOutCommand {
this.fightTagOutService.unTagOut(senderUniqueId);
this.announcer.sendMessage(sender, this.config.messages.admin.playerTagOutOff);
this.announcer.send(sender, this.config.messages.admin.playerTagOutOff);
}
}
@@ -1,6 +1,7 @@
package com.eternalcode.combat.notification;
import com.eternalcode.combat.notification.implementation.BossBarNotification;
import com.eternalcode.combat.scheduler.Scheduler;
import net.kyori.adventure.audience.Audience;
import net.kyori.adventure.bossbar.BossBar;
import net.kyori.adventure.platform.AudienceProvider;
@@ -11,20 +12,49 @@ import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import panda.utilities.text.Formatter;
import java.time.Duration;
public final class NotificationAnnouncer {
private final AudienceProvider audienceProvider;
private final MiniMessage miniMessage;
private final Scheduler scheduler;
public NotificationAnnouncer(AudienceProvider audienceProvider, MiniMessage miniMessage) {
public NotificationAnnouncer(AudienceProvider audienceProvider, MiniMessage miniMessage, Scheduler scheduler) {
this.scheduler = scheduler;
this.audienceProvider = audienceProvider;
this.miniMessage = miniMessage;
}
public void send(CommandSender sender, Notification notification) {
Audience audience = this.audience(sender);
Component message = this.miniMessage.deserialize(notification.message());
this.processNotification(notification, audience, message);
}
public void send(CommandSender sender, Notification notification, Formatter formatter) {
Audience audience = this.audience(sender);
Component message = this.miniMessage.deserialize(formatter.format(notification.message()));
this.processNotification(notification, audience, message);
}
public void sendMessage(CommandSender commandSender, String text) {
Audience audience = this.audience(commandSender);
Component message = this.miniMessage.deserialize(text);
audience.sendMessage(message);
}
public void broadcast(Notification notification, Formatter formatter) {
Audience audience = this.audienceProvider.all();
Component message = this.miniMessage.deserialize(formatter.format(notification.message()));
this.processNotification(notification, audience, message);
}
private void processNotification(Notification notification, Audience audience, Component message) {
NotificationType type = notification.type();
switch (type) {
@@ -49,26 +79,14 @@ public final class NotificationAnnouncer {
BossBar bossBar = bossBarNotification.create(message);
audience.showBossBar(bossBar);
this.scheduler.laterAsync(() -> audience.hideBossBar(bossBar), Duration.ofSeconds(4L));
}
default -> throw new IllegalStateException("Unknown notification type: " + type);
}
}
public void sendMessage(CommandSender commandSender, String text) {
Audience audience = this.audience(commandSender);
Component message = this.miniMessage.deserialize(text);
audience.sendMessage(message);
}
public void broadcast(String text) {
Audience audience = this.audienceProvider.all();
Component message = this.miniMessage.deserialize(text);
audience.sendMessage(message);
}
private Audience audience(CommandSender sender) {
if (sender instanceof Player player) {
return this.audienceProvider.player(player.getUniqueId());
@@ -5,7 +5,7 @@ import com.eternalcode.combat.notification.NotificationType;
import net.kyori.adventure.bossbar.BossBar;
import net.kyori.adventure.text.Component;
public record BossBarNotification(String message, float progress, BossBar.Color color, BossBar.Overlay overlay) implements Notification {
public record BossBarNotification(float progress, BossBar.Color color, BossBar.Overlay overlay, String message) implements Notification {
public BossBar create(Component name) {
float replacedProgress = this.progress < 0.0F ? BossBar.MAX_PROGRESS : this.progress;
@@ -1,9 +1,10 @@
package com.eternalcode.combat.notification.implementation;
package com.eternalcode.combat.notification.implementation.title;
import com.eternalcode.combat.notification.Notification;
import com.eternalcode.combat.notification.NotificationType;
import net.kyori.adventure.title.Title;
public record SubTitleNotification(String message) implements Notification {
public record SubTitleNotification(Title.Times times, String message) implements Notification {
@Override
public NotificationType type() {
@@ -1,9 +1,10 @@
package com.eternalcode.combat.notification.implementation;
package com.eternalcode.combat.notification.implementation.title;
import com.eternalcode.combat.notification.Notification;
import com.eternalcode.combat.notification.NotificationType;
import net.kyori.adventure.title.Title;
public record TitleNotification(String message) implements Notification {
public record TitleNotification(Title.Times times, String message) implements Notification {
@Override
public NotificationType type() {
@@ -0,0 +1,42 @@
package com.eternalcode.combat.notification.implementation.title.serializer;
import dev.rollczi.litecommands.shared.EstimatedTemporalAmountParser;
import eu.okaeri.configs.schema.GenericsPair;
import eu.okaeri.configs.serdes.BidirectionalTransformer;
import eu.okaeri.configs.serdes.SerdesContext;
import net.kyori.adventure.title.Title;
import org.checkerframework.checker.nullness.qual.NonNull;
import java.time.Duration;
public class TitleTimesSerializer extends BidirectionalTransformer<String, Title.Times> {
private static final String TITLE_TIMES_FORMAT = "%s %s %s";
private static final EstimatedTemporalAmountParser<Duration> DURATION_PARSER = EstimatedTemporalAmountParser.TIME_UNITS;
@Override
public GenericsPair<String, Title.Times> getPair() {
return this.genericsPair(String.class, Title.Times.class);
}
@Override
public Title.Times leftToRight(@NonNull String data, @NonNull SerdesContext serdesContext) {
String[] arguments = data.split(" ");
Duration fadeIn = DURATION_PARSER.parse(arguments[0]);
Duration stay = DURATION_PARSER.parse(arguments[1]);
Duration fadeOut = DURATION_PARSER.parse(arguments[2]);
return Title.Times.times(fadeIn, stay, fadeOut);
}
@Override
public String rightToLeft(Title.Times times, @NonNull SerdesContext serdesContext) {
String fadeIn = DURATION_PARSER.format(times.fadeIn());
String stay = DURATION_PARSER.format(times.stay());
String fadeOut = DURATION_PARSER.format(times.fadeOut());
return TITLE_TIMES_FORMAT.formatted(fadeIn, stay, fadeOut);
}
}
@@ -5,19 +5,20 @@ import com.eternalcode.combat.notification.NotificationType;
import com.eternalcode.combat.notification.implementation.ActionBarNotification;
import com.eternalcode.combat.notification.implementation.BossBarNotification;
import com.eternalcode.combat.notification.implementation.ChatNotification;
import com.eternalcode.combat.notification.implementation.SubTitleNotification;
import com.eternalcode.combat.notification.implementation.TitleNotification;
import com.eternalcode.combat.notification.implementation.title.SubTitleNotification;
import com.eternalcode.combat.notification.implementation.title.TitleNotification;
import eu.okaeri.configs.schema.GenericsDeclaration;
import eu.okaeri.configs.serdes.DeserializationData;
import eu.okaeri.configs.serdes.ObjectSerializer;
import eu.okaeri.configs.serdes.SerializationData;
import net.kyori.adventure.bossbar.BossBar;
import net.kyori.adventure.title.Title;
import org.checkerframework.checker.nullness.qual.NonNull;
import java.util.Optional;
public class NotificationSerializer implements ObjectSerializer<Notification> {
private static final String NOTIFICATION_RAW_FORMAT = "%s: %s";
@Override
public boolean supports(@NonNull Class<? super Notification> type) {
return Notification.class.isAssignableFrom(type);
@@ -25,40 +26,99 @@ public class NotificationSerializer implements ObjectSerializer<Notification> {
@Override
public void serialize(@NonNull Notification notification, @NonNull SerializationData data, @NonNull GenericsDeclaration generics) {
data.add("type", notification.type(), NotificationType.class);
data.add("message", notification.message(), String.class);
NotificationType type = notification.type();
String message = notification.message();
if (type == NotificationType.CHAT || type == NotificationType.ACTION_BAR) {
data.setValueRaw(NOTIFICATION_RAW_FORMAT.formatted(type, message));
return;
}
if (type == NotificationType.TITLE || type == NotificationType.SUB_TITLE) {
Title.Times times = this.getTitleTimes(notification);
this.addBasicNotificationFields(data, notification);
data.add("times", times, Title.Times.class);
return;
}
if (notification instanceof BossBarNotification bossBarNotification) {
this.addBasicNotificationFields(data, notification);
data.add("progress", bossBarNotification.progress(), float.class);
data.add("color", bossBarNotification.color(), BossBar.Color.class);
data.add("overlay", bossBarNotification.overlay(), BossBar.Overlay.class);
}
}
private void addBasicNotificationFields(SerializationData data, Notification notification) {
data.add("type", notification.type(), NotificationType.class);
data.add("message", notification.message(), String.class);
}
private Title.Times getTitleTimes(Notification notification) {
if (notification instanceof TitleNotification titleNotification) {
return titleNotification.times();
}
if (notification instanceof SubTitleNotification subTitleNotification) {
return subTitleNotification.times();
}
throw new IllegalArgumentException("Notification doesn't have title times.");
}
@Override
public Notification deserialize(@NonNull DeserializationData data, @NonNull GenericsDeclaration generics) {
if (!data.containsKey("type")) {
return this.deserializeRaw(data);
}
NotificationType type = data.get("type", NotificationType.class);
String message = data.get("message", String.class);
return switch (type) {
case CHAT -> new ChatNotification(message);
case ACTION_BAR -> new ActionBarNotification(message);
case TITLE -> {
Title.Times times = data.get("times", Title.Times.class);
case TITLE -> new TitleNotification(message);
case SUB_TITLE -> new SubTitleNotification(message);
yield new TitleNotification(times, message);
}
case SUB_TITLE -> {
Title.Times times = data.get("times", Title.Times.class);
yield new SubTitleNotification(times, message);
}
case BOSS_BAR -> {
float progress = Optional.ofNullable(data.get("progress", float.class))
.orElse(BossBar.MAX_PROGRESS);
float progress = data.get("progress", float.class);
BossBar.Color color = data.get("color", BossBar.Color.class);
BossBar.Overlay overlay = data.get("overlay", BossBar.Overlay.class);
BossBar.Color color = Optional.ofNullable(data.get("color", BossBar.Color.class))
.orElse(BossBar.Color.RED);
BossBar.Overlay overlay = Optional.ofNullable(data.get("overlay", BossBar.Overlay.class))
.orElse(BossBar.Overlay.PROGRESS);
yield new BossBarNotification(message, progress, color, overlay);
yield new BossBarNotification(progress, color, overlay, message);
}
default -> throw new IllegalStateException("Unexpected notification type: " + type);
};
}
private Notification deserializeRaw(DeserializationData data) {
String[] arguments = data.getValueRaw().toString().split(":", 2);
NotificationType type = NotificationType.valueOf(arguments[0]);
String message = this.replaceFirstSpace(arguments[1]);
return switch (type) {
case CHAT -> new ChatNotification(message);
case ACTION_BAR -> new ActionBarNotification(message);
default -> throw new IllegalStateException("Unexpected notification type: " + type);
};
}
private String replaceFirstSpace(String message) {
if (message.startsWith(" ")) {
return message.replaceFirst(" ", "");
}
return message;
}
}
@@ -54,7 +54,7 @@ public class RegionController implements Listener {
player.setVelocity(vector);
this.announcer.sendMessage(player, this.pluginConfig.messages.cantEnterOnRegion);
this.announcer.send(player, this.pluginConfig.messages.cantEnterOnRegion);
}
}
}
@@ -0,0 +1,49 @@
package com.eternalcode.combat.scheduler;
import com.eternalcode.combat.util.DurationUtil;
import org.bukkit.plugin.Plugin;
import org.bukkit.scheduler.BukkitScheduler;
import org.bukkit.scheduler.BukkitTask;
import java.time.Duration;
public class BukkitSchedulerImpl implements Scheduler {
private final Plugin plugin;
private final BukkitScheduler bukkitScheduler;
public BukkitSchedulerImpl(Plugin plugin, BukkitScheduler bukkitScheduler) {
this.plugin = plugin;
this.bukkitScheduler = bukkitScheduler;
}
@Override
public BukkitTask sync(Runnable task) {
return this.bukkitScheduler.runTask(this.plugin, task);
}
@Override
public BukkitTask async(Runnable task) {
return this.bukkitScheduler.runTaskAsynchronously(this.plugin, task);
}
@Override
public BukkitTask laterSync(Runnable task, Duration delay) {
return this.bukkitScheduler.runTaskLater(this.plugin, task, DurationUtil.toTicks(delay));
}
@Override
public BukkitTask laterAsync(Runnable task, Duration delay) {
return this.bukkitScheduler.runTaskLaterAsynchronously(this.plugin, task, DurationUtil.toTicks(delay));
}
@Override
public BukkitTask timerSync(Runnable task, Duration delay, Duration period) {
return this.bukkitScheduler.runTaskTimer(this.plugin, task, DurationUtil.toTicks(delay), DurationUtil.toTicks(period));
}
@Override
public BukkitTask timerAsync(Runnable task, Duration delay, Duration period) {
return this.bukkitScheduler.runTaskTimerAsynchronously(this.plugin, task, DurationUtil.toTicks(delay), DurationUtil.toTicks(period));
}
}
@@ -0,0 +1,20 @@
package com.eternalcode.combat.scheduler;
import org.bukkit.scheduler.BukkitTask;
import java.time.Duration;
public interface Scheduler {
BukkitTask sync(Runnable task);
BukkitTask async(Runnable task);
BukkitTask laterSync(Runnable task, Duration delay);
BukkitTask laterAsync(Runnable task, Duration delay);
BukkitTask timerSync(Runnable task, Duration delay, Duration period);
BukkitTask timerAsync(Runnable task, Duration delay, Duration period);
}
@@ -22,4 +22,8 @@ public final class DurationUtil {
.replaceAll("(\\d[HMS])(?!$)", "$1 ")
.toLowerCase();
}
public static long toTicks(Duration duration) {
return duration.toMillis() / 50L;
}
}
@@ -11,6 +11,10 @@ import com.eternalcode.combat.drop.DropKeepInventoryManager;
import com.eternalcode.combat.drop.DropManager;
import com.eternalcode.combat.drop.impl.PercentDropModifier;
import com.eternalcode.combat.drop.impl.PlayersHealthDropModifier;
import com.eternalcode.combat.event.EventCaller;
import com.eternalcode.combat.fight.FightManager;
import com.eternalcode.combat.fight.FightTask;
import com.eternalcode.combat.fight.bossbar.FightBossBarService;
import com.eternalcode.combat.fight.controller.FightActionBlockerController;
import com.eternalcode.combat.fight.controller.FightDeathCauseController;
import com.eternalcode.combat.fight.controller.FightEscapeController;
@@ -18,10 +22,6 @@ import com.eternalcode.combat.fight.controller.FightMessageController;
import com.eternalcode.combat.fight.controller.FightTagController;
import com.eternalcode.combat.fight.controller.FightUnTagController;
import com.eternalcode.combat.fight.effect.FightEffectController;
import com.eternalcode.combat.event.EventCaller;
import com.eternalcode.combat.fight.FightManager;
import com.eternalcode.combat.fight.FightTask;
import com.eternalcode.combat.fight.bossbar.FightBossBarService;
import com.eternalcode.combat.fight.effect.FightEffectService;
import com.eternalcode.combat.fight.pearl.FightPearlController;
import com.eternalcode.combat.fight.pearl.FightPearlManager;
@@ -31,6 +31,8 @@ import com.eternalcode.combat.fight.tagout.TagOutCommand;
import com.eternalcode.combat.notification.NotificationAnnouncer;
import com.eternalcode.combat.region.RegionController;
import com.eternalcode.combat.region.RegionProvider;
import com.eternalcode.combat.scheduler.BukkitSchedulerImpl;
import com.eternalcode.combat.scheduler.Scheduler;
import com.eternalcode.combat.updater.UpdaterNotificationController;
import com.eternalcode.combat.updater.UpdaterService;
import com.eternalcode.combat.util.legacy.LegacyColorProcessor;
@@ -49,6 +51,7 @@ import org.bukkit.entity.Player;
import org.bukkit.plugin.java.JavaPlugin;
import java.io.File;
import java.time.Duration;
import java.util.concurrent.TimeUnit;
import java.util.stream.Stream;
@@ -88,20 +91,23 @@ public final class CombatPlugin extends JavaPlugin implements EternalCombatApi {
this.dropManager = new DropManager();
this.dropKeepInventoryManager = new DropKeepInventoryManager();
UpdaterService updaterService = new UpdaterService(this.getDescription());
this.audienceProvider = BukkitAudiences.create(this);
MiniMessage miniMessage = MiniMessage.builder()
.postProcessor(new LegacyColorProcessor())
.build();
UpdaterService updaterService = new UpdaterService(this.getDescription());
FightBossBarService fightBossBarService = new FightBossBarService(this.pluginConfig, this.audienceProvider, miniMessage);
BridgeService bridgeService = new BridgeService(this.pluginConfig, server.getPluginManager(), this.getLogger());
bridgeService.init();
this.regionProvider = bridgeService.getRegionProvider();
NotificationAnnouncer notificationAnnouncer = new NotificationAnnouncer(this.audienceProvider, miniMessage);
Scheduler scheduler = new BukkitSchedulerImpl(this, server.getScheduler());
NotificationAnnouncer notificationAnnouncer = new NotificationAnnouncer(this.audienceProvider, miniMessage, scheduler);
this.liteCommands = LiteBukkitAdventurePlatformFactory.builder(server, "eternalcombat", this.audienceProvider)
.argument(Player.class, new BukkitPlayerArgument<>(this.getServer(), this.pluginConfig.messages.playerNotFound))
@@ -116,7 +122,7 @@ public final class CombatPlugin extends JavaPlugin implements EternalCombatApi {
.register();
FightTask fightTask = new FightTask(server, this.pluginConfig, this.fightManager, fightBossBarService, notificationAnnouncer);
this.getServer().getScheduler().runTaskTimer(this, fightTask, 20L, 20L);
scheduler.timerSync(fightTask, Duration.ofSeconds(1L), Duration.ofSeconds(1L));
new Metrics(this, 17803);
@@ -128,7 +134,7 @@ public final class CombatPlugin extends JavaPlugin implements EternalCombatApi {
Stream.of(
new FightDeathCauseController(this.fightManager),
new DropController(this.dropManager, this.dropKeepInventoryManager, this.pluginConfig.dropSettings, this.fightManager),
new FightTagController(this.fightManager, this.pluginConfig, notificationAnnouncer),
new FightTagController(this.fightManager, this.pluginConfig),
new FightUnTagController(this.fightManager, this.pluginConfig),
new FightEscapeController(this.fightManager, this.pluginConfig, notificationAnnouncer),
new FightActionBlockerController(this.fightManager, notificationAnnouncer, this.pluginConfig),
+24 -36
View File
@@ -1,48 +1,36 @@
[versions]
spigotApi = "1.20.2-R0.1-SNAPSHOT"
adventurePlatformBukkit = "4.3.1"
adventureTextMinimessage = "4.14.0"
liteCommands = "2.8.9"
okaeriConfigsYamlBukkit = "5.0.0-beta.5"
okaeriConfigsSerdesCommons = "5.0.0-beta.5"
okaeriConfigsSerdesBukkit = "5.0.0-beta.5"
pandaUtilities = "0.5.2-alpha"
gitCheck = "1.0.0"
apacheCommons = "2.14.0"
bStatsBukkit = "3.0.2"
worldGuardBukkit = "7.0.9"
junitJupiterApi = "5.10.0"
junitJupiterParams = "5.10.0"
junitJupiterEngine = "5.10.0"
okaeriConfigs = "5.0.0-beta.5"
junitJupiter = "5.10.0"
[libraries]
spigotApi = { group = "org.spigotmc", name = "spigot-api", version.ref = "spigotApi" }
# Spigot API
spigotApi = "org.spigotmc:spigot-api:1.20.2-R0.1-SNAPSHOT"
adventurePlatformBukkit = { group = "net.kyori", name = "adventure-platform-bukkit", version.ref = "adventurePlatformBukkit" }
adventureTextMinimessage = { group = "net.kyori", name = "adventure-text-minimessage", version.ref = "adventureTextMinimessage" }
# Adventure
adventurePlatformBukkit = "net.kyori:adventure-platform-bukkit:4.3.1"
adventureTextMinimessage = "net.kyori:adventure-text-minimessage:4.14.0"
liteCommands = { group = "dev.rollczi.litecommands", name = "bukkit-adventure", version.ref = "liteCommands" }
# LiteCommands
liteCommands = "dev.rollczi.litecommands:bukkit-adventure:2.8.9"
okaeriConfigsYamlBukkit = { group = "eu.okaeri", name = "okaeri-configs-yaml-bukkit", version.ref = "okaeriConfigsYamlBukkit" }
okaeriConfigsSerdesCommons = { group = "eu.okaeri", name = "okaeri-configs-serdes-commons", version.ref = "okaeriConfigsSerdesCommons" }
okaeriConfigsSerdesBukkit = { group = "eu.okaeri", name = "okaeri-configs-serdes-bukkit", version.ref = "okaeriConfigsSerdesBukkit" }
# Okaeri Configs
okaeriConfigsYamlBukkit = { module = "eu.okaeri:okaeri-configs-yaml-bukkit", version.ref = "okaeriConfigs" }
okaeriConfigsSerdesCommons = { module = "eu.okaeri:okaeri-configs-serdes-commons", version.ref = "okaeriConfigs" }
okaeriConfigsSerdesBukkit = { module = "eu.okaeri:okaeri-configs-serdes-bukkit", version.ref = "okaeriConfigs" }
pandaUtilities = { group = "org.panda-lang", name = "panda-utilities", version.ref = "pandaUtilities" }
# Panda Utilities
pandaUtilities = "org.panda-lang:panda-utilities:0.5.2-alpha"
gitCheck = { group = "com.eternalcode", name = "gitcheck", version.ref = "gitCheck" }
gitCheck = "com.eternalcode:gitcheck:1.0.0"
apacheCommons = { group = "commons-io", name = "commons-io", version.ref = "apacheCommons" }
apacheCommons = "commons-io:commons-io:2.14.0"
bStatsBukkit = { group = "org.bstats", name = "bstats-bukkit", version.ref = "bStatsBukkit" }
bStatsBukkit = "org.bstats:bstats-bukkit:3.0.2"
worldGuardBukkit = { group = "com.sk89q.worldguard", name = "worldguard-bukkit", version.ref = "worldGuardBukkit" }
worldGuardBukkit = "com.sk89q.worldguard:worldguard-bukkit:7.0.9"
# JUnit Jupiter
jUnitJupiterApi = { module = "org.junit.jupiter:junit-jupiter-api", version.ref = "junitJupiter" }
jUnitJupiterParams = { module = "org.junit.jupiter:junit-jupiter-params", version.ref = "junitJupiter" }
jUnitJupiterEngine = { module = "org.junit.jupiter:junit-jupiter-engine", version.ref = "junitJupiter" }
jUnitJupiterApi = { group = "org.junit.jupiter", name = "junit-jupiter-api", version.ref = "junitJupiterApi" }
jUnitJupiterParams = { group = "org.junit.jupiter", name = "junit-jupiter-params", version.ref = "junitJupiterParams" }
jUnitJupiterEngine = { group = "org.junit.jupiter", name = "junit-jupiter-engine", version.ref = "junitJupiterEngine" }