From 05372e99f8fd2bcd7e7c165d731dd52c825b697d Mon Sep 17 00:00:00 2001 From: LordTuxn Date: Wed, 19 Jan 2022 16:44:40 +0100 Subject: [PATCH 1/3] fix click event issues in review menu --- .../alpsbte/plotsystem/core/menus/ReviewMenu.java | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/src/main/java/com/alpsbte/plotsystem/core/menus/ReviewMenu.java b/src/main/java/com/alpsbte/plotsystem/core/menus/ReviewMenu.java index 6562f06f..07093cd0 100644 --- a/src/main/java/com/alpsbte/plotsystem/core/menus/ReviewMenu.java +++ b/src/main/java/com/alpsbte/plotsystem/core/menus/ReviewMenu.java @@ -26,7 +26,6 @@ import com.alpsbte.plotsystem.core.system.plot.Plot; import com.alpsbte.plotsystem.core.system.plot.PlotManager; -import com.alpsbte.plotsystem.core.system.plot.PlotHandler; import com.alpsbte.plotsystem.utils.items.builder.ItemBuilder; import com.alpsbte.plotsystem.utils.items.MenuItems; import com.alpsbte.plotsystem.utils.Utils; @@ -113,26 +112,25 @@ protected void setMenuItemsAsync() { @Override protected void setItemClickEventsAsync() { // Set click event for unreviewed and unfinished plot items - for(int i = 0; i < plotDisplayCount; i++) { - int currentIteration = i; - getMenu().getSlot(i).setClickHandler((clickPlayer, clickInformation) -> { + int index = 0; + for (Plot plot : plots.subList(0, plotDisplayCount)) { + getMenu().getSlot(index).setClickHandler((player, info) -> { try { - Plot plot = plots.get(currentIteration); + getMenuPlayer().closeInventory(); if(plot.getStatus() == Status.unreviewed) { if (!plot.getPlotOwner().getUUID().toString().equals(getMenuPlayer().getUniqueId().toString())){ - getMenuPlayer().closeInventory(); plot.getWorld().teleportPlayer(getMenuPlayer()); } else { getMenuPlayer().sendMessage(Utils.getErrorMessageFormat("You cannot review your own builds!")); } } else { - getMenuPlayer().closeInventory(); new PlotActionsMenu(getMenuPlayer(), plot); } } catch (SQLException ex) { - Bukkit.getLogger().log(Level.SEVERE, "A SQL error occurred!", ex); + Bukkit.getLogger().log(Level.SEVERE, ex.getMessage(), ex); } }); + index++; } // Set click event for previous page item From 3d5f60ae223a9858c6d1c533ef1f9aeaea7ca973 Mon Sep 17 00:00:00 2001 From: LordTuxn Date: Wed, 19 Jan 2022 22:48:30 +0100 Subject: [PATCH 2/3] add AbstractPaginatedMenu for new page system --- .../plotsystem/core/menus/AbstractMenu.java | 9 +- .../core/menus/AbstractPaginatedMenu.java | 139 ++++++++++++++++++ 2 files changed, 145 insertions(+), 3 deletions(-) create mode 100644 src/main/java/com/alpsbte/plotsystem/core/menus/AbstractPaginatedMenu.java diff --git a/src/main/java/com/alpsbte/plotsystem/core/menus/AbstractMenu.java b/src/main/java/com/alpsbte/plotsystem/core/menus/AbstractMenu.java index 5bb79445..150afa4e 100644 --- a/src/main/java/com/alpsbte/plotsystem/core/menus/AbstractMenu.java +++ b/src/main/java/com/alpsbte/plotsystem/core/menus/AbstractMenu.java @@ -1,7 +1,7 @@ /* * The MIT License (MIT) * - * Copyright © 2021, Alps BTE + * Copyright © 2021-2022, Alps BTE * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal @@ -31,17 +31,20 @@ import org.ipvp.canvas.mask.Mask; import org.ipvp.canvas.type.ChestMenu; - public abstract class AbstractMenu { private final Menu menu; private final Player menuPlayer; public AbstractMenu(int rows, String title, Player menuPlayer) { + this(rows, title, menuPlayer, true); + } + + public AbstractMenu(int rows, String title, Player menuPlayer, boolean reload) { this.menuPlayer = menuPlayer; this.menu = ChestMenu.builder(rows).title(title).redraw(true).build(); - reloadMenuAsync(); + if (reload) reloadMenuAsync(); } /** diff --git a/src/main/java/com/alpsbte/plotsystem/core/menus/AbstractPaginatedMenu.java b/src/main/java/com/alpsbte/plotsystem/core/menus/AbstractPaginatedMenu.java new file mode 100644 index 00000000..9c565a62 --- /dev/null +++ b/src/main/java/com/alpsbte/plotsystem/core/menus/AbstractPaginatedMenu.java @@ -0,0 +1,139 @@ +/* + * The MIT License (MIT) + * + * Copyright © 2021-2022, Alps BTE + * + * 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 com.alpsbte.plotsystem.core.menus; + +import com.alpsbte.plotsystem.PlotSystem; +import org.bukkit.Bukkit; +import org.bukkit.entity.Player; + +import java.util.List; + +public abstract class AbstractPaginatedMenu extends AbstractMenu { + + private final int maxItemsPerPage; + private final int totalItemsAmount; + private int currentPage = 0; + + public AbstractPaginatedMenu(int rows, int pagedRows, String title, Player menuPlayer) { + super(rows, title, menuPlayer, false); + + this.maxItemsPerPage = pagedRows * 9; + this.totalItemsAmount = getSource().size(); + + reloadMenuAsync(); + } + + /** + * Collects the source for the inventory items + * @return item sources + */ + protected abstract List getSource(); + + /** + * Places paginated items asynchronously in the menu after it is opened + * @param source paginated item sources + */ + protected abstract void setPaginatedMenuItemsAsync(List source); + + /** + * Sets click events for the paginated items placed in the menu after it is opened + * @param source paginated item sources + */ + protected abstract void setPaginatedItemClickEventsAsync(List source); + + /** + * Switch to the next page + */ + protected void nextPage() { + if (hasNextPage()) setPage(currentPage + 1); + } + + /** + * Switch to the previous page + */ + protected void previousPage() { + if (hasPreviousPage()) setPage(currentPage - 1); + } + + /** + * Sets the current page to the given index + * @param index page index + */ + protected void setPage(int index) { + currentPage = index; + reloadMenuAsync(); + } + + /** + * Collects all item sources for the current page + * @return item sources for the current page + */ + private List getItemSources() { + return getSource().subList(getMinIndex(), Math.min(getMaxIndex(), totalItemsAmount)); + } + + /** + * @return true if there is a next page + */ + protected boolean hasNextPage() { + return getMaxIndex() < totalItemsAmount; + } + + /** + * @return true if there is a previous page + */ + protected boolean hasPreviousPage() { + return getMinIndex() > 0; + } + + /** + * @return min slot index for current page + */ + private int getMinIndex() { + return currentPage * maxItemsPerPage; + } + + /** + * @return max slot index for current page + */ + private int getMaxIndex() { + return (currentPage + 1) * maxItemsPerPage; + } + + /** + * {@inheritDoc} + */ + @Override + protected void reloadMenuAsync() { + getMenu().clear(); + super.reloadMenuAsync(); + + Bukkit.getScheduler().runTaskAsynchronously(PlotSystem.getPlugin(), () -> { + List sources = getItemSources(); + setPaginatedMenuItemsAsync(sources); + setPaginatedItemClickEventsAsync(sources); + }); + } +} From 0ce097a0f33c395c835e8cad1963396d81e78a54 Mon Sep 17 00:00:00 2001 From: LordTuxn Date: Wed, 19 Jan 2022 22:48:55 +0100 Subject: [PATCH 3/3] refactor review menu for page system --- .../plotsystem/core/menus/ReviewMenu.java | 90 +++++++++++-------- .../com/alpsbte/plotsystem/utils/Utils.java | 3 +- 2 files changed, 54 insertions(+), 39 deletions(-) diff --git a/src/main/java/com/alpsbte/plotsystem/core/menus/ReviewMenu.java b/src/main/java/com/alpsbte/plotsystem/core/menus/ReviewMenu.java index 07093cd0..4dcddb92 100644 --- a/src/main/java/com/alpsbte/plotsystem/core/menus/ReviewMenu.java +++ b/src/main/java/com/alpsbte/plotsystem/core/menus/ReviewMenu.java @@ -1,7 +1,7 @@ /* * The MIT License (MIT) * - * Copyright © 2021, Alps BTE + * Copyright © 2021-2022, Alps BTE * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal @@ -43,45 +43,39 @@ import java.util.logging.Level; import java.util.stream.Collectors; -public class ReviewMenu extends AbstractMenu { - - private final List plots = new ArrayList<>(); - private int plotDisplayCount = 0; +public class ReviewMenu extends AbstractPaginatedMenu { public ReviewMenu(Player player) throws SQLException { - super(6, "Manage & Review Plots", player); + super(6, 5, "Manage & Review Plots", player); } @Override - protected void setPreviewItems() { - // Set previous page item - getMenu().getSlot(46).setItem(MenuItems.previousPageItem()); + protected List getSource() { + List plots = new ArrayList<>(); + try { + plots.addAll(PlotManager.getPlots(Status.unreviewed)); + plots.addAll(PlotManager.getPlots(Status.unfinished)); + } catch (SQLException ex) { + Bukkit.getLogger().log(Level.SEVERE, ex.getMessage(), ex); + } + return plots; + } + @Override + protected void setPreviewItems() { // Set close item getMenu().getSlot(49).setItem(MenuItems.closeMenuItem()); - // Set next page item - getMenu().getSlot(52).setItem(MenuItems.nextPageItem()); - super.setPreviewItems(); } @Override - protected void setMenuItemsAsync() { - // Get all unreviewed and unfinished plots - try { - plots.addAll(PlotManager.getPlots(Status.unreviewed)); - plots.addAll(PlotManager.getPlots(Status.unfinished)); - } catch (SQLException ex) { - Bukkit.getLogger().log(Level.SEVERE, "A SQL error occurred!", ex); - } - + protected void setPaginatedMenuItemsAsync(List source) { // Set unreviewed and unfinished plot items - plotDisplayCount = Math.min(plots.size(), 45); - for(int i = 0; i < plotDisplayCount; i++) { + List plots = source.stream().map(p -> (Plot) p).collect(Collectors.toList()); + int index = 0; + for(Plot plot : plots) { try { - Plot plot = plots.get(i); - List lines = new ArrayList<>(); lines.add("§7ID: §f" + plot.getID()); lines.add(""); @@ -98,27 +92,29 @@ protected void setMenuItemsAsync() { lines.add("§7City: §f" + plot.getCity().getName()); lines.add("§7Difficulty: §f" + plot.getDifficulty().name().charAt(0) + plot.getDifficulty().name().substring(1).toLowerCase()); - getMenu().getSlot(i).setItem(new ItemBuilder(plot.getStatus() == Status.unfinished ? Material.EMPTY_MAP : Material.MAP, 1) + getMenu().getSlot(index).setItem(new ItemBuilder(plot.getStatus() == Status.unfinished ? Material.EMPTY_MAP : Material.MAP, 1) .setName(plot.getStatus() == Status.unfinished ? "§b§lManage Plot" : "§b§lReview Plot") .setLore(lines) .build()); } catch (SQLException ex) { Bukkit.getLogger().log(Level.SEVERE, "A SQL error occurred!", ex); - getMenu().getSlot(i).setItem(MenuItems.errorItem()); + getMenu().getSlot(index).setItem(MenuItems.errorItem()); } + index++; } } @Override - protected void setItemClickEventsAsync() { + protected void setPaginatedItemClickEventsAsync(List source) { // Set click event for unreviewed and unfinished plot items + List plots = source.stream().map(p -> (Plot) p).collect(Collectors.toList()); int index = 0; - for (Plot plot : plots.subList(0, plotDisplayCount)) { + for (Plot plot : plots) { getMenu().getSlot(index).setClickHandler((player, info) -> { try { getMenuPlayer().closeInventory(); - if(plot.getStatus() == Status.unreviewed) { - if (!plot.getPlotOwner().getUUID().toString().equals(getMenuPlayer().getUniqueId().toString())){ + if (plot.getStatus() == Status.unreviewed) { + if (!plot.getPlotOwner().getUUID().toString().equals(getMenuPlayer().getUniqueId().toString())) { plot.getWorld().teleportPlayer(getMenuPlayer()); } else { getMenuPlayer().sendMessage(Utils.getErrorMessageFormat("You cannot review your own builds!")); @@ -132,19 +128,37 @@ protected void setItemClickEventsAsync() { }); index++; } + } + + @Override + protected void setMenuItemsAsync() { + // Set previous page item + if (hasPreviousPage()) getMenu().getSlot(46).setItem(MenuItems.previousPageItem()); + + // Set next page item + if (hasNextPage()) getMenu().getSlot(52).setItem(MenuItems.nextPageItem()); + } + @Override + protected void setItemClickEventsAsync() { // Set click event for previous page item - //getMenu().getSlot(46).setClickHandler((clickPlayer, clickInformation) -> { - // Not implemented yet - //}); + getMenu().getSlot(46).setClickHandler((clickPlayer, clickInformation) -> { + if (hasPreviousPage()) { + previousPage(); + clickPlayer.playSound(clickPlayer.getLocation(), Utils.INVENTORY_CLICK, 1, 1); + } + }); // Set click event for close item getMenu().getSlot(49).setClickHandler((clickPlayer, clickInformation) -> clickPlayer.closeInventory()); // Set click event for next page item - //getMenu().getSlot(52).setClickHandler((clickPlayer, clickInformation) -> { - // Not implemented yet - //}); + getMenu().getSlot(52).setClickHandler((clickPlayer, clickInformation) -> { + if (hasNextPage()) { + nextPage(); + clickPlayer.playSound(clickPlayer.getLocation(), Utils.INVENTORY_CLICK, 1, 1); + } + }); } @Override @@ -156,7 +170,7 @@ protected Mask getMask() { .pattern("000000000") .pattern("000000000") .pattern("000000000") - .pattern("101101101") + .pattern("111101111") .build(); } diff --git a/src/main/java/com/alpsbte/plotsystem/utils/Utils.java b/src/main/java/com/alpsbte/plotsystem/utils/Utils.java index 791781d0..2652c006 100644 --- a/src/main/java/com/alpsbte/plotsystem/utils/Utils.java +++ b/src/main/java/com/alpsbte/plotsystem/utils/Utils.java @@ -1,7 +1,7 @@ /* * The MIT License (MIT) * - * Copyright © 2021, Alps BTE + * Copyright © 2021-2022, Alps BTE * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal @@ -63,6 +63,7 @@ public static ItemStack getPlayerHead(UUID playerUUID) { public static Sound FinishPlotSound = Sound.ENTITY_PLAYER_LEVELUP; public static Sound AbandonPlotSound = Sound.ENTITY_ENDERDRAGON_FIREBALL_EXPLODE; public static Sound Done = Sound.ENTITY_EXPERIENCE_ORB_PICKUP; + public static Sound INVENTORY_CLICK = Sound.ENTITY_ITEMFRAME_ADD_ITEM; // Spawn Location public static Location getSpawnLocation() {