This commit is contained in:
@@ -25,7 +25,7 @@ slightly faster round. Last player standing wins.
|
|||||||
All admin/config commands live under `/blockparty` (alias `/bp`) and work from console
|
All admin/config commands live under `/blockparty` (alias `/bp`) and work from console
|
||||||
where it makes sense (`create`, `delete`, `enable`, `disable`, `info`, `list`, `reload`).
|
where it makes sense (`create`, `delete`, `enable`, `disable`, `info`, `list`, `reload`).
|
||||||
Commands that require a physical location (`setlobby`, `setspawn`, `setspectator`,
|
Commands that require a physical location (`setlobby`, `setspawn`, `setspectator`,
|
||||||
`pos1`, `pos2`) require a player sender.
|
`setbillboard`, `pos1`, `pos2`) require a player sender.
|
||||||
|
|
||||||
### Admin
|
### Admin
|
||||||
| Command | Description |
|
| Command | Description |
|
||||||
@@ -38,6 +38,8 @@ Commands that require a physical location (`setlobby`, `setspawn`, `setspectator
|
|||||||
| `/blockparty setlobby <arena>` | Set the waiting-room location |
|
| `/blockparty setlobby <arena>` | Set the waiting-room location |
|
||||||
| `/blockparty setspawn <arena>` | Set the in-game spawn location |
|
| `/blockparty setspawn <arena>` | Set the in-game spawn location |
|
||||||
| `/blockparty setspectator <arena>` | Set the spectator/eliminated location |
|
| `/blockparty setspectator <arena>` | Set the spectator/eliminated location |
|
||||||
|
| `/blockparty setbillboard <arena>` | (Optional) place a display block here that mirrors the current target color |
|
||||||
|
| `/blockparty delbillboard <arena>` | Remove the billboard, if one is set |
|
||||||
| `/blockparty pos1 <arena>` | Set floor region corner 1 |
|
| `/blockparty pos1 <arena>` | Set floor region corner 1 |
|
||||||
| `/blockparty pos2 <arena>` | Set floor region corner 2 |
|
| `/blockparty pos2 <arena>` | Set floor region corner 2 |
|
||||||
| `/blockparty setfloor <arena> <mat1,mat2,...>` | Set the allowed floor materials |
|
| `/blockparty setfloor <arena> <mat1,mat2,...>` | Set the allowed floor materials |
|
||||||
@@ -83,9 +85,12 @@ Commands that require a physical location (`setlobby`, `setspawn`, `setspectator
|
|||||||
still required once so BlockParty captures/serializes the exact layout it should restore
|
still required once so BlockParty captures/serializes the exact layout it should restore
|
||||||
each round (BlockParty does not scan the world every round — it restores from the saved
|
each round (BlockParty does not scan the world every round — it restores from the saved
|
||||||
layout for performance and determinism).
|
layout for performance and determinism).
|
||||||
8. `/bp info lobby1` to confirm there are no validation errors.
|
8. Optionally, stand somewhere visible near/above the floor and run `/bp setbillboard lobby1`
|
||||||
9. `/bp enable lobby1`.
|
to place a big display block that mirrors the round's target color — purely cosmetic and
|
||||||
10. Players run `/bp join lobby1`. Once `min-players` is reached the countdown starts
|
entirely optional (see "Billboard" below).
|
||||||
|
9. `/bp info lobby1` to confirm there are no validation errors.
|
||||||
|
10. `/bp enable lobby1`.
|
||||||
|
11. Players run `/bp join lobby1`. Once `min-players` is reached the countdown starts
|
||||||
automatically; joining an arena mid-countdown is allowed by default
|
automatically; joining an arena mid-countdown is allowed by default
|
||||||
(`allow-join-while-waiting: true`).
|
(`allow-join-while-waiting: true`).
|
||||||
|
|
||||||
@@ -99,6 +104,23 @@ Commands that require a physical location (`setlobby`, `setspawn`, `setspectator
|
|||||||
(`generated-layout`) so it can be restored exactly, every round, without re-scanning or
|
(`generated-layout`) so it can be restored exactly, every round, without re-scanning or
|
||||||
re-randomizing the world.
|
re-randomizing the world.
|
||||||
|
|
||||||
|
### Billboard
|
||||||
|
|
||||||
|
An arena billboard is a `BlockDisplay` entity that visually shows the currently selected
|
||||||
|
target color/block each round, in addition to the title/actionbar/hotbar-item cues. It is
|
||||||
|
entirely optional:
|
||||||
|
|
||||||
|
- Per-arena: only spawned if `/bp setbillboard <arena>` has been run (stored as `billboard`
|
||||||
|
in the arena's yml). `/bp delbillboard <arena>` removes it.
|
||||||
|
- Per-arena toggle: `billboard-enabled` in the arena's yml (default `true`) lets you keep the
|
||||||
|
location set but temporarily turn it off without deleting it.
|
||||||
|
- Global toggle: `ui.billboard` in `config.yml` (default `true`) disables billboards across
|
||||||
|
every arena at once, e.g. for performance-constrained servers.
|
||||||
|
|
||||||
|
The entity is non-persistent (not saved to the world, so it never survives a server restart on
|
||||||
|
its own — BlockParty re-creates it on demand) and is despawned automatically when the arena is
|
||||||
|
disabled, deleted, or the plugin shuts down, so it never leaks entities.
|
||||||
|
|
||||||
## Player usage
|
## Player usage
|
||||||
|
|
||||||
- `/bp join <arena>` to enter the waiting lobby. Your inventory, armor, offhand, health,
|
- `/bp join <arena>` to enter the waiting lobby. Your inventory, armor, offhand, health,
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ import org.bukkit.entity.Player;
|
|||||||
import org.bukkit.inventory.ItemStack;
|
import org.bukkit.inventory.ItemStack;
|
||||||
import org.bukkit.scheduler.BukkitTask;
|
import org.bukkit.scheduler.BukkitTask;
|
||||||
import us.tss3.blockparty.BlockPartyPlugin;
|
import us.tss3.blockparty.BlockPartyPlugin;
|
||||||
|
import us.tss3.blockparty.billboard.BillboardManager;
|
||||||
import us.tss3.blockparty.config.ArenaConfig;
|
import us.tss3.blockparty.config.ArenaConfig;
|
||||||
import us.tss3.blockparty.floor.FloorManager;
|
import us.tss3.blockparty.floor.FloorManager;
|
||||||
import us.tss3.blockparty.logic.ArenaPhase;
|
import us.tss3.blockparty.logic.ArenaPhase;
|
||||||
@@ -35,6 +36,7 @@ public class Arena {
|
|||||||
private final BlockPartyPlugin plugin;
|
private final BlockPartyPlugin plugin;
|
||||||
private final ArenaConfig config;
|
private final ArenaConfig config;
|
||||||
private final FloorManager floorManager;
|
private final FloorManager floorManager;
|
||||||
|
private final BillboardManager billboardManager;
|
||||||
private final ArenaStateMachine stateMachine = new ArenaStateMachine(ArenaPhase.DISABLED);
|
private final ArenaStateMachine stateMachine = new ArenaStateMachine(ArenaPhase.DISABLED);
|
||||||
private final Random random = new Random();
|
private final Random random = new Random();
|
||||||
private final TargetColorSelector selector = new TargetColorSelector(random::nextInt);
|
private final TargetColorSelector selector = new TargetColorSelector(random::nextInt);
|
||||||
@@ -56,6 +58,7 @@ public class Arena {
|
|||||||
this.plugin = plugin;
|
this.plugin = plugin;
|
||||||
this.config = config;
|
this.config = config;
|
||||||
this.floorManager = new FloorManager(plugin, config);
|
this.floorManager = new FloorManager(plugin, config);
|
||||||
|
this.billboardManager = new BillboardManager(plugin, config);
|
||||||
if (config.isEnabled()) {
|
if (config.isEnabled()) {
|
||||||
stateMachine.transition(ArenaPhase.WAITING);
|
stateMachine.transition(ArenaPhase.WAITING);
|
||||||
}
|
}
|
||||||
@@ -109,6 +112,7 @@ public class Arena {
|
|||||||
|
|
||||||
public void disable() {
|
public void disable() {
|
||||||
cancelAllTasks();
|
cancelAllTasks();
|
||||||
|
billboardManager.despawn();
|
||||||
// Force reset players out regardless of state
|
// Force reset players out regardless of state
|
||||||
List<UUID> all = new ArrayList<>();
|
List<UUID> all = new ArrayList<>();
|
||||||
all.addAll(players);
|
all.addAll(players);
|
||||||
@@ -318,6 +322,7 @@ public class Arena {
|
|||||||
p.getInventory().setItem(8, display.clone());
|
p.getInventory().setItem(8, display.clone());
|
||||||
plugin.getSoundUtil().play(p, plugin.getConfigManager().getSound("target-select"), 1f, 1f);
|
plugin.getSoundUtil().play(p, plugin.getConfigManager().getSound("target-select"), 1f, 1f);
|
||||||
}
|
}
|
||||||
|
billboardManager.show(currentTarget);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void setupBossBar() {
|
private void setupBossBar() {
|
||||||
@@ -493,6 +498,7 @@ public class Arena {
|
|||||||
floorManager.cancelActiveTask();
|
floorManager.cancelActiveTask();
|
||||||
cancelAllTasks();
|
cancelAllTasks();
|
||||||
round = 0;
|
round = 0;
|
||||||
|
billboardManager.clear();
|
||||||
stateMachine.transition(ArenaPhase.WAITING);
|
stateMachine.transition(ArenaPhase.WAITING);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -516,6 +522,7 @@ public class Arena {
|
|||||||
/** Called on plugin disable / world unload to safely stop everything and restore players. */
|
/** Called on plugin disable / world unload to safely stop everything and restore players. */
|
||||||
public void shutdown() {
|
public void shutdown() {
|
||||||
cancelAllTasks();
|
cancelAllTasks();
|
||||||
|
billboardManager.despawn();
|
||||||
List<UUID> all = allParticipants();
|
List<UUID> all = allParticipants();
|
||||||
for (UUID uuid : all) {
|
for (UUID uuid : all) {
|
||||||
Player p = plugin.getServer().getPlayer(uuid);
|
Player p = plugin.getServer().getPlayer(uuid);
|
||||||
@@ -529,6 +536,10 @@ public class Arena {
|
|||||||
spectators.clear();
|
spectators.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public BillboardManager getBillboardManager() {
|
||||||
|
return billboardManager;
|
||||||
|
}
|
||||||
|
|
||||||
private String formatMaterial(Material material) {
|
private String formatMaterial(Material material) {
|
||||||
String name = material.name().replace("_CONCRETE", "").replace("_", " ").toLowerCase();
|
String name = material.name().replace("_CONCRETE", "").replace("_", " ").toLowerCase();
|
||||||
return name.substring(0, 1).toUpperCase() + name.substring(1);
|
return name.substring(0, 1).toUpperCase() + name.substring(1);
|
||||||
|
|||||||
@@ -0,0 +1,109 @@
|
|||||||
|
package us.tss3.blockparty.billboard;
|
||||||
|
|
||||||
|
import org.bukkit.Location;
|
||||||
|
import org.bukkit.Material;
|
||||||
|
import org.bukkit.entity.BlockDisplay;
|
||||||
|
import org.bukkit.entity.Entity;
|
||||||
|
import org.bukkit.util.Transformation;
|
||||||
|
import org.joml.AxisAngle4f;
|
||||||
|
import org.joml.Vector3f;
|
||||||
|
import us.tss3.blockparty.BlockPartyPlugin;
|
||||||
|
import us.tss3.blockparty.config.ArenaConfig;
|
||||||
|
|
||||||
|
import java.util.UUID;
|
||||||
|
import java.util.logging.Level;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Owns an optional {@link BlockDisplay} entity that visually mirrors an arena's currently
|
||||||
|
* selected target color. Purely cosmetic: fully optional (global toggle + per-arena
|
||||||
|
* toggle/location), and every method safely no-ops when disabled, unset, or the arena's
|
||||||
|
* world isn't loaded.
|
||||||
|
*/
|
||||||
|
public class BillboardManager {
|
||||||
|
|
||||||
|
private static final AxisAngle4f NO_ROTATION = new AxisAngle4f(0f, 0f, 0f, 1f);
|
||||||
|
|
||||||
|
private final BlockPartyPlugin plugin;
|
||||||
|
private final ArenaConfig config;
|
||||||
|
private UUID entityId;
|
||||||
|
|
||||||
|
public BillboardManager(BlockPartyPlugin plugin, ArenaConfig config) {
|
||||||
|
this.plugin = plugin;
|
||||||
|
this.config = config;
|
||||||
|
}
|
||||||
|
|
||||||
|
private boolean isActive() {
|
||||||
|
return plugin.getConfigManager().isBillboardEnabled() && config.hasBillboard()
|
||||||
|
&& config.getBillboard().getWorld() != null;
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Shows (spawning the display entity if needed) the given material as the current target. */
|
||||||
|
public void show(Material material) {
|
||||||
|
if (!isActive()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
BlockDisplay display = resolve();
|
||||||
|
if (display == null) {
|
||||||
|
display = spawn();
|
||||||
|
}
|
||||||
|
if (display != null) {
|
||||||
|
display.setBlock(material.createBlockData());
|
||||||
|
}
|
||||||
|
} catch (Exception ex) {
|
||||||
|
plugin.getLogger().log(Level.WARNING, "Failed to update billboard for arena '" + config.getName() + "'", ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Blanks the display (e.g. between matches) without destroying the entity. */
|
||||||
|
public void clear() {
|
||||||
|
BlockDisplay display = resolve();
|
||||||
|
if (display != null) {
|
||||||
|
display.setBlock(Material.AIR.createBlockData());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Fully removes the display entity. Safe to call even if nothing was ever spawned. */
|
||||||
|
public void despawn() {
|
||||||
|
BlockDisplay display = resolve();
|
||||||
|
if (display != null) {
|
||||||
|
display.remove();
|
||||||
|
}
|
||||||
|
entityId = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Forces the entity to be re-created at its (possibly updated) configured location next time it's shown. */
|
||||||
|
public void invalidate() {
|
||||||
|
despawn();
|
||||||
|
}
|
||||||
|
|
||||||
|
private BlockDisplay resolve() {
|
||||||
|
if (entityId == null) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
Entity entity = plugin.getServer().getEntity(entityId);
|
||||||
|
if (entity instanceof BlockDisplay display && !display.isDead()) {
|
||||||
|
return display;
|
||||||
|
}
|
||||||
|
entityId = null;
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
private BlockDisplay spawn() {
|
||||||
|
Location loc = config.getBillboard();
|
||||||
|
if (loc == null || loc.getWorld() == null) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
BlockDisplay display = loc.getWorld().spawn(loc, BlockDisplay.class, bd -> {
|
||||||
|
bd.setPersistent(false);
|
||||||
|
bd.setGlowing(true);
|
||||||
|
bd.setTransformation(new Transformation(
|
||||||
|
new Vector3f(-0.75f, 0f, -0.75f),
|
||||||
|
NO_ROTATION,
|
||||||
|
new Vector3f(1.5f, 1.5f, 1.5f),
|
||||||
|
NO_ROTATION));
|
||||||
|
});
|
||||||
|
entityId = display.getUniqueId();
|
||||||
|
return display;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -45,6 +45,8 @@ public class BlockPartyCommand implements CommandExecutor, TabCompleter {
|
|||||||
case "setlobby" -> setLobby(sender, args);
|
case "setlobby" -> setLobby(sender, args);
|
||||||
case "setspawn" -> setSpawn(sender, args);
|
case "setspawn" -> setSpawn(sender, args);
|
||||||
case "setspectator" -> setSpectator(sender, args);
|
case "setspectator" -> setSpectator(sender, args);
|
||||||
|
case "setbillboard" -> setBillboard(sender, args);
|
||||||
|
case "delbillboard" -> delBillboard(sender, args);
|
||||||
case "pos1" -> pos1(sender, args);
|
case "pos1" -> pos1(sender, args);
|
||||||
case "pos2" -> pos2(sender, args);
|
case "pos2" -> pos2(sender, args);
|
||||||
case "setfloor" -> setFloor(sender, args);
|
case "setfloor" -> setFloor(sender, args);
|
||||||
@@ -75,6 +77,8 @@ public class BlockPartyCommand implements CommandExecutor, TabCompleter {
|
|||||||
"/blockparty setlobby <arena>",
|
"/blockparty setlobby <arena>",
|
||||||
"/blockparty setspawn <arena>",
|
"/blockparty setspawn <arena>",
|
||||||
"/blockparty setspectator <arena>",
|
"/blockparty setspectator <arena>",
|
||||||
|
"/blockparty setbillboard <arena>",
|
||||||
|
"/blockparty delbillboard <arena>",
|
||||||
"/blockparty pos1 <arena>",
|
"/blockparty pos1 <arena>",
|
||||||
"/blockparty pos2 <arena>",
|
"/blockparty pos2 <arena>",
|
||||||
"/blockparty setfloor <arena>",
|
"/blockparty setfloor <arena>",
|
||||||
@@ -191,6 +195,27 @@ public class BlockPartyCommand implements CommandExecutor, TabCompleter {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void setBillboard(CommandSender sender, String[] args) {
|
||||||
|
if (!requireAdmin(sender, "blockparty.admin.setup") || !requirePlayer(sender)) return;
|
||||||
|
withArena(sender, args, arena -> {
|
||||||
|
arena.getConfig().setBillboard(((Player) sender).getLocation());
|
||||||
|
arena.getConfig().setBillboardEnabled(true);
|
||||||
|
arena.getBillboardManager().invalidate();
|
||||||
|
plugin.getArenaManager().save(arena);
|
||||||
|
sender.sendMessage(plugin.getMessages().get("admin.billboard-set", Map.of("arena", arena.getConfig().getName())));
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private void delBillboard(CommandSender sender, String[] args) {
|
||||||
|
if (!requireAdmin(sender, "blockparty.admin.setup")) return;
|
||||||
|
withArena(sender, args, arena -> {
|
||||||
|
arena.getBillboardManager().despawn();
|
||||||
|
arena.getConfig().setBillboard(null);
|
||||||
|
plugin.getArenaManager().save(arena);
|
||||||
|
sender.sendMessage(plugin.getMessages().get("admin.billboard-removed", Map.of("arena", arena.getConfig().getName())));
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
private void pos1(CommandSender sender, String[] args) {
|
private void pos1(CommandSender sender, String[] args) {
|
||||||
if (!requireAdmin(sender, "blockparty.admin.setup") || !requirePlayer(sender)) return;
|
if (!requireAdmin(sender, "blockparty.admin.setup") || !requirePlayer(sender)) return;
|
||||||
withArena(sender, args, arena -> {
|
withArena(sender, args, arena -> {
|
||||||
@@ -277,6 +302,7 @@ public class BlockPartyCommand implements CommandExecutor, TabCompleter {
|
|||||||
sender.sendMessage("§7Lobby set: §f" + (cfg.getLobby() != null));
|
sender.sendMessage("§7Lobby set: §f" + (cfg.getLobby() != null));
|
||||||
sender.sendMessage("§7Spawn set: §f" + (cfg.getSpawn() != null));
|
sender.sendMessage("§7Spawn set: §f" + (cfg.getSpawn() != null));
|
||||||
sender.sendMessage("§7Spectator set: §f" + (cfg.getSpectator() != null));
|
sender.sendMessage("§7Spectator set: §f" + (cfg.getSpectator() != null));
|
||||||
|
sender.sendMessage("§7Billboard set: §f" + (cfg.getBillboard() != null) + (cfg.getBillboard() != null ? " (enabled: " + cfg.isBillboardEnabled() + ")" : ""));
|
||||||
sender.sendMessage("§7Floor region set: §f" + cfg.hasFloorRegion());
|
sender.sendMessage("§7Floor region set: §f" + cfg.hasFloorRegion());
|
||||||
sender.sendMessage("§7Floor generated: §f" + cfg.hasGeneratedLayout());
|
sender.sendMessage("§7Floor generated: §f" + cfg.hasGeneratedLayout());
|
||||||
sender.sendMessage("§7Floor materials: §f" + cfg.getFloorMaterials().size());
|
sender.sendMessage("§7Floor materials: §f" + cfg.getFloorMaterials().size());
|
||||||
@@ -394,7 +420,7 @@ public class BlockPartyCommand implements CommandExecutor, TabCompleter {
|
|||||||
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
|
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
|
||||||
if (args.length == 1) {
|
if (args.length == 1) {
|
||||||
return List.of("help", "join", "leave", "arenas", "stats", "create", "delete", "enable", "disable",
|
return List.of("help", "join", "leave", "arenas", "stats", "create", "delete", "enable", "disable",
|
||||||
"setlobby", "setspawn", "setspectator", "pos1", "pos2", "setfloor", "generate", "info", "list", "reload")
|
"setlobby", "setspawn", "setspectator", "setbillboard", "delbillboard", "pos1", "pos2", "setfloor", "generate", "info", "list", "reload")
|
||||||
.stream().filter(s -> s.startsWith(args[0].toLowerCase())).collect(Collectors.toList());
|
.stream().filter(s -> s.startsWith(args[0].toLowerCase())).collect(Collectors.toList());
|
||||||
}
|
}
|
||||||
if (args.length == 2) {
|
if (args.length == 2) {
|
||||||
|
|||||||
@@ -15,6 +15,8 @@ public class ArenaConfig {
|
|||||||
private Location lobby;
|
private Location lobby;
|
||||||
private Location spawn;
|
private Location spawn;
|
||||||
private Location spectator;
|
private Location spectator;
|
||||||
|
private Location billboard;
|
||||||
|
private boolean billboardEnabled = true;
|
||||||
private int[] pos1; // x,y,z block coords
|
private int[] pos1; // x,y,z block coords
|
||||||
private int[] pos2;
|
private int[] pos2;
|
||||||
|
|
||||||
@@ -84,6 +86,26 @@ public class ArenaConfig {
|
|||||||
this.spectator = spectator;
|
this.spectator = spectator;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Location getBillboard() {
|
||||||
|
return billboard;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setBillboard(Location billboard) {
|
||||||
|
this.billboard = billboard;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isBillboardEnabled() {
|
||||||
|
return billboardEnabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setBillboardEnabled(boolean billboardEnabled) {
|
||||||
|
this.billboardEnabled = billboardEnabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean hasBillboard() {
|
||||||
|
return billboard != null && billboardEnabled;
|
||||||
|
}
|
||||||
|
|
||||||
public int[] getPos1() {
|
public int[] getPos1() {
|
||||||
return pos1;
|
return pos1;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -57,6 +57,8 @@ public class ArenaConfigLoader {
|
|||||||
cfg.setLobby(LocationUtil.fromSection(yml.getConfigurationSection("lobby")));
|
cfg.setLobby(LocationUtil.fromSection(yml.getConfigurationSection("lobby")));
|
||||||
cfg.setSpawn(LocationUtil.fromSection(yml.getConfigurationSection("spawn")));
|
cfg.setSpawn(LocationUtil.fromSection(yml.getConfigurationSection("spawn")));
|
||||||
cfg.setSpectator(LocationUtil.fromSection(yml.getConfigurationSection("spectator")));
|
cfg.setSpectator(LocationUtil.fromSection(yml.getConfigurationSection("spectator")));
|
||||||
|
cfg.setBillboard(LocationUtil.fromSection(yml.getConfigurationSection("billboard")));
|
||||||
|
cfg.setBillboardEnabled(yml.getBoolean("billboard-enabled", true));
|
||||||
if (yml.contains("pos1")) {
|
if (yml.contains("pos1")) {
|
||||||
cfg.setPos1(new int[]{yml.getInt("pos1.x"), yml.getInt("pos1.y"), yml.getInt("pos1.z")});
|
cfg.setPos1(new int[]{yml.getInt("pos1.x"), yml.getInt("pos1.y"), yml.getInt("pos1.z")});
|
||||||
}
|
}
|
||||||
@@ -106,6 +108,10 @@ public class ArenaConfigLoader {
|
|||||||
if (cfg.getSpectator() != null) {
|
if (cfg.getSpectator() != null) {
|
||||||
LocationUtil.toSection(yml.createSection("spectator"), cfg.getSpectator());
|
LocationUtil.toSection(yml.createSection("spectator"), cfg.getSpectator());
|
||||||
}
|
}
|
||||||
|
if (cfg.getBillboard() != null) {
|
||||||
|
LocationUtil.toSection(yml.createSection("billboard"), cfg.getBillboard());
|
||||||
|
}
|
||||||
|
yml.set("billboard-enabled", cfg.isBillboardEnabled());
|
||||||
if (cfg.getPos1() != null) {
|
if (cfg.getPos1() != null) {
|
||||||
yml.set("pos1.x", cfg.getPos1()[0]);
|
yml.set("pos1.x", cfg.getPos1()[0]);
|
||||||
yml.set("pos1.y", cfg.getPos1()[1]);
|
yml.set("pos1.y", cfg.getPos1()[1]);
|
||||||
|
|||||||
@@ -33,6 +33,10 @@ public class ConfigManager {
|
|||||||
return config.getBoolean("ui.bossbar", true);
|
return config.getBoolean("ui.bossbar", true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean isBillboardEnabled() {
|
||||||
|
return config.getBoolean("ui.billboard", true);
|
||||||
|
}
|
||||||
|
|
||||||
public boolean isTitlesEnabled() {
|
public boolean isTitlesEnabled() {
|
||||||
return config.getBoolean("ui.titles", true);
|
return config.getBoolean("ui.titles", true);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,6 +6,11 @@ ui:
|
|||||||
titles: true
|
titles: true
|
||||||
actionbar: true
|
actionbar: true
|
||||||
scoreboard-update-interval-ticks: 10
|
scoreboard-update-interval-ticks: 10
|
||||||
|
# Global switch for the optional billboard: a BlockDisplay entity placed via
|
||||||
|
# /blockparty setbillboard <arena> that visually mirrors the currently selected
|
||||||
|
# target color each round. Also requires the per-arena billboard to be set and
|
||||||
|
# enabled (billboard-enabled in the arena's yml, default true).
|
||||||
|
billboard: true
|
||||||
|
|
||||||
sounds:
|
sounds:
|
||||||
join: ENTITY_EXPERIENCE_ORB_PICKUP
|
join: ENTITY_EXPERIENCE_ORB_PICKUP
|
||||||
|
|||||||
@@ -20,6 +20,8 @@ admin:
|
|||||||
lobby-set: "<green>Lobby set for '%arena%'.</green>"
|
lobby-set: "<green>Lobby set for '%arena%'.</green>"
|
||||||
spawn-set: "<green>Spawn set for '%arena%'.</green>"
|
spawn-set: "<green>Spawn set for '%arena%'.</green>"
|
||||||
spectator-set: "<green>Spectator location set for '%arena%'.</green>"
|
spectator-set: "<green>Spectator location set for '%arena%'.</green>"
|
||||||
|
billboard-set: "<green>Billboard set for '%arena%'. It will display the target color each round.</green>"
|
||||||
|
billboard-removed: "<green>Billboard removed for '%arena%'.</green>"
|
||||||
pos1-set: "<green>Position 1 set for '%arena%'.</green>"
|
pos1-set: "<green>Position 1 set for '%arena%'.</green>"
|
||||||
pos2-set: "<green>Position 2 set for '%arena%'.</green>"
|
pos2-set: "<green>Position 2 set for '%arena%'.</green>"
|
||||||
floor-set: "<green>Floor palette for '%arena%' set to %count% material(s).</green>"
|
floor-set: "<green>Floor palette for '%arena%' set to %count% material(s).</green>"
|
||||||
|
|||||||
Reference in New Issue
Block a user