Package com.bergerkiller.bukkit.mw

Source Code of com.bergerkiller.bukkit.mw.WorldManager

package com.bergerkiller.bukkit.mw;

import java.io.*;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Map.Entry;
import java.util.Random;
import java.util.logging.Level;
import java.util.zip.DeflaterOutputStream;
import java.util.zip.GZIPInputStream;
import java.util.zip.InflaterInputStream;
import java.util.zip.ZipException;

import org.bukkit.Bukkit;
import org.bukkit.ChatColor;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.World;
import org.bukkit.World.Environment;
import org.bukkit.WorldCreator;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import org.bukkit.generator.ChunkGenerator;
import org.bukkit.plugin.Plugin;
import org.bukkit.plugin.java.JavaPlugin;

import com.bergerkiller.bukkit.common.MaterialTypeProperty;
import com.bergerkiller.bukkit.common.nbt.CommonTagCompound;
import com.bergerkiller.bukkit.common.reflection.classes.RegionFileCacheRef;
import com.bergerkiller.bukkit.common.reflection.classes.RegionFileRef;
import com.bergerkiller.bukkit.common.utils.CommonUtil;
import com.bergerkiller.bukkit.common.utils.EntityUtil;
import com.bergerkiller.bukkit.common.utils.LogicUtil;
import com.bergerkiller.bukkit.common.utils.MaterialUtil;
import com.bergerkiller.bukkit.common.utils.ParseUtil;
import com.bergerkiller.bukkit.common.utils.StreamUtil;
import com.bergerkiller.bukkit.common.utils.WorldUtil;

public class WorldManager {
  private static final MaterialTypeProperty SAFE_SPAWN_AIR;
  private static final MaterialTypeProperty SAFE_SPAWN_SURFACE;
  static {
    HashSet<Material> safeAir = new HashSet<Material>();
    HashSet<Material> safeSurface = new HashSet<Material>();
    try {
      boolean isSafeSurface;
      for (Material type : Material.values()) {
        LogicUtil.addOrRemove(safeSurface, type, isSafeSurface = MaterialUtil.ISSOLID.get(type));
        LogicUtil.addOrRemove(safeAir, type, !isSafeSurface &&
            !MaterialUtil.SUFFOCATES.get(type) && !MaterialUtil.ISPRESSUREPLATE.get(type));
      }
      LogicUtil.removeArray(safeAir, Material.WATER, Material.STATIONARY_WATER, Material.LAVA, Material.STATIONARY_LAVA);
      LogicUtil.removeArray(safeAir, Material.TRIPWIRE, Material.LEAVES, Material.PORTAL, Material.ENDER_PORTAL);
      LogicUtil.removeArray(safeSurface, Material.LEAVES, Material.DRAGON_EGG, Material.PORTAL, Material.ENDER_PORTAL);
    } catch (Throwable t) {
      t.printStackTrace();
    }
    SAFE_SPAWN_AIR = new MaterialTypeProperty(safeAir.toArray(new Material[0]));
    SAFE_SPAWN_SURFACE = new MaterialTypeProperty(safeSurface.toArray(new Material[0]));
  }

  /**
   * Closes all file streams associated with the world specified.
   *
   * @param world to close
   */
  public static void closeWorldStreams(World world) {
    // Wait until all chunks of this world are saved
    WorldUtil.saveToDisk(world);
    // Close the region files
    synchronized (RegionFileCacheRef.TEMPLATE.getType()) {
      try {
        String worldPart = "." + File.separator + world.getName();
        Iterator<Entry<File, Object>> iter = RegionFileCacheRef.FILES.entrySet().iterator();
        Entry<File, Object> entry;
        while (iter.hasNext()) {
          entry = iter.next();
          if (!entry.getKey().toString().startsWith(worldPart) || entry.getValue() == null) {
            continue;
          }
          try {
            RegionFileRef.close.invoke(entry.getValue());
            iter.remove();
          } catch (Exception ex) {
            ex.printStackTrace();
          }
        }
      } catch (Exception ex) {
        MyWorlds.plugin.log(Level.WARNING, "Exception while removing world reference for '" + world.getName() + "'!");
        ex.printStackTrace();
      }
    }
  }

  /*
   * Get or set the respawn point of a world
   */
  public static void setSpawnLocation(String forWorld, Location destination) {
    setSpawn(forWorld, new Position(destination));
  }
  public static void setSpawn(String forWorld, Position destination) {
    WorldConfig.get(forWorld).spawnPoint = destination;
  }
  public static Position getRespawn(String ofWorld) {
    return WorldConfig.get(ofWorld).spawnPoint;
  }
  public static Location getRespawnLocation(String ofWorld) {
    Position pos = getRespawn(ofWorld);
    if (pos != null) {
      Location loc = pos.toLocation();
      if (loc.getWorld() != null) {
        return loc;
      }
    }
    return null;
  }
  public static Location getRespawnLocation(World ofWorld) {
    return getRespawnLocation(ofWorld.getName());
  }
 
  /*
   * Gets a possible teleport position on a certain world
   */
  public static Location getSpawnLocation(World onWorld) {
    Position[] pos = getSpawnPoints(onWorld);
    if (pos.length > 0) return pos[0].toLocation();
    return onWorld.getSpawnLocation();
  }

  /**
   * Gets the Spawn Position of a World, which permits unloaded worlds to be checked
   *
   * @param onWorldName of the World to get the spawn of
   * @return Spawn position
   */
  public static Position getSpawnPosition(String onWorldName) {
    WorldConfig worldC = WorldConfig.get(onWorldName);
    // Same world spawn
    if (worldC.spawnPoint.getWorldName().equalsIgnoreCase(onWorldName)) {
      return worldC.spawnPoint;
    }
    // Loop other worlds with a possible spawn point there
    for (WorldConfig wc : WorldConfig.all()) {
      if (wc.spawnPoint.getWorldName().equalsIgnoreCase(onWorldName)) {
        return wc.spawnPoint;
      }
    }
    // No spawn available, request it from the World (if loaded)
    World world = worldC.getWorld();
    if (world != null) {
      return new Position(world.getSpawnLocation());
    }
    // Read from level.dat (if available)
    CommonTagCompound data = worldC.getData();
    if (data != null) {
      double[] pos = data.getValue("Pos", double[].class);
      float[] rot = data.getValue("Rotation", float[].class);
      return new Position(onWorldName, pos[0], pos[1], pos[2], rot[0], rot[1]);
    }
    // Absolutely NO idea, return a generic position
    return new Position(onWorldName, 0, 64, 0);
  }

  public static Position[] getSpawnPoints() {
    Collection<WorldConfig> all = WorldConfig.all();
    Position[] pos = new Position[all.size()];
    int i = 0;
    for (WorldConfig wc : all) {
      pos[i] = wc.spawnPoint;
      i++;
    }
    return pos;
  }
  public static Position[] getSpawnPoints(World onWorld) {
    return getSpawnPoints(onWorld.getName());
  }
  public static Position[] getSpawnPoints(String onWorld) {
    ArrayList<Position> pos = new ArrayList<Position>();
    for (Position p : getSpawnPoints()) {
      if (p.getWorldName().equalsIgnoreCase(onWorld)) {
        pos.add(p);
      }
    }
    return pos.toArray(new Position[0]);
  }

  /*
   * Chunk generators
   */
  public static String[] getGeneratorPlugins() {
    ArrayList<String> gens = new ArrayList<String>();
    for (Plugin plugin : Bukkit.getServer().getPluginManager().getPlugins()) {
      try {
        String mainclass = plugin.getDescription().getMain();
        Class<?> cmain = Class.forName(mainclass);
        if (cmain == null) continue;
        if (cmain.getMethod("getDefaultWorldGenerator", String.class, String.class).getDeclaringClass() != JavaPlugin.class) {
          gens.add(plugin.getDescription().getName());
        }
      } catch (Throwable t) {}
    }
    return gens.toArray(new String[0]);
  }

  public static String fixGeneratorName(String name) {
    if (LogicUtil.nullOrEmpty(name)) {
      return null;
    }
    String genName = name;
    String args = "";
    int index = name.indexOf(":");
    if (index != -1) {
      args = name.substring(index + 1);
      genName = name.substring(0, index);
    }
    if (genName.isEmpty()) {
      // Only arguments (meant for default generator)
      return ":" + args;
    } else {
      //get plugin name
      final String pname = ParseUtil.parseArray(getGeneratorPlugins(), genName.toLowerCase(), null);
      if (pname == null) {
        // Not found
        return null;
      } else {
        // Found: append arguments
        return pname + ":" + args;
      }
    }
  }
  public static ChunkGenerator getGenerator(String worldname, String name) {
    if (name == null) {
      return null;
    }
    String id = "";
    int index = name.indexOf(":");
    if (index != -1) {
      id = name.substring(index + 1);
      name = name.substring(0, index);
    }
    Plugin plug = Bukkit.getServer().getPluginManager().getPlugin(name);
    if (plug != null) {
      return plug.getDefaultWorldGenerator(worldname, id);
    } else {
      return null;
    }
  }

  /*
   * General world fields
   */
  public static long getSeed(String seed) {
    if (seed == null) return 0;
    long seedval = 0;
    try {
      seedval = Long.parseLong(seed);
    } catch (Exception ex) {
      seedval = seed.hashCode();
    }
    return seedval;
  }

  public static long getRandomSeed(String seed) {
    long seedval = getSeed(seed);
    if (seedval == 0) {
      seedval = new Random().nextLong();
    }
    return seedval;
  }

  public static String getWorldName(CommandSender sender, String[] args, boolean useAlternative) {
    String alternative = (args == null || args.length == 0) ? null : args[args.length - 1];
    return getWorldName(sender, alternative, useAlternative);
  }

  public static String getWorldName(CommandSender sender, String alternative, boolean useAlternative) {
    String worldname = null;
    if (useAlternative) {
      worldname = WorldManager.matchWorld(alternative);
    } else if (sender instanceof Player) {
      worldname = ((Player) sender).getWorld().getName();
    } else {
      for (World w : Bukkit.getServer().getWorlds()) {
        worldname = w.getName();
        break;
      }
    }
    return worldname;
  }

  public static String matchWorld(String matchname) {
    if (matchname == null || matchname.isEmpty()) {
      return null;
    }
    Collection<String> worldnames = WorldUtil.getLoadableWorlds();
    for (String worldname : worldnames) {
      if (worldname.equalsIgnoreCase(matchname)) return worldname;
    }
    matchname = matchname.toLowerCase();
    for (String worldname : worldnames) {
      if (worldname.toLowerCase().contains(matchname)) return worldname;
    }
    return null;
  }

  public static World getWorld(String worldname) {
    if (worldname == null) return null;
    try {
      return Bukkit.getServer().getWorld(worldname);
    } catch (Exception ex) {
      return null;
    }
  }

  public static boolean isLoaded(String worldname) {
    return getWorld(worldname) != null;
  }

  public static boolean worldExists(String worldname) {
    return worldname != null && WorldUtil.isLoadableWorld(worldname);
  }

  public static World getOrCreateWorld(String worldname) {
    World w = getWorld(worldname);
    if (w != null) return w;
    return createWorld(worldname, 0);
  }

  public static boolean unload(World world) {
    if (world != null) {
      LoadChunksTask.abortWorld(world, true);
      return Bukkit.getServer().unloadWorld(world, world.isAutoSave());
    }
    return false;
  }

  /**
   * Creates a new World
   *
   * @param worldname to create
   * @param seed to use
   * @return The created World, or null on failure
   */
  public static World createWorld(String worldname, long seed) {
    return createWorld(worldname, seed, null);
  }

  /**
   * Creates a new World
   *
   * @param worldname to create
   * @param seed to use
   * @param sender to send creation problems to if they occur (null to ignore)
   * @return The created World, or null on failure
   */
  public static World createWorld(String worldname, long seed, CommandSender sender) {
    WorldConfig wc = WorldConfig.get(worldname);
    final boolean load = wc.isInitialized();
    String chunkGeneratorName = wc.getChunkGeneratorName();
    StringBuilder msg = new StringBuilder();
    if (load) {
      msg.append("Loading");
    } else {
      msg.append("Generating");
    }
    msg.append(" world '").append(worldname).append("'");
    if (seed == 0) {
      if (chunkGeneratorName != null) {
        msg.append(" using chunk generator: '").append(chunkGeneratorName).append("'");
      }
    } else {
      msg.append(" using seed ").append(seed);
      if (chunkGeneratorName != null) {
        msg.append(" and chunk generator: '").append(chunkGeneratorName).append("'");
      }
    }
    MyWorlds.plugin.log(Level.INFO, msg.toString());
   
    final int retrycount = 3;
    World w = null;
    int i = 0;
    ChunkGenerator cgen = null;
    try {
      if (chunkGeneratorName != null) {
        cgen = getGenerator(worldname, chunkGeneratorName);
      }
    } catch (Exception ex) {}
    if (cgen == null) {
      if (chunkGeneratorName != null) {
        msg.setLength(0);
        msg.append("World '").append(worldname);
        msg.append("' could not be created because the chunk generator '");
        msg.append(chunkGeneratorName).append("' was not found!");
        MyWorlds.plugin.log(Level.SEVERE, msg.toString());
        if (sender != null) {
          sender.sendMessage(ChatColor.RED + msg.toString());
        }
        return null;
      }
    }
    Exception failReason = null;
    for (i = 0; i < retrycount + 1; i++) {
      try {
        WorldCreator c = new WorldCreator(worldname);
        wc.worldmode.apply(c);
        if (seed != 0) {
          c.seed(seed);
        }
        c.generator(cgen);
        w = c.createWorld();
      } catch (Exception ex) {
        failReason = ex;
      }
      if (w != null) break;
    }
    if (w == null) {
      MyWorlds.plugin.log(Level.WARNING, "World creation failed after " + i + " retries!");
      if (failReason != null) {
        if (sender != null) {
          sender.sendMessage(ChatColor.RED + "Failed to create world: " + failReason.getMessage());
        }
        CommonUtil.filterStackTrace(failReason).printStackTrace();
      }
    } else if (i == 1) {
      MyWorlds.plugin.log(Level.INFO, "World creation succeeded after 1 retry!");
    } else if (i > 0) {
      MyWorlds.plugin.log(Level.INFO, "World creation succeeded after " + i + " retries!");
    }
    return w;
  }

  public static Location getEvacuation(Player player) {
    World world = player.getWorld();
    String[] portalnames;
    if (Permission.COMMAND_SPAWN.has(player) || Permission.COMMAND_TPP.has(player)) {
      for (Position pos : getSpawnPoints()) {
        Location loc = pos.toLocation();
        if (loc.getWorld() == null || loc.getWorld() == world) {
          continue;
        }
        if (Permission.canEnter(player, loc.getWorld())) {
          return loc;
        }
      }
      portalnames = Portal.getPortals();
    } else {
      portalnames = Portal.getPortals(world);
    }
    for (String name : portalnames) {
      if (Permission.canEnterPortal(player, name)) {
        Location loc = Portal.getPortalLocation(name, player.getWorld().getName(), true);
        if (loc == null || loc.getWorld() == null || loc.getWorld() == world) {
          continue;
        }
        if (Permission.canEnter(player, loc.getWorld())) {
          return loc;
        }
      }
    }
    return null;
  }

  public static void evacuate(World world, String message) {
    for (Player player : world.getPlayers()) {
      Location loc = getEvacuation(player);
      if (loc != null) {
        player.teleport(loc);
        player.sendMessage(ChatColor.RED + message);
      } else {
        player.kickPlayer(message);
      }
    }
  }
  public static void teleportToClonedWorld(World from, World cloned) {
    for (Player p : from.getPlayers().toArray(new Player[0])) {
      Location loc = p.getLocation();
      loc.setWorld(cloned);
      p.teleport(loc);
    }
  }

  /**
   * Tries to find a (personal) spawn location to teleport players to.
   * If last position remembering is turned on and a last position is known,
   * this Location is returned. Otherwise, the world spawn point is returned.
   *
   * @param player to find the world spawn for
   * @param world to find the world spawn in
   * @return Spawn location
   */
  public static Location getPlayerWorldSpawn(Player player, World world) {
    if (WorldConfig.get(world).rememberLastPlayerPosition || Permission.GENERAL_KEEPLASTPOS.has(player)) {
      // Player is already in the world to go to...so we just return that instead
      if (player.getWorld() == world) {
        return player.getLocation();
      }

      // Figure out the last position of the player on the world
      Location location = MWPlayerDataController.readLastLocation(player, world);
      if (location != null) {
        return location;
      }
    }
    return getSpawnLocation(world);
  }

  /**
   * Teleports a player to a world. If the world allows the last player position
   * on the world to be used, this is used instead. If no last position is known,
   * or last position remembering is disabled, the player is teleported to the
   * world spawn position.
   *
   * @param player to teleport
   * @param world to teleport to
   * @return True if successful, False if not
   */
  public static boolean teleportToWorld(Player player, World world) {
    return EntityUtil.teleport(player, getPlayerWorldSpawn(player, world));
  }

  /**
   * Teleports all players from one world to the other.
   *
   * @param from world to teleport all players from
   * @param to world to teleport to
   * @see #teleportToWorld(Player, World)
   */
  public static void teleportAllPlayersToWorld(World from, World to) {
    for (Player p : from.getPlayers().toArray(new Player[0])) {
      teleportToWorld(p, to);
    }
  }

  /**
   * Looks for a suitable place to spawn near the Start Location specified.
   *
   * @param startLocation
   * @return A safe location to spawn at
   */
  public static Location getSafeSpawn(Location startLocation) {
    return getSafeSpawn(startLocation, true);
  }

  /**
   * Looks for a suitable place to spawn near the Start Location specified.
   *
   * @param startLocation
   * @param allowPortals - whether portals can be designated as a safe spawn
   * @return A safe location to spawn at
   */
  public static Location getSafeSpawn(Location startLocation, boolean allowPortals) {
    // First, ask the internal spawn finding logic to do this for us
    // This COULD fail, proper detection for that is key!
    if (allowPortals) {
      Location pos = WorldUtil.findSpawnLocation(startLocation, false);
      if (pos != null) {
        // Sometimes an odd 128-height location is returned (nether)
        // This check prevents that from being used here
        int posX = pos.getBlockX();
        int posY = pos.getBlockY();
        int posZ = pos.getBlockZ();
        if (posX != 0 || posZ != 0 || (posY != 128 && posY != 256)) {
          return pos;
        }
      }
    }
    // Do it ourselves
    final World world = startLocation.getWorld();
    final int blockX = startLocation.getBlockX();
    final int blockY = startLocation.getBlockY();
    final int blockZ = startLocation.getBlockZ();
    final int startY = world.getEnvironment() == Environment.NETHER ? 127 : (world.getMaxHeight() - 1);
    final Random random = new Random();
    int y, x = blockX, z = blockZ;
    int alterX = blockX, alterY = blockY, alterZ = blockZ;
    int airCounter;
    Material type;
    for (int retry = 0; retry < 200; retry++) {
      airCounter = world.getEnvironment() == Environment.NETHER ? 0 : 2;
      for (y = startY; y > 0; y--) {
        type = WorldUtil.getBlockType(world, x, y, z);
        if (SAFE_SPAWN_AIR.get(type)) {
          // Air block - continue
          airCounter++;
        } else {
          // Safe spawn is only there with 2 air-blocks above the surface
          if (airCounter >= 2) {
            if (SAFE_SPAWN_SURFACE.get(type)) {
              // Safe place to spawn on - ENDING
              return new Location(world, x + 0.5, y + 1.5, z + 0.5);
            } else {
              // Unsafe place but still a surface...set as alternative
              alterX = x;
              alterY = y + 1;
              alterZ = z;
              break;
            }
          }
          airCounter = 0;
        }
      }

      // Obtain a new column to look at
      // For the first 5 calls, probe around a bit < 8 blocks away
      if (retry <= 5) {
        x = blockX + random.nextInt(8) - 3;
        z = blockZ + random.nextInt(8) - 3;
      } else {
        x = blockX + random.nextInt(128) - 63;
        z = blockZ + random.nextInt(128) - 63;
      }
    }
    // Return the alternative (unsafe) location
    // This could occur if spawning in an ocean, for example
    return new Location(world, alterX + 0.5, alterY + 0.5, alterZ + 0.5);
  }

  /**
   * Repairs the chunk region file
   * Returns -1 if the file had to be removed
   * Returns -2 if we had no access
   * Returns -3 if file removal failed (from -1)
   * Returns the amount of changed chunks otherwise
   * @param chunkfile
   * @param backupfolder
   * @return
   */
  public static int repairRegion(File chunkfile, File backupfolder) {
    MyWorlds.plugin.log(Level.INFO, "Performing repairs on region file: " + chunkfile.getName());
    RandomAccessFile raf = null;
    try {
      String name = chunkfile.getName().substring(2);
      String xname = name.substring(0, name.indexOf('.'));
      name = name.substring(xname.length() + 1);
      String zname = name.substring(0, name.indexOf('.'));
     
      int xOffset = 32 * Integer.parseInt(xname);
      int zOffset = 32 * Integer.parseInt(zname);
     
      raf = new RandomAccessFile(chunkfile, "rw");
      File backupfile = new File(backupfolder, chunkfile.getName());
      int[] locations = new int[1024];
      for (int i = 0; i < 1024; i++) {
        locations[i] = raf.readInt();
      }
      //Validate the data
      int editcount = 0;
      int chunkX = 0;
      int chunkZ = 0;
     
      //x = 5
      //z = 14
      //i = 5 + 14 * 32 = 453
      //x = i % 32 = 5
      //z = [(453 - 5)]  448 / 32 =
     
      byte[] data = new byte[8096];
      for (int i = 0; i < locations.length; i++) {
        chunkX = i % 32;
        chunkZ = (i - chunkX) >> 5;
        chunkX += xOffset;
        chunkZ += zOffset;
        int location = locations[i];
        if (location == 0) {
          continue;
        }
        try {
          int offset = location >> 8;
                    int size = location & 255;
                    long seekindex = (long) (offset * 4096);
          raf.seek(seekindex);
          int length = raf.readInt();
          //Read and test the data
          if (length > 4096 * size) {
            editcount++;
            locations[i] = 0;
            MyWorlds.plugin.log(Level.WARNING, "Invalid length: " + length + " > 4096 * " + size);
            //Invalid length
          } else if (size > 0 && length > 0) {
            byte version = raf.readByte();
            if (data.length < length + 10) {
              data = new byte[length + 10];
            }
            raf.read(data, 0, length - 1);
            ByteArrayInputStream bais = new ByteArrayInputStream(data, 0, length - 1);
            //Try to load it all...
            DataInputStream stream;
            if (version == 1) {
              stream = new DataInputStream(new BufferedInputStream(new GZIPInputStream(bais)));
            } else if (version == 2) {
              stream = new DataInputStream(new BufferedInputStream(new InflaterInputStream(bais)));
            } else {
              stream = null;
              //Unknown version
              MyWorlds.plugin.log(Level.WARNING, "Unknown region version: " + version + " (we probably need an update here!)");
            }
            if (stream != null) {
             
              //Validate the stream and close
              try {
                CommonTagCompound comp = CommonTagCompound.readFromUncompressed(stream);
                if (comp == null) {
                  editcount++;
                  locations[i] = 0;
                  MyWorlds.plugin.log(Level.WARNING, "Invalid tag compound at chunk " + chunkX + "/" + chunkZ);
                } else {
                  //correct location?
                  if (comp.containsKey("Level")) {
                    CommonTagCompound level = comp.createCompound("Level");
                    int xPos = level.getValue("xPos", Integer.MIN_VALUE);
                    int zPos = level.getValue("zPos", Integer.MIN_VALUE);
                    //valid coordinates?
                    if (xPos != chunkX || zPos != chunkZ) {
                      MyWorlds.plugin.log(Level.WARNING, "Chunk [" + xPos + "/" + zPos + "] was stored at [" + chunkX + "/" + chunkZ + "], moving...");
                      level.putValue("xPos", chunkX);
                      level.putValue("zPos", chunkZ);
                      //rewrite to stream
                      ByteArrayOutputStream baos = new ByteArrayOutputStream(8096);
                          OutputStream outputstream = new DeflaterOutputStream(baos);
                          level.writeToUncompressed(outputstream);
                          outputstream.close();
                          //write to region file
                          raf.seek(seekindex);
                          byte[] newdata = baos.toByteArray();
                          raf.writeInt(newdata.length + 1);
                          raf.writeByte(2);
                          raf.write(newdata, 0, newdata.length);
                          editcount++;
                    }
                  } else {
                    editcount++;
                    locations[i] = 0;
                    MyWorlds.plugin.log(Level.WARNING, "Invalid tag compound at chunk " + chunkX + "/" + chunkZ);
                  }
                }
              } catch (ZipException ex) {
                //Invalid.
                editcount++;
                locations[i] = 0;
                MyWorlds.plugin.log(Level.WARNING, "Chunk at position " + chunkX + "/" + chunkZ + " is not in a valid ZIP format (it's corrupted, and thus lost)");
              } catch (Exception ex) {
                //Invalid.
                editcount++;
                locations[i] = 0;
                MyWorlds.plugin.log(Level.WARNING, "Failed to properly read chunk at position " + chunkX + "/" + chunkZ + ":");
                ex.printStackTrace();
              }
              stream.close();
            }
          }
        } catch (Exception ex) {
          editcount++;
          locations[i] = 0;
          ex.printStackTrace();
        }
      }
      if (editcount > 0) {
        if ((backupfolder.exists() || backupfolder.mkdirs()) && StreamUtil.tryCopyFile(chunkfile, backupfile)) {
          //Write out the new locations
          raf.seek(0);
          for (int location : locations) {
            raf.writeInt(location);
          }
        } else {
          MyWorlds.plugin.log(Level.WARNING, "Failed to make a copy of the file, no changes are made.");
          return -2;
        }
      }
      //Done.
      raf.close();
      return editcount;
    } catch (FileNotFoundException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    } catch (IOException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }
   
    try {
      if (raf != null) raf.close();
    } catch (Exception ex) {}
   
    try {
      chunkfile.delete();
      return -1;
    } catch (Exception ex) {
      return -3;
    }
  }

  @Deprecated
  public static boolean generateData(String worldname, String seed) {
    return WorldConfig.get(worldname).resetData(seed);
  }

  @Deprecated
  public static boolean generateData(String worldname, long seed) {
      return WorldConfig.get(worldname).resetData(seed);
  }

  @Deprecated
  public static CommonTagCompound createData(String worldname, long seed) {
    return WorldConfig.get(worldname).createData(seed);
  }

  @Deprecated
  public static CommonTagCompound getData(String worldname) {
    return WorldConfig.get(worldname).getData();
  }

  @Deprecated
  public static boolean setData(String worldname, CommonTagCompound data) {
      return WorldConfig.get(worldname).setData(data);
  }

  @Deprecated
  public static File getDataFile(String worldname) {
    return WorldConfig.get(worldname).getDataFile();
  }

  @Deprecated
  public static File getUIDFile(String worldname) {
    return WorldConfig.get(worldname).getUIDFile();
  }

  @Deprecated
  public static long getWorldSize(String worldname) {
    return WorldConfig.get(worldname).getWorldSize();
  }

  @Deprecated
  public static WorldInfo getInfo(String worldname) {
    return WorldConfig.get(worldname).getInfo();
  }

  @Deprecated
  public static boolean isBroken(String worldname) {
    return WorldConfig.get(worldname).isBroken();
  }

  @Deprecated
  public static boolean isInitialized(String worldname) {
    return WorldConfig.get(worldname).isInitialized();
  }

  @Deprecated
  public static boolean copyWorld(String worldname, String newname) {
    return WorldConfig.get(worldname).copyTo(WorldConfig.get(newname));
  }

  @Deprecated
  public static boolean deleteWorld(String worldname) {
    return WorldConfig.get(worldname).deleteWorld();
  }
}
TOP

Related Classes of com.bergerkiller.bukkit.mw.WorldManager

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.