package net.voltexstudios.applicationLobby.holograms; import net.voltexstudios.applicationLobby.holograms.types.TextHologram; import org.bukkit.Bukkit; import org.bukkit.Location; import org.bukkit.entity.Entity; import org.bukkit.entity.Interaction; import org.bukkit.entity.Player; import java.util.*; public final class HologramService { private static HologramService instance; private final Set holograms; private final Map hovering; public HologramService(Set holograms) { instance = this; this.holograms = holograms; this.hovering = new HashMap<>(); } public Hologram createHologram(HologramType type, String name, UUID interactionUUID, String data) { if (interactionExists(interactionUUID)) { return null; } Hologram hologram = null; switch (type) { case TEXT: hologram = createTextHologram(name, interactionUUID, data); break; } if (hologram != null) { addHologram(hologram); } return hologram; } private void addHologram(Hologram hologram) { holograms.add(hologram); for (Player player : Bukkit.getServer().getOnlinePlayers()) { hologram.addDisplay(player.getUniqueId()); } } private TextHologram createTextHologram(String name, UUID interactionUUID, String text) { return new TextHologram(name, interactionUUID, text); } public void handleHologramHover(Player player, Entity entity) { if (entity == null) { if (isHovering(player)) { getHovering(player).onUnhover(player); hovering.remove(player.getUniqueId()); } return; } if (!(entity instanceof Interaction)) { return; } Hologram hologram = getHologram(entity.getUniqueId()); if (isHovering(player)) { Hologram lastHovering = getHovering(player); if (lastHovering.getInteractionUUID().equals(hologram.getInteractionUUID())) { return; } } hovering.put(player.getUniqueId(), hologram); hologram.onHover(player); } public void handleHologramClick(Player player, Hologram hologram) { if (hologram == null) { return; } hologram.onClick(player); } public Location getClosestHologramLocation(Player player) { return holograms.stream() .map(Hologram::getInteractionUUID) .map(interactionUUID -> (Interaction) player.getWorld().getEntity(interactionUUID)) .filter(Objects::nonNull) .min(Comparator.comparingDouble(interaction -> interaction.getLocation().distance(player.getLocation()))) .map(Entity::getLocation) .orElse(null); } public void addPlayerDisplays(Player player) { holograms.forEach(hologram -> hologram.addDisplay(player.getUniqueId())); } public void removePlayerDisplays(Player player) { holograms.forEach(hologram -> hologram.removeDisplay(player.getUniqueId())); } public Hologram getHologram(UUID interactionUUID) { return holograms.stream().filter(hologram -> hologram.getInteractionUUID().equals(interactionUUID)).findFirst().orElse(null); } public boolean isHologram(UUID interactionUUID) { return holograms.stream().anyMatch(hologram -> hologram.getInteractionUUID().equals(interactionUUID)); } public boolean isHovering(Player player) { return hovering.containsKey(player.getUniqueId()); } public Hologram getHovering(Player player) { return hovering.get(player.getUniqueId()); } public void removeHovering(Player player) { hovering.remove(player.getUniqueId()); } private boolean interactionExists(UUID interactionUUID) { return holograms.stream().anyMatch(hologram -> hologram.getInteractionUUID().equals(interactionUUID)); } public Set getHolograms() { return holograms; } public HologramData getHologramData() { return new HologramData(holograms); } public static HologramService getInstance() { if(instance == null) { instance = new HologramService(new HashSet<>()); } return instance; } }