From 357fbe1d69e98208fb83fd299564301d79211167 Mon Sep 17 00:00:00 2001 From: Eluinhost Date: Fri, 15 Apr 2016 16:07:14 +0100 Subject: [PATCH 1/5] start of work on tab list render for /timer --- .../gg/uhc/uhc/modules/timer/TimerModule.java | 37 +++++- .../timer/renderer/TabListPosition.java | 33 +++++ .../timer/renderer/TabListRenderer.java | 115 ++++++++++++++++++ 3 files changed, 182 insertions(+), 3 deletions(-) create mode 100644 src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListPosition.java create mode 100644 src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java diff --git a/src/main/java/gg/uhc/uhc/modules/timer/TimerModule.java b/src/main/java/gg/uhc/uhc/modules/timer/TimerModule.java index b5b87cd..8bb99e3 100644 --- a/src/main/java/gg/uhc/uhc/modules/timer/TimerModule.java +++ b/src/main/java/gg/uhc/uhc/modules/timer/TimerModule.java @@ -32,9 +32,7 @@ import gg.uhc.uhc.modules.Module; import gg.uhc.uhc.modules.ModuleRegistry; import gg.uhc.uhc.modules.timer.messages.TimerMessage; -import gg.uhc.uhc.modules.timer.renderer.ActionBarRenderer; -import gg.uhc.uhc.modules.timer.renderer.BossBarRenderer; -import gg.uhc.uhc.modules.timer.renderer.TimerRenderer; +import gg.uhc.uhc.modules.timer.renderer.*; import gg.uhc.uhc.util.ActionBarMessenger; import com.comphenix.protocol.ProtocolLibrary; @@ -57,6 +55,9 @@ public class TimerModule extends Module { protected static final String BOSS_BAR_COLOUR_KEY = "boss bar colour"; protected static final String BOSS_BAR_STYLE_KEY = "boss bar style"; protected static final String USE_ACTION_BAR_KEY = "use action bar"; + protected static final String USE_TAB_LIST_KEY = "use tab list"; + protected static final String TAB_LIST_POSITION_KEY = "tab list position"; + protected static final int TICKS_PER_SECOND = 20; protected static final double PERCENT_MULTIPLIER = 100D; @@ -145,6 +146,36 @@ public void initialize() throws InvalidConfigurationException { } } + if (!config.contains(USE_TAB_LIST_KEY)) { + config.set(USE_TAB_LIST_KEY, true); + } + + if (config.getBoolean(USE_TAB_LIST_KEY)) { + if (!config.contains(TAB_LIST_POSITION_KEY)) { + config.set(TAB_LIST_POSITION_KEY, TabListPosition.BOTTOM.name()); + } + + // attempt to parse the style + TabListPosition position; + try { + position = EnumConverter.forEnum(TabListPosition.class).convert(config.getString(TAB_LIST_POSITION_KEY)); + } catch (ValueConversionException ex) { + plugin.getLogger().warning("Invalid postion for tab list, switching to BOTTOM"); + config.set(TAB_LIST_POSITION_KEY, TabListPosition.BOTTOM.name()); + position = TabListPosition.BOTTOM; + } + + try { + renderers.add(new TabListRenderer(plugin, ProtocolLibrary.getProtocolManager(), position)); + } catch (NoClassDefFoundError ex) { + // Happens when protocollib isn't installed, don't disable in config just give a warning + plugin.getLogger().severe( + "Could not load the tab list timer type, this is only supported when ProtocolLib is installed." + ); + } + } + + // No renders worked, throw an error to stop the module from loading if (renderers.size() == 0) { throw new InvalidConfigurationException( diff --git a/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListPosition.java b/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListPosition.java new file mode 100644 index 0000000..4dfb94c --- /dev/null +++ b/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListPosition.java @@ -0,0 +1,33 @@ +/* + * Project: UHC + * Class: gg.uhc.uhc.modules.timer.renderer.TabListPosition + * + * The MIT License (MIT) + * + * Copyright (c) 2015 Graham Howden . + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +package gg.uhc.uhc.modules.timer.renderer; + +public enum TabListPosition { + TOP, + BOTTOM +} diff --git a/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java b/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java new file mode 100644 index 0000000..5d6e81f --- /dev/null +++ b/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java @@ -0,0 +1,115 @@ +/* + * Project: UHC + * Class: gg.uhc.uhc.modules.timer.renderer.TabListRenderer + * + * The MIT License (MIT) + * + * Copyright (c) 2015 Graham Howden . + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +package gg.uhc.uhc.modules.timer.renderer; + +import com.comphenix.protocol.PacketType; +import com.comphenix.protocol.ProtocolManager; +import com.comphenix.protocol.events.PacketAdapter; +import com.comphenix.protocol.events.PacketContainer; +import com.comphenix.protocol.events.PacketEvent; +import com.comphenix.protocol.reflect.StructureModifier; +import com.comphenix.protocol.wrappers.WrappedChatComponent; +import com.google.common.base.Optional; +import org.bukkit.plugin.Plugin; + +public class TabListRenderer implements TimerRenderer { + + protected static final WrappedChatComponent CLEAR_BAR_JSON = WrappedChatComponent.fromJson("{\"translate\":\"\"}"); + protected static final PacketType PACKET_TYPE = PacketType.Play.Server.PLAYER_LIST_HEADER_FOOTER; + protected static final int TOP_INDEX = 0; + protected static final int BOTTOM_INDEX = 1; + + protected final ProtocolManager manager; + + protected final int writeIndex; + protected final int clearIndex; + + protected WrappedChatComponent[] lastInterceptedMessages = new WrappedChatComponent[] { + CLEAR_BAR_JSON, + CLEAR_BAR_JSON + }; + + public TabListRenderer(Plugin plugin, ProtocolManager manager, TabListPosition position) { + this.manager = manager; + + if (position == TabListPosition.TOP) { + writeIndex = TOP_INDEX; + clearIndex = BOTTOM_INDEX; + } else { + writeIndex = BOTTOM_INDEX; + clearIndex = TOP_INDEX; + } + + manager.addPacketListener(new PacketAdapter(plugin, PACKET_TYPE) { + @Override + public void onPacketSending(PacketEvent event) { + final StructureModifier components = event.getPacket().getChatComponents(); + + lastInterceptedMessages[TOP_INDEX] = + Optional.fromNullable(components.readSafely(TOP_INDEX)).or(CLEAR_BAR_JSON); + lastInterceptedMessages[BOTTOM_INDEX] = + Optional.fromNullable(components.readSafely(BOTTOM_INDEX)).or(CLEAR_BAR_JSON); + } + }); + } + + protected void sendBarMessage(String message) { + final PacketContainer container = this.manager.createPacket(PACKET_TYPE); + + container.getChatComponents() + .write(writeIndex, WrappedChatComponent.fromText(message)) + .write(clearIndex, lastInterceptedMessages[clearIndex]); + + this.manager.broadcastServerPacket(container); + } + + protected void removeBar() { + final PacketContainer container = this.manager.createPacket(PACKET_TYPE); + + container.getChatComponents() + .write(TOP_INDEX, lastInterceptedMessages[TOP_INDEX]) + .write(BOTTOM_INDEX, lastInterceptedMessages[BOTTOM_INDEX]); + + this.manager.broadcastServerPacket(container); + } + + @Override + public void onStart(String message) { + sendBarMessage(message); + } + + @Override + public void onUpdate(String message, double progress) { + sendBarMessage(message); + } + + @Override + public void onStop() { + removeBar(); + } +} From bdb2e51cd27e668665035bd5dacfe1da24f2ee6a Mon Sep 17 00:00:00 2001 From: Eluinhost Date: Sat, 16 Apr 2016 20:27:41 +0100 Subject: [PATCH 2/5] dont update last sent for our own packets --- .../timer/renderer/TabListRenderer.java | 25 +++++++++++++++---- 1 file changed, 20 insertions(+), 5 deletions(-) diff --git a/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java b/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java index 5d6e81f..3adcf9b 100644 --- a/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java +++ b/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java @@ -54,6 +54,8 @@ public class TabListRenderer implements TimerRenderer { CLEAR_BAR_JSON }; + protected WrappedChatComponent lastSentMessage = null; + public TabListRenderer(Plugin plugin, ProtocolManager manager, TabListPosition position) { this.manager = manager; @@ -70,25 +72,38 @@ public TabListRenderer(Plugin plugin, ProtocolManager manager, TabListPosition p public void onPacketSending(PacketEvent event) { final StructureModifier components = event.getPacket().getChatComponents(); - lastInterceptedMessages[TOP_INDEX] = - Optional.fromNullable(components.readSafely(TOP_INDEX)).or(CLEAR_BAR_JSON); - lastInterceptedMessages[BOTTOM_INDEX] = - Optional.fromNullable(components.readSafely(BOTTOM_INDEX)).or(CLEAR_BAR_JSON); + final WrappedChatComponent[] intercepted = new WrappedChatComponent[] { + Optional + .fromNullable(components.readSafely(TOP_INDEX)) + .or(CLEAR_BAR_JSON), + Optional + .fromNullable(components.readSafely(BOTTOM_INDEX)) + .or(CLEAR_BAR_JSON) + }; + + // Only write if it wasn't one of our timer messages + if (lastSentMessage != null && !intercepted[writeIndex].equals(lastSentMessage)) { + lastInterceptedMessages[TOP_INDEX] = intercepted[TOP_INDEX]; + lastInterceptedMessages[BOTTOM_INDEX] = intercepted[BOTTOM_INDEX]; + } } }); } protected void sendBarMessage(String message) { + lastSentMessage = WrappedChatComponent.fromText(message); final PacketContainer container = this.manager.createPacket(PACKET_TYPE); container.getChatComponents() - .write(writeIndex, WrappedChatComponent.fromText(message)) + .write(writeIndex, lastSentMessage) .write(clearIndex, lastInterceptedMessages[clearIndex]); this.manager.broadcastServerPacket(container); } protected void removeBar() { + lastSentMessage = null; + final PacketContainer container = this.manager.createPacket(PACKET_TYPE); container.getChatComponents() From b21da4208f45bca6387b273607889b0d962a36be Mon Sep 17 00:00:00 2001 From: Eluinhost Date: Sat, 16 Apr 2016 21:57:19 +0100 Subject: [PATCH 3/5] flawless logic --- .../java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java b/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java index 3adcf9b..f046010 100644 --- a/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java +++ b/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java @@ -82,7 +82,7 @@ public void onPacketSending(PacketEvent event) { }; // Only write if it wasn't one of our timer messages - if (lastSentMessage != null && !intercepted[writeIndex].equals(lastSentMessage)) { + if (lastSentMessage == null || !intercepted[writeIndex].equals(lastSentMessage)) { lastInterceptedMessages[TOP_INDEX] = intercepted[TOP_INDEX]; lastInterceptedMessages[BOTTOM_INDEX] = intercepted[BOTTOM_INDEX]; } From 09f7c797d6c36880f5861e82c650c9215b08e396 Mon Sep 17 00:00:00 2001 From: Eluinhost Date: Sat, 16 Apr 2016 22:10:06 +0100 Subject: [PATCH 4/5] split up initialization logic --- .../gg/uhc/uhc/modules/timer/TimerModule.java | 187 ++++++++++-------- .../timer/renderer/TabListRenderer.java | 54 ++--- 2 files changed, 135 insertions(+), 106 deletions(-) diff --git a/src/main/java/gg/uhc/uhc/modules/timer/TimerModule.java b/src/main/java/gg/uhc/uhc/modules/timer/TimerModule.java index 8bb99e3..19d3390 100644 --- a/src/main/java/gg/uhc/uhc/modules/timer/TimerModule.java +++ b/src/main/java/gg/uhc/uhc/modules/timer/TimerModule.java @@ -37,17 +37,20 @@ import com.comphenix.protocol.ProtocolLibrary; import com.google.common.base.Preconditions; +import com.google.common.base.Predicates; +import com.google.common.collect.Iterables; import com.google.common.collect.Lists; import net.md_5.bungee.api.ChatColor; import org.bukkit.Bukkit; import org.bukkit.Material; import org.bukkit.boss.BarColor; import org.bukkit.boss.BarStyle; +import org.bukkit.configuration.ConfigurationSection; import org.bukkit.configuration.InvalidConfigurationException; import org.bukkit.scheduler.BukkitRunnable; import org.bukkit.scheduler.BukkitTask; -import java.util.List; +import java.util.Iterator; public class TimerModule extends Module { @@ -75,118 +78,140 @@ public TimerModule() { this.icon.setWeight(ModuleRegistry.CATEGORY_MISC); } - @Override - public void initialize() throws InvalidConfigurationException { - this.icon.setLore(messages.getRawStrings("lore")); - - final List renderers = Lists.newArrayList(); - + protected TimerRenderer setupBossBar(ConfigurationSection section) { if (!config.contains(USE_BOSS_BAR_KEY)) { config.set(USE_BOSS_BAR_KEY, true); } - if (config.getBoolean(USE_BOSS_BAR_KEY)) { - try { - if (!config.contains(BOSS_BAR_COLOUR_KEY)) { - config.set(BOSS_BAR_COLOUR_KEY, BarColor.BLUE.name()); - } - if (!config.contains(BOSS_BAR_STYLE_KEY)) { - config.set(BOSS_BAR_STYLE_KEY, BarStyle.SOLID.name()); - } + if (!config.getBoolean(USE_BOSS_BAR_KEY)) { + return null; + } - // attempt to parse the colour - BarColor colour; - try { - colour = EnumConverter.forEnum(BarColor.class).convert(config.getString(BOSS_BAR_COLOUR_KEY)); - } catch (ValueConversionException ex) { - plugin.getLogger().warning("Invalid colour for boss bar, switching to blue"); - config.set(BOSS_BAR_COLOUR_KEY, BarColor.BLUE.name()); - colour = BarColor.BLUE; - } + try { + if (!config.contains(BOSS_BAR_COLOUR_KEY)) { + config.set(BOSS_BAR_COLOUR_KEY, BarColor.BLUE.name()); + } + if (!config.contains(BOSS_BAR_STYLE_KEY)) { + config.set(BOSS_BAR_STYLE_KEY, BarStyle.SOLID.name()); + } - // attempt to parse the style - BarStyle style; - try { - style = EnumConverter.forEnum(BarStyle.class).convert(config.getString(BOSS_BAR_STYLE_KEY)); - } catch (ValueConversionException ex) { - plugin.getLogger().warning("Invalid style for boss bar, switching to solid"); - config.set(BOSS_BAR_STYLE_KEY, BarStyle.SOLID.name()); - style = BarStyle.SOLID; - } + // attempt to parse the colour + BarColor colour; + try { + colour = EnumConverter.forEnum(BarColor.class).convert(config.getString(BOSS_BAR_COLOUR_KEY)); + } catch (ValueConversionException ex) { + plugin.getLogger().warning("Invalid colour for boss bar, switching to blue"); + config.set(BOSS_BAR_COLOUR_KEY, BarColor.BLUE.name()); + colour = BarColor.BLUE; + } - // setup the renderer - final BossBarRenderer bossbar = new BossBarRenderer(Bukkit.createBossBar("", colour, style)); - Bukkit.getPluginManager().registerEvents(bossbar, plugin); - renderers.add(bossbar); - } catch (NoClassDefFoundError ex) { - // happens when boss bar API not implemented, < 1.9 - plugin.getLogger().severe( - "Could not load the boss bar timer type, this is only supported in 1.9+, " - + "disabling in the config file..." - ); - - // turn of the boss bar in the config to stop it happening over again - config.set(USE_BOSS_BAR_KEY, false); + // attempt to parse the style + BarStyle style; + try { + style = EnumConverter.forEnum(BarStyle.class).convert(config.getString(BOSS_BAR_STYLE_KEY)); + } catch (ValueConversionException ex) { + plugin.getLogger().warning("Invalid style for boss bar, switching to solid"); + config.set(BOSS_BAR_STYLE_KEY, BarStyle.SOLID.name()); + style = BarStyle.SOLID; } + + // setup the renderer + return new BossBarRenderer(Bukkit.createBossBar("", colour, style)); + } catch (NoClassDefFoundError ex) { + // happens when boss bar API not implemented, < 1.9 + plugin.getLogger().severe( + "Could not load the boss bar timer type, this is only supported in 1.9+, " + + "disabling in the config file..." + ); + + // turn of the boss bar in the config to stop it happening over again + config.set(USE_BOSS_BAR_KEY, false); + return null; } + } + protected TimerRenderer setupActionBar(ConfigurationSection section) { if (!config.contains(USE_ACTION_BAR_KEY)) { config.set(USE_ACTION_BAR_KEY, true); } - if (config.getBoolean(USE_ACTION_BAR_KEY)) { - try { - renderers.add(new ActionBarRenderer(new ActionBarMessenger(ProtocolLibrary.getProtocolManager()))); - } catch (NoClassDefFoundError ex) { - // Happens when protocollib isn't installed, don't disable in config just give a warning - plugin.getLogger().severe( - "Could not load the action bar timer type," - + "this is only supported when ProtocolLib is installed." - ); - } + + if (!config.getBoolean(USE_ACTION_BAR_KEY)) { + return null; + } + + + try { + return new ActionBarRenderer(new ActionBarMessenger(ProtocolLibrary.getProtocolManager())); + } catch (NoClassDefFoundError ex) { + // Happens when protocollib isn't installed, don't disable in config just give a warning + plugin.getLogger().severe( + "Could not load the action bar timer type," + + "this is only supported when ProtocolLib is installed." + ); + return null; } + } + protected TimerRenderer setupTabList(ConfigurationSection section) { if (!config.contains(USE_TAB_LIST_KEY)) { config.set(USE_TAB_LIST_KEY, true); } - if (config.getBoolean(USE_TAB_LIST_KEY)) { - if (!config.contains(TAB_LIST_POSITION_KEY)) { - config.set(TAB_LIST_POSITION_KEY, TabListPosition.BOTTOM.name()); - } + if (!config.getBoolean(USE_TAB_LIST_KEY)) { + return null; + } - // attempt to parse the style - TabListPosition position; - try { - position = EnumConverter.forEnum(TabListPosition.class).convert(config.getString(TAB_LIST_POSITION_KEY)); - } catch (ValueConversionException ex) { - plugin.getLogger().warning("Invalid postion for tab list, switching to BOTTOM"); - config.set(TAB_LIST_POSITION_KEY, TabListPosition.BOTTOM.name()); - position = TabListPosition.BOTTOM; - } + if (!config.contains(TAB_LIST_POSITION_KEY)) { + config.set(TAB_LIST_POSITION_KEY, TabListPosition.BOTTOM.name()); + } - try { - renderers.add(new TabListRenderer(plugin, ProtocolLibrary.getProtocolManager(), position)); - } catch (NoClassDefFoundError ex) { - // Happens when protocollib isn't installed, don't disable in config just give a warning - plugin.getLogger().severe( - "Could not load the tab list timer type, this is only supported when ProtocolLib is installed." - ); - } + // attempt to parse the style + TabListPosition position; + try { + position = EnumConverter.forEnum(TabListPosition.class).convert(config.getString(TAB_LIST_POSITION_KEY)); + } catch (ValueConversionException ex) { + plugin.getLogger().warning("Invalid postion for tab list, switching to BOTTOM"); + config.set(TAB_LIST_POSITION_KEY, TabListPosition.BOTTOM.name()); + position = TabListPosition.BOTTOM; + } + + try { + return new TabListRenderer(plugin, ProtocolLibrary.getProtocolManager(), position); + } catch (NoClassDefFoundError ex) { + // Happens when protocollib isn't installed, don't disable in config just give a warning + plugin.getLogger().severe( + "Could not load the tab list timer type, this is only supported when ProtocolLib is installed." + ); + return null; } + } + + + @Override + public void initialize() throws InvalidConfigurationException { + this.icon.setLore(messages.getRawStrings("lore")); + final Iterator renderers = Iterables.filter( + Lists.newArrayList( + setupBossBar(config), + setupTabList(config), + setupActionBar(config) + ), + Predicates.notNull() + ).iterator(); // No renders worked, throw an error to stop the module from loading - if (renderers.size() == 0) { + if (!renderers.hasNext()) { throw new InvalidConfigurationException( - "The timer module can only be used when the Boss bar or Action bar type are loaded" + "The timer module can only be used when the Boss bar, Action bar or Tab list type are loaded" ); } // if more than one renderer is chosen pick the first one - renderer = renderers.get(0); + renderer = renderers.next(); - if (renderers.size() > 1) { + if (renderers.hasNext()) { plugin.getLogger().warning( "More than one style of timer is being used, using only the first one loaded " + "(" + renderer.getClass().getName() + ")" diff --git a/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java b/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java index f046010..374c853 100644 --- a/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java +++ b/src/main/java/gg/uhc/uhc/modules/timer/renderer/TabListRenderer.java @@ -29,9 +29,7 @@ import com.comphenix.protocol.PacketType; import com.comphenix.protocol.ProtocolManager; -import com.comphenix.protocol.events.PacketAdapter; -import com.comphenix.protocol.events.PacketContainer; -import com.comphenix.protocol.events.PacketEvent; +import com.comphenix.protocol.events.*; import com.comphenix.protocol.reflect.StructureModifier; import com.comphenix.protocol.wrappers.WrappedChatComponent; import com.google.common.base.Optional; @@ -54,7 +52,7 @@ public class TabListRenderer implements TimerRenderer { CLEAR_BAR_JSON }; - protected WrappedChatComponent lastSentMessage = null; + protected WrappedChatComponent lastSentMessage; public TabListRenderer(Plugin plugin, ProtocolManager manager, TabListPosition position) { this.manager = manager; @@ -67,27 +65,7 @@ public TabListRenderer(Plugin plugin, ProtocolManager manager, TabListPosition p clearIndex = TOP_INDEX; } - manager.addPacketListener(new PacketAdapter(plugin, PACKET_TYPE) { - @Override - public void onPacketSending(PacketEvent event) { - final StructureModifier components = event.getPacket().getChatComponents(); - - final WrappedChatComponent[] intercepted = new WrappedChatComponent[] { - Optional - .fromNullable(components.readSafely(TOP_INDEX)) - .or(CLEAR_BAR_JSON), - Optional - .fromNullable(components.readSafely(BOTTOM_INDEX)) - .or(CLEAR_BAR_JSON) - }; - - // Only write if it wasn't one of our timer messages - if (lastSentMessage == null || !intercepted[writeIndex].equals(lastSentMessage)) { - lastInterceptedMessages[TOP_INDEX] = intercepted[TOP_INDEX]; - lastInterceptedMessages[BOTTOM_INDEX] = intercepted[BOTTOM_INDEX]; - } - } - }); + manager.addPacketListener(new TabListListener(plugin)); } protected void sendBarMessage(String message) { @@ -127,4 +105,30 @@ public void onUpdate(String message, double progress) { public void onStop() { removeBar(); } + + class TabListListener extends PacketAdapter { + TabListListener(Plugin plugin) { + super(plugin, PACKET_TYPE); + } + + @Override + public void onPacketSending(PacketEvent event) { + final StructureModifier components = event.getPacket().getChatComponents(); + + final WrappedChatComponent[] intercepted = new WrappedChatComponent[] { + Optional + .fromNullable(components.readSafely(TOP_INDEX)) + .or(CLEAR_BAR_JSON), + Optional + .fromNullable(components.readSafely(BOTTOM_INDEX)) + .or(CLEAR_BAR_JSON) + }; + + // Only write if it wasn't one of our timer messages + if (lastSentMessage == null || !intercepted[writeIndex].equals(lastSentMessage)) { + lastInterceptedMessages[TOP_INDEX] = intercepted[TOP_INDEX]; + lastInterceptedMessages[BOTTOM_INDEX] = intercepted[BOTTOM_INDEX]; + } + } + } } From e80375b2be07dba882f27765320defa72236f807 Mon Sep 17 00:00:00 2001 From: Eluinhost Date: Sat, 16 Apr 2016 22:13:28 +0100 Subject: [PATCH 5/5] update docs to include new type --- docs/modules/Timer.md | 19 +++++++++++++++---- 1 file changed, 15 insertions(+), 4 deletions(-) diff --git a/docs/modules/Timer.md b/docs/modules/Timer.md index 9cb5926..5c0b61c 100644 --- a/docs/modules/Timer.md +++ b/docs/modules/Timer.md @@ -7,11 +7,16 @@ The icon for this module is clock. For documentation on the timer command visit the [/timer documentation](../commands/timer.md) -At least 1 of 'boss bar' or 'action bar' must be used for this module to load. -If neither are enabled this module will fail to load, if both are loaded then -the boss bar takes precendence. +At least 1 of 'boss bar' or 'action bar' or 'tab list' must be used for this module to load. +If none are enabled this module will fail to load, if all are loaded then +they are use in this order: + +BOSS BAR > TAB LIST > ACTION BAR + +BOSS BAR requires Minecraft 1.9+ + +TAB LIST and ACTION BAR both require ProtocolLib to also be installed -This module requires either 1.9+ (boss bar) or ProtocolLib (action bar) to run ### Configuration @@ -19,6 +24,8 @@ This module requires either 1.9+ (boss bar) or ProtocolLib (action bar) to run use boss bar: true boss bar colour: BLUE boss bar style: SOLID +use tab list: true +tab list position: BOTTOM use action bar: true ``` @@ -28,6 +35,10 @@ use action bar: true `boss bar style` The style of the boss bar, values can be found [here](https://hub.spigotmc.org/javadocs/spigot/org/bukkit/boss/BarStyle.html) +`use tab list` Whether to use the tab list for the timer, requires ProtocolLib + +`tab list position` Either TOP or BOTTOM, what end of the tab list to render on + `use action bar` Whether to use the action bar for the timer, requires ProtocolLib