diff --git a/build.gradle b/build.gradle index b590cf7..c62e57d 100644 --- a/build.gradle +++ b/build.gradle @@ -18,7 +18,7 @@ repositories { } dependencies { - compileOnly "org.spigotmc:spigot-api:1.19.4-R0.1-SNAPSHOT" + compileOnly "org.spigotmc:spigot-api:1.20.2-R0.1-SNAPSHOT" } def targetJavaVersion = 17 @@ -31,6 +31,10 @@ java { } } +jar { + destinationDirectory.set(file("/Users/linusglimm/Desktop/mineopoly stuff/servers/spigotTest/plugins")) +} + tasks.withType(JavaCompile).configureEach { options.encoding = 'UTF-8' @@ -46,4 +50,4 @@ processResources { filesMatching('plugin.yml') { expand props } -} +} \ No newline at end of file diff --git a/src/main/java/de/littleprogrammer/guiapi/Api.java b/src/main/java/de/littleprogrammer/guiapi/Api.java deleted file mode 100644 index 712d889..0000000 --- a/src/main/java/de/littleprogrammer/guiapi/Api.java +++ /dev/null @@ -1,17 +0,0 @@ -package de.littleprogrammer.guiapi; - -import org.bukkit.plugin.java.JavaPlugin; - -public final class Api extends JavaPlugin { - - @Override - public void onEnable() { - // Plugin startup logic - - } - - @Override - public void onDisable() { - // Plugin shutdown logic - } -} diff --git a/src/main/java/de/littleprogrammer/guiapi/GuiApi.java b/src/main/java/de/littleprogrammer/guiapi/GuiApi.java new file mode 100644 index 0000000..932ead0 --- /dev/null +++ b/src/main/java/de/littleprogrammer/guiapi/GuiApi.java @@ -0,0 +1,93 @@ +package de.littleprogrammer.guiapi; + +import de.littleprogrammer.guiapi.enums.ServerVersion; +import de.littleprogrammer.guiapi.listeners.GuiEvents; +import de.littleprogrammer.guiapi.listeners.MoveListener; +import org.bukkit.Bukkit; +import org.bukkit.entity.Player; +import org.bukkit.event.Listener; +import org.bukkit.plugin.java.JavaPlugin; +import org.bukkit.scheduler.BukkitScheduler; + +import java.util.HashMap; +import java.util.Map; +import java.util.UUID; + +public final class GuiApi { + + private JavaPlugin plugin; + private static GuiApi instance; + private ServerVersion version; + private final Listener listener = new GuiEvents(); + private final Listener moveListener = new MoveListener(); + private Map guis = new HashMap<>(); + + public GuiApi(JavaPlugin plugin) { + this.plugin = plugin; + instance = this; + } + + /*@Override + public void onEnable() { + // Plugin startup logic + this.plugin = this; + instance = this; + + init(); + } + + @Override + public void onDisable() { + // Plugin shutdown logic + }*/ + + public void init() { + //This method checks the server version, to determine weather it should use the new 1.20.2 teleport interpolation or my own teleport interpolation + String secIndicator = plugin.getServer().getBukkitVersion().split("\\.")[1]; + String preTrdIndicator = plugin.getServer().getBukkitVersion().split("\\.")[2]; + String trdIndicator = preTrdIndicator.split("-")[0]; + + if (Integer.parseInt(secIndicator) == 20) { + if (Integer.parseInt(trdIndicator) >= 2) { + version = ServerVersion.POST_1_20_2; + } else { + version = ServerVersion.PRE_1_20_2; + } + } else { + if (Integer.parseInt(secIndicator) > 20) { + version = ServerVersion.POST_1_20_2; + } else { + version = ServerVersion.PRE_1_20_2; + } + } + + //register the two listeners needed + getPlugin().getServer().getPluginManager().registerEvents(this.listener, this.plugin); + getPlugin().getServer().getPluginManager().registerEvents(this.moveListener, this.plugin); + } + + public JavaPlugin getPlugin() {return this.plugin;} + public static GuiApi getInstance() {return instance;} + public ServerVersion getVersion() { + return version; + } + public static BukkitScheduler getScheduler() { + return GuiApi.getInstance().getPlugin().getServer().getScheduler(); + } + + public SimpleGui getGUI(UUID uuid) { + return guis.get(uuid); + } + + public SimpleGui getGUI(Player player) { + return guis.get(player.getUniqueId()); + } + + public Map getGuis() { + return guis; + } + + public Listener getListener() { + return listener; + } +} diff --git a/src/main/java/de/littleprogrammer/guiapi/SimpleGui.java b/src/main/java/de/littleprogrammer/guiapi/SimpleGui.java new file mode 100644 index 0000000..9d898f7 --- /dev/null +++ b/src/main/java/de/littleprogrammer/guiapi/SimpleGui.java @@ -0,0 +1,125 @@ +package de.littleprogrammer.guiapi; + +import de.littleprogrammer.guiapi.components.Button; +import de.littleprogrammer.guiapi.components.Component; +import de.littleprogrammer.guiapi.components.Text; +import de.littleprogrammer.guiapi.enums.ServerVersion; +import de.littleprogrammer.guiapi.utils.Calculations; +import de.littleprogrammer.guiapi.utils.TeleportInterpolator; +import org.bukkit.Location; +import org.bukkit.entity.Player; + +import java.util.*; + +public class SimpleGui { + + private Player player; + private final UUID uuid; + private final Map components; + private final Map buttons; + private final String title; + private Component content; + private Location centerLocation; + private boolean open; + + public SimpleGui(String title) { + this.title = title; + this.uuid = UUID.randomUUID(); + this.components = new HashMap<>(); + this.buttons = new HashMap<>(); + } + + public void updatePosition(Location playerLoc) { + if (player != null) { + centerLocation = Calculations.calculateInventoryCenter(playerLoc); + + if (GuiApi.getInstance().getVersion().equals(ServerVersion.PRE_1_20_2)) { + for (Component component : components.values()) { + Location newComponentLocation = Calculations.calculateComponentLocation(this, component, buttons.size()); + + TeleportInterpolator teleportInterpolator = new TeleportInterpolator(component.getEntity(), newComponentLocation, 5, 1); + teleportInterpolator.startInterpolation(); + } + } else { + for (Component component : components.values()) { + Location newComponentLocation = Calculations.calculateComponentLocation(this, component, buttons.size()); + + component.getDisplay().setTeleportDuration(5); + component.getDisplay().teleport(newComponentLocation); + } + } + } + } + + public void close() { + //close GUI + GuiApi.getInstance().getGuis().remove(player.getUniqueId()); + + for (Component component : components.values()) { + component.hide(player); + component.remove(); + } + open = false; + } + + public SimpleGui open(Player player) { + if (this.player != null && this.player.getUniqueId().equals(player.getUniqueId())) { + //close GUI and open for the new player + close(); + } + this.player = player; + GuiApi.getInstance().getGuis().put(player.getUniqueId(), this); + centerLocation = new Location(player.getWorld(), 0, 0, 0); + + for (Component component : components.values()) { + component.spawn(); + component.show(player); + } + open = true; + return this; + } + + public Component getComponent(UUID uuid) { + return components.get(uuid); + } + + public Location getCenterLocation() { + return centerLocation; + } + + public Player getPlayer() { + return player; + } + + public List getComponents() { + return new ArrayList<>(components.values()); + } + + public int getButtonAmount() { + return buttons.size(); + } + + public boolean isOpen() { + return open; + } + + public SimpleGui addButton(Button button) { + if (buttons.size() < 3) { + components.put(button.getUniqueId(), button); + buttons.put(button.getUniqueId(), button); + button.setGui(this); + } + return this; + } + + public SimpleGui addContent(Text content) { + if (this.content != null) { + components.remove(this.content.getUniqueId()); + this.content.remove(); + } + this.content = content; + components.put(content.getUniqueId(), content); + content.setGui(this); + return this; + } +} diff --git a/src/main/java/de/littleprogrammer/guiapi/components/Button.java b/src/main/java/de/littleprogrammer/guiapi/components/Button.java new file mode 100644 index 0000000..12cdc3e --- /dev/null +++ b/src/main/java/de/littleprogrammer/guiapi/components/Button.java @@ -0,0 +1,154 @@ +package de.littleprogrammer.guiapi.components; + +import de.littleprogrammer.guiapi.GuiApi; +import de.littleprogrammer.guiapi.SimpleGui; +import de.littleprogrammer.guiapi.customeEvents.HoverButtonEvent; +import de.littleprogrammer.guiapi.customeEvents.UnHoverButtonEvent; +import de.littleprogrammer.guiapi.utils.Calculations; +import org.bukkit.Location; +import org.bukkit.entity.*; +import org.bukkit.event.player.PlayerInteractEntityEvent; +import org.bukkit.util.Transformation; +import org.joml.Vector3f; + +import javax.annotation.Nonnull; +import java.util.UUID; +import java.util.function.Consumer; + +public class Button implements Component { + + private String texture; + private String hoverTexture; + private UUID uuid; + private TextDisplay textDisplay; + private Location location; + private Consumer clickAction; + private Consumer hoverAction; + private Consumer unHoverAction; + private int slot; + private float size = 2; + private SimpleGui simpleGui; + private boolean hover = false; + + public Button(String texture, String hoverTexture, int slot) { + this.texture = texture; + this.hoverTexture = hoverTexture; + this.slot = slot; + + uuid = UUID.randomUUID(); + } + + public void spawn() { + textDisplay = (TextDisplay) simpleGui.getCenterLocation().getWorld().spawnEntity(Calculations.calculateComponentLocation(simpleGui, this, simpleGui.getButtonAmount()), EntityType.TEXT_DISPLAY); + textDisplay.setCustomName(uuid.toString()); + textDisplay.setCustomNameVisible(false); + textDisplay.setText(texture); + textDisplay.setGlowing(true); + textDisplay.setBillboard(Display.Billboard.CENTER); + textDisplay.setDisplayWidth(30); + textDisplay.setDisplayHeight(30); + textDisplay.setVisibleByDefault(false); + textDisplay.setDefaultBackground(false); + Transformation transformation = textDisplay.getTransformation(); + transformation.getScale().set(new Vector3f(size, size, size)); + textDisplay.setTransformation(transformation); + } + + public void show(Player player) { + player.showEntity(GuiApi.getInstance().getPlugin(), textDisplay); + } + + public void hide(Player player) { + player.hideEntity(GuiApi.getInstance().getPlugin(), textDisplay); + } + + public void remove() { + textDisplay.remove(); + } + + @Nonnull + public Consumer getClickAction() { + if (clickAction != null) { + return clickAction; + } else { + return (event -> {}); + } + } + + @Nonnull + public Button onClick(Consumer clickAction) { + this.clickAction = clickAction; + return this; + } + + public Consumer getHoverAction() { + if (hoverAction != null) { + return hoverAction; + } else { + return (event -> {}); + } + } + + public Button onHover(Consumer hoverAction) { + this.hoverAction = hoverAction; + return this; + } + + public Consumer getUnHoverAction() { + if (unHoverAction != null) { + return unHoverAction; + } else { + return (event -> {}); + } + } + + public Button onUnHover(Consumer unHoverAction) { + this.unHoverAction = unHoverAction; + return this; + } + + public Entity getEntity() { + return textDisplay; + } + + public TextDisplay getDisplay() { + return textDisplay; + } + + public UUID getUniqueId() { + return uuid; + } + + public SimpleGui getGui() { + return simpleGui; + } + + public String getText() { + return texture; + } + + public String getHoverText() { + return hoverTexture; + } + + public int getSlot() { + return slot; + } + + public void setGui(SimpleGui gui) { + simpleGui = gui; + } + + public Button setSize(float size) { + this.size = size; + return this; + } + + public void setHover(boolean hover) { + this.hover = hover; + } + + public boolean isHover() { + return hover; + } +} diff --git a/src/main/java/de/littleprogrammer/guiapi/components/Component.java b/src/main/java/de/littleprogrammer/guiapi/components/Component.java new file mode 100644 index 0000000..5fa061f --- /dev/null +++ b/src/main/java/de/littleprogrammer/guiapi/components/Component.java @@ -0,0 +1,20 @@ +package de.littleprogrammer.guiapi.components; + +import de.littleprogrammer.guiapi.SimpleGui; +import org.bukkit.entity.Display; +import org.bukkit.entity.Entity; +import org.bukkit.entity.Player; + +import java.util.UUID; + +public interface Component { + + public Entity getEntity(); + public Display getDisplay(); + public UUID getUniqueId(); + public void show(Player player); + public void hide(Player player); + public void remove(); + public void spawn(); + +} diff --git a/src/main/java/de/littleprogrammer/guiapi/components/Text.java b/src/main/java/de/littleprogrammer/guiapi/components/Text.java new file mode 100644 index 0000000..98ba122 --- /dev/null +++ b/src/main/java/de/littleprogrammer/guiapi/components/Text.java @@ -0,0 +1,87 @@ +package de.littleprogrammer.guiapi.components; + +import de.littleprogrammer.guiapi.GuiApi; +import de.littleprogrammer.guiapi.SimpleGui; +import org.bukkit.entity.*; +import org.bukkit.util.Transformation; +import org.joml.Vector3f; + +import java.util.UUID; + +public class Text implements Component { + + private String text; + private UUID uuid; + private float size = 2; + private TextDisplay textDisplay; + private SimpleGui simpleGui; + + public Text(String text) { + this.text = text; + uuid = UUID.randomUUID(); + } + + @Override + public void spawn() { + textDisplay = (TextDisplay) simpleGui.getCenterLocation().getWorld().spawnEntity(simpleGui.getCenterLocation(), EntityType.TEXT_DISPLAY); + textDisplay.setCustomName(uuid.toString()); + textDisplay.setCustomNameVisible(false); + textDisplay.setText(text); + textDisplay.setGlowing(true); + textDisplay.setBillboard(Display.Billboard.CENTER); + textDisplay.setDisplayWidth(30); + textDisplay.setDisplayHeight(30); + textDisplay.setVisibleByDefault(false); + textDisplay.setDefaultBackground(false); + Transformation transformation = textDisplay.getTransformation(); + transformation.getScale().set(new Vector3f(size, size, size)); + textDisplay.setTransformation(transformation); + } + + @Override + public Entity getEntity() { + return textDisplay; + } + + @Override + public Display getDisplay() { + return textDisplay; + } + + @Override + public UUID getUniqueId() { + return uuid; + } + + public SimpleGui getGui() { + return simpleGui; + } + + public float getSize() { + return size; + } + + public void setGui(SimpleGui simpleGui) { + this.simpleGui = simpleGui; + } + + public Text setSize(float size) { + this.size = size; + return this; + } + + @Override + public void show(Player player) { + player.showEntity(GuiApi.getInstance().getPlugin(), textDisplay); + } + + @Override + public void hide(Player player) { + player.hideEntity(GuiApi.getInstance().getPlugin(), textDisplay); + } + + @Override + public void remove() { + textDisplay.remove(); + } +} diff --git a/src/main/java/de/littleprogrammer/guiapi/customeEvents/HoverButtonEvent.java b/src/main/java/de/littleprogrammer/guiapi/customeEvents/HoverButtonEvent.java new file mode 100644 index 0000000..ff3c493 --- /dev/null +++ b/src/main/java/de/littleprogrammer/guiapi/customeEvents/HoverButtonEvent.java @@ -0,0 +1,56 @@ +package de.littleprogrammer.guiapi.customeEvents; + +import de.littleprogrammer.guiapi.SimpleGui; +import de.littleprogrammer.guiapi.components.Button; +import org.bukkit.entity.Player; +import org.bukkit.event.Event; +import org.bukkit.event.HandlerList; + +public class HoverButtonEvent extends Event { + private static final HandlerList HANDLERS = new HandlerList(); + + private final SimpleGui gui; + private final Player player; + private final Button button; + private final String hoverText; + private final String text; + + public HoverButtonEvent(SimpleGui gui, Player player, Button button, String hoverText, String text) { + this.gui = gui; + this.player = player; + this.button = button; + this.hoverText = hoverText; + this.text = text; + + button.getDisplay().setText(hoverText); + } + + @Override + public HandlerList getHandlers() { + return HANDLERS; + } + + public static HandlerList getHandlerList() { + return HANDLERS; + } + + public SimpleGui getGui() { + return gui; + } + + public Player getPlayer() { + return player; + } + + public Button getButton() { + return button; + } + + public String getHoverText() { + return hoverText; + } + + public String getText() { + return text; + } +} diff --git a/src/main/java/de/littleprogrammer/guiapi/customeEvents/UnHoverButtonEvent.java b/src/main/java/de/littleprogrammer/guiapi/customeEvents/UnHoverButtonEvent.java new file mode 100644 index 0000000..03966e1 --- /dev/null +++ b/src/main/java/de/littleprogrammer/guiapi/customeEvents/UnHoverButtonEvent.java @@ -0,0 +1,56 @@ +package de.littleprogrammer.guiapi.customeEvents; + +import de.littleprogrammer.guiapi.SimpleGui; +import de.littleprogrammer.guiapi.components.Button; +import org.bukkit.entity.Player; +import org.bukkit.event.Event; +import org.bukkit.event.HandlerList; + +public class UnHoverButtonEvent extends Event { + private static final HandlerList HANDLERS = new HandlerList(); + + private final SimpleGui gui; + private final Player player; + private final Button button; + private final String hoverText; + private final String text; + + public UnHoverButtonEvent(SimpleGui gui, Player player, Button button, String hoverText, String text) { + this.gui = gui; + this.player = player; + this.button = button; + this.hoverText = hoverText; + this.text = text; + + button.getDisplay().setText(text); + } + + @Override + public HandlerList getHandlers() { + return HANDLERS; + } + + public static HandlerList getHandlerList() { + return HANDLERS; + } + + public SimpleGui getGui() { + return gui; + } + + public Player getPlayer() { + return player; + } + + public Button getButton() { + return button; + } + + public String getHoverText() { + return hoverText; + } + + public String getText() { + return text; + } +} diff --git a/src/main/java/de/littleprogrammer/guiapi/enums/ServerVersion.java b/src/main/java/de/littleprogrammer/guiapi/enums/ServerVersion.java new file mode 100644 index 0000000..fe43d3e --- /dev/null +++ b/src/main/java/de/littleprogrammer/guiapi/enums/ServerVersion.java @@ -0,0 +1,9 @@ +package de.littleprogrammer.guiapi.enums; + +public enum ServerVersion { + PRE_1_20_2, + POST_1_20_2; + ServerVersion() { + + } +} diff --git a/src/main/java/de/littleprogrammer/guiapi/listeners/GuiEvents.java b/src/main/java/de/littleprogrammer/guiapi/listeners/GuiEvents.java new file mode 100644 index 0000000..18b2b34 --- /dev/null +++ b/src/main/java/de/littleprogrammer/guiapi/listeners/GuiEvents.java @@ -0,0 +1,45 @@ +package de.littleprogrammer.guiapi.listeners; + +import de.littleprogrammer.guiapi.GuiApi; +import de.littleprogrammer.guiapi.SimpleGui; +import de.littleprogrammer.guiapi.components.Button; +import de.littleprogrammer.guiapi.components.Component; +import de.littleprogrammer.guiapi.utils.Calculations; +import org.bukkit.entity.Display; +import org.bukkit.entity.Entity; +import org.bukkit.event.EventHandler; +import org.bukkit.event.Listener; +import org.bukkit.event.player.PlayerInteractEntityEvent; +import org.bukkit.event.player.PlayerInteractEvent; + +import java.util.UUID; + +public class GuiEvents implements Listener { + + @EventHandler + public void onPlayerInteractEvent(PlayerInteractEvent event) { + final SimpleGui simpleGui = GuiApi.getInstance().getGUI(event.getPlayer()); + + if (simpleGui == null) return; + + Entity awaitenEntity = null; + for (Entity entity : event.getPlayer().getNearbyEntities(7, 7, 7)) { + if (entity instanceof Display && entity.getCustomName() != null) { + if (Calculations.playerLookingAtEntity(event.getPlayer(), entity)) { + awaitenEntity = entity; + break; + } + } + } + + if (awaitenEntity == null) { return; } + + UUID uuid = UUID.fromString(awaitenEntity.getCustomName()); + Component component = simpleGui.getComponent(uuid); + if (!(component instanceof Button)) return; + + Button button = (Button) component; + //System.out.println("Click on button: " + button.getUniqueId()); + button.getClickAction().accept(new PlayerInteractEntityEvent(event.getPlayer(), button.getEntity())); + } +} diff --git a/src/main/java/de/littleprogrammer/guiapi/listeners/MoveListener.java b/src/main/java/de/littleprogrammer/guiapi/listeners/MoveListener.java new file mode 100644 index 0000000..f63a764 --- /dev/null +++ b/src/main/java/de/littleprogrammer/guiapi/listeners/MoveListener.java @@ -0,0 +1,61 @@ +package de.littleprogrammer.guiapi.listeners; + +import de.littleprogrammer.guiapi.GuiApi; +import de.littleprogrammer.guiapi.SimpleGui; +import de.littleprogrammer.guiapi.components.Button; +import de.littleprogrammer.guiapi.components.Component; +import de.littleprogrammer.guiapi.customeEvents.HoverButtonEvent; +import de.littleprogrammer.guiapi.customeEvents.UnHoverButtonEvent; +import de.littleprogrammer.guiapi.utils.Calculations; +import org.bukkit.entity.Display; +import org.bukkit.entity.Entity; +import org.bukkit.event.EventHandler; +import org.bukkit.event.Listener; +import org.bukkit.event.player.PlayerMoveEvent; + +import java.util.UUID; + +public class MoveListener implements Listener { + + @EventHandler + public void onPlayerMove(PlayerMoveEvent event) { + if (GuiApi.getInstance().getGuis().containsKey(event.getPlayer().getUniqueId())) { + SimpleGui simpleGui = GuiApi.getInstance().getGuis().get(event.getPlayer().getUniqueId()); + + if (event.getFrom().getX() != event.getTo().getX() || event.getFrom().getY() != event.getTo().getY() || event.getFrom().getZ() != event.getTo().getZ()) { + //Location is different + simpleGui.updatePosition(event.getPlayer().getEyeLocation()); + } else if (!Calculations.isInRange(event.getPlayer().getEyeLocation(), simpleGui.getCenterLocation(), 40)) { + simpleGui.updatePosition(event.getPlayer().getEyeLocation()); + } + + Entity hoveredEntity = null; + for (Entity entity : event.getPlayer().getNearbyEntities(8, 8, 8)) { + if (entity instanceof Display && entity.getCustomName() != null) { + if (Calculations.isInRange(event.getPlayer().getEyeLocation(), entity.getLocation(), 7)) { + hoveredEntity = entity; + break; + } + } + } + + if (hoveredEntity != null) { + if (simpleGui.getComponent(UUID.fromString(hoveredEntity.getCustomName())) instanceof Button) { + Button button = (Button) simpleGui.getComponent(UUID.fromString(hoveredEntity.getCustomName())); + button.getHoverAction().accept(new HoverButtonEvent(simpleGui, event.getPlayer(), button, button.getHoverText(), button.getText())); + button.setHover(true); + } + } else { + for (Component component : simpleGui.getComponents()) { + if (component instanceof Button) { + Button button = (Button) component; + if (button.isHover()) { + button.getUnHoverAction().accept(new UnHoverButtonEvent(simpleGui, event.getPlayer(), button, button.getHoverText(), button.getText())); + button.setHover(false); + } + } + } + } + } + } +} diff --git a/src/main/java/de/littleprogrammer/guiapi/utils/Calculations.java b/src/main/java/de/littleprogrammer/guiapi/utils/Calculations.java new file mode 100644 index 0000000..80e87af --- /dev/null +++ b/src/main/java/de/littleprogrammer/guiapi/utils/Calculations.java @@ -0,0 +1,100 @@ +package de.littleprogrammer.guiapi.utils; + +import de.littleprogrammer.guiapi.SimpleGui; +import de.littleprogrammer.guiapi.components.Button; +import de.littleprogrammer.guiapi.components.Component; +import org.bukkit.Location; +import org.bukkit.entity.Entity; +import org.bukkit.entity.Player; +import org.bukkit.util.Vector; + +public class Calculations { + + public static Location calculateInventoryCenter(Location midLocation) { + double distance = 4; // 4 blocks away + double yawRadians = Math.toRadians(midLocation.getYaw()); + double pitchRadians = Math.toRadians(midLocation.getPitch()); + double x = midLocation.getX() - distance * Math.sin(yawRadians); + double y = midLocation.getY() - 1; + double z = midLocation.getZ() + distance * Math.cos(yawRadians); // Negative here to match player rotation direction + + return new Location(midLocation.getWorld(), x, y, z, midLocation.getYaw(), 0); + } + + public static Location calculateComponentLocation(SimpleGui simpleGui, Component component, int buttonAmount) { + Location centerLoc = simpleGui.getCenterLocation(); + if (component instanceof Button) { + Button button = (Button) component; + + Location[] locations = calculateTrianglePoints(simpleGui.getPlayer().getLocation(), centerLoc); + //Is button in row + switch (buttonAmount) { + case 1: + return centerLoc.clone().subtract(0, 0, 0); + case 2: + if (button.getSlot() == 1) { + return locations[0]; + } else if (button.getSlot() == 2) { + return locations[1]; + } + break; + case 3: + if (button.getSlot() == 1) { + return locations[0]; + } else if (button.getSlot() == 2) { + return centerLoc.clone().subtract(0, 0, 0); + } else if (button.getSlot() == 3) { + return locations[1]; + } + break; + } + } else { + //Is content + return centerLoc.clone().add(0, 1.5, 0); + } + return null; + } + + /** + * @param playerLocation the location of the player (the point in the middle) + * @param centerLocation the location on the circle to get the correct height + */ + private static Location[] calculateTrianglePoints(Location playerLocation, Location centerLocation) { + double radius = playerLocation.distance(centerLocation); + + Vector vector1 = playerLocation.getDirection().setY(0).normalize().multiply(radius).rotateAroundY(Math.toRadians(30)); + Vector vector2 = playerLocation.getDirection().setY(0).normalize().multiply(radius).rotateAroundY(Math.toRadians(-30)); + + Location loc1 = playerLocation.clone().add(vector1); + loc1.setY(centerLocation.getY()); + + Location loc2 = playerLocation.clone().add(vector2); + loc2.setY(centerLocation.getY()); + + return new Location[]{loc1, loc2}; + } + + public static boolean playerLookingAtEntity(Player player, Entity entity) { + Vector playerDirection = player.getLocation().getDirection().normalize(); + + Location entityLocation = entity.getLocation(); + Location playerEyeLocation = player.getEyeLocation(); + + Vector playerToEntity = entityLocation.toVector().subtract(playerEyeLocation.toVector()).normalize(); + double dotProduct = playerDirection.dot(playerToEntity); + + //System.out.println("Checking entity" + entity + " " + entity.getCustomName() + " dot: " + dotProduct); + + return dotProduct > 0.97; + } + + public static boolean isInRange(Location playerEyeLocation, Location centerLocation, double rangeInDegrees) { + Vector playerEyeVector = playerEyeLocation.getDirection().setY(0).normalize(); + Vector playerToCenter = centerLocation.toVector().subtract(playerEyeLocation.toVector()).setY(0).normalize(); + + double dotProduct = playerToCenter.dot(playerEyeVector); + double angle = Math.toDegrees(Math.acos(dotProduct)); + + return angle <= rangeInDegrees; + } +} diff --git a/src/main/java/de/littleprogrammer/guiapi/utils/TeleportInterpolator.java b/src/main/java/de/littleprogrammer/guiapi/utils/TeleportInterpolator.java new file mode 100644 index 0000000..c4d8870 --- /dev/null +++ b/src/main/java/de/littleprogrammer/guiapi/utils/TeleportInterpolator.java @@ -0,0 +1,46 @@ +package de.littleprogrammer.guiapi.utils; + +import de.littleprogrammer.guiapi.GuiApi; +import org.bukkit.Location; +import org.bukkit.entity.Entity; + +public class TeleportInterpolator { + + private Entity entity; + private Location targetLocation; + private int steps; + private int delay; + + public TeleportInterpolator(Entity entity, Location targetLocation, int steps, int delay) { + this.entity = entity; + this.targetLocation = targetLocation; + this.steps = steps; + this.delay = delay; + } + + public void startInterpolation() { + Location currentLocation = entity.getLocation(); + + double dx = (targetLocation.getX() - currentLocation.getX()) / steps; + double dy = (targetLocation.getY() - currentLocation.getY()) / steps; + double dz = (targetLocation.getZ() - currentLocation.getZ()) / steps; + + for (int i = 1; i <= steps; i++) { + double newX = currentLocation.getX() + dx * i; + double newY = currentLocation.getY() + dy * i; + double newZ = currentLocation.getZ() + dz * i; + + Location intermediateLocation = new Location(targetLocation.getWorld(), newX, newY, newZ); + + // Teleport the entity to the intermediate location after a delay + teleportWithDelay(intermediateLocation, i * delay); + } + } + + private void teleportWithDelay(Location location, int delayTicks) { + GuiApi.getScheduler().runTaskLater(GuiApi.getInstance().getPlugin(), () -> { + entity.teleport(location); + }, delayTicks); + } + +} diff --git a/src/main/resources/plugin.yml b/src/main/resources/plugin.yml index 96665f6..63eedf4 100644 --- a/src/main/resources/plugin.yml +++ b/src/main/resources/plugin.yml @@ -1,6 +1,8 @@ name: 3dGuiApi version: '${version}' -main: de.littleprogrammer.guiapi.Api +main: de.littleprogrammer.guiapi.GuiApi api-version: '1.19' authors: [LittleProgrammer] description: An API to make 3D Gui's in minecraft +commands: + spawnGui: \ No newline at end of file