Update to 1.13.

Adds "verifyPortals" config option, which sets whether a stargate layout is verified when it is loaded. This can be used if, for example, the material ids in your previous gate layouts cannot match new material names, but you don't want existing stargates to break. Or if you want to change a stargate design with something like WorldEdit after it's built.
This commit is contained in:
PseudoKnight 2018-08-27 05:25:13 -07:00
parent 9c36596cca
commit f07aac9907
8 changed files with 144 additions and 130 deletions

View File

@ -2,7 +2,7 @@
<modelVersion>4.0.0</modelVersion>
<groupId>org.TheDgtl</groupId>
<artifactId>Stargate</artifactId>
<version>0.7.9.11-SNAPSHOT</version>
<version>0.8.0.0-SNAPSHOT</version>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
@ -20,7 +20,7 @@
<dependency>
<groupId>org.spigotmc</groupId>
<artifactId>spigot-api</artifactId>
<version>1.12.2-R0.1-SNAPSHOT</version>
<version>1.13.1-R0.1-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>net.milkbowl.vault</groupId>
@ -51,8 +51,8 @@
<artifactId>maven-compiler-plugin</artifactId>
<version>3.6.1</version>
<configuration>
<source>1.7</source>
<target>1.7</target>
<source>1.8</source>
<target>1.8</target>
</configuration>
</plugin>
</plugins>

View File

@ -12,7 +12,8 @@
# handleVehicles - Whether to allow vehicles through gates
# sortLists - Whether to sort network lists alphabetically
# protectEntrance - Whether to protect gate entrance material (More resource intensive. Only enable if using destroyable open/closed material)
# signColor - The color used for drawing signs (Default: BLACK). See:
# signColor - The color used for drawing signs (Default: BLACK).
# verifyPortals - Whether or not all the non-sign blocks are checked to match the gate layout when a stargate is loaded.
############################
# Stargate economy options #
############################
@ -49,4 +50,5 @@ chargefreedestination: true
freegatesgreen: false
debug: false
permdebug: false
enableBungee: false
enableBungee: false
verifyPortals: true

View File

@ -4,6 +4,9 @@ import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.World;
import org.bukkit.block.Block;
import org.bukkit.block.BlockFace;
import org.bukkit.block.data.type.Sign;
import org.bukkit.block.data.type.WallSign;
/**
* Stargate - A portal plugin for Bukkit
@ -85,14 +88,6 @@ public class Blox {
return world.getBlockAt(x, y, z).getType();
}
public void setData(int data) {
world.getBlockAt(x, y, z).setData((byte)data);
}
public int getData() {
return world.getBlockAt(x, y, z).getData();
}
public Block getBlock() {
return world.getBlockAt(x, y, z);
}
@ -125,16 +120,10 @@ public class Blox {
int offsetZ = 0;
if (getBlock().getType() == Material.WALL_SIGN) {
if (getData() == 0x2) {
offsetZ = 1;
} else if (getData() == 0x3) {
offsetZ = -1;
} else if (getData() == 0x4) {
offsetX = 1;
} else if (getData() == 0x5) {
offsetX = -1;
}
} else if (getBlock().getType() == Material.SIGN_POST) {
BlockFace facing = ((WallSign) getBlock().getBlockData()).getFacing().getOppositeFace();
offsetX = facing.getModX();
offsetZ = facing.getModZ();
} else if (getBlock().getType() == Material.SIGN) {
offsetY = -1;
} else {
return;

View File

@ -1,22 +1,23 @@
package net.TheDgtl.Stargate;
import org.bukkit.Axis;
import org.bukkit.Material;
public class BloxPopulator {
private Blox blox;
private Material nextMat;
private byte nextData;
private Axis nextAxis;
public BloxPopulator(Blox b, Material m) {
blox = b;
nextMat = m;
nextData = 0;
nextAxis = null;
}
public BloxPopulator(Blox b, Material m, byte d) {
public BloxPopulator(Blox b, Material m, Axis a) {
blox = b;
nextMat = m;
nextData = d;
nextAxis = a;
}
public void setBlox(Blox b) {
@ -27,8 +28,8 @@ public class BloxPopulator {
nextMat = m;
}
public void setData(byte d) {
nextData = d;
public void setAxis(Axis a) {
nextAxis = a;
}
public Blox getBlox() {
@ -39,8 +40,8 @@ public class BloxPopulator {
return nextMat;
}
public byte getData() {
return nextData;
public Axis getAxis() {
return nextAxis;
}
}

View File

@ -51,7 +51,7 @@ public class Gate {
private RelativeBlockVector[] controls = new RelativeBlockVector[0];
private RelativeBlockVector exitBlock = null;
private HashMap<RelativeBlockVector, Integer> exits = new HashMap<>();
private Material portalBlockOpen = Material.PORTAL;
private Material portalBlockOpen = Material.NETHER_PORTAL;
private Material portalBlockClosed = Material.AIR;
// Economy information
@ -138,7 +138,9 @@ public class Gate {
bw.append(type);
bw.append('=');
bw.append(value.toString());
if(value != null) {
bw.append(value.toString());
}
bw.newLine();
}
@ -247,6 +249,7 @@ public class Gate {
}
public boolean matches(Blox topleft, int modX, int modZ, boolean onCreate) {
HashMap<Character, Material> portalTypes = new HashMap<>(types);
for (int y = 0; y < layout.length; y++) {
for (int x = 0; x < layout[y].length; x++) {
Character key = layout[y][x];
@ -260,27 +263,17 @@ public class Gate {
if (onCreate && type == Material.AIR) continue;
if (type != portalBlockClosed && type != portalBlockOpen) {
// Special case for water gates
if (portalBlockOpen == Material.WATER || portalBlockOpen == Material.STATIONARY_WATER) {
if (type == Material.WATER || type == Material.STATIONARY_WATER) {
continue;
}
}
// Special case for lava gates
if (portalBlockOpen == Material.LAVA || portalBlockOpen == Material.STATIONARY_LAVA) {
if (type == Material.LAVA || type == Material.STATIONARY_LAVA) {
continue;
}
}
Stargate.debug("Gate::Matches", "Entrance/Exit Material Mismatch: " + type);
return false;
}
} else if (!key.equals(ANYTHING)) {
Material id = types.get(key);
if (topleft.modRelative(x, y, 0, modX, 1, modZ).getType() != id) {
Stargate.debug("Gate::Matches", "Block Type Mismatch: " + topleft.modRelative(x, y, 0, modX, 1, modZ).getType() + " != " + id);
return false;
}
Material id = portalTypes.get(key);
if(id == null) {
portalTypes.put(key, topleft.modRelative(x, y, 0, modX, 1, modZ).getType());
} else if(topleft.modRelative(x, y, 0, modX, 1, modZ).getType() != id) {
Stargate.debug("Gate::Matches", "Block Type Mismatch: " + topleft.modRelative(x, y, 0, modX, 1, modZ).getType() + " != " + id);
return false;
}
}
}
}
@ -294,7 +287,7 @@ public class Gate {
Material blockID = gate.getControlBlock();
if (!controlBlocks.containsKey(blockID)) {
controlBlocks.put(blockID, new ArrayList<Gate>());
controlBlocks.put(blockID, new ArrayList<>());
}
controlBlocks.get(blockID).add(gate);

View File

@ -7,6 +7,7 @@ import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Random;
import java.util.Scanner;
import java.util.logging.Level;
@ -18,20 +19,23 @@ import net.TheDgtl.Stargate.event.StargateDeactivateEvent;
import net.TheDgtl.Stargate.event.StargateOpenEvent;
import net.TheDgtl.Stargate.event.StargatePortalEvent;
import org.bukkit.Axis;
import org.bukkit.ChatColor;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.World;
import org.bukkit.block.Block;
import org.bukkit.block.BlockFace;
import org.bukkit.block.Sign;
import org.bukkit.block.data.BlockData;
import org.bukkit.block.data.Directional;
import org.bukkit.block.data.Powerable;
import org.bukkit.entity.Entity;
import org.bukkit.entity.Player;
import org.bukkit.entity.minecart.StorageMinecart;
import org.bukkit.entity.Vehicle;
import org.bukkit.event.block.SignChangeEvent;
import org.bukkit.event.player.PlayerMoveEvent;
import org.bukkit.material.Button;
import org.bukkit.material.MaterialData;
import org.bukkit.material.Step;
import org.bukkit.util.Vector;
@ -72,6 +76,7 @@ public class Portal {
private int modX;
private int modZ;
private float rotX;
private Axis rot;
// Block references
private Blox id;
@ -117,6 +122,7 @@ public class Portal {
this.modX = modX;
this.modZ = modZ;
this.rotX = rotX;
this.rot = rotX == 90.0F || rotX == 270.0F ? Axis.X : Axis.Z;
this.id = id;
this.destination = dest;
this.button = button;
@ -234,6 +240,10 @@ public class Portal {
public float getRotation() {
return rotX;
}
public Axis getAxis() {
return rot;
}
public Player getActivePlayer() {
return activePlayer;
@ -366,8 +376,9 @@ public class Portal {
getWorld().loadChunk(getWorld().getChunkAt(topLeft.getBlock()));
Material openType = gate.getPortalBlockOpen();
Axis ax = openType == Material.NETHER_PORTAL ? rot : null;
for (Blox inside : getEntrances()) {
Stargate.blockPopulatorQueue.add(new BloxPopulator(inside, openType));
Stargate.blockPopulatorQueue.add(new BloxPopulator(inside, openType, ax));
}
isOpen = true;
@ -442,10 +453,11 @@ public class Portal {
RelativeBlockVector[] controls = gate.getControls();
for (RelativeBlockVector vector : controls) {
MaterialData mat = getBlockAt(vector).getBlock().getState().getData();
BlockData data = getBlockAt(vector).getBlock().getBlockData();
if (mat instanceof Button && ((Button)mat).isPowered())
if (data instanceof Powerable && ((Powerable) data).isPowered()) {
return true;
}
}
return false;
@ -496,34 +508,20 @@ public class Portal {
vehicle.setVelocity(new Vector());
// Get new velocity
final Vector newVelocity = new Vector();
switch (id.getBlock().getData()) {
case 2:
newVelocity.setZ(-1);
break;
case 3:
newVelocity.setZ(1);
break;
case 4:
newVelocity.setX(-1);
break;
case 5:
newVelocity.setX(1);
break;
}
final Vector newVelocity = new Vector(modX, 0.0F, modZ);
newVelocity.multiply(velocity);
final Entity passenger = vehicle.getPassenger();
if (passenger != null) {
List<Entity> passengers = vehicle.getPassengers();
if (!passengers.isEmpty()) {
final Vehicle v = exit.getWorld().spawn(exit, vehicle.getClass());
final Entity passenger = passengers.get(0);
vehicle.eject();
vehicle.remove();
passenger.eject();
passenger.teleport(exit);
Stargate.server.getScheduler().scheduleSyncDelayedTask(Stargate.stargate, new Runnable() {
public void run() {
v.setPassenger(passenger);
v.setVelocity(newVelocity);
}
Stargate.server.getScheduler().scheduleSyncDelayedTask(Stargate.stargate, () -> {
v.addPassenger(passenger);
v.setVelocity(newVelocity);
}, 1);
} else {
Vehicle mc = exit.getWorld().spawn(exit, vehicle.getClass());
@ -568,6 +566,9 @@ public class Portal {
public boolean isVerified() {
verified = true;
if(!Stargate.verifyPortals) {
return true;
}
for (RelativeBlockVector control : gate.getControls()) {
verified = verified && getBlockAt(control).getBlock().getType().equals(gate.getControlBlock());
}
@ -575,10 +576,16 @@ public class Portal {
}
public boolean wasVerified() {
if(!Stargate.verifyPortals) {
return true;
}
return verified;
}
public boolean checkIntegrity() {
if(!Stargate.verifyPortals) {
return true;
}
return gate.matches(topLeft, modX, modZ);
}
@ -692,7 +699,7 @@ public class Portal {
public final void drawSign() {
Material sMat = id.getBlock().getType();
if (sMat != Material.SIGN && sMat != Material.WALL_SIGN && sMat != Material.SIGN_POST) {
if (sMat != Material.SIGN && sMat != Material.WALL_SIGN) {
Stargate.log.warning("[Stargate] Sign block is not a Sign object");
Stargate.debug("Portal::drawSign", "Block: " + id.getBlock().getType() + " @ " + id.getBlock().getLocation());
return;
@ -854,14 +861,14 @@ public class Portal {
// Check if network exists in our network list
if (!lookupNamesNet.containsKey(getNetwork().toLowerCase())) {
Stargate.debug("register", "Network " + getNetwork() + " not in lookupNamesNet, adding");
lookupNamesNet.put(getNetwork().toLowerCase(), new HashMap<String, Portal>());
lookupNamesNet.put(getNetwork().toLowerCase(), new HashMap<>());
}
lookupNamesNet.get(getNetwork().toLowerCase()).put(getName().toLowerCase(), this);
// Check if this network exists
if (!allPortalsNet.containsKey(getNetwork().toLowerCase())) {
Stargate.debug("register", "Network " + getNetwork() + " not in allPortalsNet, adding");
allPortalsNet.put(getNetwork().toLowerCase(), new ArrayList<String>());
allPortalsNet.put(getNetwork().toLowerCase(), new ArrayList<>());
}
allPortalsNet.get(getNetwork().toLowerCase()).add(getName().toLowerCase());
}
@ -952,24 +959,24 @@ public class Portal {
int modX = 0;
int modZ = 0;
float rotX = 0f;
int facing = 0;
BlockFace buttonfacing = BlockFace.DOWN;
if (idParent.getX() > id.getBlock().getX()) {
modZ -= 1;
rotX = 90f;
facing = 2;
buttonfacing = BlockFace.WEST;
} else if (idParent.getX() < id.getBlock().getX()) {
modZ += 1;
rotX = 270f;
facing = 1;
buttonfacing = BlockFace.EAST;
} else if (idParent.getZ() > id.getBlock().getZ()) {
modX += 1;
rotX = 180f;
facing = 4;
buttonfacing = BlockFace.NORTH;
} else if (idParent.getZ() < id.getBlock().getZ()) {
modX -= 1;
rotX = 0f;
facing = 3;
buttonfacing = BlockFace.SOUTH;
}
Gate[] possibleGates = Gate.getGatesByControlBlock(idParent);
@ -1145,7 +1152,9 @@ public class Portal {
if (!alwaysOn) {
button = topleft.modRelative(buttonVector.getRight(), buttonVector.getDepth(), buttonVector.getDistance() + 1, modX, 1, modZ);
button.setType(Material.STONE_BUTTON);
button.setData(facing);
Directional buttondata = (Directional) button.getBlock().getBlockData();
buttondata.setFacing(buttonfacing);
button.getBlock().setBlockData(buttondata);
portal.setButton(button);
}
@ -1198,6 +1207,34 @@ public class Portal {
public static Portal getByEntrance(Block block) {
return lookupEntrances.get(new Blox(block));
}
public static Portal getByAdjacentEntrance(Location loc) {
int centerX = loc.getBlockX();
int centerY = loc.getBlockY();
int centerZ = loc.getBlockZ();
World world = loc.getWorld();
Portal portal = lookupEntrances.get(new Blox(world, centerX, centerY, centerZ));
if(portal != null) {
return portal;
}
portal = lookupEntrances.get(new Blox(world, centerX + 1, centerY, centerZ));
if(portal != null) {
return portal;
}
portal = lookupEntrances.get(new Blox(world, centerX - 1, centerY, centerZ));
if(portal != null) {
return portal;
}
portal = lookupEntrances.get(new Blox(world, centerX, centerY, centerZ + 1));
if(portal != null) {
return portal;
}
portal = lookupEntrances.get(new Blox(world, centerX, centerY, centerZ - 1));
if(portal != null) {
return portal;
}
return null;
}
public static Portal getByControl(Block block) {
return lookupControls.get(new Blox(block));
@ -1355,18 +1392,17 @@ public class Portal {
// DEBUG
for (RelativeBlockVector control : portal.getGate().getControls()) {
if (!portal.getBlockAt(control).getBlock().getType().equals(portal.getGate().getControlBlock())) {
Stargate.debug("loadAllGates", "Control Block Type == " + portal.getBlockAt(control).getBlock().getTypeId());
Stargate.debug("loadAllGates", "Control Block Type == " + portal.getBlockAt(control).getBlock().getType().name());
}
}
portal.unregister(false);
iter.remove();
Stargate.log.info("[Stargate] Destroying stargate at " + portal.toString());
continue;
} else {
portal.drawSign();
portalCount++;
}
}
portal.drawSign();
portalCount++;
if (!portal.isFixed()) continue;

View File

@ -19,12 +19,13 @@ import net.TheDgtl.Stargate.event.StargateDestroyEvent;
import org.bukkit.Bukkit;
import org.bukkit.ChatColor;
import org.bukkit.GameMode;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.Server;
import org.bukkit.World;
import org.bukkit.block.Block;
import org.bukkit.block.EndGateway;
import org.bukkit.block.Sign;
import org.bukkit.block.data.Orientable;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.configuration.file.FileConfiguration;
@ -46,7 +47,7 @@ import org.bukkit.event.entity.EntityExplodeEvent;
import org.bukkit.event.player.PlayerInteractEvent;
import org.bukkit.event.player.PlayerJoinEvent;
import org.bukkit.event.player.PlayerMoveEvent;
import org.bukkit.event.player.PlayerPortalEvent;
import org.bukkit.event.player.PlayerTeleportEvent;
import org.bukkit.event.server.PluginDisableEvent;
import org.bukkit.event.server.PluginEnableEvent;
import org.bukkit.event.vehicle.VehicleMoveEvent;
@ -100,6 +101,7 @@ public class Stargate extends JavaPlugin {
public static boolean sortLists = false;
public static boolean protectEntrance = false;
public static boolean enableBungee = true;
public static boolean verifyPortals = true;
public static ChatColor signColor;
// Temp workaround for snowmen, don't check gate entrance
@ -191,6 +193,7 @@ public class Stargate extends JavaPlugin {
sortLists = newConfig.getBoolean("sortLists");
protectEntrance = newConfig.getBoolean("protectEntrance");
enableBungee = newConfig.getBoolean("enableBungee");
verifyPortals = newConfig.getBoolean("verifyPortals");
// Sign color
String sc = newConfig.getString("signColor");
try {
@ -681,32 +684,14 @@ public class Stargate extends JavaPlugin {
}
@EventHandler
public void onPlayerPortal(PlayerPortalEvent event) {
if (event.isCancelled()) return;
// Do a quick check for a stargate
Location from = event.getFrom();
if (from == null) {
Stargate.debug("onPlayerPortal", "From location is null. Stupid Bukkit");
return;
}
World world = from.getWorld();
int cX = from.getBlockX();
int cY = from.getBlockY();
int cZ = from.getBlockZ();
for (int i = -2; i < 2; i++) {
for (int j = -2; j < 2; j++) {
for (int k = -2; k < 2; k++) {
Block b = world.getBlockAt(cX + i, cY + j, cZ + k);
// We only need to worry about portal mat
// Commented out for now, due to new Minecraft insta-nether
//if (b.getType() != Material.PORTAL) continue;
Portal portal = Portal.getByEntrance(b);
if (portal != null) {
event.setCancelled(true);
return;
}
}
}
public void onPlayerTeleport(PlayerTeleportEvent event) {
// cancel portal and endgateway teleportation if it's from a Stargate entrance
PlayerTeleportEvent.TeleportCause cause = event.getCause();
if(!event.isCancelled()
&& (cause == PlayerTeleportEvent.TeleportCause.NETHER_PORTAL
|| cause == PlayerTeleportEvent.TeleportCause.END_GATEWAY && World.Environment.THE_END == event.getFrom().getWorld().getEnvironment())
&& Portal.getByAdjacentEntrance(event.getFrom()) != null) {
event.setCancelled(true);
}
}
@ -1012,7 +997,7 @@ public class Stargate extends JavaPlugin {
Portal portal = null;
// Handle keeping portal material and buttons around
if (block.getType() == Material.PORTAL) {
if (block.getType() == Material.NETHER_PORTAL) {
portal = Portal.getByEntrance(block);
} else if (block.getType() == Material.STONE_BUTTON) {
portal = Portal.getByControl(block);
@ -1056,11 +1041,7 @@ public class Stargate extends JavaPlugin {
private class wListener implements Listener {
@EventHandler
public void onWorldLoad(WorldLoadEvent event) {
World w = event.getWorld();
// We have to make sure the world is actually loaded. This gets called twice for some reason.
if (w.getBlockAt(w.getSpawnLocation()).getWorld() != null) {
Portal.loadAllGates(w);
}
Portal.loadAllGates(event.getWorld());
}
// We need to reload all gates on world unload, boo
@ -1090,8 +1071,8 @@ public class Stargate extends JavaPlugin {
if (destroyExplosion) {
portal.unregister(true);
} else {
Stargate.blockPopulatorQueue.add(new BloxPopulator(new Blox(b), b.getType(), b.getData()));
event.setCancelled(true);
break;
}
}
}
@ -1116,11 +1097,22 @@ public class Stargate extends JavaPlugin {
private class BlockPopulatorThread implements Runnable {
public void run() {
long sTime = System.nanoTime();
while (System.nanoTime() - sTime < 50000000) {
while (System.nanoTime() - sTime < 25000000) {
BloxPopulator b = Stargate.blockPopulatorQueue.poll();
if (b == null) return;
b.getBlox().getBlock().setType(b.getMat(), false);
b.getBlox().getBlock().setData(b.getData(), false);
Block blk = b.getBlox().getBlock();
blk.setType(b.getMat(), false);
if(b.getMat() == Material.END_GATEWAY && blk.getWorld().getEnvironment() == World.Environment.THE_END) {
// force a location to prevent exit gateway generation
EndGateway gateway = (EndGateway) blk.getState();
gateway.setExitLocation(blk.getWorld().getSpawnLocation());
gateway.setExactTeleport(true);
gateway.update(false, false);
} else if(b.getAxis() != null) {
Orientable orientable = (Orientable) blk.getBlockData();
orientable.setAxis(b.getAxis());
blk.setBlockData(orientable);
}
}
}
}

View File

@ -4,6 +4,7 @@ version: 0.7.9.11
description: Stargate mod for Bukkit
author: Drakia
website: http://www.thedgtl.net
api-version: 1.13
commands:
sg:
description: Used to reload the plugin. Console use only.