/* * This file is a part of the SteamWar software. * * Copyright (C) 2022 SteamWar.de-Serverteam * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Affero General Public License for more details. * * You should have received a copy of the GNU Affero General Public License * along with this program. If not, see . */ package de.steamwar.lobby.team; import de.steamwar.lobby.LobbySystem; import de.steamwar.lobby.display.NPC; import de.steamwar.lobby.listener.BasicListener; import de.steamwar.sql.SteamwarUser; import de.steamwar.sql.UserPerm; import lombok.AllArgsConstructor; import org.bukkit.Bukkit; import org.bukkit.Location; import org.bukkit.World; import org.bukkit.entity.Entity; import org.bukkit.entity.EntityType; import org.bukkit.entity.Player; import org.bukkit.entity.Villager; import org.bukkit.event.EventHandler; import org.bukkit.event.entity.EntityDamageEvent; import org.bukkit.event.entity.EntityInteractEvent; import org.bukkit.event.player.PlayerInteractEntityEvent; import org.bukkit.event.player.PlayerQuitEvent; import org.bukkit.potion.PotionEffect; import org.bukkit.potion.PotionEffectType; import java.util.*; import java.util.concurrent.atomic.AtomicInteger; import java.util.logging.Level; import java.util.stream.Collectors; public class TeamPlayer extends BasicListener { private static final List cuboids = new ArrayList<>(); static { cuboids.add(new Cuboid(2743, 58, 2306, 2744, 59, 1316)); } private static final World world = Bukkit.getWorlds().get(0); private static final Map entities = new HashMap<>(); private static final Map villagers = new HashMap<>(); private Set players = new HashSet<>(); private Random random = new Random(); private List strings = new ArrayList<>(); { strings.add("NPC_CHAT_1"); strings.add("NPC_CHAT_2"); } public static void spawnTeamPlayer(World world, SteamwarUser steamwarUser) { Location location = new Location(world, 2790.5, 69, 1311.5); String name = steamwarUser.getUserName(); NPC npc = new NPC(location, steamwarUser.getUUID(), name); Villager villager = (Villager) world.spawnEntity(location, EntityType.VILLAGER); villager.setSilent(true); villager.setInvulnerable(true); villager.addPotionEffect(new PotionEffect(PotionEffectType.INVISIBILITY, Integer.MAX_VALUE, 1, false, false, false)); villager.setCustomName(name); villager.setProfession(Villager.Profession.NONE); villagers.put(name, villager); entities.put(name, npc); } { SteamwarUser.getServerTeam().forEach(user -> { spawnTeamPlayer(world, user); }); AtomicInteger count = new AtomicInteger(); LobbySystem.getPlugin().getLogger().log(Level.INFO, "Loaded " + entities.size() + " team players"); Bukkit.getScheduler().runTaskTimer(LobbySystem.getPlugin(), () -> { Collection active = world.getEntitiesByClass(Villager.class); if (active.size() > entities.size()) { Set duplicates = new HashSet<>(); active.stream() .filter(villager -> !duplicates.add(villager.getCustomName())) .forEach(Entity::remove); } count.incrementAndGet(); if (count.get() % (20 * 60 * 60) == 0) { count.set(0); List steamwarUsers = SteamwarUser.getServerTeam(); AtomicInteger added = new AtomicInteger(); steamwarUsers.forEach(user -> { if (!entities.containsKey(user.getUserName())) { spawnTeamPlayer(world, user); added.incrementAndGet(); } }); AtomicInteger removed = new AtomicInteger(); List names = steamwarUsers.stream().map(SteamwarUser::getUserName).collect(Collectors.toList()); new HashSet<>(entities.keySet()).stream().filter(name -> !names.contains(name)).forEach(name -> { villagers.remove(name).remove(); entities.remove(name).delete(); removed.incrementAndGet(); }); if (added.get() > 0 || removed.get() > 0) { LobbySystem.getPlugin().getLogger().log(Level.INFO, "Loaded " + added.get() + " team players, removed " + removed.get() + " team players"); } } world.getEntitiesByClasses(Villager.class).forEach(entity -> { NPC npc = entities.get(entity.getName()); if (npc != null) { if (illegalLocation(entity.getLocation())) { entity.teleport(npc.getLocation()); return; } npc.setLocation(entity.getLocation()); } }); }, 1L, 1L); } private boolean illegalLocation(Location location) { for (Cuboid cuboid : cuboids) { if (cuboid.contains(location)) { return true; } } return false; } @EventHandler public void onPlayerInteractEntity(PlayerInteractEntityEvent event) { if (!(event.getRightClicked() instanceof Villager)) { return; } if (!players.add(event.getPlayer())) { players.remove(event.getPlayer()); return; } int randomNum = random.nextInt(6); String message = "NPC_Chat_" + randomNum; SteamwarUser user = SteamwarUser.get(event.getRightClicked().getName()); UserPerm.Prefix prefix = user.prefix(); LobbySystem.getMessage().send(message, event.getPlayer(), event.getRightClicked().getName(), prefix.getColorCode() + prefix.getChatPrefix()); } @EventHandler public void onPlayerQuit(PlayerQuitEvent event) { players.remove(event.getPlayer()); } @EventHandler public void onEntityInteract(EntityInteractEvent event) { if (event.getEntityType() == EntityType.VILLAGER) { event.setCancelled(true); } } @EventHandler public void onEntityDamage(EntityDamageEvent event) { if (event.getEntityType() == EntityType.VILLAGER) { event.setCancelled(true); } } @AllArgsConstructor private static class Cuboid { private double x1; private double y1; private double z1; private double x2; private double y2; private double z2; public boolean contains(Location location) { return location.getX() >= x1 && location.getX() <= x2 && location.getY() >= y1 && location.getY() <= y2 && location.getZ() >= z1 && location.getZ() <= z2; } } }