Private pocket fixes

This commit is contained in:
Runemoro 2017-12-18 18:09:31 -05:00
parent 4c7c10f5d3
commit 26b3035b77
3 changed files with 46 additions and 29 deletions
src/main/java/com/zixiken/dimdoors/shared

View file

@ -13,6 +13,7 @@ import java.util.Map;
import lombok.Getter;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.entity.player.EntityPlayerMP;
import net.minecraft.nbt.NBTBase;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.nbt.NBTTagList;
import net.minecraft.world.storage.MapStorage;
@ -29,9 +30,9 @@ public class PocketRegistry extends WorldSavedData {
@Getter private int publicPocketSize;
private Map<String, Integer> privatePocketMap; // Player UUID -> Pocket ID, in pocket dim only
@Getter private Map<Integer, Pocket> pockets; // TODO: remove getter?
@Getter private int nextID;
@Getter private int dimID;
@Getter private int nextFreeID;
public PocketRegistry() {
super(DATA_NAME);
@ -63,7 +64,7 @@ public class PocketRegistry extends WorldSavedData {
privatePocketSize = DDConfig.getPrivatePocketSize();
publicPocketSize = DDConfig.getPublicPocketSize();
nextFreeID = 0;
nextID = 0;
pockets = new HashMap<>();
privatePocketMap = new HashMap<>();
}
@ -85,15 +86,13 @@ public class PocketRegistry extends WorldSavedData {
privatePocketSize = nbt.getInteger("privatePocketSize");
publicPocketSize = nbt.getInteger("publicPocketSize");
privatePocketMap = NBTUtils.readMapStringInteger(nbt.getCompoundTag("privatePocketMap"));
nextID = nbt.getInteger("nextID");
NBTTagList pocketsTagList = (NBTTagList) nbt.getTag("pockets");
pockets = new HashMap<>();
for (int id = 0; id < pocketsTagList.tagCount(); id++) { // TODO: convert to map to be able to skip IDs efficiently
NBTTagCompound pocketTag = pocketsTagList.getCompoundTagAt(id);
if (!pocketTag.getBoolean("nullPocket")) {
Pocket pocket = Pocket.readFromNBT(pocketTag);
pockets.put(id, pocket);
}
NBTTagList pocketsNBT = (NBTTagList) nbt.getTag("pockets");
for (NBTBase pocketNBT : pocketsNBT) { // TODO: convert to map to be able to skip IDs efficiently
NBTTagCompound pocketNBTC = (NBTTagCompound) pocketNBT;
pockets.put(pocketNBTC.getInteger("id"), Pocket.readFromNBT(pocketNBTC));
}
for (Pocket pocket : pockets.values()) {
@ -126,19 +125,16 @@ public class PocketRegistry extends WorldSavedData {
nbt.setInteger("privatePocketSize", privatePocketSize);
nbt.setInteger("publicPocketSize", publicPocketSize);
nbt.setTag("privatePocketMap", NBTUtils.writeMapStringInteger(privatePocketMap));
nbt.setInteger("nextID", nextID);
NBTTagList pocketsTagList = new NBTTagList();
for (int i = 0; i < nextFreeID; i++) {
Pocket pocket = pockets.get(i);
if (pocket == null) {
NBTTagCompound nullPocket = new NBTTagCompound();
nullPocket.setBoolean("nullPocket", true);
pocketsTagList.appendTag(nullPocket);
} else {
pocketsTagList.appendTag(Pocket.writeToNBT(pocket));
}
NBTTagList pocketsNBT = new NBTTagList();
for (Map.Entry<Integer, Pocket> pocketEntry : pockets.entrySet()) {
if (pocketEntry.getValue() == null) continue;
NBTTagCompound pocketNBT = (NBTTagCompound) Pocket.writeToNBT(pocketEntry.getValue());
pocketNBT.setInteger("id", pocketEntry.getKey()); // TODO: store separately?
pocketsNBT.appendTag(pocketNBT);
}
nbt.setTag("pockets", pocketsTagList);
nbt.setTag("pockets", pocketsNBT);
return nbt;
}
@ -150,7 +146,7 @@ public class PocketRegistry extends WorldSavedData {
*/
public Pocket newPocket(int depth) {
Pocket pocket = null;
while(pocket == null) pocket = newPocket(nextFreeID++, depth); // TODO: config option to reuse IDs (start at 0 rather than nextFreePocket)
while(pocket == null) pocket = newPocket(nextID++, depth); // TODO: config option to reuse IDs (start at 0 rather than nextFreePocket)
return pocket;
}
@ -165,7 +161,7 @@ public class PocketRegistry extends WorldSavedData {
GridUtils.GridPos pos = getGridPosFromID(id);
Pocket pocket = new Pocket(id, dimID, pos.getX(), pos.getZ(), depth);
pockets.put(id, pocket);
if (id >= nextFreeID) nextFreeID = id + 1;
if (id >= nextID) nextID = id + 1;
markDirty();
return pocket;
}

View file

@ -15,13 +15,18 @@ import com.zixiken.dimdoors.shared.world.DimDoorDimensions;
import lombok.Getter;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.Entity;
import net.minecraft.entity.EntityLiving;
import net.minecraft.entity.IEntityOwnable;
import net.minecraft.entity.item.EntityItem;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.entity.player.EntityPlayerMP;
import net.minecraft.entity.projectile.*;
import net.minecraft.nbt.NBTBase;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.nbt.NBTTagList;
import net.minecraft.network.NetworkManager;
import net.minecraft.network.play.server.SPacketUpdateTileEntity;
import net.minecraft.server.management.PlayerList;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.ITickable;
import net.minecraft.util.math.BlockPos;
@ -269,6 +274,7 @@ public abstract class TileEntityRift extends TileEntity implements ITickable { /
RiftDestination dest = weightedDestination.getDestination();
Location destLoc;
GlobalDestination destHere = new GlobalDestination(new Location(world, pos)); // TODO: local if possible
String uuid = getEntityOwnerUUID(entity);
switch (dest.getType()) {
case RELATIVE:
case LOCAL:
@ -283,9 +289,6 @@ public abstract class TileEntityRift extends TileEntity implements ITickable { /
if (destLoc != null) makeDestinationPermanent(weightedDestination, destLoc);
break;
case PRIVATE: // TODO: move logic to PrivatePocketTeleportDestination
String uuid = null;
if (entity instanceof EntityPlayer) uuid = entity.getUniqueID().toString();
if (entity instanceof IEntityOwnable && ((IEntityOwnable) entity).getOwnerId() != null) uuid = ((IEntityOwnable) entity).getOwnerId().toString();
if (uuid != null) {
PocketRegistry privatePocketRegistry = PocketRegistry.getForDim(DimDoorDimensions.getPrivateDimID());
RiftRegistry privateRiftRegistry = RiftRegistry.getForDim(DimDoorDimensions.getPrivateDimID());
@ -312,9 +315,6 @@ public abstract class TileEntityRift extends TileEntity implements ITickable { /
break;
case ESCAPE:
case PRIVATE_POCKET_EXIT:
/*String*/ uuid = null;
if (entity instanceof EntityPlayer) uuid = entity.getUniqueID().toString();
if (entity instanceof IEntityOwnable && ((IEntityOwnable) entity).getOwnerId() != null) uuid = ((IEntityOwnable) entity).getOwnerId().toString();
if (uuid != null) {
RiftRegistry privateRiftRegistry = RiftRegistry.getForDim(DimDoorDimensions.getPrivateDimID());
destLoc = RiftRegistry.getEscapeRift(uuid);
@ -390,7 +390,6 @@ public abstract class TileEntityRift extends TileEntity implements ITickable { /
if (!(tileEntityAtLoc instanceof TileEntityRift)) throw new RuntimeException("The rift referenced by this rift does not exist, this is a bug.");
TileEntityRift destRift = (TileEntityRift) tileEntityAtLoc;
if (entity instanceof EntityPlayer && !DimDoorDimensions.isPocketDimension(WorldUtils.getDim(world))) { // TODO: What about player-owned entities? We should store their exit rift separately to avoid having problems if they enter different rifts
String uuid = entity.getUniqueID().toString(); // TODO: More configuration on which worlds should be considered normal worlds. Other mods might add mostly void worlds, causing problems with random coordinates
RiftRegistry.setEscapeRift(uuid, new Location(world, pos));
}
destRift.teleportTo(entity);
@ -403,6 +402,27 @@ public abstract class TileEntityRift extends TileEntity implements ITickable { /
}
}
public String getEntityOwnerUUID(Entity entity) { // TODO: make this recursive, move to utils
if (entity instanceof EntityThrowable) entity = ((EntityThrowable) entity).getThrower();
if (entity instanceof EntityArrow) entity = ((EntityArrow) entity).shootingEntity;
if (entity instanceof EntityFireball) entity = ((EntityFireball) entity).shootingEntity;
if (entity instanceof EntityLlamaSpit) entity = ((EntityLlamaSpit) entity).owner; // Llamas are ownable
if (entity.getControllingPassenger() != null && !(entity instanceof EntityPlayer)) entity = entity.getControllingPassenger();
if (entity.getPassengers().size() > 0) entity.getPassengers().get(0);
if (entity instanceof EntityFishHook) entity = ((EntityFishHook) entity).getAngler();
if (entity instanceof EntityLiving && ((EntityLiving) entity).getLeashed()) entity = ((EntityLiving) entity).getLeashHolder();
if (entity instanceof EntityItem) {
String playerName = ((EntityItem) entity).getThrower();
EntityPlayer player = null;
if (playerName != null) player = entity.world.getPlayerEntityByName(((EntityItem) entity).getThrower());
if (player != null) entity = player;
}
if (entity instanceof IEntityOwnable && ((IEntityOwnable) entity).getOwnerId() != null) return ((IEntityOwnable) entity).getOwnerId().toString();
if (entity instanceof EntityPlayer) return entity.getUniqueID().toString(); // ownable players shouldn't be a problem, but just in case we have a slave mod, check their owner's uuid first to send them to their owner's pocket :)
return null;
}
private void makeDestinationPermanent(WeightedRiftDestination weightedDestination, Location destLoc) {
riftStateChanged = true;
RiftDestination newDest;

View file

@ -49,6 +49,7 @@ public class LimboDecay {
blocksImmuneToDecay = new IBlockState[] {
ModBlocks.FABRIC.getDefaultState().withProperty(BlockFabric.TYPE, BlockFabric.EnumType.UNRAVELED),
ModBlocks.FABRIC.getDefaultState().withProperty(BlockFabric.TYPE, BlockFabric.EnumType.ETERNAL),
ModBlocks.FABRIC.getDefaultState().withProperty(BlockFabric.TYPE, BlockFabric.EnumType.ANCIENT),
ModBlocks.TRANSIENT_DIMENSIONAL_DOOR.getDefaultState(),
ModBlocks.DIMENSIONAL_DOOR.getDefaultState(),
ModBlocks.WARP_DIMENSIONAL_DOOR.getDefaultState(),