v2.2.0: refactored patch rooms to be more extensible

This commit is contained in:
Evan Debenham
2023-08-03 16:47:40 -04:00
parent 36e21c0ffc
commit c48b372bfc
6 changed files with 159 additions and 66 deletions

View File

@@ -40,7 +40,29 @@ public class BurnedRoom extends PatchRoom {
int cell = l.pointToCell(pointInside(p, 1));
return l.map[cell] == Terrain.EMPTY;
}
@Override
protected float fill() {
//past 8x8 each point of width/height decreases fill by 3%
// e.g. a 14x14 burned room has a fill of 54%
return Math.min( 1f, 1.48f - (width()+height())*0.03f);
}
@Override
protected int clustering() {
return 2;
}
@Override
protected boolean ensurePath() {
return false;
}
@Override
protected boolean cleanEdges() {
return false;
}
@Override
public void paint(Level level) {
Painter.fill( level, this, Terrain.WALL );
@@ -49,10 +71,7 @@ public class BurnedRoom extends PatchRoom {
door.set( Door.Type.REGULAR );
}
//past 8x8 each point of width/height decreases fill by 3%
// e.g. a 14x14 burned room has a fill of 54%
float fill = Math.min( 1f, 1.48f - (width()+height())*0.03f);
setupPatch(level, fill, 2, false );
setupPatch(level);
for (int i=top + 1; i < bottom; i++) {
for (int j=left + 1; j < right; j++) {

View File

@@ -27,11 +27,42 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.painters.Painter;
public class CaveRoom extends PatchRoom {
@Override
public int minWidth() { return Math.max(6, super.minWidth()); }
@Override
public int minHeight() { return Math.max(6, super.minHeight()); }
@Override
public float[] sizeCatProbs() {
return new float[]{4, 2, 1};
}
@Override
protected float fill() {
//fill scales from ~30% at 4x4, to ~60% at 18x18
// normal ~30% to ~40%
// large ~40% to ~50%
// giant ~50% to ~60%
int scale = Math.min(width()*height(), 18*18);
return 0.30f + scale/1024f;
}
@Override
protected int clustering() {
return 3;
}
@Override
protected boolean ensurePath() {
return connected.size() > 0;
}
@Override
protected boolean cleanEdges() {
return true;
}
@Override
public void paint(Level level) {
Painter.fill( level, this, Terrain.WALL );
@@ -39,25 +70,8 @@ public class CaveRoom extends PatchRoom {
for (Door door : connected.values()) {
door.set( Door.Type.REGULAR );
}
//fill scales from ~30% at 4x4, to ~60% at 18x18
// normal ~30% to ~40%
// large ~40% to ~50%
// giant ~50% to ~60%
int scale = Math.min(width()*height(), 18*18);
float fill = 0.30f + scale/1024f;
setupPatch(level, fill, 3, connected.size() > 0);
cleanDiagonalEdges();
for (int i = top + 1; i < bottom; i++) {
for (int j = left + 1; j < right; j++) {
if (patch[xyToPatchCoords(j, i)]) {
int cell = i * level.width() + j;
level.map[cell] = Terrain.WALL;
}
}
}
setupPatch(level);
fillPatch(level, Terrain.WALL);
}
}

View File

@@ -34,6 +34,31 @@ public class ChasmRoom extends PatchRoom {
return new float[]{4, 2, 1};
}
@Override
protected float fill() {
//fill scales from ~30% at 4x4, to ~60% at 18x18
// normal ~30% to ~40%
// large ~40% to ~50%
// giant ~50% to ~60%
int scale = Math.min(width()*height(), 18*18);
return 0.30f + scale/1024f;
}
@Override
protected int clustering() {
return 1;
}
@Override
protected boolean ensurePath() {
return connected.size() > 0;
}
@Override
protected boolean cleanEdges() {
return true;
}
@Override
public void merge(Level l, Room other, Rect merge, int mergeTerrain) {
if (mergeTerrain == Terrain.EMPTY
@@ -53,24 +78,9 @@ public class ChasmRoom extends PatchRoom {
door.set( Room.Door.Type.REGULAR );
}
//fill scales from ~30% at 4x4, to ~60% at 18x18
// normal ~30% to ~40%
// large ~40% to ~50%
// giant ~50% to ~60%
int scale = Math.min(width()*height(), 18*18);
float fill = 0.30f + scale/1024f;
setupPatch(level);
setupPatch(level, fill, 1, connected.size() > 0);
cleanDiagonalEdges();
for (int i = top + 1; i < bottom; i++) {
for (int j = left + 1; j < right; j++) {
if (patch[xyToPatchCoords(j, i)]) {
int cell = i * level.width() + j;
level.map[cell] = Terrain.CHASM;
}
}
}
fillPatch(level, Terrain.CHASM);
}
}

View File

@@ -49,6 +49,26 @@ public class CircleBasinRoom extends PatchRoom {
return this;
}
@Override
protected float fill() {
return 0.5f;
}
@Override
protected int clustering() {
return 5;
}
@Override
protected boolean ensurePath() {
return false;
}
@Override
protected boolean cleanEdges() {
return false;
}
@Override
public void paint(Level level) {
Painter.fill( level, this, Terrain.WALL );
@@ -80,7 +100,7 @@ public class CircleBasinRoom extends PatchRoom {
Painter.set( level, center, Terrain.WALL );
}
setupPatch(level, 0.5f, 5, true);
setupPatch(level);
for (int i = top + 1; i < bottom; i++) {
for (int j = left + 1; j < right; j++) {
int cell = i * level.width() + j;

View File

@@ -31,15 +31,21 @@ import com.watabou.utils.PathFinder;
public abstract class PatchRoom extends StandardRoom {
protected boolean[] patch;
protected abstract float fill();
protected abstract int clustering();
protected abstract boolean ensurePath();
protected abstract boolean cleanEdges();
protected void setupPatch(Level level, float fill, int clustering, boolean ensurePath){
protected void setupPatch(Level level){
int attempts = 0;
if (ensurePath){
if (ensurePath()){
float fill = fill();
PathFinder.setMapSize(width()-2, height()-2);
boolean valid;
do {
patch = Patch.generate(width()-2, height()-2, fill, clustering, true);
patch = Patch.generate(width()-2, height()-2, fill, clustering(), true);
int startPoint = level.pointToCell(center());
for (Door door : connected.values()) {
if (door.x == left) {
@@ -78,7 +84,22 @@ public abstract class PatchRoom extends StandardRoom {
} while (!valid);
PathFinder.setMapSize(level.width(), level.height());
} else {
patch = Patch.generate(width()-2, height()-2, fill, clustering, true);
patch = Patch.generate(width()-2, height()-2, fill(), clustering(), true);
}
if (cleanEdges()){
cleanDiagonalEdges();
}
}
//convenience method for the common case of just setting all terrain in the patch to a value
protected void fillPatch(Level level, int terrain){
for (int i = top + 1; i < bottom; i++) {
for (int j = left + 1; j < right; j++) {
if (patch[xyToPatchCoords(j, i)]) {
int cell = i * level.width() + j;
level.map[cell] = terrain;
}
}
}
}

View File

@@ -38,6 +38,31 @@ public class RuinsRoom extends PatchRoom {
return true;
}
@Override
protected float fill() {
//fill scales from ~20% at 4x4, to ~50% at 18x18
// normal ~20% to ~30%
// large ~30% to ~40%
// giant ~40% to ~50%
int scale = Math.min(width()*height(), 18*18);
return 0.20f + scale/1024f;
}
@Override
protected int clustering() {
return 9;
}
@Override
protected boolean ensurePath() {
return connected.size() > 0;
}
@Override
protected boolean cleanEdges() {
return true;
}
@Override
public void paint(Level level) {
Painter.fill( level, this, Terrain.WALL );
@@ -45,24 +70,8 @@ public class RuinsRoom extends PatchRoom {
for (Door door : connected.values()) {
door.set( Door.Type.REGULAR );
}
//fill scales from ~20% at 4x4, to ~50% at 18x18
// normal ~20% to ~30%
// large ~30% to ~40%
// giant ~40% to ~50%
int scale = Math.min(width()*height(), 18*18);
float fill = 0.20f + scale/1024f;
setupPatch(level, fill, 0, connected.size() > 0);
cleanDiagonalEdges();
for (int i = top + 1; i < bottom; i++) {
for (int j = left + 1; j < right; j++) {
if (patch[xyToPatchCoords(j, i)]) {
int cell = i * level.width() + j;
level.map[cell] = Terrain.WALL;
}
}
}
setupPatch(level);
fillPatch(level, Terrain.WALL);
}
}