From 563ef49ea650c7592c51be334f39727b238e9997 Mon Sep 17 00:00:00 2001 From: ExcuseMe Date: Mon, 29 Jul 2019 23:11:20 +0200 Subject: [PATCH 1/3] Make self posts readable as an image --- pom.xml | 197 ++++++++++-------- .../interaction/InteractiveEnum.java | 13 +- .../listeners/EventListener.java | 80 ++++--- .../RedditMarkupToImageConverter.java | 74 +++++++ .../delta2force/redditbrowser/room/Room.java | 30 +-- .../room/screen/ControlStation.java | 94 +++++++++ .../room/{ => screen}/Screen.java | 85 ++++---- .../room/screen/ScreenController.java | 94 +++++++++ .../room/screen/ScreenControllerFactory.java | 21 ++ .../room/screen/ScreenModel.java | 33 +++ .../screen}/renderer/RedditRenderer.java | 13 +- .../screen}/renderer/TiledRenderer.java | 33 ++- .../RedditMarkupToImageConverterTest.java | 66 ++++++ 13 files changed, 632 insertions(+), 201 deletions(-) create mode 100644 src/main/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverter.java create mode 100644 src/main/java/me/delta2force/redditbrowser/room/screen/ControlStation.java rename src/main/java/me/delta2force/redditbrowser/room/{ => screen}/Screen.java (63%) create mode 100644 src/main/java/me/delta2force/redditbrowser/room/screen/ScreenController.java create mode 100644 src/main/java/me/delta2force/redditbrowser/room/screen/ScreenControllerFactory.java create mode 100644 src/main/java/me/delta2force/redditbrowser/room/screen/ScreenModel.java rename src/main/java/me/delta2force/redditbrowser/{ => room/screen}/renderer/RedditRenderer.java (66%) rename src/main/java/me/delta2force/redditbrowser/{ => room/screen}/renderer/TiledRenderer.java (65%) create mode 100644 src/test/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverterTest.java diff --git a/pom.xml b/pom.xml index f478931..8a220b2 100644 --- a/pom.xml +++ b/pom.xml @@ -2,96 +2,121 @@ - 4.0.0 + 4.0.0 - me.delta2force - redditbrowser - 1.7 - jar + me.delta2force + redditbrowser + 1.7 + jar - RedditBrowser + RedditBrowser - Browse reddit in minecraft - Browse Reddit in Minecraft. - - 1.8 - UTF-8 - + Browse reddit in minecraft + Browse Reddit in Minecraft. + + + 1.8 + UTF-8 + - - clean package - - - org.apache.maven.plugins - maven-compiler-plugin - 3.7.0 - - ${java.version} - ${java.version} - - - - org.apache.maven.plugins - maven-shade-plugin - 3.1.0 - - - package - - shade - - - false - - - - - - org.apache.maven.plugins - maven-surefire-plugin - 2.22.1 - - - - - src/main/resources - true - - - + + clean package + + + org.apache.maven.plugins + maven-compiler-plugin + 3.7.0 + + ${java.version} + ${java.version} + + + + org.apache.maven.plugins + maven-shade-plugin + 3.1.0 + + + package + + shade + + + false + + + + + + org.apache.maven.plugins + maven-surefire-plugin + 2.22.1 + + + + + src/main/resources + true + + + - - - spigotmc-repo - https://hub.spigotmc.org/nexus/content/groups/public/ - - - sonatype - https://oss.sonatype.org/content/groups/public/ - - - spring - http://repo.spring.io/libs-release/ - - + + + spigotmc-repo + https://hub.spigotmc.org/nexus/content/groups/public/ + + + sonatype + https://oss.sonatype.org/content/groups/public/ + + + spring + http://repo.spring.io/libs-release/ + + + yoava + AOL yoava + http://yoava.artifactoryonline.com/yoava/repo + + - - - org.spigotmc - spigot-api - 1.14.4-R0.1-SNAPSHOT - provided - - - net.dean.jraw - JRAW - 1.1.0 - - - org.junit.jupiter - junit-jupiter-engine - 5.5.1 - test - - + + + org.spigotmc + spigot-api + 1.14.4-R0.1-SNAPSHOT + provided + + + net.dean.jraw + JRAW + 1.1.0 + + + + com.vladsch.flexmark + flexmark-all + 0.50.20 + + + com.vladsch.flexmark + mark-pdf-converter + + + + + gui.ava + html2image + 0.9 + + + + + org.junit.jupiter + junit-jupiter-engine + 5.5.1 + test + + \ No newline at end of file diff --git a/src/main/java/me/delta2force/redditbrowser/interaction/InteractiveEnum.java b/src/main/java/me/delta2force/redditbrowser/interaction/InteractiveEnum.java index 5cef229..1ead467 100644 --- a/src/main/java/me/delta2force/redditbrowser/interaction/InteractiveEnum.java +++ b/src/main/java/me/delta2force/redditbrowser/interaction/InteractiveEnum.java @@ -1,6 +1,17 @@ package me.delta2force.redditbrowser.interaction; public enum InteractiveEnum { - UPVOTE, DOWNVOTE, COMMENT_CHEST, PREVIOUS_ROOM, NEXT_ROOM, LOAD_COMMENTS, REFRESH, LEAVE, WRITE_COMMENT, SHOW_URL; + UPVOTE, + DOWNVOTE, + COMMENT_CHEST, + PREVIOUS_ROOM, + NEXT_ROOM, + LOAD_COMMENTS, + REFRESH, + LEAVE, + WRITE_COMMENT, + SHOW_URL, + SCROLL_DOWN, + SCROLL_UP; } diff --git a/src/main/java/me/delta2force/redditbrowser/listeners/EventListener.java b/src/main/java/me/delta2force/redditbrowser/listeners/EventListener.java index 0692db2..049ee44 100644 --- a/src/main/java/me/delta2force/redditbrowser/listeners/EventListener.java +++ b/src/main/java/me/delta2force/redditbrowser/listeners/EventListener.java @@ -2,7 +2,6 @@ import me.delta2force.redditbrowser.RedditBrowserPlugin; import me.delta2force.redditbrowser.interaction.InteractiveEnum; -import me.delta2force.redditbrowser.renderer.RedditRenderer; import me.delta2force.redditbrowser.room.Room; import net.dean.jraw.models.Comment; import net.dean.jraw.tree.CommentNode; @@ -14,7 +13,6 @@ import org.bukkit.*; import org.bukkit.block.Chest; -import org.bukkit.entity.ItemFrame; import org.bukkit.entity.Player; import org.bukkit.event.EventHandler; import org.bukkit.event.Listener; @@ -25,14 +23,11 @@ import org.bukkit.event.inventory.InventoryClickEvent; import org.bukkit.event.inventory.InventoryCloseEvent; import org.bukkit.event.inventory.InventoryType; -import org.bukkit.event.player.PlayerInteractAtEntityEvent; import org.bukkit.event.player.PlayerInteractEvent; import org.bukkit.event.player.PlayerQuitEvent; import org.bukkit.inventory.Inventory; import org.bukkit.inventory.ItemStack; import org.bukkit.inventory.meta.BookMeta; -import org.bukkit.inventory.meta.MapMeta; -import org.bukkit.map.MapRenderer; import org.bukkit.metadata.FixedMetadataValue; import org.bukkit.metadata.MetadataValue; @@ -60,10 +55,18 @@ public void interact(PlayerInteractEvent event) { Bukkit.getScheduler().runTaskAsynchronously(reddit, new Runnable() { @Override public void run() { - event.getPlayer().playSound(event.getClickedBlock().getLocation(), Sound.ENTITY_VILLAGER_YES, VOLUME, 1); reddit.redditClient.submission(submissionID).upvote(); int karma = reddit.redditClient.submission(submissionID).inspect().getScore(); - event.getPlayer().sendMessage(ChatColor.GREEN + "You have upvoted the post! It now has " + karma + " karma."); + UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); + if (reddit.roomMap.containsKey(roomId)) { + final Room room = reddit.roomMap.get(roomId); + room.getPlayers().forEach(player -> { + player.sendMessage(ChatColor.GREEN + "You have upvoted the post! It now has " + karma + " karma."); + player.playSound(event.getClickedBlock().getLocation(), Sound.ENTITY_VILLAGER_YES, VOLUME, 1); + }); + } else { + event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); + } } }); } else if (metadataContains(metadata, InteractiveEnum.DOWNVOTE)) { @@ -74,11 +77,19 @@ public void run() { event.getPlayer().playSound(event.getClickedBlock().getLocation(), Sound.ENTITY_VILLAGER_NO, VOLUME, 1); reddit.redditClient.submission(submissionID).downvote(); int karma = reddit.redditClient.submission(submissionID).inspect().getScore(); - event.getPlayer().sendMessage(ChatColor.RED + "You have downvoted the post! It now has " + karma + " karma."); - } + UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); + if (reddit.roomMap.containsKey(roomId)) { + final Room room = reddit.roomMap.get(roomId); + room.getPlayers().forEach(player -> { + event.getPlayer().sendMessage(ChatColor.RED + "You have downvoted the post! It now has " + karma + " karma."); + player.playSound(event.getClickedBlock().getLocation(), Sound.ENTITY_VILLAGER_NO, VOLUME, 1); + }); + } else { + event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); + } } }); } else if (metadataContains(metadata, InteractiveEnum.NEXT_ROOM)) { - if(!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); if (reddit.roomMap.containsKey(roomId)) { @@ -89,7 +100,7 @@ public void run() { } } } else if (metadataContains(metadata, InteractiveEnum.PREVIOUS_ROOM)) { - if(!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); if (reddit.roomMap.containsKey(roomId)) { @@ -100,7 +111,7 @@ public void run() { } } } else if (metadataContains(metadata, InteractiveEnum.LOAD_COMMENTS)) { - if(!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); if (reddit.roomMap.containsKey(roomId)) { @@ -111,7 +122,7 @@ public void run() { } } } else if (metadataContains(metadata, InteractiveEnum.REFRESH)) { - if(!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); if (reddit.roomMap.containsKey(roomId)) { @@ -122,12 +133,12 @@ public void run() { } } } else if (metadataContains(metadata, InteractiveEnum.LEAVE)) { - if(!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); reddit.kickOut(event.getPlayer()); } } else if (metadataContains(metadata, InteractiveEnum.WRITE_COMMENT)) { - if(!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); final ItemStack writableBookStack = createWritableBookStack(); event.getPlayer().getInventory().setItemInMainHand(writableBookStack); @@ -141,6 +152,25 @@ public void run() { event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); } event.setCancelled(true); + } else if (metadataContains(metadata, InteractiveEnum.SCROLL_UP)) { + UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); + if (reddit.roomMap.containsKey(roomId) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + final Room room = reddit.roomMap.get(roomId); + event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); + room.getScreenController().back(); + } else { + event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); + } + } else if (metadataContains(metadata, InteractiveEnum.SCROLL_DOWN) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); + if (reddit.roomMap.containsKey(roomId) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + final Room room = reddit.roomMap.get(roomId); + event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); + room.getScreenController().forward(); + } else { + event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); + } + } } } @@ -149,14 +179,14 @@ public void run() { public void interactInventory(InventoryClickEvent event) { Player p = (Player) event.getWhoClicked(); - if(event.getCurrentItem() != null && + if (event.getCurrentItem() != null && event.getCurrentItem().getType().equals(Material.WRITTEN_BOOK) && event.getInventory().getType().equals(InventoryType.CHEST) && event.isRightClick()) { - if(!event.getView().getTitle().startsWith("Comment ")) { - if(reddit.roomMap.values() + if (!event.getView().getTitle().startsWith("Comment ")) { + if (reddit.roomMap.values() .stream() - .noneMatch(o->o.hasPlayer(p.getUniqueId()))){ - return ; + .noneMatch(o -> o.hasPlayer(p.getUniqueId()))) { + return; } } String commentID = event.getCurrentItem().getItemMeta().getLore().get(0); @@ -250,8 +280,8 @@ public void closeInventory(InventoryCloseEvent event) { @EventHandler public void onLeave(PlayerQuitEvent event) { - if(reddit.roomMap.values().stream() - .anyMatch(o->o.hasPlayer(event.getPlayer().getUniqueId()))) { + if (reddit.roomMap.values().stream() + .anyMatch(o -> o.hasPlayer(event.getPlayer().getUniqueId()))) { Player player = event.getPlayer(); reddit.kickOut(player); } @@ -260,7 +290,7 @@ public void onLeave(PlayerQuitEvent event) { @EventHandler public void onBlockBreak(BlockBreakEvent blockBreakEvent) { final Location location = blockBreakEvent.getBlock().getLocation(); - if(reddit.roomMap.values().stream().anyMatch(o->o.isInside(location))) { + if (reddit.roomMap.values().stream().anyMatch(o -> o.isInside(location))) { blockBreakEvent.setCancelled(true); } } @@ -268,7 +298,7 @@ public void onBlockBreak(BlockBreakEvent blockBreakEvent) { @EventHandler public void onBlockPlace(BlockPlaceEvent blockPlaceEvent) { final Location location = blockPlaceEvent.getBlock().getLocation(); - if(reddit.roomMap.values().stream().anyMatch(o->o.isInside(location))) { + if (reddit.roomMap.values().stream().anyMatch(o -> o.isInside(location))) { blockPlaceEvent.setCancelled(true); } } @@ -276,7 +306,7 @@ public void onBlockPlace(BlockPlaceEvent blockPlaceEvent) { @EventHandler public void onBlockPlace(HangingBreakEvent hangingBreakEvent) { final Location location = hangingBreakEvent.getEntity().getLocation(); - if(reddit.roomMap.values().stream().anyMatch(o->o.isInside(location))) { + if (reddit.roomMap.values().stream().anyMatch(o -> o.isInside(location))) { hangingBreakEvent.setCancelled(true); } } diff --git a/src/main/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverter.java b/src/main/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverter.java new file mode 100644 index 0000000..c9edee4 --- /dev/null +++ b/src/main/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverter.java @@ -0,0 +1,74 @@ +package me.delta2force.redditbrowser.reddittext; + +import com.vladsch.flexmark.html.HtmlRenderer; +import com.vladsch.flexmark.parser.Parser; +import com.vladsch.flexmark.profiles.pegdown.Extensions; +import com.vladsch.flexmark.profiles.pegdown.PegdownOptionsAdapter; +import com.vladsch.flexmark.util.ast.Document; +import com.vladsch.flexmark.util.data.DataHolder; +import com.vladsch.flexmark.util.data.MutableDataSet; +import gui.ava.html.image.generator.HtmlImageGenerator; + +import java.awt.*; +import java.awt.image.BufferedImage; +import java.util.ArrayList; +import java.util.List; + + +public class RedditMarkupToImageConverter { + static final DataHolder OPTIONS = PegdownOptionsAdapter.flexmarkOptions( + Extensions.ALL + ); + + static final MutableDataSet FORMAT_OPTIONS = new MutableDataSet(); + static { + // copy extensions from Pegdown compatible to Formatting, but leave the rest default + FORMAT_OPTIONS.set(Parser.EXTENSIONS, OPTIONS.get(Parser.EXTENSIONS)); + } + + public static List render(String text, int width, int height) { + Parser parser = Parser.builder(OPTIONS).build(); + HtmlRenderer renderer = HtmlRenderer.builder(FORMAT_OPTIONS).build(); + + // You can re-use parser and renderer instances + Document document = parser.parse(text); + String html = renderer.render(document); + //Trying to force the width + final double estimatedTextWidth = Math.floor(width * .7); + html = "
" + html + "
"; + + final HtmlImageGenerator htmlImageGenerator = new HtmlImageGenerator(); + htmlImageGenerator.setSize(new Dimension(width, height * 100)); + htmlImageGenerator.loadHtml(html); + final BufferedImage bufferedImage = htmlImageGenerator.getBufferedImage(); + BufferedImage whiteBackgroundBufferedImage = new BufferedImage(bufferedImage.getWidth(), bufferedImage.getHeight(), BufferedImage.TYPE_INT_RGB); + final Graphics2D graphics = whiteBackgroundBufferedImage.createGraphics(); + graphics.drawImage(bufferedImage, 0, 0, Color.WHITE, null); + + return splitImage(whiteBackgroundBufferedImage, width, height); + } + + private static List splitImage(BufferedImage image, int width, int height) { + final List pages = new ArrayList<>(); + for(int y = 0; y startingPlayers) { Bukkit.getScheduler().runTaskLater(redditBrowserPlugin, () -> { setupPlayers(submission, startingPlayers); - }, 10); + }, 30); }); } else { Bukkit.getScheduler().runTask(redditBrowserPlugin, () -> { @@ -81,7 +81,7 @@ public void build(Collection startingPlayers) { setupPlayers(submission, startingPlayers); startingPlayers.forEach(player -> player.sendMessage(ChatColor.RED + "No posts found.")); - }, 10); + }, 30); }); } }); @@ -93,7 +93,7 @@ public void addPlayer(Player player) { public void refresh() { redditQueue.reset(); - screen.clean(); + screenController.clean(); build(getPlayers()); } @@ -205,7 +205,7 @@ private void updateRoom(Submission submission) { emptyCommentsChest(); buildLeaveButton(); removeNewCommentsButton(); - screen.buildScreen(submission); + screenController.showPost(submission); if (submission != null) { buildNavigationButton(); buildVoteButtons(submission); @@ -389,6 +389,7 @@ private void buildVoteButtons(Submission submission) { Block uv = location.getWorld().getBlockAt(location.clone().add(-roomDimensions.getRoomWidth() + 1, -roomDimensions.getRoomHeight() + 1, -roomDimensions.getRoomDepth() + 1)); uv.setType(Material.OAK_BUTTON); uv.setMetadata(SUBMISSION_ID, new FixedMetadataValue(redditBrowserPlugin, submission.getId())); + uv.setMetadata(ROOM_ID, new FixedMetadataValue(redditBrowserPlugin, getRoomId())); uv.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(redditBrowserPlugin, InteractiveEnum.UPVOTE)); Directional uvdir = (Directional) uv.getBlockData(); uvdir.setFacing(BlockFace.SOUTH); @@ -399,6 +400,7 @@ private void buildVoteButtons(Submission submission) { Block dv = location.getWorld().getBlockAt(location.clone().add(-1, -roomDimensions.getRoomHeight() + 1, -roomDimensions.getRoomDepth() + 1)); dv.setType(Material.OAK_BUTTON); dv.setMetadata(SUBMISSION_ID, new FixedMetadataValue(redditBrowserPlugin, submission.getId())); + dv.setMetadata(ROOM_ID, new FixedMetadataValue(redditBrowserPlugin, getRoomId())); dv.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(redditBrowserPlugin, InteractiveEnum.DOWNVOTE)); Directional dvdir = (Directional) dv.getBlockData(); @@ -474,8 +476,8 @@ private void cube(Material blockMaterial, Location from, Location to) { } } - private void spawnHologram(Location l, String name) { - ArmorStand as = (ArmorStand) l.getWorld().spawnEntity(l, EntityType.ARMOR_STAND); + public static void spawnHologram(Location location, String name) { + ArmorStand as = (ArmorStand) location.getWorld().spawnEntity(location, EntityType.ARMOR_STAND); as.setCustomName(name); as.setCustomNameVisible(true); as.setGravity(false); @@ -563,4 +565,8 @@ public Material getRoomMaterial() { public RedditBrowserPlugin getRedditBrowserPlugin() { return redditBrowserPlugin; } + + public ScreenController getScreenController() { + return screenController; + } } diff --git a/src/main/java/me/delta2force/redditbrowser/room/screen/ControlStation.java b/src/main/java/me/delta2force/redditbrowser/room/screen/ControlStation.java new file mode 100644 index 0000000..89caf1b --- /dev/null +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/ControlStation.java @@ -0,0 +1,94 @@ +package me.delta2force.redditbrowser.room.screen; + +import me.delta2force.redditbrowser.interaction.InteractiveEnum; +import me.delta2force.redditbrowser.room.Room; +import org.bukkit.Location; +import org.bukkit.Material; +import org.bukkit.block.Block; +import org.bukkit.block.BlockFace; +import org.bukkit.block.Sign; +import org.bukkit.block.data.Directional; +import org.bukkit.entity.Entity; +import org.bukkit.entity.EntityType; +import org.bukkit.metadata.FixedMetadataValue; + +import java.util.Collection; +import java.util.Objects; + +import static me.delta2force.redditbrowser.RedditBrowserPlugin.*; +import static me.delta2force.redditbrowser.room.Room.spawnHologram; + +public class ControlStation { + private static final String SCROLL_DOWN = "Scroll down"; + private static final String SCROLL_UP = "Scroll up"; + private ScreenController screenController; + private final Room room; + private final Location location; + + + public ControlStation(ScreenController screenController, Room room, Location location) { + this.screenController = screenController; + this.room = room; + this.location = location; + } + + public void build() { + buildScrollDownButton(); + buildScrollUpButton(); + } + + private void buildScrollDownButton() { + final Location blockLocation = location.clone(); + final Block block = blockLocation.getBlock(); + block.setType(Material.GOLD_BLOCK); + Block downButton = blockLocation.getWorld().getBlockAt(blockLocation.clone().add(0, 0, 1)); + + if(screenController.canForward()) { + downButton.setType(Material.OAK_WALL_SIGN); + final Sign sign = (Sign) downButton.getState(); + sign.setLine(0, SCROLL_DOWN); + sign.setEditable(false); + sign.update(); + downButton.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(room.getRedditBrowserPlugin(), InteractiveEnum.SCROLL_DOWN)); + downButton.setMetadata(ROOM_ID, new FixedMetadataValue(room.getRedditBrowserPlugin(), room.getRoomId())); + downButton.setMetadata(BUTTON_ACTIVATED, new FixedMetadataValue(room.getRedditBrowserPlugin(), false)); + + Directional downButtonDirection = (Directional) downButton.getBlockData(); + downButtonDirection.setFacing(BlockFace.SOUTH); + downButton.setBlockData(downButtonDirection); + + } else { + downButton.setType(Material.AIR); + } + } + + private void buildScrollUpButton() { + final Location blockLocation = location.clone().add(0, 1, 0); + final Block block = blockLocation.getBlock(); + block.setType(Material.GOLD_BLOCK); + Block upButton = blockLocation.getWorld().getBlockAt(blockLocation.clone().add(0, 0, 1)); + + if(screenController.canBack()) { + upButton.setType(Material.OAK_WALL_SIGN); + final Sign sign = (Sign) upButton.getState(); + sign.setLine(0, SCROLL_UP); + sign.setEditable(false); + sign.update(); + upButton.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(room.getRedditBrowserPlugin(), InteractiveEnum.SCROLL_UP)); + upButton.setMetadata(ROOM_ID, new FixedMetadataValue(room.getRedditBrowserPlugin(), room.getRoomId())); + upButton.setMetadata(BUTTON_ACTIVATED, new FixedMetadataValue(room.getRedditBrowserPlugin(), false)); + + Directional downButtonDirection = (Directional) upButton.getBlockData(); + downButtonDirection.setFacing(BlockFace.SOUTH); + upButton.setBlockData(downButtonDirection); + + } else { + upButton.setType(Material.AIR); + } + } + + public void clean() { + + } + +} diff --git a/src/main/java/me/delta2force/redditbrowser/room/Screen.java b/src/main/java/me/delta2force/redditbrowser/room/screen/Screen.java similarity index 63% rename from src/main/java/me/delta2force/redditbrowser/room/Screen.java rename to src/main/java/me/delta2force/redditbrowser/room/screen/Screen.java index cf4533c..60e4977 100644 --- a/src/main/java/me/delta2force/redditbrowser/room/Screen.java +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/Screen.java @@ -1,17 +1,14 @@ -package me.delta2force.redditbrowser.room; +package me.delta2force.redditbrowser.room.screen; -import me.delta2force.redditbrowser.RedditBrowserPlugin; import me.delta2force.redditbrowser.interaction.InteractiveEnum; -import me.delta2force.redditbrowser.renderer.TiledRenderer; -import me.delta2force.redditbrowser.repository.URLToImageRepository; -import net.dean.jraw.models.Submission; +import me.delta2force.redditbrowser.room.screen.renderer.TiledRenderer; +import me.delta2force.redditbrowser.room.Room; import org.bukkit.*; import org.bukkit.block.BlockFace; import org.bukkit.entity.Entity; import org.bukkit.entity.EntityType; import org.bukkit.entity.ItemFrame; import org.bukkit.inventory.ItemStack; -import org.bukkit.inventory.meta.BookMeta; import org.bukkit.inventory.meta.MapMeta; import org.bukkit.map.MapView; import org.bukkit.metadata.FixedMetadataValue; @@ -20,31 +17,34 @@ import java.util.Collection; import java.util.Objects; -import static java.lang.Math.ceil; import static me.delta2force.redditbrowser.RedditBrowserPlugin.INTERACTIVE_ENUM; import static me.delta2force.redditbrowser.RedditBrowserPlugin.ROOM_ID; -import static me.delta2force.redditbrowser.room.Room.COMMENT_DISPLAY_NAME; public class Screen { + public static final int BLOCK_PIXELS = 128; + private final Room room; private TiledRenderer tiledRenderer = null; private final Location screenLocation; private final int screenWidth; private final int screenHeight; + private final ScreenController screenController; public Screen( Room room, Location screenLocation, int screenWidth, - int screenHeight) { + int screenHeight, + ScreenController screenController) { this.room = room; this.screenLocation = screenLocation; this.screenWidth = screenWidth; this.screenHeight = screenHeight; + this.screenController = screenController; } - public void buildScreen(Submission submission) { - if (submission != null && !submission.isSelfPost()) { + public void buildScreen(BufferedImage bufferedImage) { + if (bufferedImage != null) { if (tiledRenderer == null) { cleanBackWall(); final World world = screenLocation.getWorld(); @@ -74,24 +74,21 @@ public void buildScreen(Submission submission) { } } - updateRenderer(submission); + updateRenderer(bufferedImage); - }, 5); + }, 50); } else { - updateRenderer(submission); + updateRenderer(bufferedImage); } - } else if (submission != null && submission.isSelfPost()) { - buildSelfPost(submission); } else { cleanBackWall(); } } - private void updateRenderer(Submission submission) { + private void updateRenderer(BufferedImage bufferedImage) { Bukkit.getScheduler().runTaskAsynchronously(room.getRedditBrowserPlugin(), () -> { - final BufferedImage image = URLToImageRepository.findImage(submission); if (tiledRenderer != null) { - tiledRenderer.updateImage(submission.getUrl(), image); + tiledRenderer.updateImage(bufferedImage); } }); } @@ -100,36 +97,6 @@ public void clean() { cleanBackWall(); } - private void buildSelfPost(Submission submission) { - cleanBackWall(); - ItemStack book = new ItemStack(Material.WRITTEN_BOOK); - BookMeta bookmeta = (BookMeta) book.getItemMeta(); - bookmeta.setTitle(submission.getTitle()); - bookmeta.setDisplayName(COMMENT_DISPLAY_NAME); - bookmeta.setAuthor(submission.getAuthor()); - if (submission.getSelfText().length() > 255) { - double f = ceil(((float) submission.getSelfText().length()) / 255f); - for (int i = 0; i < f; i++) { - if (submission.getSelfText().length() < (i + 1) * 255) { - bookmeta.addPage(submission.getSelfText().substring(i * 255)); - } else { - bookmeta.addPage(submission.getSelfText().substring(i * 255, (i + 1) * 255)); - } - } - } else { - bookmeta.addPage(submission.getSelfText()); - } - - Bukkit.getScheduler().runTaskLater(room.getRedditBrowserPlugin(), () -> { - final Location smallScreenLocation = screenLocation.clone().add(screenWidth / 2, -screenHeight + 1, 0); - smallScreenLocation.getBlock().setType(Material.GLOWSTONE); - ItemFrame itf = (ItemFrame) smallScreenLocation.getWorld().spawnEntity(smallScreenLocation.clone().add(0, 0, 1), EntityType.ITEM_FRAME); - itf.setFacingDirection(BlockFace.SOUTH); - book.setItemMeta(bookmeta); - itf.setItem(book); - }, 5); - } - private void cleanBackWall() { clearItemFrames(); tiledRenderer = null; @@ -151,4 +118,24 @@ private void clearItemFrames() { o -> Objects.equals(EntityType.ITEM_FRAME, o.getType())); nearbyEntities.forEach(Entity::remove); } + + public int getBlockPixels() { + return BLOCK_PIXELS; + } + + public int getScreenWidth() { + return screenWidth; + } + + public int getScreenHeight() { + return screenHeight; + } + + public ScreenController getScreenController() { + return screenController; + } + + public Room getRoom() { + return room; + } } diff --git a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenController.java b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenController.java new file mode 100644 index 0000000..7b1adb0 --- /dev/null +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenController.java @@ -0,0 +1,94 @@ +package me.delta2force.redditbrowser.room.screen; + +import me.delta2force.redditbrowser.reddittext.RedditMarkupToImageConverter; +import me.delta2force.redditbrowser.repository.URLToImageRepository; +import net.dean.jraw.models.Comment; +import net.dean.jraw.models.Submission; +import org.bukkit.Bukkit; + +import java.awt.image.BufferedImage; +import java.util.Collections; +import java.util.List; + +public class ScreenController { + private Screen screen; + private ScreenModel screenModel; + private ControlStation controlStation; + + ScreenController() { + } + + public void setScreen(Screen screen) { + this.screen = screen; + } + + public void setControlStation(ControlStation controlStation) { + this.controlStation = controlStation; + } + + public void showPost(Submission submission) { + Bukkit.getScheduler().runTaskAsynchronously(screen.getRoom().getRedditBrowserPlugin(), new Runnable() { + @Override + public void run() { + screenModel = findBufferedImagesForPost(submission); + Bukkit.getScheduler().runTask(screen.getRoom().getRedditBrowserPlugin(), new Runnable() { + @Override + public void run() { + update(); + } + }); + } + }); + } + + private void update() { + screen.buildScreen(screenModel.getSelectedImage()); + controlStation.build(); + } + + public void showComment(Comment comment) { + + } + + private ScreenModel findBufferedImagesForPost(Submission submission) { + if(!submission.isSelfPost()) { + final BufferedImage image = URLToImageRepository.findImage(submission); + return new ScreenModel(Collections.singletonList(image)); + } else { + final int blockPixels = screen.getBlockPixels(); + final List bufferedImages = RedditMarkupToImageConverter.render( + submission.getSelfText(), + screen.getScreenWidth() * blockPixels / 2 , + screen.getScreenHeight() * blockPixels /2 ); + return new ScreenModel(bufferedImages); + } + } + + + public boolean canBack() { + return screenModel.getSelectedIndex() > 0; + } + + public boolean canForward() { + return screenModel.getImages().size() > screenModel.getSelectedIndex() +1; + } + + public void back() { + if(canBack()) { + screenModel.setSelectedIndex(screenModel.getSelectedIndex() - 1 ); + update(); + } + } + + public void forward() { + if(canForward()) { + screenModel.setSelectedIndex(screenModel.getSelectedIndex() + 1 ); + update(); + } + } + + public void clean() { + screen.clean(); + controlStation.clean(); + } +} diff --git a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenControllerFactory.java b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenControllerFactory.java new file mode 100644 index 0000000..931a6af --- /dev/null +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenControllerFactory.java @@ -0,0 +1,21 @@ +package me.delta2force.redditbrowser.room.screen; + +import me.delta2force.redditbrowser.room.Room; +import org.bukkit.Location; + +public class ScreenControllerFactory { + + public static ScreenController create(Room room, + Location screenLocation, + Location controlStationLocation, + int screenWidth, + int screenHeight) { + + final ScreenController screenController = new ScreenController(); + final Screen screen = new Screen(room, screenLocation, screenWidth, screenHeight, screenController); + final ControlStation controlStation = new ControlStation(screenController, room, controlStationLocation); + screenController.setScreen(screen); + screenController.setControlStation(controlStation); + return screenController; + } +} diff --git a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenModel.java b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenModel.java new file mode 100644 index 0000000..0eff2a8 --- /dev/null +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenModel.java @@ -0,0 +1,33 @@ +package me.delta2force.redditbrowser.room.screen; + +import java.awt.image.BufferedImage; +import java.util.List; + +public class ScreenModel { + private List images; + private int selectedIndex = 0; + + public ScreenModel(List images) { + this.images = images; + } + + public List getImages() { + return images; + } + + public BufferedImage getSelectedImage() { + if(selectedIndex < images.size()) { + return images.get(selectedIndex); + } + return null; + } + + + public int getSelectedIndex() { + return selectedIndex; + } + + public void setSelectedIndex(int index) { + this.selectedIndex = index; + } +} diff --git a/src/main/java/me/delta2force/redditbrowser/renderer/RedditRenderer.java b/src/main/java/me/delta2force/redditbrowser/room/screen/renderer/RedditRenderer.java similarity index 66% rename from src/main/java/me/delta2force/redditbrowser/renderer/RedditRenderer.java rename to src/main/java/me/delta2force/redditbrowser/room/screen/renderer/RedditRenderer.java index b44eeb5..9a74783 100644 --- a/src/main/java/me/delta2force/redditbrowser/renderer/RedditRenderer.java +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/renderer/RedditRenderer.java @@ -1,26 +1,17 @@ -package me.delta2force.redditbrowser.renderer; +package me.delta2force.redditbrowser.room.screen.renderer; import java.awt.image.BufferedImage; -import java.io.IOException; -import java.net.MalformedURLException; -import java.net.URL; - -import javax.imageio.ImageIO; import org.bukkit.entity.Player; import org.bukkit.map.MapCanvas; import org.bukkit.map.MapRenderer; import org.bukkit.map.MapView; -import me.delta2force.redditbrowser.RedditBrowserPlugin; - public class RedditRenderer extends MapRenderer{ public BufferedImage image; - public String url; private boolean drawn; - public void setImage(String url, BufferedImage image) { - this.url = url; + public void setImage( BufferedImage image) { this.drawn = false; this.image = image; } diff --git a/src/main/java/me/delta2force/redditbrowser/renderer/TiledRenderer.java b/src/main/java/me/delta2force/redditbrowser/room/screen/renderer/TiledRenderer.java similarity index 65% rename from src/main/java/me/delta2force/redditbrowser/renderer/TiledRenderer.java rename to src/main/java/me/delta2force/redditbrowser/room/screen/renderer/TiledRenderer.java index 507dde0..be73f0d 100644 --- a/src/main/java/me/delta2force/redditbrowser/renderer/TiledRenderer.java +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/renderer/TiledRenderer.java @@ -1,4 +1,4 @@ -package me.delta2force.redditbrowser.renderer; +package me.delta2force.redditbrowser.room.screen.renderer; import me.delta2force.redditbrowser.RedditBrowserPlugin; import org.bukkit.map.MapRenderer; @@ -6,10 +6,10 @@ import java.awt.*; import java.awt.image.BufferedImage; +import static me.delta2force.redditbrowser.room.screen.Screen.BLOCK_PIXELS; + public class TiledRenderer { - private static final int IMAGE_SIZE = 128; private final RedditRenderer[][] tiles; - private String url; private final RedditBrowserPlugin redditBrowserPlugin; private final int tileWidth; private final int tileHeight; @@ -30,22 +30,21 @@ public TiledRenderer( } } - public void updateImage(String originalURL, BufferedImage originalImage) { - url = originalURL; + public void updateImage( BufferedImage originalImage) { if (originalImage != null) { - BufferedImage image = new BufferedImage(IMAGE_SIZE * tileWidth, IMAGE_SIZE * tileHeight, BufferedImage.TYPE_INT_ARGB); - image.createGraphics().drawImage(originalImage, 0, 0, IMAGE_SIZE * tileWidth, IMAGE_SIZE * tileHeight, null); + BufferedImage image = new BufferedImage(BLOCK_PIXELS * tileWidth, BLOCK_PIXELS * tileHeight, BufferedImage.TYPE_INT_ARGB); + image.createGraphics().drawImage(originalImage, 0, 0, BLOCK_PIXELS * tileWidth, BLOCK_PIXELS * tileHeight, null); BufferedImage[][] bufferedImages = splitImage(image, tileHeight, tileWidth); for (int row = 0; row < tileHeight; row++) { for (int col = 0; col < tileWidth; col++) { - tiles[row][col].setImage(originalURL, bufferedImages[row][col]); + tiles[row][col].setImage(bufferedImages[row][col]); } } } else { - BufferedImage fallbackImage = new BufferedImage(IMAGE_SIZE, IMAGE_SIZE, BufferedImage.TYPE_BYTE_GRAY); + BufferedImage fallbackImage = new BufferedImage(BLOCK_PIXELS, BLOCK_PIXELS, BufferedImage.TYPE_BYTE_GRAY); for (int row = 0; row < tileHeight; row++) { for (int col = 0; col < tileWidth; col++) { - tiles[row][col].setImage(originalURL, fallbackImage); + tiles[row][col].setImage(fallbackImage); } } } @@ -55,16 +54,16 @@ private BufferedImage[][] splitImage(BufferedImage image, int rows, int cols) { BufferedImage[][] imgs = new BufferedImage[rows][cols]; //Image array to hold image chunks for (int col = 0; col < cols; col++) { for (int row = 0; row < rows; row++) { - imgs[row][col] = new BufferedImage(IMAGE_SIZE, IMAGE_SIZE, image.getType()); + imgs[row][col] = new BufferedImage(BLOCK_PIXELS, BLOCK_PIXELS, image.getType()); Graphics2D gr = imgs[row][col].createGraphics(); gr.drawImage(image, 0, 0, - IMAGE_SIZE, - IMAGE_SIZE, - IMAGE_SIZE * col, - IMAGE_SIZE * row, - IMAGE_SIZE * (col + 1), - IMAGE_SIZE * (row + 1), + BLOCK_PIXELS, + BLOCK_PIXELS, + BLOCK_PIXELS * col, + BLOCK_PIXELS * row, + BLOCK_PIXELS * (col + 1), + BLOCK_PIXELS * (row + 1), null); gr.dispose(); } diff --git a/src/test/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverterTest.java b/src/test/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverterTest.java new file mode 100644 index 0000000..2cd182f --- /dev/null +++ b/src/test/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverterTest.java @@ -0,0 +1,66 @@ +package me.delta2force.redditbrowser.reddittext; + +import org.junit.jupiter.api.BeforeAll; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +import javax.imageio.ImageIO; +import java.awt.image.BufferedImage; +import java.io.File; +import java.io.IOException; +import java.util.List; + +import static org.junit.jupiter.api.Assertions.*; + +class RedditMarkupToImageConverterTest { + @BeforeAll + public static void setup() { + new File("target/images").mkdir(); + } + + public static final String TEXT = "Hello Reddit!!! This is my first TIFU, and it's because I chose to fly EasyJet, even after a bunch of people told me to avoid it! I hope you all enjoy this story so here it begins.\n" + + "\n" + + "**UPDATES POSTED BELOW** \n" + + "\n" + + "My wife and I decided to take a trip to Amsterdam from the states this summer to visit family. During said trip we booked a seperate flight to London for 3 days. The 22nd-24th. We arrived in Amsterdam on the 21st and left the next day, all went smooth. We enjoyed the city of London and visited pretty much all of it in the time we had. Then the chaos began.\n" + + "\n" + + "On the 24th while at Gatwick Airport our flight to Amsterdam was canceled due to a fueling issue in Amsterdam, this was understandable as our flight home from Amsterdam was on the 28th, so no big deal; we'd catch another flight. My wife had purchased alcohol after security and was told by a manager we could get a free checked bag. After being online at customer service for 3 hours the airline said the next flight was on the 26th and they had booked us for 2 nights at a hotel. When we arrived at the hotel they said we were booked for only 1 night and dinner was no longer being served.\n" + + "\n" + + "On the 25th we went back to the airport to request another hotel since they had mistakingly booked just a night, and we had to wait another 5 hours on line. They eventually booked us a night at a different hotel. When we arrived at the hotel they told us nothing was booked, and to go back to EasyJet. We went back and had to wait another 3 hours, totalling 8. They apologized and said the confirmation was never sent. So a whole day of opportunity wasted. We got back to the hotel and missed our food vouchers, again.\n" + + "\n" + + "On the 26th we got to the airport and our flights were canceled again, due to weather issues. However employees told us it was due to a crew issue and other airlines were flying to Amsterdam without a problem. We had to stay on line again for 4 hours, only for them to tell us there were no available flights for a few days. We needed to be back in Amsterdam by the 28th. They hired a taxi, and drove us to Luton airport 2 hours away on the 27th. Another whole day wasted. \n" + + "\n" + + "On the 27th when we arrived at Luton Airport we asked about our free checked bag we were promised on the 24th, and an employee told us \"I don't care what a random person or employee told you, it's not happening\". I tried to explain how we have had multiple canceled flights and the employee said \"I'm going to walk away now.\"I started to get upset.. my wife made me walk away. We decided it wasn't worth our fight. Another hour at customer service. When we got to our hotel we were told we had no food accommodations and had to argue there for an hour, which then they only allowed us pizza for dinner. Whatever, it was food! Yet again, another day wasted. \n" + + "\n" + + "On the 28th our 7 am flight was canceled again due to a crew issue.. It was unbelievable. We had only gotten 4 hours of sleep. In response they put us on the 8 am flight. We ran to security, got to the gate and got loaded into a bus. After 20 minutes waiting to be driven to the plane our flight got canceled.. For the fourth time; and they announced it was a crew issue. We would now miss our flight home. When we got back into the airport the attendant told us to wait in an area to recieve further information. They had then come to us and told us they don't know where our checked bags went and may be lost and could take a few hours to have them returned. I was livid! This whole trip had become a comic book! We got our bags an hour later. We waited on customer service for another 3 hours and they told us we had to go 2 hours back to Gatwick Airport to catch a flight home and they would pay for our flight to the states. We called Norwegian, who we missed, and to reschedule our flights cost us 900 pounds, which we are hoping EasyJet will refund (they said they would, and wrote a notice in our account.. But who knows, my trust is gone). They drove us back to Gatwick and we stayed the night. \n" + + "\n" + + "So now today, on the 29th, we were told we had no check in bags on our account. We explained our insane situation and they still were hesitant to check a bag for us at no cost. Eventually after a long period of time they did. Now we await in the airport for our 5th flight to Amsterdam.. And hopefully then home. I won't ever choose this airline again. \n" + + "\n" + + "I understand the first cancelation, the second, third and fourth not at all. The people we dealt with were mostly aggressive, stressful, and non-caring. We totalled 19 hours dealing with customer service, we were told different things by different employees, failures in bookings, missed accommodations, etc.\n" + + "\n" + + "**UPDATE 1: Loaded onto a bus for the 5th flight and have turned around due to a technical failure on the plane! Currently in a permanent delay!! 5 flights!!!**\n" + + "\n" + + "**UPDATE 2: They are trying to divert a new plane for us to use.. May be another canceled**\n" + + "\n" + + "**UPDATE 3: FINALLY ARRIVED IN AMSTERDAM! It took EasyJet an additional 2 hours to get us a new plane and allow us to fly to Amsterdam, they weren't allowed any discretion to give us free water or snacks and were demanding it be charged even after everything. At any rate, now I need to wait a few days to fly home.. Hopefully that doesn't get fucked!!**\n" + + "\n" + + "TL;DR - Stuck in England from the 24th-29th, 4 canceled flights at 2 different airports with EasyJet. Driven to another airport and then back to the original airport. Three cancelations likely from crew issues. Miss managed accommodations, rude and aggressive employees, rescheduling our flights home, lost baggage... What a trip!"; + + @Test + public void test() throws IOException { + final int width = 128 * 5; + final int height = 128 * 5; + final List bufferedImages = new RedditMarkupToImageConverter().render(TEXT, width, height); + assertNotNull(bufferedImages); + assertFalse(bufferedImages.isEmpty()); + for(int i = 0; i Date: Mon, 5 Aug 2019 01:03:19 +0200 Subject: [PATCH 2/3] WIP Show selfs post and comments as images. --- pom.xml | 15 +- .../interaction/InteractiveEnum.java | 9 +- .../listeners/EventListener.java | 55 +++++- .../reddittext/CommentRenderer.java | 34 ++++ .../RedditMarkupToImageConverter.java | 22 ++- .../repository/PostToImageConverter.java | 4 - .../delta2force/redditbrowser/room/Room.java | 152 +++++------------ .../room/comments/CommentNavigator.java | 6 +- .../room/comments/CommentsControlStation.java | 156 ++++++++++++++++++ .../room/comments/CommentsController.java | 55 ++++-- .../comments/CommentsControllerFactory.java | 21 +++ .../room/screen/ScreenControlStation.java | 45 ++++- .../room/screen/ScreenController.java | 51 ++++-- .../room/screen/ScreenControllerFactory.java | 10 +- .../room/screen/ScreenModelType.java | 2 + .../RedditMarkupToImageConverterTest.java | 18 +- 16 files changed, 493 insertions(+), 162 deletions(-) delete mode 100644 src/main/java/me/delta2force/redditbrowser/repository/PostToImageConverter.java diff --git a/pom.xml b/pom.xml index 8a220b2..2fb4198 100644 --- a/pom.xml +++ b/pom.xml @@ -6,7 +6,7 @@ me.delta2force redditbrowser - 1.7 + 1.8 jar RedditBrowser @@ -35,6 +35,10 @@ org.apache.maven.plugins maven-shade-plugin 3.1.0 + + + false + package @@ -58,6 +62,14 @@ src/main/resources true + + + ${project.basedir} + + lib/*.jar + + + @@ -110,7 +122,6 @@ html2image 0.9 - org.junit.jupiter diff --git a/src/main/java/me/delta2force/redditbrowser/interaction/InteractiveEnum.java b/src/main/java/me/delta2force/redditbrowser/interaction/InteractiveEnum.java index 1ead467..99a13fb 100644 --- a/src/main/java/me/delta2force/redditbrowser/interaction/InteractiveEnum.java +++ b/src/main/java/me/delta2force/redditbrowser/interaction/InteractiveEnum.java @@ -6,12 +6,17 @@ public enum InteractiveEnum { COMMENT_CHEST, PREVIOUS_ROOM, NEXT_ROOM, - LOAD_COMMENTS, REFRESH, LEAVE, WRITE_COMMENT, SHOW_URL, SCROLL_DOWN, - SCROLL_UP; + SCROLL_UP, + SHOW_COMMENTS, + SHOW_POST, + PARENT_COMMENT, + CHILD_COMMENT, + PREVIOUS_COMMENT, + NEXT_COMMENT; } diff --git a/src/main/java/me/delta2force/redditbrowser/listeners/EventListener.java b/src/main/java/me/delta2force/redditbrowser/listeners/EventListener.java index 049ee44..81b87eb 100644 --- a/src/main/java/me/delta2force/redditbrowser/listeners/EventListener.java +++ b/src/main/java/me/delta2force/redditbrowser/listeners/EventListener.java @@ -110,13 +110,24 @@ public void run() { event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); } } - } else if (metadataContains(metadata, InteractiveEnum.LOAD_COMMENTS)) { + } else if (metadataContains(metadata, InteractiveEnum.SHOW_COMMENTS)) { if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); if (reddit.roomMap.containsKey(roomId)) { final Room room = reddit.roomMap.get(roomId); - room.displayComments(); + room.showComment(); + } else { + event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); + } + } + } else if (metadataContains(metadata, InteractiveEnum.SHOW_POST)) { + if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); + event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); + if (reddit.roomMap.containsKey(roomId)) { + final Room room = reddit.roomMap.get(roomId); + room.showPost(); } else { event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); } @@ -170,9 +181,43 @@ public void run() { } else { event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); } - - } - } + } else if (metadataContains(metadata, InteractiveEnum.PARENT_COMMENT) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); + if (reddit.roomMap.containsKey(roomId) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + final Room room = reddit.roomMap.get(roomId); + event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); + room.getCommentsController().parent(); + } else { + event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); + } + } else if (metadataContains(metadata, InteractiveEnum.CHILD_COMMENT) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); + if (reddit.roomMap.containsKey(roomId) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + final Room room = reddit.roomMap.get(roomId); + event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); + room.getCommentsController().child(); + } else { + event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); + } + } else if (metadataContains(metadata, InteractiveEnum.NEXT_COMMENT) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); + if (reddit.roomMap.containsKey(roomId) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + final Room room = reddit.roomMap.get(roomId); + event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); + room.getCommentsController().next(); + } else { + event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); + } + } else if (metadataContains(metadata, InteractiveEnum.PREVIOUS_COMMENT) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); + if (reddit.roomMap.containsKey(roomId) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + final Room room = reddit.roomMap.get(roomId); + event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); + room.getCommentsController().previous(); + } else { + event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); + } + } } } @EventHandler diff --git a/src/main/java/me/delta2force/redditbrowser/reddittext/CommentRenderer.java b/src/main/java/me/delta2force/redditbrowser/reddittext/CommentRenderer.java index 4c86399..09aa674 100644 --- a/src/main/java/me/delta2force/redditbrowser/reddittext/CommentRenderer.java +++ b/src/main/java/me/delta2force/redditbrowser/reddittext/CommentRenderer.java @@ -1,4 +1,38 @@ package me.delta2force.redditbrowser.reddittext; +import net.dean.jraw.models.Comment; + +import java.awt.image.BufferedImage; +import java.time.LocalDateTime; +import java.time.ZoneId; +import java.time.format.DateTimeFormatter; +import java.util.Date; +import java.util.List; + public class CommentRenderer { + + public static List createImageFrom( + Comment comment, + int width, + int height, + int blockHeight + ) { + final StringBuilder headerBuilder = new StringBuilder(); + final Date created = comment.getCreated(); + final LocalDateTime createdLocalDateTime = LocalDateTime.ofInstant(created.toInstant(), ZoneId.systemDefault()); + headerBuilder.append("
") + .append(comment.getAuthor()) + .append("") + .append(" - ") + .append(comment.getScore()) + .append(" points - ") + .append(createdLocalDateTime.format(DateTimeFormatter.ISO_DATE_TIME)) + .append("
"); + return RedditMarkupToImageConverter.render( + headerBuilder.toString(), + comment.getBody(), + width, + height, + blockHeight); + } } diff --git a/src/main/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverter.java b/src/main/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverter.java index c9edee4..e29e0d7 100644 --- a/src/main/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverter.java +++ b/src/main/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverter.java @@ -26,7 +26,7 @@ public class RedditMarkupToImageConverter { FORMAT_OPTIONS.set(Parser.EXTENSIONS, OPTIONS.get(Parser.EXTENSIONS)); } - public static List render(String text, int width, int height) { + public static List render(String htmlHeader, String text, int width, int height, int blockHeight) { Parser parser = Parser.builder(OPTIONS).build(); HtmlRenderer renderer = HtmlRenderer.builder(FORMAT_OPTIONS).build(); @@ -35,22 +35,32 @@ public static List render(String text, int width, int height) { String html = renderer.render(document); //Trying to force the width final double estimatedTextWidth = Math.floor(width * .7); - html = "
" + html + "
"; + StringBuilder stringBuilder = new StringBuilder(); + stringBuilder.append("
") + .append(htmlHeader) + .append(html) + .append("
"); final HtmlImageGenerator htmlImageGenerator = new HtmlImageGenerator(); htmlImageGenerator.setSize(new Dimension(width, height * 100)); - htmlImageGenerator.loadHtml(html); + htmlImageGenerator.loadHtml(stringBuilder.toString()); final BufferedImage bufferedImage = htmlImageGenerator.getBufferedImage(); BufferedImage whiteBackgroundBufferedImage = new BufferedImage(bufferedImage.getWidth(), bufferedImage.getHeight(), BufferedImage.TYPE_INT_RGB); final Graphics2D graphics = whiteBackgroundBufferedImage.createGraphics(); graphics.drawImage(bufferedImage, 0, 0, Color.WHITE, null); - return splitImage(whiteBackgroundBufferedImage, width, height); + return splitImage(whiteBackgroundBufferedImage, width, height, blockHeight); } - private static List splitImage(BufferedImage image, int width, int height) { + public static List render(String text, int width, int height, int blockHeight) { + return render(null, text, width, height, blockHeight); + } + + private static List splitImage(BufferedImage image, int width, int height,int blockHeight) { final List pages = new ArrayList<>(); - for(int y = 0; y startingPlayers) { final Submission submission = redditQueue.next(); if (submission != null) { currentSubmission = submission; - Bukkit.getScheduler().runTask(redditBrowserPlugin, () -> { + Bukkit.getScheduler().runTask( redditBrowserPlugin, () -> { createRoom(submission); Bukkit.getScheduler().runTaskLater(redditBrowserPlugin, () -> { @@ -209,7 +212,6 @@ private void updateRoom(Submission submission) { if (submission != null) { buildNavigationButton(); buildVoteButtons(submission); - buildCommentsButton(); buildRefreshButton(); buildLeaveButton(); buildSubredditHologram(submission); @@ -269,23 +271,6 @@ private void emptyCommentsChest() { } } - private void buildCommentsButton() { - Location chestLocation = location.clone().add(-roomDimensions.getRoomWidth() / 2, -roomDimensions.getRoomHeight() + 1, -roomDimensions.getRoomDepth() + 1); - final Block block = chestLocation.getBlock(); - block.setType(ROOM_MATERIAL); - Block commentButton = location.getWorld().getBlockAt(chestLocation.clone().add(0, 0, 1)); - commentButton.setType(Material.OAK_BUTTON); - commentButton.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(redditBrowserPlugin, InteractiveEnum.LOAD_COMMENTS)); - commentButton.setMetadata(ROOM_ID, new FixedMetadataValue(redditBrowserPlugin, owner.getUniqueId())); - commentButton.setMetadata(BUTTON_ACTIVATED, new FixedMetadataValue(redditBrowserPlugin, false)); - - Directional commentsButtonDirection = (Directional) commentButton.getBlockData(); - commentsButtonDirection.setFacing(BlockFace.SOUTH); - commentButton.setBlockData(commentsButtonDirection); - - spawnHologram(commentButton.getLocation().clone().add(.5, -2, .5), COMMENTS_HOLOGRAM); - } - private void buildEmptyRoom() { emptyCommentsChest(); cube(ROOM_MATERIAL, location, location.clone().add(-roomDimensions.getRoomWidth(), -roomDimensions.getRoomHeight(), -roomDimensions.getRoomDepth())); @@ -298,87 +283,6 @@ private void createRoom( updateRoom(submission); } - public void displayComments() { - Bukkit.getScheduler().runTaskAsynchronously(redditBrowserPlugin, () -> { - final RootCommentNode comments = redditBrowserPlugin.redditClient - .submission(currentSubmission.getId()) - .comments(); - Bukkit.getScheduler().runTask( - redditBrowserPlugin, - () -> buildCommentsChest(location, currentSubmission.getId(), comments, roomDimensions)); - }); - } - - private void buildCommentsChest( - Location location, - String submissionId, - RootCommentNode comments, - RoomDimensions roomDimensions) { - if (comments != null) { - buildNewCommentButton(); - Location chestLocation = location.clone().add(-roomDimensions.getRoomWidth() / 2, -roomDimensions.getRoomHeight() + 1, -roomDimensions.getRoomDepth() + 1); - final Location buttonLocation = chestLocation.clone().add(0, 0, 1); - buttonLocation.getBlock().setType(Material.AIR); - Block b = chestLocation.getBlock(); - - b.setType(Material.CHEST); - Directional chestDirection = (Directional) b.getBlockData(); - chestDirection.setFacing(BlockFace.SOUTH); - b.setBlockData(chestDirection); - b.setMetadata(SUBMISSION_ID, new FixedMetadataValue(redditBrowserPlugin, submissionId)); - b.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(redditBrowserPlugin, InteractiveEnum.COMMENT_CHEST)); - Chest chest = (Chest) b.getState(); - - chest.setCustomName(UUID.randomUUID().toString()); - - int in = 0; - for (CommentNode cn : comments.getReplies()) { - Comment c = cn.getSubject(); - if (in < 26) { - ItemStack book = new ItemStack(Material.WRITTEN_BOOK); - BookMeta bookmeta = (BookMeta) book.getItemMeta(); - bookmeta.setTitle("Comment"); - bookmeta.setAuthor("u/" + c.getAuthor()); - if (c.getBody().length() > 255) { - double f = ceil(((float) c.getBody().length()) / 255f); - for (int i = 0; i < f; i++) { - if (c.getBody().length() < (i + 1) * 255) { - bookmeta.addPage(c.getBody().substring(i * 255)); - } else { - bookmeta.addPage(c.getBody().substring(i * 255, (i + 1) * 255)); - } - } - } else { - bookmeta.addPage(c.getBody()); - } - bookmeta.setLore(Arrays.asList(c.getId(), c.getBody())); - bookmeta.setDisplayName(COMMENT_DISPLAY_NAME); - book.setItemMeta(bookmeta); - redditBrowserPlugin.commentCache.put(c.getId(), cn); - chest.getInventory().addItem(book); - } else { - break; - } - in++; - } - } - } - - private void buildNewCommentButton() { - Location buttonLocation = location.clone().add(-roomDimensions.getRoomWidth() / 2 - 1, -roomDimensions.getRoomHeight() + 1, -roomDimensions.getRoomDepth() + 1); - final Block writeCommentsButton = buttonLocation.getBlock(); - writeCommentsButton.setType(Material.OAK_BUTTON); - writeCommentsButton.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(redditBrowserPlugin, InteractiveEnum.WRITE_COMMENT)); - writeCommentsButton.setMetadata(ROOM_ID, new FixedMetadataValue(redditBrowserPlugin, owner.getUniqueId())); - writeCommentsButton.setMetadata(BUTTON_ACTIVATED, new FixedMetadataValue(redditBrowserPlugin, false)); - - Directional commentsButtonDirection = (Directional) writeCommentsButton.getBlockData(); - commentsButtonDirection.setFacing(BlockFace.SOUTH); - writeCommentsButton.setBlockData(commentsButtonDirection); - - spawnHologram(writeCommentsButton.getLocation().clone().add(.5, -2, .5), WRITE_COMMENT_HOLOGRAM); - } - private void removeNewCommentsButton() { Location buttonLocation = location.clone().add(-roomDimensions.getRoomWidth() / 2 - 1, -roomDimensions.getRoomHeight() + 1, -roomDimensions.getRoomDepth() + 1); final Block writeCommentsButton = buttonLocation.getBlock(); @@ -569,4 +473,36 @@ public RedditBrowserPlugin getRedditBrowserPlugin() { public ScreenController getScreenController() { return screenController; } + + public void showPost() { + if(currentSubmission != null) { + Bukkit.getScheduler().runTaskAsynchronously(redditBrowserPlugin, () -> { + final RootCommentNode comments = redditBrowserPlugin.redditClient + .submission(currentSubmission.getId()) + .comments(); + Bukkit.getScheduler().runTask( + redditBrowserPlugin, + () -> { + screenController.showPost(currentSubmission); + }); + }); + } + } + + public void showComment() { + if(currentSubmission != null) { + Bukkit.getScheduler().runTaskAsynchronously(redditBrowserPlugin, () -> { + final RootCommentNode comments = redditBrowserPlugin.redditClient + .submission(currentSubmission.getId()) + .comments(); + Bukkit.getScheduler().runTask( + redditBrowserPlugin, + () -> screenController.getCommentsController().updateComments(comments != null ? comments.getReplies(): Collections.emptyList())); + }); + } + } + + public CommentsController getCommentsController() { + return screenController.getCommentsController(); + } } diff --git a/src/main/java/me/delta2force/redditbrowser/room/comments/CommentNavigator.java b/src/main/java/me/delta2force/redditbrowser/room/comments/CommentNavigator.java index 00f7d24..f8e5014 100644 --- a/src/main/java/me/delta2force/redditbrowser/room/comments/CommentNavigator.java +++ b/src/main/java/me/delta2force/redditbrowser/room/comments/CommentNavigator.java @@ -1,4 +1,4 @@ -package me.delta2force.redditbrowser.room.screen; +package me.delta2force.redditbrowser.room.comments; import net.dean.jraw.models.Comment; import net.dean.jraw.tree.CommentNode; @@ -89,14 +89,14 @@ private Comment findElement(List path) { boolean first = true; for (int index : path) { if (first) { - if (commentNodes != null && index >= 0 && commentNodes.size() >= index) { + if (commentNodes != null && index >= 0 && commentNodes.size() > index) { lastNode = commentNodes.get(index); first = false; } else { return null; } - } else if (lastNode != null && index >= 0 && lastNode.getReplies().size() >= index) { + } else if (lastNode != null && index >= 0 && lastNode.getReplies().size() > index) { lastNode = lastNode.getReplies().get(index); } else { return null; diff --git a/src/main/java/me/delta2force/redditbrowser/room/comments/CommentsControlStation.java b/src/main/java/me/delta2force/redditbrowser/room/comments/CommentsControlStation.java index 7d8eab2..ed00259 100644 --- a/src/main/java/me/delta2force/redditbrowser/room/comments/CommentsControlStation.java +++ b/src/main/java/me/delta2force/redditbrowser/room/comments/CommentsControlStation.java @@ -1,4 +1,160 @@ package me.delta2force.redditbrowser.room.comments; +import me.delta2force.redditbrowser.interaction.InteractiveEnum; +import me.delta2force.redditbrowser.room.Room; +import me.delta2force.redditbrowser.room.screen.ScreenController; +import me.delta2force.redditbrowser.room.screen.ScreenModelType; +import org.bukkit.Location; +import org.bukkit.Material; +import org.bukkit.block.Block; +import org.bukkit.block.BlockFace; +import org.bukkit.block.Sign; +import org.bukkit.block.data.Directional; +import org.bukkit.metadata.FixedMetadataValue; + +import static me.delta2force.redditbrowser.RedditBrowserPlugin.*; + public class CommentsControlStation { + public static final String PARENT_COMMENT = "Parent comment"; + public static final String CHILD_COMMENT = "Child comment"; + public static final String NEXT_COMMENT = "Next comment"; + public static final String PREVIOUS_COMMENT = "Previous comment"; + private final Location location; + private final CommentsController commentsController; + private final ScreenController screenController; + private final Room room; + + public CommentsControlStation( + Location location, + CommentsController commentsController, + ScreenController screenController, + Room room) { + this.location = location; + this.commentsController = commentsController; + this.screenController = screenController; + this.room = room; + } + + public void build() { + if(ScreenModelType.COMMENT.equals(screenController.getScreenModelType())) { + buildParentButton(); + buildNextButton(); + buildPreviousButton(); + buildChildButton(); + } else { + clean(); + } + } + + public void clean() { + location.clone().add(0, 1, 1).getBlock().setType(Material.AIR); + location.clone().add(1, 1, 1).getBlock().setType(Material.AIR); + location.clone().add(1, 2, 1).getBlock().setType(Material.AIR); + location.clone().add(2, 1, 1).getBlock().setType(Material.AIR); + + location.clone().add(0, 1, 0).getBlock().setType(Material.AIR); + location.clone().add(1, 1, 0).getBlock().setType(Material.AIR); + location.clone().add(1, 2, 0).getBlock().setType(Material.AIR); + location.clone().add(2, 1, 0).getBlock().setType(Material.AIR); + } + + private void buildParentButton() { + final Location blockLocation = location.clone().add(0, 1, 0); + final Block block = blockLocation.getBlock(); + block.setType(room.getRoomMaterial()); + Block upButton = blockLocation.getWorld().getBlockAt(blockLocation.clone().add(0, 0, 1)); + + if(commentsController.canParent()) { + upButton.setType(Material.OAK_WALL_SIGN); + final Sign sign = (Sign) upButton.getState(); + sign.setLine(1, PARENT_COMMENT); + sign.setEditable(false); + sign.update(); + upButton.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(room.getRedditBrowserPlugin(), InteractiveEnum.PARENT_COMMENT)); + upButton.setMetadata(ROOM_ID, new FixedMetadataValue(room.getRedditBrowserPlugin(), room.getRoomId())); + upButton.setMetadata(BUTTON_ACTIVATED, new FixedMetadataValue(room.getRedditBrowserPlugin(), false)); + + Directional downButtonDirection = (Directional) upButton.getBlockData(); + downButtonDirection.setFacing(BlockFace.SOUTH); + upButton.setBlockData(downButtonDirection); + + } else { + upButton.setType(Material.AIR); + } + } + + private void buildChildButton() { + final Location blockLocation = location.clone().add(2, 1, 0); + final Block block = blockLocation.getBlock(); + block.setType(room.getRoomMaterial()); + Block button = blockLocation.getWorld().getBlockAt(blockLocation.clone().add(0, 0, 1)); + + if(commentsController.canChild()) { + button.setType(Material.OAK_WALL_SIGN); + final Sign sign = (Sign) button.getState(); + sign.setLine(1, CHILD_COMMENT); + sign.setEditable(false); + sign.update(); + button.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(room.getRedditBrowserPlugin(), InteractiveEnum.CHILD_COMMENT)); + button.setMetadata(ROOM_ID, new FixedMetadataValue(room.getRedditBrowserPlugin(), room.getRoomId())); + button.setMetadata(BUTTON_ACTIVATED, new FixedMetadataValue(room.getRedditBrowserPlugin(), false)); + + Directional downButtonDirection = (Directional) button.getBlockData(); + downButtonDirection.setFacing(BlockFace.SOUTH); + button.setBlockData(downButtonDirection); + + } else { + button.setType(Material.AIR); + } + } + + private void buildNextButton() { + final Location blockLocation = location.clone().add(1, 2, 0); + final Block block = blockLocation.getBlock(); + block.setType(room.getRoomMaterial()); + Block button = blockLocation.getWorld().getBlockAt(blockLocation.clone().add(0, 0, 1)); + + if(commentsController.canNext()) { + button.setType(Material.OAK_WALL_SIGN); + final Sign sign = (Sign) button.getState(); + sign.setLine(1, NEXT_COMMENT); + sign.setEditable(false); + sign.update(); + button.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(room.getRedditBrowserPlugin(), InteractiveEnum.NEXT_COMMENT)); + button.setMetadata(ROOM_ID, new FixedMetadataValue(room.getRedditBrowserPlugin(), room.getRoomId())); + button.setMetadata(BUTTON_ACTIVATED, new FixedMetadataValue(room.getRedditBrowserPlugin(), false)); + + Directional downButtonDirection = (Directional) button.getBlockData(); + downButtonDirection.setFacing(BlockFace.SOUTH); + button.setBlockData(downButtonDirection); + + } else { + button.setType(Material.AIR); + } + } + + private void buildPreviousButton() { + final Location blockLocation = location.clone().add(1, 1, 0); + final Block block = blockLocation.getBlock(); + block.setType(room.getRoomMaterial()); + Block button = blockLocation.getWorld().getBlockAt(blockLocation.clone().add(0, 0, 1)); + + if(commentsController.canPrevious()) { + button.setType(Material.OAK_WALL_SIGN); + final Sign sign = (Sign) button.getState(); + sign.setLine(1, PREVIOUS_COMMENT); + sign.setEditable(false); + sign.update(); + button.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(room.getRedditBrowserPlugin(), InteractiveEnum.PREVIOUS_COMMENT)); + button.setMetadata(ROOM_ID, new FixedMetadataValue(room.getRedditBrowserPlugin(), room.getRoomId())); + button.setMetadata(BUTTON_ACTIVATED, new FixedMetadataValue(room.getRedditBrowserPlugin(), false)); + + Directional downButtonDirection = (Directional) button.getBlockData(); + downButtonDirection.setFacing(BlockFace.SOUTH); + button.setBlockData(downButtonDirection); + + } else { + button.setType(Material.AIR); + } + } } diff --git a/src/main/java/me/delta2force/redditbrowser/room/comments/CommentsController.java b/src/main/java/me/delta2force/redditbrowser/room/comments/CommentsController.java index ad610a8..b332a87 100644 --- a/src/main/java/me/delta2force/redditbrowser/room/comments/CommentsController.java +++ b/src/main/java/me/delta2force/redditbrowser/room/comments/CommentsController.java @@ -1,5 +1,7 @@ -package me.delta2force.redditbrowser.room.screen; +package me.delta2force.redditbrowser.room.comments; +import me.delta2force.redditbrowser.room.screen.ScreenController; +import me.delta2force.redditbrowser.room.screen.ScreenModelType; import net.dean.jraw.models.Comment; import net.dean.jraw.tree.CommentNode; @@ -7,47 +9,80 @@ public class CommentsController { private CommentNavigator commentNavigator; + private CommentsControlStation commentsControlStation; + private ScreenController screenController; public CommentsController() { } + public void setScreenController(ScreenController screenController) { + this.screenController = screenController; + } + + public void setCommentsControlStation(CommentsControlStation commentsControlStation) { + this.commentsControlStation = commentsControlStation; + } + + public void update() { + commentsControlStation.build(); + if(ScreenModelType.COMMENT.equals(screenController.getScreenModelType())) { + screenController.showComment(commentNavigator.current()); + } + } + + public CommentsControlStation getCommentsControlStation() { + return commentsControlStation; + } + public void updateComments(List> commentNodeList) { commentNavigator = new CommentNavigator(commentNodeList); + screenController.showComment(commentNavigator.current()); } public Comment getCurrent() { - return commentNavigator.current(); + final Comment current = commentNavigator.current(); + commentsControlStation.build(); + return current; } public boolean canNext() { - return commentNavigator.canNext(); + return commentNavigator != null && commentNavigator.canNext(); } public boolean canPrevious() { - return commentNavigator.canPrevious(); + return commentNavigator != null && commentNavigator.canPrevious(); } public boolean canChild() { - return commentNavigator.canChild(); + return commentNavigator != null && commentNavigator.canChild(); } public boolean canParent() { - return commentNavigator.canParent(); + return commentNavigator != null && commentNavigator.canParent(); } public Comment next() { - return commentNavigator.next(); + final Comment comment = commentNavigator.next(); + update(); + return comment; } public Comment previous() { - return commentNavigator.previous(); + final Comment previous = commentNavigator.previous(); + update(); + + return previous; } public Comment child() { - return commentNavigator.child(); + final Comment child = commentNavigator.child(); + update(); + return child; } public Comment parent() { - return commentNavigator.parent(); + final Comment parent = commentNavigator.parent(); + update(); + return parent; } } diff --git a/src/main/java/me/delta2force/redditbrowser/room/comments/CommentsControllerFactory.java b/src/main/java/me/delta2force/redditbrowser/room/comments/CommentsControllerFactory.java index fa9219a..7be374d 100644 --- a/src/main/java/me/delta2force/redditbrowser/room/comments/CommentsControllerFactory.java +++ b/src/main/java/me/delta2force/redditbrowser/room/comments/CommentsControllerFactory.java @@ -1,4 +1,25 @@ package me.delta2force.redditbrowser.room.comments; +import me.delta2force.redditbrowser.room.Room; +import me.delta2force.redditbrowser.room.screen.ScreenController; +import org.bukkit.Location; + public class CommentsControllerFactory { + + public static CommentsController create( + Location location, + ScreenController screenController, + Room room + ) { + final CommentsController commentsController = new CommentsController(); + final CommentsControlStation commentsControlStation = new CommentsControlStation( + location, + commentsController, + screenController, + room + ); + commentsController.setCommentsControlStation(commentsControlStation); + commentsController.setScreenController(screenController); + return commentsController; + } } diff --git a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenControlStation.java b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenControlStation.java index a802e27..ef57dff 100644 --- a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenControlStation.java +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenControlStation.java @@ -12,15 +12,17 @@ import static me.delta2force.redditbrowser.RedditBrowserPlugin.*; -public class ControlStation { +public class ScreenControlStation { private static final String SCROLL_DOWN = "Scroll down"; private static final String SCROLL_UP = "Scroll up"; + private static final String SHOW_POST = "Show post"; + private static final String SHOW_COMMENTS = "Show comments"; private ScreenController screenController; private final Room room; private final Location location; + private ScreenModelType screenModelType = ScreenModelType.POST; - - public ControlStation(ScreenController screenController, Room room, Location location) { + public ScreenControlStation(ScreenController screenController, Room room, Location location) { this.screenController = screenController; this.room = room; this.location = location; @@ -29,18 +31,43 @@ public ControlStation(ScreenController screenController, Room room, Location loc public void build() { buildScrollDownButton(); buildScrollUpButton(); + buildCommentsSwitchButton(); + } + + private void buildCommentsSwitchButton() { + final Location blockLocation = location.clone().add(1,0,0); + final Block block = blockLocation.getBlock(); + block.setType(room.getRoomMaterial()); + Block showPostCommentsSwitch = blockLocation.getWorld().getBlockAt(blockLocation.clone().add(0, 0, 1)); + showPostCommentsSwitch.setType(Material.OAK_WALL_SIGN); + final Sign sign = (Sign) showPostCommentsSwitch.getState(); + if(ScreenModelType.POST.equals(screenController.getScreenModelType())) { + sign.setLine(1, SHOW_COMMENTS); + showPostCommentsSwitch.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(room.getRedditBrowserPlugin(), InteractiveEnum.SHOW_COMMENTS)); + } else { + sign.setLine(1, SHOW_POST); + showPostCommentsSwitch.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(room.getRedditBrowserPlugin(), InteractiveEnum.SHOW_POST)); + } + sign.setEditable(false); + sign.update(); + showPostCommentsSwitch.setMetadata(ROOM_ID, new FixedMetadataValue(room.getRedditBrowserPlugin(), room.getRoomId())); + showPostCommentsSwitch.setMetadata(BUTTON_ACTIVATED, new FixedMetadataValue(room.getRedditBrowserPlugin(), false)); + Directional downButtonDirection = (Directional) showPostCommentsSwitch.getBlockData(); + downButtonDirection.setFacing(BlockFace.SOUTH); + showPostCommentsSwitch.setBlockData(downButtonDirection); + } private void buildScrollDownButton() { final Location blockLocation = location.clone(); final Block block = blockLocation.getBlock(); - block.setType(Material.GOLD_BLOCK); + block.setType(room.getRoomMaterial()); Block downButton = blockLocation.getWorld().getBlockAt(blockLocation.clone().add(0, 0, 1)); if(screenController.canForward()) { downButton.setType(Material.OAK_WALL_SIGN); final Sign sign = (Sign) downButton.getState(); - sign.setLine(0, SCROLL_DOWN); + sign.setLine(1, SCROLL_DOWN); sign.setEditable(false); sign.update(); downButton.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(room.getRedditBrowserPlugin(), InteractiveEnum.SCROLL_DOWN)); @@ -59,13 +86,13 @@ private void buildScrollDownButton() { private void buildScrollUpButton() { final Location blockLocation = location.clone().add(0, 1, 0); final Block block = blockLocation.getBlock(); - block.setType(Material.GOLD_BLOCK); + block.setType(room.getRoomMaterial()); Block upButton = blockLocation.getWorld().getBlockAt(blockLocation.clone().add(0, 0, 1)); if(screenController.canBack()) { upButton.setType(Material.OAK_WALL_SIGN); final Sign sign = (Sign) upButton.getState(); - sign.setLine(0, SCROLL_UP); + sign.setLine(1, SCROLL_UP); sign.setEditable(false); sign.update(); upButton.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(room.getRedditBrowserPlugin(), InteractiveEnum.SCROLL_UP)); @@ -88,5 +115,9 @@ public void clean() { final Location blockLocation2 = location.clone().add(0, 2, 0); blockLocation2.getBlock().setType(Material.AIR); blockLocation2.clone().add(0, 0, 1).getBlock().setType(Material.AIR); + final Location blockLocation3 = location.clone().add(1, 1, 0); + blockLocation3.getBlock().setType(Material.AIR); + blockLocation3.clone().add(0, 0, 1).getBlock().setType(Material.AIR); + } } diff --git a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenController.java b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenController.java index 7b1adb0..adfc5fe 100644 --- a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenController.java +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenController.java @@ -1,7 +1,9 @@ package me.delta2force.redditbrowser.room.screen; +import me.delta2force.redditbrowser.reddittext.CommentRenderer; import me.delta2force.redditbrowser.reddittext.RedditMarkupToImageConverter; import me.delta2force.redditbrowser.repository.URLToImageRepository; +import me.delta2force.redditbrowser.room.comments.CommentsController; import net.dean.jraw.models.Comment; import net.dean.jraw.models.Submission; import org.bukkit.Bukkit; @@ -13,7 +15,8 @@ public class ScreenController { private Screen screen; private ScreenModel screenModel; - private ControlStation controlStation; + private ScreenControlStation screenControlStation; + private CommentsController commentsController; ScreenController() { } @@ -22,8 +25,12 @@ public void setScreen(Screen screen) { this.screen = screen; } - public void setControlStation(ControlStation controlStation) { - this.controlStation = controlStation; + public void setCommentsController(CommentsController commentsController) { + this.commentsController = commentsController; + } + + public void setScreenControlStation(ScreenControlStation screenControlStation) { + this.screenControlStation = screenControlStation; } public void showPost(Submission submission) { @@ -41,26 +48,38 @@ public void run() { }); } - private void update() { - screen.buildScreen(screenModel.getSelectedImage()); - controlStation.build(); - } - public void showComment(Comment comment) { + Bukkit.getScheduler().runTaskAsynchronously(screen.getRoom().getRedditBrowserPlugin(), () -> { + final List imageFrom = CommentRenderer.createImageFrom( + comment, + screen.getScreenWidth() * screen.getBlockPixels(), + screen.getScreenHeight() * screen.getBlockPixels(), + screen.getBlockPixels()); + screenModel = new ScreenModel(imageFrom, ScreenModelType.COMMENT); + Bukkit.getScheduler().runTaskAsynchronously(screen.getRoom().getRedditBrowserPlugin(), () -> { + Bukkit.getScheduler().runTask(screen.getRoom().getRedditBrowserPlugin(), this::update); + }); + }); + } + private void update() { + screen.buildScreen(screenModel.getSelectedImage()); + screenControlStation.build(); + commentsController.update(); } private ScreenModel findBufferedImagesForPost(Submission submission) { if(!submission.isSelfPost()) { final BufferedImage image = URLToImageRepository.findImage(submission); - return new ScreenModel(Collections.singletonList(image)); + return new ScreenModel(Collections.singletonList(image), ScreenModelType.POST); } else { final int blockPixels = screen.getBlockPixels(); final List bufferedImages = RedditMarkupToImageConverter.render( submission.getSelfText(), screen.getScreenWidth() * blockPixels / 2 , - screen.getScreenHeight() * blockPixels /2 ); - return new ScreenModel(bufferedImages); + screen.getScreenHeight() * blockPixels /2, + blockPixels); + return new ScreenModel(bufferedImages, ScreenModelType.POST); } } @@ -87,8 +106,16 @@ public void forward() { } } + public ScreenModelType getScreenModelType() { + return screenModel.getScreenModelType(); + } + public void clean() { screen.clean(); - controlStation.clean(); + screenControlStation.clean(); + } + + public CommentsController getCommentsController() { + return commentsController; } } diff --git a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenControllerFactory.java b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenControllerFactory.java index 931a6af..306541a 100644 --- a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenControllerFactory.java +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenControllerFactory.java @@ -1,6 +1,9 @@ package me.delta2force.redditbrowser.room.screen; import me.delta2force.redditbrowser.room.Room; +import me.delta2force.redditbrowser.room.comments.CommentsControlStation; +import me.delta2force.redditbrowser.room.comments.CommentsController; +import me.delta2force.redditbrowser.room.comments.CommentsControllerFactory; import org.bukkit.Location; public class ScreenControllerFactory { @@ -8,14 +11,17 @@ public class ScreenControllerFactory { public static ScreenController create(Room room, Location screenLocation, Location controlStationLocation, + Location commentsControlStationLocation, int screenWidth, int screenHeight) { final ScreenController screenController = new ScreenController(); final Screen screen = new Screen(room, screenLocation, screenWidth, screenHeight, screenController); - final ControlStation controlStation = new ControlStation(screenController, room, controlStationLocation); + final ScreenControlStation screenControlStation = new ScreenControlStation(screenController, room, controlStationLocation); screenController.setScreen(screen); - screenController.setControlStation(controlStation); + screenController.setScreenControlStation(screenControlStation); + final CommentsController commentsController = CommentsControllerFactory.create(commentsControlStationLocation, screenController, room); + screenController.setCommentsController(commentsController); return screenController; } } diff --git a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenModelType.java b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenModelType.java index d748376..034360d 100644 --- a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenModelType.java +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenModelType.java @@ -1,4 +1,6 @@ package me.delta2force.redditbrowser.room.screen; public enum ScreenModelType { + POST, + COMMENT } diff --git a/src/test/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverterTest.java b/src/test/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverterTest.java index 2cd182f..f115f35 100644 --- a/src/test/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverterTest.java +++ b/src/test/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverterTest.java @@ -50,7 +50,7 @@ public static void setup() { public void test() throws IOException { final int width = 128 * 5; final int height = 128 * 5; - final List bufferedImages = new RedditMarkupToImageConverter().render(TEXT, width, height); + final List bufferedImages = new RedditMarkupToImageConverter().render(TEXT, width, height, 128); assertNotNull(bufferedImages); assertFalse(bufferedImages.isEmpty()); for(int i = 0; i bufferedImages = new RedditMarkupToImageConverter().render("
nosir_nomaam - 10 points - 2019-07-29T21:23:18
", "Their faces are priceless!", width, height, 128); + assertNotNull(bufferedImages); + assertFalse(bufferedImages.isEmpty()); + for(int i = 0; i Date: Sat, 10 Aug 2019 05:50:02 +0200 Subject: [PATCH 3/3] New comments system You now directly reply to the post on screen or the comment on screen. You can also upvote/downvote the post or comment on the screen. --- pom.xml | 8 + .../redditbrowser/RedditBrowserPlugin.java | 4 +- .../interaction/InteractiveEnum.java | 2 +- .../listeners/EventListener.java | 367 +++++------------- .../reddittext/CommentRenderer.java | 5 +- .../RedditMarkupToImageConverter.java | 21 +- .../delta2force/redditbrowser/room/Room.java | 179 +++++++-- .../redditbrowser/room/screen/Screen.java | 2 - .../room/screen/ScreenController.java | 11 +- 9 files changed, 287 insertions(+), 312 deletions(-) diff --git a/pom.xml b/pom.xml index 2fb4198..bfe3d71 100644 --- a/pom.xml +++ b/pom.xml @@ -115,6 +115,14 @@ com.vladsch.flexmark mark-pdf-converter + + org.apache.pdfbox + * + + + com.openhtmltopdf + * +
diff --git a/src/main/java/me/delta2force/redditbrowser/RedditBrowserPlugin.java b/src/main/java/me/delta2force/redditbrowser/RedditBrowserPlugin.java index 912dd4c..c2129fc 100644 --- a/src/main/java/me/delta2force/redditbrowser/RedditBrowserPlugin.java +++ b/src/main/java/me/delta2force/redditbrowser/RedditBrowserPlugin.java @@ -221,8 +221,8 @@ private RoomDimensions createRoomDimensions(Client client) { } int roomHeight = screenHeight > 1 ? screenHeight + 3 : screenHeight + 3; int roomWidth = screenWidth >= 3 ? screenWidth + 3 : screenWidth + 2; - if (roomWidth < 5) { - roomWidth = 5; + if (roomWidth < 10) { + roomWidth = 10; } return new RoomDimensions( roomWidth, diff --git a/src/main/java/me/delta2force/redditbrowser/interaction/InteractiveEnum.java b/src/main/java/me/delta2force/redditbrowser/interaction/InteractiveEnum.java index 99a13fb..f26c5c4 100644 --- a/src/main/java/me/delta2force/redditbrowser/interaction/InteractiveEnum.java +++ b/src/main/java/me/delta2force/redditbrowser/interaction/InteractiveEnum.java @@ -3,7 +3,7 @@ public enum InteractiveEnum { UPVOTE, DOWNVOTE, - COMMENT_CHEST, + COMMENT_HOPPER, PREVIOUS_ROOM, NEXT_ROOM, REFRESH, diff --git a/src/main/java/me/delta2force/redditbrowser/listeners/EventListener.java b/src/main/java/me/delta2force/redditbrowser/listeners/EventListener.java index 81b87eb..d256af8 100644 --- a/src/main/java/me/delta2force/redditbrowser/listeners/EventListener.java +++ b/src/main/java/me/delta2force/redditbrowser/listeners/EventListener.java @@ -5,14 +5,12 @@ import me.delta2force.redditbrowser.room.Room; import net.dean.jraw.models.Comment; import net.dean.jraw.tree.CommentNode; - -import java.util.Arrays; -import java.util.List; -import java.util.Objects; -import java.util.UUID; - -import org.bukkit.*; +import org.bukkit.ChatColor; +import org.bukkit.Location; +import org.bukkit.Material; import org.bukkit.block.Chest; +import org.bukkit.block.Hopper; +import org.bukkit.entity.Item; import org.bukkit.entity.Player; import org.bukkit.event.EventHandler; import org.bukkit.event.Listener; @@ -22,16 +20,20 @@ import org.bukkit.event.hanging.HangingBreakEvent; import org.bukkit.event.inventory.InventoryClickEvent; import org.bukkit.event.inventory.InventoryCloseEvent; +import org.bukkit.event.inventory.InventoryPickupItemEvent; import org.bukkit.event.inventory.InventoryType; +import org.bukkit.event.player.PlayerInteractEntityEvent; import org.bukkit.event.player.PlayerInteractEvent; import org.bukkit.event.player.PlayerQuitEvent; import org.bukkit.inventory.Inventory; +import org.bukkit.inventory.InventoryHolder; import org.bukkit.inventory.ItemStack; import org.bukkit.inventory.meta.BookMeta; - import org.bukkit.metadata.FixedMetadataValue; import org.bukkit.metadata.MetadataValue; +import java.util.*; + import static me.delta2force.redditbrowser.room.Room.createWritableBookStack; public class EventListener implements Listener { @@ -43,119 +45,14 @@ public EventListener(RedditBrowserPlugin reddit) { this.reddit = reddit; } - @EventHandler - public void interact(PlayerInteractEvent event) { - if (event.getClickedBlock() != null - && Action.RIGHT_CLICK_BLOCK.equals(event.getAction()) - && event.getClickedBlock().hasMetadata(RedditBrowserPlugin.INTERACTIVE_ENUM)) { - List metadata = event.getClickedBlock().getMetadata(RedditBrowserPlugin.INTERACTIVE_ENUM); - if (metadataContains(metadata, InteractiveEnum.UPVOTE)) { - String submissionID = event.getClickedBlock().getMetadata(RedditBrowserPlugin.SUBMISSION_ID).get(0).asString(); - Bukkit.getScheduler().runTaskAsynchronously(reddit, new Runnable() { - @Override - public void run() { - reddit.redditClient.submission(submissionID).upvote(); - int karma = reddit.redditClient.submission(submissionID).inspect().getScore(); - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - if (reddit.roomMap.containsKey(roomId)) { - final Room room = reddit.roomMap.get(roomId); - room.getPlayers().forEach(player -> { - player.sendMessage(ChatColor.GREEN + "You have upvoted the post! It now has " + karma + " karma."); - player.playSound(event.getClickedBlock().getLocation(), Sound.ENTITY_VILLAGER_YES, VOLUME, 1); - }); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } - } - }); - } else if (metadataContains(metadata, InteractiveEnum.DOWNVOTE)) { - String submissionID = event.getClickedBlock().getMetadata(RedditBrowserPlugin.SUBMISSION_ID).get(0).asString(); - Bukkit.getScheduler().runTaskAsynchronously(reddit, new Runnable() { - @Override - public void run() { - event.getPlayer().playSound(event.getClickedBlock().getLocation(), Sound.ENTITY_VILLAGER_NO, VOLUME, 1); - reddit.redditClient.submission(submissionID).downvote(); - int karma = reddit.redditClient.submission(submissionID).inspect().getScore(); - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - if (reddit.roomMap.containsKey(roomId)) { - final Room room = reddit.roomMap.get(roomId); - room.getPlayers().forEach(player -> { - event.getPlayer().sendMessage(ChatColor.RED + "You have downvoted the post! It now has " + karma + " karma."); - player.playSound(event.getClickedBlock().getLocation(), Sound.ENTITY_VILLAGER_NO, VOLUME, 1); - }); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } } - }); - } else if (metadataContains(metadata, InteractiveEnum.NEXT_ROOM)) { - if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - if (reddit.roomMap.containsKey(roomId)) { - final Room room = reddit.roomMap.get(roomId); - room.nextPost(); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } - } - } else if (metadataContains(metadata, InteractiveEnum.PREVIOUS_ROOM)) { - if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - if (reddit.roomMap.containsKey(roomId)) { - final Room room = reddit.roomMap.get(roomId); - room.previousPost(); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } - } - } else if (metadataContains(metadata, InteractiveEnum.SHOW_COMMENTS)) { - if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - if (reddit.roomMap.containsKey(roomId)) { - final Room room = reddit.roomMap.get(roomId); - room.showComment(); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } - } - } else if (metadataContains(metadata, InteractiveEnum.SHOW_POST)) { - if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - if (reddit.roomMap.containsKey(roomId)) { - final Room room = reddit.roomMap.get(roomId); - room.showPost(); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } - } - } else if (metadataContains(metadata, InteractiveEnum.REFRESH)) { - if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - if (reddit.roomMap.containsKey(roomId)) { - final Room room = reddit.roomMap.get(roomId); - room.refresh(); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } - } - } else if (metadataContains(metadata, InteractiveEnum.LEAVE)) { - if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - reddit.kickOut(event.getPlayer()); - } - } else if (metadataContains(metadata, InteractiveEnum.WRITE_COMMENT)) { - if (!event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - final ItemStack writableBookStack = createWritableBookStack(); - event.getPlayer().getInventory().setItemInMainHand(writableBookStack); - } - } else if (metadataContains(metadata, InteractiveEnum.SHOW_URL)) { - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); + public void playerInteractEntity(PlayerInteractEntityEvent event) { + if (event.getRightClicked() != null + && event.getRightClicked().hasMetadata(RedditBrowserPlugin.INTERACTIVE_ENUM)) { + List metadata = event.getRightClicked().getMetadata(RedditBrowserPlugin.INTERACTIVE_ENUM); + + if (metadataContains(metadata, InteractiveEnum.SHOW_URL)) { + UUID roomId = (UUID) event.getRightClicked().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); if (reddit.roomMap.containsKey(roomId)) { final Room room = reddit.roomMap.get(roomId); room.showURLtoPlayers(event.getPlayer()); @@ -163,162 +60,109 @@ public void run() { event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); } event.setCancelled(true); - } else if (metadataContains(metadata, InteractiveEnum.SCROLL_UP)) { - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - if (reddit.roomMap.containsKey(roomId) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - final Room room = reddit.roomMap.get(roomId); - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - room.getScreenController().back(); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } - } else if (metadataContains(metadata, InteractiveEnum.SCROLL_DOWN) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - if (reddit.roomMap.containsKey(roomId) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - final Room room = reddit.roomMap.get(roomId); - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - room.getScreenController().forward(); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } - } else if (metadataContains(metadata, InteractiveEnum.PARENT_COMMENT) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - if (reddit.roomMap.containsKey(roomId) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - final Room room = reddit.roomMap.get(roomId); - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - room.getCommentsController().parent(); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } - } else if (metadataContains(metadata, InteractiveEnum.CHILD_COMMENT) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - if (reddit.roomMap.containsKey(roomId) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - final Room room = reddit.roomMap.get(roomId); - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - room.getCommentsController().child(); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } - } else if (metadataContains(metadata, InteractiveEnum.NEXT_COMMENT) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - if (reddit.roomMap.containsKey(roomId) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - final Room room = reddit.roomMap.get(roomId); - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - room.getCommentsController().next(); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } - } else if (metadataContains(metadata, InteractiveEnum.PREVIOUS_COMMENT) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); - if (reddit.roomMap.containsKey(roomId) && !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { - final Room room = reddit.roomMap.get(roomId); - event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); - room.getCommentsController().previous(); - } else { - event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); - } - } } + } + } } @EventHandler - public void interactInventory(InventoryClickEvent event) { - Player p = (Player) event.getWhoClicked(); - - if (event.getCurrentItem() != null && - event.getCurrentItem().getType().equals(Material.WRITTEN_BOOK) - && event.getInventory().getType().equals(InventoryType.CHEST) && event.isRightClick()) { - if (!event.getView().getTitle().startsWith("Comment ")) { - if (reddit.roomMap.values() - .stream() - .noneMatch(o -> o.hasPlayer(p.getUniqueId()))) { - return; - } - } - String commentID = event.getCurrentItem().getItemMeta().getLore().get(0); - List> replies = reddit.commentCache.get(commentID).getReplies(); - Inventory commentInventory = reddit.getServer().createInventory(event.getClickedInventory().getHolder(), InventoryType.CHEST, "Comment " + commentID); - int in = 0; - for (CommentNode cn : replies) { - Comment c = cn.getSubject(); - if (in < 26) { - ItemStack book = new ItemStack(Material.WRITTEN_BOOK); - BookMeta bookmeta = (BookMeta) book.getItemMeta(); - bookmeta.setTitle("Comment"); - bookmeta.setDisplayName(Room.COMMENT_DISPLAY_NAME); - bookmeta.setAuthor("u/" + c.getAuthor()); - if (c.getBody().length() > 255) { - double f = Math.ceil(((float) c.getBody().length()) / 255f); - for (int i = 0; i < f; i++) { - if (c.getBody().length() < (i + 1) * 255) { - bookmeta.addPage(c.getBody().substring(i * 255)); - } else { - bookmeta.addPage(c.getBody().substring(i * 255, (i + 1) * 255)); - } - } - } else { - bookmeta.addPage(c.getBody()); + public void closeInventory(InventoryCloseEvent event) { + if (event.getInventory().getHolder() instanceof Hopper) { + Hopper hopper = (Hopper) event.getInventory().getHolder(); + if (hopper.hasMetadata(RedditBrowserPlugin.INTERACTIVE_ENUM)) { + List metadata = hopper.getMetadata(RedditBrowserPlugin.INTERACTIVE_ENUM); + if (metadataContains(metadata, InteractiveEnum.COMMENT_HOPPER)) { + final ListIterator iterator = hopper.getInventory().iterator(); + while(iterator.hasNext()) { + final ItemStack itemStack = iterator.next(); + itemAddedToHopper(hopper, itemStack); } - bookmeta.setLore(Arrays.asList(c.getId(), c.getBody())); - book.setItemMeta(bookmeta); - reddit.commentCache.put(c.getId(), cn); - commentInventory.addItem(book); - } else { - break; + hopper.getInventory().clear(); } - in++; } - p.openInventory(commentInventory); } } + private void itemAddedToHopper(Hopper hopper, ItemStack itemStack) { + if(itemStack != null) { + UUID roomId = (UUID) hopper.getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); + if (reddit.roomMap.containsKey(roomId)) { + final Room room = reddit.roomMap.get(roomId); + if (Material.WRITTEN_BOOK.equals(itemStack.getType())) { + BookMeta bookMeta = (BookMeta) itemStack.getItemMeta(); + final String comment = String.join(" ", bookMeta.getPages()); + room.replyComment(comment); + } + } + } + } @EventHandler - public void closeInventory(InventoryCloseEvent event) { -// redditClient.setKarma((Player) event.getPlayer()); Overloading the server - - if (event.getView().getTitle().startsWith("Comment ")) { - String commentID = event.getView().getTitle().split(" ")[1]; - for (ItemStack is : event.getInventory().getContents()) { - if (is != null) { - if (is.getType() == Material.WRITTEN_BOOK) { - BookMeta bm = (BookMeta) is.getItemMeta(); - if (bm.getAuthor().equals(event.getPlayer().getName())) { - String comment = ""; - for (String page : bm.getPages()) { - comment += page + " "; - } - reddit.commentCache.get(commentID).getSubject().toReference(reddit.redditClient).reply(comment); - event.getPlayer().sendMessage(ChatColor.GREEN + "You have left a comment on a comment!"); - event.getPlayer().getInventory().addItem(createWritableBookStack()); - event.getInventory().remove(is); - } - } + public void inventoryPickedUp(InventoryPickupItemEvent inventoryPickupItemEvent) { + final InventoryHolder holder = inventoryPickupItemEvent.getInventory().getHolder(); + if (holder instanceof Hopper) { + final Hopper hopper = (Hopper) holder; + if (hopper.hasMetadata(RedditBrowserPlugin.INTERACTIVE_ENUM)) { + final List metadata = hopper.getMetadata(RedditBrowserPlugin.INTERACTIVE_ENUM); + if (metadataContains(metadata, InteractiveEnum.COMMENT_HOPPER)) { + final Item item = inventoryPickupItemEvent.getItem(); + final ItemStack itemStack = item.getItemStack(); + itemAddedToHopper(hopper, itemStack); + item.remove(); } } - } else if (event.getInventory().getHolder() instanceof Chest) { - Chest chest = (Chest) event.getInventory().getHolder(); - if (chest.hasMetadata(RedditBrowserPlugin.INTERACTIVE_ENUM)) { - List metadata = chest.getMetadata(RedditBrowserPlugin.INTERACTIVE_ENUM); - if (metadataContains(metadata, InteractiveEnum.COMMENT_CHEST)) { - String submissionID = chest.getMetadata(RedditBrowserPlugin.SUBMISSION_ID).get(0).asString(); - for (ItemStack is : event.getInventory().getContents()) { - if (is != null) { - if (is.getType() == Material.WRITTEN_BOOK) { - BookMeta bm = (BookMeta) is.getItemMeta(); - if (bm.getAuthor().equals(event.getPlayer().getName())) { - String comment = ""; - for (String page : bm.getPages()) { - comment += page + " "; - } - reddit.redditClient.submission(submissionID).reply(comment); - event.getPlayer().sendMessage(ChatColor.GREEN + "You have left a comment!"); - event.getPlayer().getInventory().addItem(createWritableBookStack()); - event.getInventory().remove(is); - } - } - } + } + } + + @EventHandler + public void interact(PlayerInteractEvent event) { + if (event.getClickedBlock() != null + && Action.RIGHT_CLICK_BLOCK.equals(event.getAction()) + && event.getClickedBlock().hasMetadata(RedditBrowserPlugin.INTERACTIVE_ENUM)) { + List metadata = event.getClickedBlock().getMetadata(RedditBrowserPlugin.INTERACTIVE_ENUM); + UUID roomId = (UUID) event.getClickedBlock().getMetadata(RedditBrowserPlugin.ROOM_ID).get(0).value(); + if (reddit.roomMap.containsKey(roomId)) { + final Room room = reddit.roomMap.get(roomId); + if (!event.getClickedBlock().hasMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED) || + !event.getClickedBlock().getMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED).get(0).asBoolean()) { + event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, true)); + if (metadataContains(metadata, InteractiveEnum.UPVOTE)) { + room.upvote(); + } else if (metadataContains(metadata, InteractiveEnum.DOWNVOTE)) { + room.downvote(); + } else if (metadataContains(metadata, InteractiveEnum.NEXT_ROOM)) { + room.nextPost(); + } else if (metadataContains(metadata, InteractiveEnum.PREVIOUS_ROOM)) { + room.previousPost(); + } else if (metadataContains(metadata, InteractiveEnum.SHOW_COMMENTS)) { + room.showComment(); + } else if (metadataContains(metadata, InteractiveEnum.SHOW_POST)) { + room.showPost(); + } else if (metadataContains(metadata, InteractiveEnum.REFRESH)) { + room.refresh(); + } else if (metadataContains(metadata, InteractiveEnum.LEAVE)) { + reddit.kickOut(event.getPlayer()); + } else if (metadataContains(metadata, InteractiveEnum.WRITE_COMMENT)) { + final ItemStack writableBookStack = createWritableBookStack(); + event.getPlayer().getInventory().setItemInMainHand(writableBookStack); + event.getClickedBlock().setMetadata(RedditBrowserPlugin.BUTTON_ACTIVATED, new FixedMetadataValue(reddit, false)); + } else if (metadataContains(metadata, InteractiveEnum.SCROLL_UP)) { + room.getScreenController().back(); + } else if (metadataContains(metadata, InteractiveEnum.SCROLL_DOWN)) { + room.getScreenController().forward(); + } else if (metadataContains(metadata, InteractiveEnum.PARENT_COMMENT)) { + room.getCommentsController().parent(); + } else if (metadataContains(metadata, InteractiveEnum.CHILD_COMMENT)) { + room.getCommentsController().child(); + } else if (metadataContains(metadata, InteractiveEnum.NEXT_COMMENT)) { + room.getCommentsController().next(); + } else if (metadataContains(metadata, InteractiveEnum.PREVIOUS_COMMENT)) { + room.getCommentsController().previous(); + } else if (metadataContains(metadata, InteractiveEnum.COMMENT_HOPPER)) { + event.setCancelled(true); } } + } else { + event.getPlayer().sendMessage(ChatColor.RED + "Room not found!"); } } } @@ -356,6 +200,7 @@ public void onBlockPlace(HangingBreakEvent hangingBreakEvent) { } } + private static boolean metadataContains(List values, Object value) { if (values != null && !values.isEmpty()) { return values.stream().anyMatch(o -> Objects.equals(o.value(), value)); diff --git a/src/main/java/me/delta2force/redditbrowser/reddittext/CommentRenderer.java b/src/main/java/me/delta2force/redditbrowser/reddittext/CommentRenderer.java index 09aa674..60d9574 100644 --- a/src/main/java/me/delta2force/redditbrowser/reddittext/CommentRenderer.java +++ b/src/main/java/me/delta2force/redditbrowser/reddittext/CommentRenderer.java @@ -6,6 +6,7 @@ import java.time.LocalDateTime; import java.time.ZoneId; import java.time.format.DateTimeFormatter; +import java.time.format.FormatStyle; import java.util.Date; import java.util.List; @@ -20,13 +21,13 @@ public static List createImageFrom( final StringBuilder headerBuilder = new StringBuilder(); final Date created = comment.getCreated(); final LocalDateTime createdLocalDateTime = LocalDateTime.ofInstant(created.toInstant(), ZoneId.systemDefault()); - headerBuilder.append("
") + headerBuilder.append("
") .append(comment.getAuthor()) .append("") .append(" - ") .append(comment.getScore()) .append(" points - ") - .append(createdLocalDateTime.format(DateTimeFormatter.ISO_DATE_TIME)) + .append(createdLocalDateTime.format(DateTimeFormatter.ofLocalizedDateTime(FormatStyle.SHORT))) .append("
"); return RedditMarkupToImageConverter.render( headerBuilder.toString(), diff --git a/src/main/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverter.java b/src/main/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverter.java index e29e0d7..c63fe0a 100644 --- a/src/main/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverter.java +++ b/src/main/java/me/delta2force/redditbrowser/reddittext/RedditMarkupToImageConverter.java @@ -8,6 +8,7 @@ import com.vladsch.flexmark.util.data.DataHolder; import com.vladsch.flexmark.util.data.MutableDataSet; import gui.ava.html.image.generator.HtmlImageGenerator; +import org.apache.commons.lang.StringUtils; import java.awt.*; import java.awt.image.BufferedImage; @@ -21,12 +22,13 @@ public class RedditMarkupToImageConverter { ); static final MutableDataSet FORMAT_OPTIONS = new MutableDataSet(); + static { // copy extensions from Pegdown compatible to Formatting, but leave the rest default FORMAT_OPTIONS.set(Parser.EXTENSIONS, OPTIONS.get(Parser.EXTENSIONS)); } - public static List render(String htmlHeader, String text, int width, int height, int blockHeight) { + public static List render(String htmlHeader, String text, int width, int height, int blockHeight) { Parser parser = Parser.builder(OPTIONS).build(); HtmlRenderer renderer = HtmlRenderer.builder(FORMAT_OPTIONS).build(); @@ -36,10 +38,13 @@ public static List render(String htmlHeader, String text, int wi //Trying to force the width final double estimatedTextWidth = Math.floor(width * .7); StringBuilder stringBuilder = new StringBuilder(); - stringBuilder.append("
") - .append(htmlHeader) + .append("px; word-break: break-all; overflow-wrap: break-word;\">"); + if (StringUtils.isNotBlank(htmlHeader)) { + stringBuilder.append(htmlHeader); + } + stringBuilder .append(html) .append("
"); @@ -54,18 +59,18 @@ public static List render(String htmlHeader, String text, int wi return splitImage(whiteBackgroundBufferedImage, width, height, blockHeight); } - public static List render(String text, int width, int height, int blockHeight) { + public static List render(String text, int width, int height, int blockHeight) { return render(null, text, width, height, blockHeight); } - private static List splitImage(BufferedImage image, int width, int height,int blockHeight) { + private static List splitImage(BufferedImage image, int width, int height, int blockHeight) { final List pages = new ArrayList<>(); - for(int y = 0; y startingPlayers) { final Submission submission = redditQueue.next(); if (submission != null) { currentSubmission = submission; - Bukkit.getScheduler().runTask( redditBrowserPlugin, () -> { + Bukkit.getScheduler().runTask(redditBrowserPlugin, () -> { createRoom(submission); Bukkit.getScheduler().runTaskLater(redditBrowserPlugin, () -> { @@ -205,28 +214,26 @@ public void previousPost() { private void updateRoom(Submission submission) { removeHologramByType(location, EntityType.ARMOR_STAND); - emptyCommentsChest(); + emptyCommentsHopper(); buildLeaveButton(); removeNewCommentsButton(); screenController.showPost(submission); + removeHopper(); if (submission != null) { buildNavigationButton(); buildVoteButtons(submission); + buildNewCommentButton(); + buildCommentHopper(); buildRefreshButton(); buildLeaveButton(); buildSubredditHologram(submission); - realignItemFrames(); } } - private void realignItemFrames() { - location.getWorld() - .getNearbyEntities(location, - -roomDimensions.getRoomWidth(), - -roomDimensions.getRoomHeight(), - -roomDimensions.getRoomDepth(), - o -> Objects.equals(EntityType.ITEM_FRAME, o.getType())) - .forEach(o -> ((ItemFrame) o).setRotation(Rotation.NONE)); + private void removeHopper() { + Location chopperLocation = location.clone().add(-roomDimensions.getRoomWidth() / 2, -roomDimensions.getRoomHeight(), -roomDimensions.getRoomDepth() + 1); + final Block hopper = chopperLocation.getBlock(); + hopper.setType(Material.AIR); } private void buildSubredditHologram(Submission submission) { @@ -238,6 +245,7 @@ private void buildSubredditHologram(Submission submission) { .clone().add(.5, -2, .5), colorCode("a") + "r/" + submission.getSubreddit()); } + private void buildRefreshButton() { Block refreshButton = location.getWorld().getBlockAt(location.clone().add(-(roomDimensions.getRoomWidth() / 2), -roomDimensions.getRoomHeight() + 2, -1)); refreshButton.setType(Material.OAK_BUTTON); @@ -250,6 +258,31 @@ private void buildRefreshButton() { spawnHologram(refreshButton.getLocation().clone().add(.5, -2, .5), colorCode("a") + "Refresh"); } + private void buildNewCommentButton() { + Location buttonLocation = location.clone().add(-roomDimensions.getRoomWidth() / 2 - 1, -roomDimensions.getRoomHeight() + 1, -roomDimensions.getRoomDepth() + 1); + final Block writeCommentsButton = buttonLocation.getBlock(); + writeCommentsButton.setType(Material.OAK_BUTTON); + writeCommentsButton.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(redditBrowserPlugin, InteractiveEnum.WRITE_COMMENT)); + writeCommentsButton.setMetadata(ROOM_ID, new FixedMetadataValue(redditBrowserPlugin, owner.getUniqueId())); + writeCommentsButton.setMetadata(BUTTON_ACTIVATED, new FixedMetadataValue(redditBrowserPlugin, false)); + + Directional commentsButtonDirection = (Directional) writeCommentsButton.getBlockData(); + commentsButtonDirection.setFacing(BlockFace.SOUTH); + writeCommentsButton.setBlockData(commentsButtonDirection); + + spawnHologram(writeCommentsButton.getLocation().clone().add(.5, -2, .5), WRITE_COMMENT_HOLOGRAM); + } + + private void buildCommentHopper() { + Location chopperLocation = location.clone().add(-roomDimensions.getRoomWidth() / 2, -roomDimensions.getRoomHeight(), -roomDimensions.getRoomDepth() + 1); + final Block hopper = chopperLocation.getBlock(); + hopper.setType(Material.HOPPER); + hopper.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(redditBrowserPlugin, InteractiveEnum.COMMENT_HOPPER)); + hopper.setMetadata(ROOM_ID, new FixedMetadataValue(redditBrowserPlugin, owner.getUniqueId())); + spawnHologram(hopper.getLocation().clone().add(.5, -2, .5), REPLY_COMMENT_HOLOGRAM); + } + + private void buildLeaveButton() { Block leaveButton = location.getWorld().getBlockAt(location.clone().add(-(roomDimensions.getRoomWidth() / 2) - 1, -roomDimensions.getRoomHeight() + 2, -1)); leaveButton.setType(Material.OAK_BUTTON); @@ -262,17 +295,17 @@ private void buildLeaveButton() { spawnHologram(leaveButton.getLocation().clone().add(.5, -2, .5), colorCode("c") + "Leave"); } - private void emptyCommentsChest() { - Location chestLocation = location.clone().add(-roomDimensions.getRoomWidth() / 2, -roomDimensions.getRoomHeight() + 1, -roomDimensions.getRoomDepth() + 1); + private void emptyCommentsHopper() { + Location chestLocation = location.clone().add(-roomDimensions.getRoomWidth() / 2, -roomDimensions.getRoomHeight(), -roomDimensions.getRoomDepth() + 1); final Block block = chestLocation.getBlock(); - if (Material.CHEST.equals(block.getType())) { - Chest chest = (Chest) block.getState(); - chest.getBlockInventory().clear(); + if (Material.HOPPER.equals(block.getType())) { + Hopper hopper = (Hopper) block.getState(); + hopper.getInventory().clear(); } } private void buildEmptyRoom() { - emptyCommentsChest(); + emptyCommentsHopper(); cube(ROOM_MATERIAL, location, location.clone().add(-roomDimensions.getRoomWidth(), -roomDimensions.getRoomHeight(), -roomDimensions.getRoomDepth())); cube(Material.AIR, location.clone().add(-1, -1, -1), location.clone().add(-roomDimensions.getRoomWidth() + 1, -roomDimensions.getRoomHeight() + 1, -roomDimensions.getRoomDepth() + 1)); } @@ -307,6 +340,7 @@ private void buildVoteButtons(Submission submission) { dv.setMetadata(ROOM_ID, new FixedMetadataValue(redditBrowserPlugin, getRoomId())); dv.setMetadata(INTERACTIVE_ENUM, new FixedMetadataValue(redditBrowserPlugin, InteractiveEnum.DOWNVOTE)); + Directional dvdir = (Directional) dv.getBlockData(); dvdir.setFacing(BlockFace.SOUTH); dv.setBlockData(dvdir); @@ -315,7 +349,6 @@ private void buildVoteButtons(Submission submission) { } - private void buildNavigationButton() { int zPosition = (-roomDimensions.getRoomDepth() / 2) + 1; if (zPosition > -2) { @@ -475,14 +508,11 @@ public ScreenController getScreenController() { } public void showPost() { - if(currentSubmission != null) { + if (currentSubmission != null) { Bukkit.getScheduler().runTaskAsynchronously(redditBrowserPlugin, () -> { - final RootCommentNode comments = redditBrowserPlugin.redditClient - .submission(currentSubmission.getId()) - .comments(); Bukkit.getScheduler().runTask( redditBrowserPlugin, - () -> { + () -> { screenController.showPost(currentSubmission); }); }); @@ -490,14 +520,14 @@ public void showPost() { } public void showComment() { - if(currentSubmission != null) { + if (currentSubmission != null) { Bukkit.getScheduler().runTaskAsynchronously(redditBrowserPlugin, () -> { final RootCommentNode comments = redditBrowserPlugin.redditClient .submission(currentSubmission.getId()) .comments(); Bukkit.getScheduler().runTask( redditBrowserPlugin, - () -> screenController.getCommentsController().updateComments(comments != null ? comments.getReplies(): Collections.emptyList())); + () -> screenController.getCommentsController().updateComments(comments != null ? comments.getReplies() : Collections.emptyList())); }); } } @@ -505,4 +535,91 @@ public void showComment() { public CommentsController getCommentsController() { return screenController.getCommentsController(); } + + public void replyComment(String comment) { + if (ScreenModelType.POST.equals(getScreenController().getScreenModelType())) { + if (currentSubmission != null) { + final String currentSubmissionId = currentSubmission.getId(); + Bukkit.getScheduler().runTaskAsynchronously(redditBrowserPlugin, () -> { + try { + redditBrowserPlugin.redditClient + .submission(currentSubmissionId) + .reply(comment); + getPlayers().forEach(p -> p.sendMessage("You've replied to the post!")); + } catch (ApiException apiException) { + getPlayers().forEach(p->p.sendMessage("Error occurred: " + apiException.getExplanation())); + } + }); + } + } else if (ScreenModelType.COMMENT.equals(getScreenController().getScreenModelType())) { + final Comment current = getCommentsController().getCurrent(); + if (current != null) { + final String currentId = current.getId(); + Bukkit.getScheduler().runTaskAsynchronously(redditBrowserPlugin, () -> { + try { + redditBrowserPlugin.redditClient.comment(currentId).reply(comment); + getPlayers().forEach(p -> p.sendMessage("You've replied to the comment!")); + } catch (ApiException apiException) { + getPlayers().forEach(p->p.sendMessage("Error occurred: " + apiException.getExplanation())); + } + }); + } + } + } + + public void upvote() { + if (ScreenModelType.POST.equals(getScreenController().getScreenModelType())) { + if (currentSubmission != null) { + final String currentSubmissionId = currentSubmission.getId(); + Bukkit.getScheduler().runTaskAsynchronously(redditBrowserPlugin, () -> { + redditBrowserPlugin.redditClient.submission(currentSubmissionId).upvote(); + int karma = redditBrowserPlugin.redditClient.submission(currentSubmissionId).inspect().getScore(); + getPlayers().forEach(player -> { + player.sendMessage(ChatColor.GREEN + "You have upvoted the post! It now has " + karma + " karma."); + player.playSound(location, Sound.ENTITY_VILLAGER_YES, VOLUME, 1); + }); + }); + } + } else if (ScreenModelType.COMMENT.equals(getScreenController().getScreenModelType())) { + final Comment current = getCommentsController().getCurrent(); + if (current != null) { + final String currentId = current.getId(); + Bukkit.getScheduler().runTaskAsynchronously(redditBrowserPlugin, () -> { + redditBrowserPlugin.redditClient.comment(currentId).upvote(); + getPlayers().forEach(player -> { + player.sendMessage(ChatColor.GREEN + "You have upvoted the comment!"); + player.playSound(location, Sound.ENTITY_VILLAGER_YES, VOLUME, 1); + }); + }); + } + } + } + + public void downvote() { + if (ScreenModelType.POST.equals(getScreenController().getScreenModelType())) { + if (currentSubmission != null) { + final String currentSubmissionId = currentSubmission.getId(); + Bukkit.getScheduler().runTaskAsynchronously(redditBrowserPlugin, () -> { + redditBrowserPlugin.redditClient.submission(currentSubmissionId).downvote(); + int karma = redditBrowserPlugin.redditClient.submission(currentSubmissionId).inspect().getScore(); + getPlayers().forEach(player -> { + player.sendMessage(ChatColor.RED + "You have downvoted the post! It now has " + karma + " karma."); + player.playSound(location, Sound.ENTITY_VILLAGER_NO, VOLUME, 1); + }); + }); + } + } else if (ScreenModelType.COMMENT.equals(getScreenController().getScreenModelType())) { + final Comment current = getCommentsController().getCurrent(); + if (current != null) { + final String currentId = current.getId(); + Bukkit.getScheduler().runTaskAsynchronously(redditBrowserPlugin, () -> { + redditBrowserPlugin.redditClient.comment(currentId).upvote(); + getPlayers().forEach(player -> { + player.sendMessage(ChatColor.RED + "You have downvoted the comment!"); + player.playSound(location, Sound.ENTITY_VILLAGER_NO, VOLUME, 1); + }); + }); + } + } + } } diff --git a/src/main/java/me/delta2force/redditbrowser/room/screen/Screen.java b/src/main/java/me/delta2force/redditbrowser/room/screen/Screen.java index 60e4977..b6ea553 100644 --- a/src/main/java/me/delta2force/redditbrowser/room/screen/Screen.java +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/Screen.java @@ -64,8 +64,6 @@ public void buildScreen(BufferedImage bufferedImage) { MapMeta mapMeta = (MapMeta) map.getItemMeta(); MapView mapView = Bukkit.createMap(world); mapView.setTrackingPosition(false); - mapView.setLocked(true); - mapView.setUnlimitedTracking(false); mapView.getRenderers().forEach(mapView::removeRenderer); mapView.addRenderer(tiledRenderer.getRenderer(row, col)); mapMeta.setMapView(mapView); diff --git a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenController.java b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenController.java index adfc5fe..35c6866 100644 --- a/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenController.java +++ b/src/main/java/me/delta2force/redditbrowser/room/screen/ScreenController.java @@ -63,9 +63,9 @@ public void showComment(Comment comment) { } private void update() { - screen.buildScreen(screenModel.getSelectedImage()); - screenControlStation.build(); - commentsController.update(); + screen.buildScreen(screenModel != null ? screenModel.getSelectedImage() : null); + screenControlStation.build(); + commentsController.update(); } private ScreenModel findBufferedImagesForPost(Submission submission) { @@ -85,11 +85,11 @@ private ScreenModel findBufferedImagesForPost(Submission submission) { public boolean canBack() { - return screenModel.getSelectedIndex() > 0; + return screenModel != null && screenModel.getSelectedIndex() > 0; } public boolean canForward() { - return screenModel.getImages().size() > screenModel.getSelectedIndex() +1; + return screenModel != null && screenModel.getImages().size() > screenModel.getSelectedIndex() +1; } public void back() { @@ -112,6 +112,7 @@ public ScreenModelType getScreenModelType() { public void clean() { screen.clean(); + screenModel = null; screenControlStation.clean(); }