Fixed Vertical Dungeon Clipping

Added code to SchematicLoader to adjust the Y coordinate of the
destination link into a dungeon before the dungeon is created.
IMPORTANT: The code is commented out at the moment because it causes a
link-related NullPointerException. A link needs to be updated through
DimHelper but the code is hard to follow so I've decided to just not
touch it - Steven will have to do it.

The function adjustDestinationY() checks if the given entrance location
would place any portion of the dungeon outside the vertical bounds of
the world. If so, it corrects the location while moving it as little as
possible from its original place.

Also added some checks to make sure that any schematic we load has an
entrance door. Otherwise, load defaultBreak instead. And I cut down on
the absurd number of compiler warnings in dimHelper. <_< Stop accessing
static fields as instance fields!
This commit is contained in:
SenseiKiwi
2013-07-31 12:09:47 -04:00
parent 356bfe4bd0
commit 96c1b3d7a4
3 changed files with 129 additions and 96 deletions

View File

@@ -42,19 +42,39 @@ public class SchematicLoader
}
DungeonSchematic dungeon = checkSourceAndLoad(schematicPath);
boolean valid;
//Validate the dungeon's dimensions
if (!hasValidDimensions(dungeon))
if (hasValidDimensions(dungeon))
{
dungeon.applyImportFilters(properties);
//Check that the dungeon has an entrance or we'll have a crash
if (dungeon.getEntranceDoorLocation() != null)
{
valid = true;
}
else
{
System.err.println("The following schematic file does not have an entrance: " + schematicPath);
valid = false;
}
}
else
{
System.err.println("The following schematic file has dimensions that exceed the maximum permitted dimensions for dungeons: " + schematicPath);
valid = false;
}
if (!valid)
{
//TODO: In the future, remove this dungeon from the generation lists altogether.
//That will have to wait until our code is updated to support that more easily.
System.err.println("The following schematic file has dimensions that exceed the maximum permitted dimensions for dungeons: " + schematicPath);
System.err.println("The dungeon will not be loaded.");
dungeon = checkSourceAndLoad(DungeonHelper.instance().defaultBreak.schematicPath);
dungeon.applyImportFilters(properties);
}
dungeon.applyImportFilters(properties);
dimList.get(destDimID).hasBeenFilled = true;
if (dimHelper.getWorld(destDimID) == null)
{
@@ -62,6 +82,12 @@ public class SchematicLoader
}
World world = dimHelper.getWorld(destDimID);
//Adjust the height at which the dungeon is placed to prevent vertical clipping
//link.destYCoord = adjustDestinationY(world, link.destYCoord, dungeon);
//Adjust the data for the destination link to prevent crashes
//TODO: I really have no idea how to do this. =/ The LinkData/dimHelper implementation causes me sadness. ~SenseiKiwi
dungeon.copyToWorld(world, new Point3D(link.destXCoord, link.destYCoord, link.destZCoord), link.linkOrientation, originDimID, destDimID);
return true;
}
@@ -72,6 +98,29 @@ public class SchematicLoader
}
}
private static int adjustDestinationY(World world, int y, DungeonSchematic dungeon)
{
//The goal here is to guarantee that the dungeon fits within the vertical bounds
//of the world while shifting it as little as possible.
int destY = y;
//Is the top of the dungeon going to be at Y < worldHeight?
int entranceY = dungeon.getEntranceDoorLocation().getY();
int pocketTop = (dungeon.getHeight() - 1) + destY - entranceY;
int worldHeight = world.getHeight();
if (pocketTop >= worldHeight)
{
destY = (worldHeight - 1) - (dungeon.getHeight() - 1) + entranceY;
}
//Is the bottom of the dungeon at Y >= 0?
if (destY < entranceY)
{
destY = entranceY;
}
return destY;
}
private static boolean hasValidDimensions(DungeonSchematic dungeon)
{
return (dungeon.getWidth() <= DungeonHelper.MAX_DUNGEON_WIDTH &&