v0.4.2: added support for variable map sizes

This commit is contained in:
Evan Debenham
2016-08-17 21:04:58 -04:00
parent 36e44340a8
commit 806217e209
142 changed files with 821 additions and 759 deletions
@@ -34,20 +34,26 @@ public class PathFinder {
private static int size = 0; private static int size = 0;
private static int[] dir; private static int[] dir;
//performance-light shortcuts for some common pathfinder cases
public static int[] NEIGHBOURS4;
public static int[] NEIGHBOURS8;
public static int[] NEIGHBOURS9;
public static void setMapSize( int width, int height ) { public static void setMapSize( int width, int height ) {
int size = width * height; int size = width * height;
if (PathFinder.size != size) {
PathFinder.size = size; PathFinder.size = size;
distance = new int[size]; distance = new int[size];
goals = new boolean[size]; goals = new boolean[size];
queue = new int[size]; queue = new int[size];
dir = new int[]{-1, +1, -width, +width, -width-1, -width+1, +width-1, +width+1}; dir = new int[]{-1, +1, -width, +width, -width-1, -width+1, +width-1, +width+1};
}
NEIGHBOURS4 = new int[]{-width, +1, +width, -1};
NEIGHBOURS8 = new int[]{-width, +1-width, +1, +1+width, +width, -1+width, -1, -1-width};
NEIGHBOURS9 = new int[]{0, -width, +1-width, +1, +1+width, +width, -1+width, -1, -1-width};
} }
public static Path find( int from, int to, boolean[] passable ) { public static Path find( int from, int to, boolean[] passable ) {
@@ -129,7 +129,7 @@ public class Dungeon {
public static HashSet<Integer> chapters; public static HashSet<Integer> chapters;
// Hero's field of view // Hero's field of view
public static boolean[] visible = new boolean[Level.LENGTH]; public static boolean[] visible;
public static SparseArray<ArrayList<Item>> droppedItems; public static SparseArray<ArrayList<Item>> droppedItems;
@@ -143,8 +143,6 @@ public class Dungeon {
Actor.clear(); Actor.clear();
Actor.resetNextID(); Actor.resetNextID();
PathFinder.setMapSize( Level.WIDTH, Level.HEIGHT );
Scroll.initLabels(); Scroll.initLabels();
Potion.initColors(); Potion.initColors();
Ring.initGems(); Ring.initGems();
@@ -203,8 +201,6 @@ public class Dungeon {
} }
} }
Arrays.fill( visible, false );
Level level; Level level;
switch (depth) { switch (depth) {
case 1: case 1:
@@ -261,7 +257,8 @@ public class Dungeon {
level = new DeadEndLevel(); level = new DeadEndLevel();
Statistics.deepestFloor--; Statistics.deepestFloor--;
} }
visible = new boolean[level.length()];
level.create(); level.create();
Statistics.qualifiedForNoKilling = !bossLevel(); Statistics.qualifiedForNoKilling = !bossLevel();
@@ -273,8 +270,6 @@ public class Dungeon {
Actor.clear(); Actor.clear();
Arrays.fill( visible, false );
level.reset(); level.reset();
switchLevel( level, level.entrance ); switchLevel( level, level.entrance );
} }
@@ -296,6 +291,9 @@ public class Dungeon {
Dungeon.level = level; Dungeon.level = level;
Actor.init(); Actor.init();
PathFinder.setMapSize(level.width(), level.height());
visible = new boolean[level.length()];
Actor respawner = level.respawner(); Actor respawner = level.respawner();
if (respawner != null) { if (respawner != null) {
@@ -531,10 +529,6 @@ public class Dungeon {
Dungeon.level = null; Dungeon.level = null;
Dungeon.depth = -1; Dungeon.depth = -1;
if (fullLoad) {
PathFinder.setMapSize( Level.WIDTH, Level.HEIGHT );
}
Scroll.restore( bundle ); Scroll.restore( bundle );
Potion.restore( bundle ); Potion.restore( bundle );
Ring.restore( bundle ); Ring.restore( bundle );
@@ -677,18 +671,17 @@ public class Dungeon {
GameScene.afterObserve(); GameScene.afterObserve();
} }
private static boolean[] passable = new boolean[Level.LENGTH];
public static int findPath( Char ch, int from, int to, boolean pass[], boolean[] visible ) { public static int findPath( Char ch, int from, int to, boolean pass[], boolean[] visible ) {
if (Level.adjacent( from, to )) { if (level.adjacent( from, to )) {
return Actor.findChar( to ) == null && (pass[to] || Level.avoid[to]) ? to : -1; return Actor.findChar( to ) == null && (pass[to] || Level.avoid[to]) ? to : -1;
} }
boolean[] passable = new boolean[Dungeon.level.length()];
if (ch.flying || ch.buff( Amok.class ) != null) { if (ch.flying || ch.buff( Amok.class ) != null) {
BArray.or( pass, Level.avoid, passable ); BArray.or( pass, Level.avoid, passable );
} else { } else {
System.arraycopy( pass, 0, passable, 0, Level.LENGTH ); System.arraycopy( pass, 0, passable, 0, Dungeon.level.length() );
} }
for (Char c : Actor.chars()) { for (Char c : Actor.chars()) {
@@ -702,11 +695,12 @@ public class Dungeon {
} }
public static int flee( Char ch, int cur, int from, boolean pass[], boolean[] visible ) { public static int flee( Char ch, int cur, int from, boolean pass[], boolean[] visible ) {
boolean[] passable = new boolean[Dungeon.level.length()];
if (ch.flying) { if (ch.flying) {
BArray.or( pass, Level.avoid, passable ); BArray.or( pass, Level.avoid, passable );
} else { } else {
System.arraycopy( pass, 0, passable, 0, Level.LENGTH ); System.arraycopy( pass, 0, passable, 0, Dungeon.level.length() );
} }
for (Char c : Actor.chars()) { for (Char c : Actor.chars()) {
@@ -38,7 +38,7 @@ public class DungeonTilemap extends Tilemap {
super( super(
Dungeon.level.tilesTex(), Dungeon.level.tilesTex(),
new TextureFilm( Dungeon.level.tilesTex(), SIZE, SIZE ) ); new TextureFilm( Dungeon.level.tilesTex(), SIZE, SIZE ) );
map( Dungeon.level.map, Level.WIDTH ); map( Dungeon.level.map, Dungeon.level.width() );
instance = this; instance = this;
} }
@@ -48,7 +48,12 @@ public class DungeonTilemap extends Tilemap {
offset( this.point().negate() ). offset( this.point().negate() ).
invScale( SIZE ). invScale( SIZE ).
floor(); floor();
return p.x >= 0 && p.x < Level.WIDTH && p.y >= 0 && p.y < Level.HEIGHT ? p.x + p.y * Level.WIDTH : -1; return p.x >= 0
&& p.x < Dungeon.level.width()
&& p.y >= 0
&& p.y < Dungeon.level.height() ?
p.x + p.y * Dungeon.level.width()
: -1;
} }
@Override @Override
@@ -75,13 +80,13 @@ public class DungeonTilemap extends Tilemap {
} }
public static PointF tileToWorld( int pos ) { public static PointF tileToWorld( int pos ) {
return new PointF( pos % Level.WIDTH, pos / Level.WIDTH ).scale( SIZE ); return new PointF( pos % Dungeon.level.width(), pos / Dungeon.level.width() ).scale( SIZE );
} }
public static PointF tileCenterToWorld( int pos ) { public static PointF tileCenterToWorld( int pos ) {
return new PointF( return new PointF(
(pos % Level.WIDTH + 0.5f) * SIZE, (pos % Dungeon.level.width() + 0.5f) * SIZE,
(pos / Level.WIDTH + 0.5f) * SIZE ); (pos / Dungeon.level.width() + 0.5f) * SIZE );
} }
public static Image tile( int index ) { public static Image tile( int index ) {
@@ -49,6 +49,7 @@ import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Bundlable; import com.watabou.utils.Bundlable;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.GameMath; import com.watabou.utils.GameMath;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.HashSet; import java.util.HashSet;
@@ -399,9 +400,9 @@ public abstract class Char extends Actor {
public void move( int step ) { public void move( int step ) {
if (Level.adjacent( step, pos ) && buff( Vertigo.class ) != null) { if (Dungeon.level.adjacent( step, pos ) && buff( Vertigo.class ) != null) {
sprite.interruptMotion(); sprite.interruptMotion();
int newPos = pos + Level.NEIGHBOURS8[Random.Int( 8 )]; int newPos = pos + PathFinder.NEIGHBOURS8[Random.Int( 8 )];
if (!(Level.passable[newPos] || Level.avoid[newPos]) || Actor.findChar( newPos ) != null) if (!(Level.passable[newPos] || Level.avoid[newPos]) || Actor.findChar( newPos ) != null)
return; return;
else { else {
@@ -426,7 +427,7 @@ public abstract class Char extends Actor {
} }
public int distance( Char other ) { public int distance( Char other ) {
return Level.distance( pos, other.pos ); return Dungeon.level.distance( pos, other.pos );
} }
public void onMotionComplete() { public void onMotionComplete() {
@@ -26,6 +26,7 @@ import com.shatteredpixel.shatteredpixeldungeon.effects.BlobEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.Speck; import com.shatteredpixel.shatteredpixeldungeon.effects.Speck;
import com.shatteredpixel.shatteredpixeldungeon.items.Heap; import com.shatteredpixel.shatteredpixeldungeon.items.Heap;
import com.shatteredpixel.shatteredpixeldungeon.items.Item; import com.shatteredpixel.shatteredpixeldungeon.items.Item;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
public class Alchemy extends Blob { public class Alchemy extends Blob {
@@ -35,8 +36,8 @@ public class Alchemy extends Blob {
@Override @Override
public void restoreFromBundle( Bundle bundle ) { public void restoreFromBundle( Bundle bundle ) {
super.restoreFromBundle( bundle ); super.restoreFromBundle( bundle );
for (int i=0; i < LENGTH; i++) { for (int i=0; i < cur.length; i++) {
if (cur[i] > 0) { if (cur[i] > 0) {
pos = i; pos = i;
break; break;
@@ -54,7 +55,10 @@ public class Alchemy extends Blob {
} }
@Override @Override
public void seed( int cell, int amount ) { public void seed( Level level, int cell, int amount ) {
if (cur == null) cur = new int[level.length()];
if (off == null) off = new int[cur.length];
cur[pos] = 0; cur[pos] = 0;
pos = cell; pos = cell;
volume = cur[pos] = amount; volume = cur[pos] = amount;
@@ -33,13 +33,9 @@ import java.util.Arrays;
public class Blob extends Actor { public class Blob extends Actor {
{ {
actPriority = 1; //take prioerity over mobs, but not the hero actPriority = 1; //take priority over mobs, but not the hero
} }
public static final int WIDTH = Level.WIDTH;
public static final int HEIGHT = Level.HEIGHT;
public static final int LENGTH = Level.LENGTH;
public int volume = 0; public int volume = 0;
public int[] cur; public int[] cur;
@@ -47,16 +43,9 @@ public class Blob extends Actor {
public BlobEmitter emitter; public BlobEmitter emitter;
protected Blob() {
cur = new int[LENGTH];
off = new int[LENGTH];
volume = 0;
}
private static final String CUR = "cur"; private static final String CUR = "cur";
private static final String START = "start"; private static final String START = "start";
private static final String LENGTH = "length";
@Override @Override
public void storeInBundle( Bundle bundle ) { public void storeInBundle( Bundle bundle ) {
@@ -65,19 +54,20 @@ public class Blob extends Actor {
if (volume > 0) { if (volume > 0) {
int start; int start;
for (start=0; start < LENGTH; start++) { for (start=0; start < Dungeon.level.length(); start++) {
if (cur[start] > 0) { if (cur[start] > 0) {
break; break;
} }
} }
int end; int end;
for (end=LENGTH-1; end > start; end--) { for (end=Dungeon.level.length()-1; end > start; end--) {
if (cur[end] > 0) { if (cur[end] > 0) {
break; break;
} }
} }
bundle.put( START, start ); bundle.put( START, start );
bundle.put( LENGTH, cur.length );
bundle.put( CUR, trim( start, end + 1 ) ); bundle.put( CUR, trim( start, end + 1 ) );
} }
@@ -94,6 +84,13 @@ public class Blob extends Actor {
public void restoreFromBundle( Bundle bundle ) { public void restoreFromBundle( Bundle bundle ) {
super.restoreFromBundle( bundle ); super.restoreFromBundle( bundle );
if (bundle.contains(LENGTH)) {
cur = new int[bundle.getInt(LENGTH)];
} else {
//compatability with pre-0.4.2
cur = new int[1024];
}
int[] data = bundle.getIntArray( CUR ); int[] data = bundle.getIntArray( CUR );
if (data != null) { if (data != null) {
@@ -103,18 +100,6 @@ public class Blob extends Actor {
volume += data[i]; volume += data[i];
} }
} }
if (Level.resizingNeeded) {
int[] cur = new int[Level.LENGTH];
Arrays.fill( cur, 0 );
int loadedMapSize = Level.loadedMapSize;
for (int i=0; i < loadedMapSize; i++) {
System.arraycopy( this.cur, i * loadedMapSize, cur, i * Level.WIDTH, loadedMapSize );
}
this.cur = cur;
}
} }
@Override @Override
@@ -144,10 +129,10 @@ public class Blob extends Actor {
boolean[] notBlocking = BArray.not( Level.solid, null ); boolean[] notBlocking = BArray.not( Level.solid, null );
for (int i=1; i < HEIGHT-1; i++) { for (int i=1; i < Dungeon.level.height()-1; i++) {
int from = i * WIDTH + 1; int from = i * Dungeon.level.width() + 1;
int to = from + WIDTH - 2; int to = from + Dungeon.level.width() - 2;
for (int pos=from; pos < to; pos++) { for (int pos=from; pos < to; pos++) {
if (notBlocking[pos]) { if (notBlocking[pos]) {
@@ -163,12 +148,12 @@ public class Blob extends Actor {
sum += cur[pos+1]; sum += cur[pos+1];
count++; count++;
} }
if (notBlocking[pos-WIDTH]) { if (notBlocking[pos-Dungeon.level.width()]) {
sum += cur[pos-WIDTH]; sum += cur[pos-Dungeon.level.width()];
count++; count++;
} }
if (notBlocking[pos+WIDTH]) { if (notBlocking[pos+Dungeon.level.width()]) {
sum += cur[pos+WIDTH]; sum += cur[pos+Dungeon.level.width()];
count++; count++;
} }
@@ -182,8 +167,11 @@ public class Blob extends Actor {
} }
} }
} }
public void seed( int cell, int amount ) { public void seed( Level level, int cell, int amount ) {
if (cur == null) cur = new int[level.length()];
if (off == null) off = new int[cur.length];
cur[cell] += amount; cur[cell] += amount;
volume += amount; volume += amount;
} }
@@ -195,8 +183,8 @@ public class Blob extends Actor {
public void fullyClear(){ public void fullyClear(){
volume = 0; volume = 0;
cur = new int[LENGTH]; cur = new int[Dungeon.level.length()];
off = new int[LENGTH]; off = new int[Dungeon.level.length()];
} }
public String tileDesc() { public String tileDesc() {
@@ -213,7 +201,7 @@ public class Blob extends Actor {
Dungeon.level.blobs.put( type, gas ); Dungeon.level.blobs.put( type, gas );
} }
gas.seed( cell, amount ); gas.seed( Dungeon.level, cell, amount );
return gas; return gas;
@@ -20,6 +20,7 @@
*/ */
package com.shatteredpixel.shatteredpixeldungeon.actors.blobs; package com.shatteredpixel.shatteredpixeldungeon.actors.blobs;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
@@ -35,7 +36,7 @@ public class ConfusionGas extends Blob {
super.evolve(); super.evolve();
Char ch; Char ch;
for (int i=0; i < LENGTH; i++) { for (int i = 0; i < Dungeon.level.length(); i++) {
if (cur[i] > 0 && (ch = Actor.findChar( i )) != null) { if (cur[i] > 0 && (ch = Actor.findChar( i )) != null) {
if (!ch.immunities().contains(this.getClass())) if (!ch.immunities().contains(this.getClass()))
Buff.prolong( ch, Vertigo.class, 2 ); Buff.prolong( ch, Vertigo.class, 2 );
@@ -40,8 +40,8 @@ public class Fire extends Blob {
boolean[] flamable = Level.flamable; boolean[] flamable = Level.flamable;
int from = WIDTH + 1; int from = Dungeon.level.width() + 1;
int to = Level.LENGTH - WIDTH - 1; int to = Dungeon.level.length() - Dungeon.level.width() - 1;
boolean observe = false; boolean observe = false;
@@ -68,7 +68,11 @@ public class Fire extends Blob {
} else { } else {
if (flamable[pos] && (cur[pos-1] > 0 || cur[pos+1] > 0 || cur[pos-WIDTH] > 0 || cur[pos+WIDTH] > 0)) { if (flamable[pos]
&& (cur[pos-1] > 0
|| cur[pos+1] > 0
|| cur[pos-Dungeon.level.width()] > 0
|| cur[pos+Dungeon.level.width()] > 0)) {
fire = 4; fire = 4;
burn( pos ); burn( pos );
} else { } else {
@@ -103,7 +107,9 @@ public class Fire extends Blob {
} }
} }
public void seed( int cell, int amount ) { public void seed( Level level, int cell, int amount ) {
if (cur == null) cur = new int[level.length()];
if (off == null) off = new int[cur.length];
if (cur[cell] == 0) { if (cur[cell] == 0) {
volume += amount; volume += amount;
cur[cell] = amount; cur[cell] = amount;
@@ -37,8 +37,8 @@ public class Foliage extends Blob {
@Override @Override
protected void evolve() { protected void evolve() {
int from = WIDTH + 1; int from = Dungeon.level.width() + 1;
int to = Level.LENGTH - WIDTH - 1; int to = Dungeon.level.length() - Dungeon.level.width() - 1;
int[] map = Dungeon.level.map; int[] map = Dungeon.level.map;
boolean regrowth = false; boolean regrowth = false;
@@ -22,7 +22,9 @@ package com.shatteredpixel.shatteredpixeldungeon.actors.blobs;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.effects.BlobEmitter; import com.shatteredpixel.shatteredpixeldungeon.effects.BlobEmitter;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages; import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.sprites.GooSprite; import com.shatteredpixel.shatteredpixeldungeon.sprites.GooSprite;
@@ -39,7 +41,7 @@ public class GooWarn extends Blob {
@Override @Override
protected void evolve() { protected void evolve() {
for (int i=0; i < LENGTH; i++) { for (int i = 0; i < Dungeon.level.length(); i++) {
int offv = cur[i] > 0 ? cur[i] - 1 : 0; int offv = cur[i] > 0 ? cur[i] - 1 : 0;
off[i] = offv; off[i] = offv;
@@ -52,7 +54,9 @@ public class GooWarn extends Blob {
} }
public void seed( int cell, int amount ) { public void seed(Level level, int cell, int amount ) {
if (cur == null) cur = new int[level.length()];
if (off == null) off = new int[cur.length];
int diff = amount - cur[cell]; int diff = amount - cur[cell];
if (diff > 0) { if (diff > 0) {
cur[cell] = amount; cur[cell] = amount;
@@ -20,6 +20,7 @@
*/ */
package com.shatteredpixel.shatteredpixeldungeon.actors.blobs; package com.shatteredpixel.shatteredpixeldungeon.actors.blobs;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
@@ -35,7 +36,7 @@ public class ParalyticGas extends Blob {
super.evolve(); super.evolve();
Char ch; Char ch;
for (int i=0; i < LENGTH; i++) { for (int i = 0; i < Dungeon.level.length(); i++) {
if (cur[i] > 0 && (ch = Actor.findChar( i )) != null) { if (cur[i] > 0 && (ch = Actor.findChar( i )) != null) {
if (!ch.immunities().contains(this.getClass())) if (!ch.immunities().contains(this.getClass()))
Buff.prolong( ch, Paralysis.class, Paralysis.duration( ch ) ); Buff.prolong( ch, Paralysis.class, Paralysis.duration( ch ) );
@@ -39,7 +39,7 @@ public class Regrowth extends Blob {
if (volume > 0) { if (volume > 0) {
for (int i=0; i < LENGTH; i++) { for (int i=0; i < Dungeon.level.length(); i++) {
if (off[i] > 0) { if (off[i] > 0) {
int c = Dungeon.level.map[i]; int c = Dungeon.level.map[i];
int c1 = c; int c1 = c;
@@ -20,6 +20,7 @@
*/ */
package com.shatteredpixel.shatteredpixeldungeon.actors.blobs; package com.shatteredpixel.shatteredpixeldungeon.actors.blobs;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
@@ -35,7 +36,7 @@ public class StenchGas extends Blob {
super.evolve(); super.evolve();
Char ch; Char ch;
for (int i=0; i < LENGTH; i++) { for (int i = 0; i < Dungeon.level.length(); i++) {
if (cur[i] > 0 && (ch = Actor.findChar(i)) != null) { if (cur[i] > 0 && (ch = Actor.findChar(i)) != null) {
if (!ch.immunities().contains(this.getClass())) if (!ch.immunities().contains(this.getClass()))
Buff.prolong( ch, Paralysis.class, Paralysis.duration( ch )/5 ); Buff.prolong( ch, Paralysis.class, Paralysis.duration( ch )/5 );
@@ -40,7 +40,7 @@ public class ToxicGas extends Blob implements Hero.Doom {
int levelDamage = 5 + Dungeon.depth * 5; int levelDamage = 5 + Dungeon.depth * 5;
Char ch; Char ch;
for (int i=0; i < LENGTH; i++) { for (int i=0; i < Dungeon.level.length(); i++) {
if (cur[i] > 0 && (ch = Actor.findChar( i )) != null) { if (cur[i] > 0 && (ch = Actor.findChar( i )) != null) {
int damage = (ch.HT + levelDamage) / 40; int damage = (ch.HT + levelDamage) / 40;
@@ -20,6 +20,7 @@
*/ */
package com.shatteredpixel.shatteredpixeldungeon.actors.blobs; package com.shatteredpixel.shatteredpixeldungeon.actors.blobs;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
@@ -41,7 +42,7 @@ public class VenomGas extends Blob {
strength = 0; strength = 0;
} else { } else {
Char ch; Char ch;
for (int i = 0; i < LENGTH; i++) { for (int i = 0; i < Dungeon.level.length(); i++) {
if (cur[i] > 0 && (ch = Actor.findChar(i)) != null) { if (cur[i] > 0 && (ch = Actor.findChar(i)) != null) {
if (!ch.immunities().contains(this.getClass())) if (!ch.immunities().contains(this.getClass()))
Buff.affect(ch, Venom.class).set(2f, strength); Buff.affect(ch, Venom.class).set(2f, strength);
@@ -50,7 +50,7 @@ public class WaterOfAwareness extends WellWater {
hero.belongings.observe(); hero.belongings.observe();
for (int i=0; i < Level.LENGTH; i++) { for (int i=0; i < Dungeon.level.length(); i++) {
int terr = Dungeon.level.map[i]; int terr = Dungeon.level.map[i];
if ((Terrain.flags[terr] & Terrain.SECRET) != 0) { if ((Terrain.flags[terr] & Terrain.SECRET) != 0) {
@@ -20,12 +20,14 @@
*/ */
package com.shatteredpixel.shatteredpixeldungeon.actors.blobs; package com.shatteredpixel.shatteredpixeldungeon.actors.blobs;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Roots; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Roots;
import com.shatteredpixel.shatteredpixeldungeon.effects.BlobEmitter; import com.shatteredpixel.shatteredpixeldungeon.effects.BlobEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.particles.WebParticle; import com.shatteredpixel.shatteredpixeldungeon.effects.particles.WebParticle;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages; import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
public class Web extends Blob { public class Web extends Blob {
@@ -33,7 +35,7 @@ public class Web extends Blob {
@Override @Override
protected void evolve() { protected void evolve() {
for (int i=0; i < LENGTH; i++) { for (int i = 0; i < Dungeon.level.length(); i++) {
int offv = cur[i] > 0 ? cur[i] - 1 : 0; int offv = cur[i] > 0 ? cur[i] - 1 : 0;
off[i] = offv; off[i] = offv;
@@ -57,7 +59,9 @@ public class Web extends Blob {
emitter.pour( WebParticle.FACTORY, 0.4f ); emitter.pour( WebParticle.FACTORY, 0.4f );
} }
public void seed( int cell, int amount ) { public void seed(Level level, int cell, int amount ) {
if (cur == null) cur = new int[level.length()];
if (off == null) off = new int[cur.length];
int diff = amount - cur[cell]; int diff = amount - cur[cell];
if (diff > 0) { if (diff > 0) {
cur[cell] = amount; cur[cell] = amount;
@@ -30,6 +30,7 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain; import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene; import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
public class WellWater extends Blob { public class WellWater extends Blob {
@@ -39,8 +40,8 @@ public class WellWater extends Blob {
@Override @Override
public void restoreFromBundle( Bundle bundle ) { public void restoreFromBundle( Bundle bundle ) {
super.restoreFromBundle( bundle ); super.restoreFromBundle( bundle );
for (int i=0; i < LENGTH; i++) { for (int i=0; i < cur.length; i++) {
if (cur[i] > 0) { if (cur[i] > 0) {
pos = i; pos = i;
break; break;
@@ -99,7 +100,7 @@ public class WellWater extends Blob {
int newPlace; int newPlace;
do { do {
newPlace = pos + Level.NEIGHBOURS8[Random.Int( 8 )]; newPlace = pos + PathFinder.NEIGHBOURS8[Random.Int( 8 )];
} while (!Level.passable[newPlace] && !Level.avoid[newPlace]); } while (!Level.passable[newPlace] && !Level.avoid[newPlace]);
Dungeon.level.drop( heap.pickUp(), newPlace ).sprite.drop( pos ); Dungeon.level.drop( heap.pickUp(), newPlace ).sprite.drop( pos );
@@ -123,7 +124,9 @@ public class WellWater extends Blob {
} }
@Override @Override
public void seed( int cell, int amount ) { public void seed( Level level, int cell, int amount ) {
if (cur == null) cur = new int[level.length()];
if (off == null) off = new int[cur.length];
cur[pos] = 0; cur[pos] = 0;
pos = cell; pos = cell;
volume = cur[pos] = amount; volume = cur[pos] = amount;
@@ -43,6 +43,7 @@ import com.watabou.noosa.Image;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.Callback; import com.watabou.utils.Callback;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
public class Combo extends Buff implements ActionIndicator.Action { public class Combo extends Buff implements ActionIndicator.Action {
@@ -231,8 +232,8 @@ public class Combo extends Buff implements ActionIndicator.Action {
case CLOBBER: case CLOBBER:
if (enemy.isAlive()){ if (enemy.isAlive()){
if (!enemy.properties().contains(Char.Property.IMMOVABLE)){ if (!enemy.properties().contains(Char.Property.IMMOVABLE)){
for (int i=0; i < Level.NEIGHBOURS8.length; i++) { for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++) {
int ofs = Level.NEIGHBOURS8[i]; int ofs = PathFinder.NEIGHBOURS8[i];
if (enemy.pos - target.pos == ofs) { if (enemy.pos - target.pos == ofs) {
int newPos = enemy.pos + ofs; int newPos = enemy.pos + ofs;
if ((Level.passable[newPos] || Level.avoid[newPos]) && Actor.findChar( newPos ) == null) { if ((Level.passable[newPos] || Level.avoid[newPos]) && Actor.findChar( newPos ) == null) {
@@ -258,7 +258,7 @@ public class Hero extends Char {
@Override @Override
public int attackSkill( Char target ) { public int attackSkill( Char target ) {
float accuracy = 1; float accuracy = 1;
if (rangedWeapon != null && Level.distance( pos, target.pos ) == 1) { if (rangedWeapon != null && Dungeon.level.distance( pos, target.pos ) == 1) {
accuracy *= 0.5f; accuracy *= 0.5f;
} }
@@ -391,12 +391,12 @@ public class Hero extends Char {
return false; return false;
//can always attack adjacent enemies //can always attack adjacent enemies
if (Level.adjacent(pos, enemy.pos)) if (Dungeon.level.adjacent(pos, enemy.pos))
return true; return true;
KindOfWeapon wep = Dungeon.hero.belongings.weapon; KindOfWeapon wep = Dungeon.hero.belongings.weapon;
if (wep != null && Level.distance( pos, enemy.pos ) <= wep.reachFactor(this)){ if (wep != null && Dungeon.level.distance( pos, enemy.pos ) <= wep.reachFactor(this)){
boolean[] passable = BArray.not(Level.solid, null); boolean[] passable = BArray.not(Level.solid, null);
for (Mob m : Dungeon.level.mobs) for (Mob m : Dungeon.level.mobs)
@@ -575,7 +575,7 @@ public class Hero extends Char {
NPC npc = action.npc; NPC npc = action.npc;
if (Level.adjacent( pos, npc.pos )) { if (Dungeon.level.adjacent( pos, npc.pos )) {
ready(); ready();
sprite.turnTo( pos, npc.pos ); sprite.turnTo( pos, npc.pos );
@@ -598,7 +598,7 @@ public class Hero extends Char {
private boolean actBuy( HeroAction.Buy action ) { private boolean actBuy( HeroAction.Buy action ) {
int dst = action.dst; int dst = action.dst;
if (pos == dst || Level.adjacent( pos, dst )) { if (pos == dst || Dungeon.level.adjacent( pos, dst )) {
ready(); ready();
@@ -690,7 +690,7 @@ public class Hero extends Char {
private boolean actOpenChest( HeroAction.OpenChest action ) { private boolean actOpenChest( HeroAction.OpenChest action ) {
int dst = action.dst; int dst = action.dst;
if (Level.adjacent( pos, dst ) || pos == dst) { if (Dungeon.level.adjacent( pos, dst ) || pos == dst) {
Heap heap = Dungeon.level.heaps.get( dst ); Heap heap = Dungeon.level.heaps.get( dst );
if (heap != null && (heap.type != Type.HEAP && heap.type != Type.FOR_SALE)) { if (heap != null && (heap.type != Type.HEAP && heap.type != Type.FOR_SALE)) {
@@ -737,7 +737,7 @@ public class Hero extends Char {
private boolean actUnlock( HeroAction.Unlock action ) { private boolean actUnlock( HeroAction.Unlock action ) {
int doorCell = action.dst; int doorCell = action.dst;
if (Level.adjacent( pos, doorCell )) { if (Dungeon.level.adjacent( pos, doorCell )) {
boolean hasKey = false; boolean hasKey = false;
int door = Dungeon.level.map[doorCell]; int door = Dungeon.level.map[doorCell];
@@ -1015,7 +1015,7 @@ public class Hero extends Char {
int step = -1; int step = -1;
if (Level.adjacent( pos, target )) { if (Dungeon.level.adjacent( pos, target )) {
if (Actor.findChar( target ) == null) { if (Actor.findChar( target ) == null) {
if (Level.pit[target] && !flying && !Level.solid[target]) { if (Level.pit[target] && !flying && !Level.solid[target]) {
@@ -1034,7 +1034,7 @@ public class Hero extends Char {
} else { } else {
int len = Level.LENGTH; int len = Dungeon.level.length();
boolean[] p = Level.passable; boolean[] p = Level.passable;
boolean[] v = Dungeon.level.visited; boolean[] v = Dungeon.level.visited;
boolean[] m = Dungeon.level.mapped; boolean[] m = Dungeon.level.mapped;
@@ -1281,7 +1281,7 @@ public class Hero extends Char {
public static void reallyDie( Object cause ) { public static void reallyDie( Object cause ) {
int length = Level.LENGTH; int length = Dungeon.level.length();
int[] map = Dungeon.level.map; int[] map = Dungeon.level.map;
boolean[] visited = Dungeon.level.visited; boolean[] visited = Dungeon.level.visited;
boolean[] discoverable = Level.discoverable; boolean[] discoverable = Level.discoverable;
@@ -1308,7 +1308,7 @@ public class Hero extends Char {
int pos = Dungeon.hero.pos; int pos = Dungeon.hero.pos;
ArrayList<Integer> passable = new ArrayList<Integer>(); ArrayList<Integer> passable = new ArrayList<Integer>();
for (Integer ofs : Level.NEIGHBOURS8) { for (Integer ofs : PathFinder.NEIGHBOURS8) {
int cell = pos + ofs; int cell = pos + ofs;
if ((Level.passable[cell] || Level.avoid[cell]) && Dungeon.level.heaps.get( cell ) == null) { if ((Level.passable[cell] || Level.avoid[cell]) && Dungeon.level.heaps.get( cell ) == null) {
passable.add( cell ); passable.add( cell );
@@ -1440,23 +1440,23 @@ public class Hero extends Char {
distance = 1; distance = 1;
} }
int cx = pos % Level.WIDTH; int cx = pos % Dungeon.level.width();
int cy = pos / Level.WIDTH; int cy = pos / Dungeon.level.width();
int ax = cx - distance; int ax = cx - distance;
if (ax < 0) { if (ax < 0) {
ax = 0; ax = 0;
} }
int bx = cx + distance; int bx = cx + distance;
if (bx >= Level.WIDTH) { if (bx >= Dungeon.level.width()) {
bx = Level.WIDTH - 1; bx = Dungeon.level.width() - 1;
} }
int ay = cy - distance; int ay = cy - distance;
if (ay < 0) { if (ay < 0) {
ay = 0; ay = 0;
} }
int by = cy + distance; int by = cy + distance;
if (by >= Level.HEIGHT) { if (by >= Dungeon.level.height()) {
by = Level.HEIGHT - 1; by = Dungeon.level.height() - 1;
} }
TalismanOfForesight.Foresight foresight = buff( TalismanOfForesight.Foresight.class ); TalismanOfForesight.Foresight foresight = buff( TalismanOfForesight.Foresight.class );
@@ -1467,7 +1467,7 @@ public class Hero extends Char {
} }
for (int y = ay; y <= by; y++) { for (int y = ay; y <= by; y++) {
for (int x = ax, p = ax + y * Level.WIDTH; x <= bx; x++, p++) { for (int x = ax, p = ax + y * Dungeon.level.width(); x <= bx; x++, p++) {
if (Dungeon.visible[p]) { if (Dungeon.visible[p]) {
@@ -121,18 +121,18 @@ public class Bee extends Mob {
//if already targeting something, and that thing is still alive and near the pot, keeping targeting it. //if already targeting something, and that thing is still alive and near the pot, keeping targeting it.
if (enemy != null && enemy.isAlive() && Dungeon.level.mobs.contains(enemy) if (enemy != null && enemy.isAlive() && Dungeon.level.mobs.contains(enemy)
&& Level.fieldOfView[enemy.pos] && enemy.invisible == 0 && Level.fieldOfView[enemy.pos] && enemy.invisible == 0
&& Level.distance(enemy.pos, potPos) <= 3) && Dungeon.level.distance(enemy.pos, potPos) <= 3)
return enemy; return enemy;
//find all mobs near the pot //find all mobs near the pot
HashSet<Char> enemies = new HashSet<>(); HashSet<Char> enemies = new HashSet<>();
for (Mob mob : Dungeon.level.mobs) for (Mob mob : Dungeon.level.mobs)
if (!(mob instanceof Bee) && Level.distance(mob.pos, potPos) <= 3 && (mob.hostile || mob.ally)) if (!(mob instanceof Bee) && Dungeon.level.distance(mob.pos, potPos) <= 3 && (mob.hostile || mob.ally))
enemies.add(mob); enemies.add(mob);
//pick one, if there are none, check if the hero is near the pot, go for them, otherwise go for nothing. //pick one, if there are none, check if the hero is near the pot, go for them, otherwise go for nothing.
if (enemies.size() > 0) return Random.element(enemies); if (enemies.size() > 0) return Random.element(enemies);
else return (Level.distance(Dungeon.hero.pos, potPos) <= 3) ? Dungeon.hero : null ; else return (Dungeon.level.distance(Dungeon.hero.pos, potPos) <= 3) ? Dungeon.hero : null ;
} }
} }
@@ -140,7 +140,7 @@ public class Bee extends Mob {
protected boolean getCloser(int target) { protected boolean getCloser(int target) {
if (enemy != null && Actor.findById(potHolder) == enemy) { if (enemy != null && Actor.findById(potHolder) == enemy) {
target = enemy.pos; target = enemy.pos;
} else if (potPos != -1 && (state == WANDERING || Level.distance(target, potPos) > 3)) } else if (potPos != -1 && (state == WANDERING || Dungeon.level.distance(target, potPos) > 3))
this.target = target = potPos; this.target = target = potPos;
return super.getCloser( target ); return super.getCloser( target );
} }
@@ -106,11 +106,11 @@ public class DM300 extends Mob {
} }
int[] cells = { int[] cells = {
step-1, step+1, step-Level.WIDTH, step+Level.WIDTH, step-1, step+1, step-Dungeon.level.width(), step+Dungeon.level.width(),
step-1-Level.WIDTH, step-1-Dungeon.level.width(),
step-1+Level.WIDTH, step-1+Dungeon.level.width(),
step+1-Level.WIDTH, step+1-Dungeon.level.width(),
step+1+Level.WIDTH step+1+Dungeon.level.width()
}; };
int cell = cells[Random.Int( cells.length )]; int cell = cells[Random.Int( cells.length )];
@@ -20,6 +20,7 @@
*/ */
package com.shatteredpixel.shatteredpixeldungeon.actors.mobs; package com.shatteredpixel.shatteredpixeldungeon.actors.mobs;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Fire; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Fire;
@@ -64,7 +65,7 @@ public class GnollTrickster extends Gnoll {
@Override @Override
protected boolean canAttack( Char enemy ) { protected boolean canAttack( Char enemy ) {
Ballistica attack = new Ballistica( pos, enemy.pos, Ballistica.PROJECTILE); Ballistica attack = new Ballistica( pos, enemy.pos, Ballistica.PROJECTILE);
return !Level.adjacent(pos, enemy.pos) && attack.collisionPos == enemy.pos; return !Dungeon.level.adjacent(pos, enemy.pos) && attack.collisionPos == enemy.pos;
} }
@Override @Override
@@ -43,10 +43,12 @@ import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.sprites.CharSprite; import com.shatteredpixel.shatteredpixeldungeon.sprites.CharSprite;
import com.shatteredpixel.shatteredpixeldungeon.sprites.GooSprite; import com.shatteredpixel.shatteredpixeldungeon.sprites.GooSprite;
import com.shatteredpixel.shatteredpixeldungeon.ui.BossHealthBar; import com.shatteredpixel.shatteredpixeldungeon.ui.BossHealthBar;
import com.shatteredpixel.shatteredpixeldungeon.utils.BArray;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog; import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.noosa.Camera; import com.watabou.noosa.Camera;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.HashSet; import java.util.HashSet;
@@ -74,10 +76,10 @@ public class Goo extends Mob {
int max = (HP*2 <= HT) ? 15 : 10; int max = (HP*2 <= HT) ? 15 : 10;
if (pumpedUp > 0) { if (pumpedUp > 0) {
pumpedUp = 0; pumpedUp = 0;
for (int i = 0; i < Level.NEIGHBOURS9DIST2.length; i++) { PathFinder.buildDistanceMap( pos, BArray.not( Level.solid, null ), 2 );
int j = pos + Level.NEIGHBOURS9DIST2[i]; for (int i = 0; i < PathFinder.distance.length; i++) {
if (Level.insideMap(j) && Level.passable[j]) if (PathFinder.distance[i] < Integer.MAX_VALUE)
CellEmitter.get(j).burst(ElmoParticle.FACTORY, 10); CellEmitter.get(i).burst(ElmoParticle.FACTORY, 10);
} }
Sample.INSTANCE.play( Assets.SND_BURNING ); Sample.INSTANCE.play( Assets.SND_BURNING );
return Random.NormalIntRange( min*3, max*3 ); return Random.NormalIntRange( min*3, max*3 );
@@ -142,10 +144,10 @@ public class Goo extends Mob {
protected boolean doAttack( Char enemy ) { protected boolean doAttack( Char enemy ) {
if (pumpedUp == 1) { if (pumpedUp == 1) {
((GooSprite)sprite).pumpUp(); ((GooSprite)sprite).pumpUp();
for (int i = 0; i < Level.NEIGHBOURS9DIST2.length; i++) { PathFinder.buildDistanceMap( pos, BArray.not( Level.solid, null ), 2 );
int j = pos + Level.NEIGHBOURS9DIST2[i]; for (int i = 0; i < PathFinder.distance.length; i++) {
if (Level.insideMap(j) && Level.passable[j]) if (PathFinder.distance[i] < Integer.MAX_VALUE)
GameScene.add(Blob.seed(j, 2, GooWarn.class)); GameScene.add(Blob.seed(i, 2, GooWarn.class));
} }
pumpedUp++; pumpedUp++;
@@ -176,9 +178,9 @@ public class Goo extends Mob {
((GooSprite)sprite).pumpUp(); ((GooSprite)sprite).pumpUp();
for (int i=0; i < Level.NEIGHBOURS9.length; i++) { for (int i=0; i < PathFinder.NEIGHBOURS9.length; i++) {
int j = pos + Level.NEIGHBOURS9[i]; int j = pos + PathFinder.NEIGHBOURS9[i];
if (Level.passable[j]) { if (!Level.solid[j]) {
GameScene.add(Blob.seed(j, 2, GooWarn.class)); GameScene.add(Blob.seed(j, 2, GooWarn.class));
} }
} }
@@ -72,7 +72,8 @@ public class Guard extends Mob {
enemy != null && enemy != null &&
enemy.invisible == 0 && enemy.invisible == 0 &&
Level.fieldOfView[enemy.pos] && Level.fieldOfView[enemy.pos] &&
Level.distance( pos, enemy.pos ) < 5 && !Level.adjacent( pos, enemy.pos ) && Dungeon.level.distance( pos, enemy.pos ) < 5 &&
!Dungeon.level.adjacent( pos, enemy.pos ) &&
Random.Int(3) == 0 && Random.Int(3) == 0 &&
chain(enemy.pos)) { chain(enemy.pos)) {
@@ -105,20 +105,20 @@ public class King extends Mob {
@Override @Override
protected boolean getCloser( int target ) { protected boolean getCloser( int target ) {
return canTryToSummon() ? return canTryToSummon() ?
super.getCloser( CityBossLevel.pedestal( nextPedestal ) ) : super.getCloser( ((CityBossLevel)Dungeon.level).pedestal( nextPedestal ) ) :
super.getCloser( target ); super.getCloser( target );
} }
@Override @Override
protected boolean canAttack( Char enemy ) { protected boolean canAttack( Char enemy ) {
return canTryToSummon() ? return canTryToSummon() ?
pos == CityBossLevel.pedestal( nextPedestal ) : pos == ((CityBossLevel)Dungeon.level).pedestal( nextPedestal ) :
Level.adjacent( pos, enemy.pos ); Dungeon.level.adjacent( pos, enemy.pos );
} }
private boolean canTryToSummon() { private boolean canTryToSummon() {
if (Undead.count < maxArmySize()) { if (Undead.count < maxArmySize()) {
Char ch = Actor.findChar( CityBossLevel.pedestal( nextPedestal ) ); Char ch = Actor.findChar( ((CityBossLevel)Dungeon.level).pedestal( nextPedestal ) );
return ch == this || ch == null; return ch == this || ch == null;
} else { } else {
return false; return false;
@@ -127,11 +127,11 @@ public class King extends Mob {
@Override @Override
public boolean attack( Char enemy ) { public boolean attack( Char enemy ) {
if (canTryToSummon() && pos == CityBossLevel.pedestal( nextPedestal )) { if (canTryToSummon() && pos == ((CityBossLevel)Dungeon.level).pedestal( nextPedestal )) {
summon(); summon();
return true; return true;
} else { } else {
if (Actor.findChar( CityBossLevel.pedestal( nextPedestal ) ) == enemy) { if (Actor.findChar( ((CityBossLevel)Dungeon.level).pedestal( nextPedestal ) ) == enemy) {
nextPedestal = !nextPedestal; nextPedestal = !nextPedestal;
} }
return super.attack(enemy); return super.attack(enemy);
@@ -199,7 +199,7 @@ public class King extends Mob {
undeadLabel: undeadLabel:
for (int i=0; i < undeadsToSummon; i++) { for (int i=0; i < undeadsToSummon; i++) {
do { do {
for (int j=0; j < Level.LENGTH; j++) { for (int j=0; j < Dungeon.level.length(); j++) {
if (PathFinder.distance[j] == dist) { if (PathFinder.distance[j] == dist) {
Undead undead = new Undead(); Undead undead = new Undead();
@@ -36,6 +36,7 @@ import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.sprites.MimicSprite; import com.shatteredpixel.shatteredpixeldungeon.sprites.MimicSprite;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -115,7 +116,7 @@ public class Mimic extends Mob {
Char ch = Actor.findChar( pos ); Char ch = Actor.findChar( pos );
if (ch != null) { if (ch != null) {
ArrayList<Integer> candidates = new ArrayList<>(); ArrayList<Integer> candidates = new ArrayList<>();
for (int n : Level.NEIGHBOURS8) { for (int n : PathFinder.NEIGHBOURS8) {
int cell = pos + n; int cell = pos + n;
if ((Level.passable[cell] || Level.avoid[cell]) && Actor.findChar( cell ) == null) { if ((Level.passable[cell] || Level.avoid[cell]) && Actor.findChar( cell ) == null) {
candidates.add( cell ); candidates.add( cell );
@@ -285,7 +285,7 @@ public abstract class Mob extends Char {
} }
protected boolean canAttack( Char enemy ) { protected boolean canAttack( Char enemy ) {
return Level.adjacent( pos, enemy.pos ); return Dungeon.level.adjacent( pos, enemy.pos );
} }
protected boolean getCloser( int target ) { protected boolean getCloser( int target ) {
@@ -662,7 +662,7 @@ public abstract class Mob extends Char {
public boolean act( boolean enemyInFOV, boolean justAlerted ) { public boolean act( boolean enemyInFOV, boolean justAlerted ) {
enemySeen = enemyInFOV; enemySeen = enemyInFOV;
//loses target when 0-dist rolls a 6 or greater. //loses target when 0-dist rolls a 6 or greater.
if (enemy == null || !enemyInFOV && 1 + Random.Int(Level.distance(pos, target)) >= 6){ if (enemy == null || !enemyInFOV && 1 + Random.Int(Dungeon.level.distance(pos, target)) >= 6){
target = -1; target = -1;
} else { } else {
target = enemy.pos; target = enemy.pos;
@@ -20,6 +20,7 @@
*/ */
package com.shatteredpixel.shatteredpixeldungeon.actors.mobs; package com.shatteredpixel.shatteredpixeldungeon.actors.mobs;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.ToxicGas; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.ToxicGas;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
@@ -52,7 +53,7 @@ public class RotLasher extends Mob {
@Override @Override
protected boolean act() { protected boolean act() {
if (enemy == null || !Level.adjacent(pos, enemy.pos)) { if (enemy == null || !Dungeon.level.adjacent(pos, enemy.pos)) {
HP = Math.min(HT, HP + 3); HP = Math.min(HT, HP + 3);
} }
return super.act(); return super.act();
@@ -73,7 +73,7 @@ public class Scorpio extends Mob {
@Override @Override
protected boolean canAttack( Char enemy ) { protected boolean canAttack( Char enemy ) {
Ballistica attack = new Ballistica( pos, enemy.pos, Ballistica.PROJECTILE); Ballistica attack = new Ballistica( pos, enemy.pos, Ballistica.PROJECTILE);
return !Level.adjacent( pos, enemy.pos ) && attack.collisionPos == enemy.pos; return !Dungeon.level.adjacent( pos, enemy.pos ) && attack.collisionPos == enemy.pos;
} }
@Override @Override
@@ -77,7 +77,7 @@ public class Shaman extends Mob implements Callback {
@Override @Override
protected boolean doAttack( Char enemy ) { protected boolean doAttack( Char enemy ) {
if (Level.distance( pos, enemy.pos ) <= 1) { if (Dungeon.level.distance( pos, enemy.pos ) <= 1) {
return super.doAttack( enemy ); return super.doAttack( enemy );
@@ -32,6 +32,7 @@ import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.sprites.SkeletonSprite; import com.shatteredpixel.shatteredpixeldungeon.sprites.SkeletonSprite;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog; import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.HashSet; import java.util.HashSet;
@@ -66,8 +67,8 @@ public class Skeleton extends Mob {
super.die( cause ); super.die( cause );
boolean heroKilled = false; boolean heroKilled = false;
for (int i=0; i < Level.NEIGHBOURS8.length; i++) { for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++) {
Char ch = findChar( pos + Level.NEIGHBOURS8[i] ); Char ch = findChar( pos + PathFinder.NEIGHBOURS8[i] );
if (ch != null && ch.isAlive()) { if (ch != null && ch.isAlive()) {
int damage = Math.max( 0, damageRoll() - (ch.drRoll() / 2) ); int damage = Math.max( 0, damageRoll() - (ch.drRoll() / 2) );
ch.damage( damage, this ); ch.damage( damage, this );
@@ -103,7 +103,7 @@ public class Statue extends Mob {
@Override @Override
protected boolean canAttack(Char enemy) { protected boolean canAttack(Char enemy) {
return Level.distance( pos, enemy.pos ) <= weapon.RCH; return Dungeon.level.distance( pos, enemy.pos ) <= weapon.RCH;
} }
@Override @Override
@@ -21,6 +21,7 @@
package com.shatteredpixel.shatteredpixeldungeon.actors.mobs; package com.shatteredpixel.shatteredpixeldungeon.actors.mobs;
import com.shatteredpixel.shatteredpixeldungeon.Assets; import com.shatteredpixel.shatteredpixeldungeon.Assets;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
@@ -35,6 +36,7 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica; import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica;
import com.shatteredpixel.shatteredpixeldungeon.sprites.SuccubusSprite; import com.shatteredpixel.shatteredpixeldungeon.sprites.SuccubusSprite;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -81,7 +83,7 @@ public class Succubus extends Mob {
@Override @Override
protected boolean getCloser( int target ) { protected boolean getCloser( int target ) {
if (Level.fieldOfView[target] && Level.distance( pos, target ) > 2 && delay <= 0) { if (Level.fieldOfView[target] && Dungeon.level.distance( pos, target ) > 2 && delay <= 0) {
blink( target ); blink( target );
spend( -1 / speed() ); spend( -1 / speed() );
@@ -106,7 +108,7 @@ public class Succubus extends Mob {
if (Level.avoid[ cell ]){ if (Level.avoid[ cell ]){
ArrayList<Integer> candidates = new ArrayList<>(); ArrayList<Integer> candidates = new ArrayList<>();
for (int n : Level.NEIGHBOURS8) { for (int n : PathFinder.NEIGHBOURS8) {
cell = route.collisionPos + n; cell = route.collisionPos + n;
if (Level.passable[cell] && Actor.findChar( cell ) == null) { if (Level.passable[cell] && Actor.findChar( cell ) == null) {
candidates.add( cell ); candidates.add( cell );
@@ -88,7 +88,7 @@ public class Swarm extends Mob {
ArrayList<Integer> candidates = new ArrayList<>(); ArrayList<Integer> candidates = new ArrayList<>();
boolean[] passable = Level.passable; boolean[] passable = Level.passable;
int[] neighbours = {pos + 1, pos - 1, pos + Level.WIDTH, pos - Level.WIDTH}; int[] neighbours = {pos + 1, pos - 1, pos + Dungeon.level.width(), pos - Dungeon.level.width()};
for (int n : neighbours) { for (int n : neighbours) {
if (passable[n] && Actor.findChar( n ) == null) { if (passable[n] && Actor.findChar( n ) == null) {
candidates.add( n ); candidates.add( n );
@@ -166,7 +166,7 @@ public class Tengu extends Mob {
for (int i=0; i < 4; i++) { for (int i=0; i < 4; i++) {
int trapPos; int trapPos;
do { do {
trapPos = Random.Int( Level.LENGTH ); trapPos = Random.Int( Dungeon.level.length() );
} while (!Level.fieldOfView[trapPos] || Level.solid[trapPos]); } while (!Level.fieldOfView[trapPos] || Level.solid[trapPos]);
if (Dungeon.level.map[trapPos] == Terrain.INACTIVE_TRAP) { if (Dungeon.level.map[trapPos] == Terrain.INACTIVE_TRAP) {
@@ -182,20 +182,20 @@ public class Tengu extends Mob {
//if we're in phase 1, want to warp around within the room //if we're in phase 1, want to warp around within the room
if (HP > HT/2) { if (HP > HT/2) {
do { do {
newPos = Random.Int(Level.LENGTH); newPos = Random.Int(Dungeon.level.length());
} while ( } while (
!(Dungeon.level.map[newPos] == Terrain.INACTIVE_TRAP || Dungeon.level.map[newPos] == Terrain.TRAP)|| !(Dungeon.level.map[newPos] == Terrain.INACTIVE_TRAP || Dungeon.level.map[newPos] == Terrain.TRAP)||
Level.solid[newPos] || Level.solid[newPos] ||
Level.adjacent(newPos, enemy.pos) || Dungeon.level.adjacent(newPos, enemy.pos) ||
Actor.findChar(newPos) != null); Actor.findChar(newPos) != null);
//otherwise go wherever, as long as it's a little bit away //otherwise go wherever, as long as it's a little bit away
} else { } else {
do { do {
newPos = Random.Int(Level.LENGTH); newPos = Random.Int(Dungeon.level.length());
} while ( } while (
Level.solid[newPos] || Level.solid[newPos] ||
Level.distance(newPos, enemy.pos) < 8 || Dungeon.level.distance(newPos, enemy.pos) < 8 ||
Actor.findChar(newPos) != null); Actor.findChar(newPos) != null);
} }
@@ -191,7 +191,7 @@ public class Thief extends Mob {
if (count-- <= 0) { if (count-- <= 0) {
break; break;
} }
} while (newPos == -1 || Dungeon.visible[newPos] || Level.distance(newPos, pos) < (count/3)); } while (newPos == -1 || Dungeon.visible[newPos] || Dungeon.level.distance(newPos, pos) < (count/3));
if (newPos != -1) { if (newPos != -1) {
@@ -80,7 +80,7 @@ public class Warlock extends Mob implements Callback {
protected boolean doAttack( Char enemy ) { protected boolean doAttack( Char enemy ) {
if (Level.adjacent( pos, enemy.pos )) { if (Dungeon.level.adjacent( pos, enemy.pos )) {
return super.doAttack( enemy ); return super.doAttack( enemy );
@@ -31,6 +31,7 @@ import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.sprites.WraithSprite; import com.shatteredpixel.shatteredpixeldungeon.sprites.WraithSprite;
import com.watabou.noosa.tweeners.AlphaTweener; import com.watabou.noosa.tweeners.AlphaTweener;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.HashSet; import java.util.HashSet;
@@ -90,7 +91,7 @@ public class Wraith extends Mob {
} }
public static void spawnAround( int pos ) { public static void spawnAround( int pos ) {
for (int n : Level.NEIGHBOURS4) { for (int n : PathFinder.NEIGHBOURS4) {
int cell = pos + n; int cell = pos + n;
if (Level.passable[cell] && Actor.findChar( cell ) == null) { if (Level.passable[cell] && Actor.findChar( cell ) == null) {
spawnAt( cell ); spawnAt( cell );
@@ -53,6 +53,7 @@ import com.shatteredpixel.shatteredpixeldungeon.sprites.YogSprite;
import com.shatteredpixel.shatteredpixeldungeon.ui.BossHealthBar; import com.shatteredpixel.shatteredpixeldungeon.ui.BossHealthBar;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog; import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -83,8 +84,8 @@ public class Yog extends Mob {
BurningFist fist2 = new BurningFist(); BurningFist fist2 = new BurningFist();
do { do {
fist1.pos = pos + Level.NEIGHBOURS8[Random.Int( 8 )]; fist1.pos = pos + PathFinder.NEIGHBOURS8[Random.Int( 8 )];
fist2.pos = pos + Level.NEIGHBOURS8[Random.Int( 8 )]; fist2.pos = pos + PathFinder.NEIGHBOURS8[Random.Int( 8 )];
} while (!Level.passable[fist1.pos] || !Level.passable[fist2.pos] || fist1.pos == fist2.pos); } while (!Level.passable[fist1.pos] || !Level.passable[fist2.pos] || fist1.pos == fist2.pos);
GameScene.add( fist1 ); GameScene.add( fist1 );
@@ -128,8 +129,8 @@ public class Yog extends Mob {
ArrayList<Integer> spawnPoints = new ArrayList<>(); ArrayList<Integer> spawnPoints = new ArrayList<>();
for (int i=0; i < Level.NEIGHBOURS8.length; i++) { for (int i=0; i < PathFinder.NEIGHBOURS8.length; i++) {
int p = pos + Level.NEIGHBOURS8[i]; int p = pos + PathFinder.NEIGHBOURS8[i];
if (Actor.findChar( p ) == null && (Level.passable[p] || Level.avoid[p])) { if (Actor.findChar( p ) == null && (Level.passable[p] || Level.avoid[p])) {
spawnPoints.add( p ); spawnPoints.add( p );
} }
@@ -332,7 +333,7 @@ public class Yog extends Mob {
@Override @Override
public boolean attack( Char enemy ) { public boolean attack( Char enemy ) {
if (!Level.adjacent( pos, enemy.pos )) { if (!Dungeon.level.adjacent( pos, enemy.pos )) {
spend( attackDelay() ); spend( attackDelay() );
if (hit( this, enemy, true )) { if (hit( this, enemy, true )) {
@@ -362,8 +363,8 @@ public class Yog extends Mob {
@Override @Override
public boolean act() { public boolean act() {
for (int i=0; i < Level.NEIGHBOURS9.length; i++) { for (int i=0; i < PathFinder.NEIGHBOURS9.length; i++) {
GameScene.add( Blob.seed( pos + Level.NEIGHBOURS9[i], 2, Fire.class ) ); GameScene.add( Blob.seed( pos + PathFinder.NEIGHBOURS9[i], 2, Fire.class ) );
} }
return super.act(); return super.act();
@@ -24,6 +24,7 @@ import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.Mob; import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.Mob;
import com.shatteredpixel.shatteredpixeldungeon.items.Heap; import com.shatteredpixel.shatteredpixeldungeon.items.Heap;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level; import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
public abstract class NPC extends Mob { public abstract class NPC extends Mob {
@@ -41,7 +42,7 @@ public abstract class NPC extends Mob {
if (heap != null) { if (heap != null) {
int n; int n;
do { do {
n = pos + Level.NEIGHBOURS8[Random.Int( 8 )]; n = pos + PathFinder.NEIGHBOURS8[Random.Int( 8 )];
} while (!Level.passable[n] && !Level.avoid[n]); } while (!Level.passable[n] && !Level.avoid[n]);
Dungeon.level.drop( heap.pickUp(), n ).sprite.drop( pos ); Dungeon.level.drop( heap.pickUp(), n ).sprite.drop( pos );
} }
@@ -259,7 +259,7 @@ public class Wandmaker extends NPC {
if (setRoom( rooms )){ if (setRoom( rooms )){
Wandmaker npc = new Wandmaker(); Wandmaker npc = new Wandmaker();
do { do {
npc.pos = room.random(); npc.pos = Dungeon.level.pointToCell(room.random());
} while (level.map[npc.pos] == Terrain.ENTRANCE || level.map[npc.pos] == Terrain.SIGN); } while (level.map[npc.pos] == Terrain.ENTRANCE || level.map[npc.pos] == Terrain.SIGN);
level.mobs.add( npc ); level.mobs.add( npc );
@@ -27,9 +27,6 @@ import com.watabou.noosa.particles.Emitter;
import com.watabou.utils.Random; import com.watabou.utils.Random;
public class BlobEmitter extends Emitter { public class BlobEmitter extends Emitter {
private static final int WIDTH = Blob.WIDTH;
private static final int LENGTH = Blob.LENGTH;
private Blob blob; private Blob blob;
@@ -51,10 +48,10 @@ public class BlobEmitter extends Emitter {
int[] map = blob.cur; int[] map = blob.cur;
float size = DungeonTilemap.SIZE; float size = DungeonTilemap.SIZE;
for (int i=0; i < LENGTH; i++) { for (int i=0; i < Dungeon.level.length(); i++) {
if (map[i] > 0 && Dungeon.visible[i]) { if (map[i] > 0 && Dungeon.visible[i]) {
float x = ((i % WIDTH) + Random.Float()) * size; float x = ((i % Dungeon.level.width()) + Random.Float()) * size;
float y = ((i / WIDTH) + Random.Float()) * size; float y = ((i / Dungeon.level.width()) + Random.Float()) * size;
factory.emit( this, index, x, y ); factory.emit( this, index, x, y );
} }
} }
@@ -20,6 +20,7 @@
*/ */
package com.shatteredpixel.shatteredpixeldungeon.effects; package com.shatteredpixel.shatteredpixeldungeon.effects;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.DungeonTilemap; import com.shatteredpixel.shatteredpixeldungeon.DungeonTilemap;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level; import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.watabou.noosa.Game; import com.watabou.noosa.Game;
@@ -38,8 +39,8 @@ public class Ripple extends Image {
public void reset( int p ) { public void reset( int p ) {
revive(); revive();
x = (p % Level.WIDTH) * DungeonTilemap.SIZE; x = (p % Dungeon.level.width()) * DungeonTilemap.SIZE;
y = (p / Level.WIDTH) * DungeonTilemap.SIZE; y = (p / Dungeon.level.width()) * DungeonTilemap.SIZE;
origin.set( width / 2, height / 2 ); origin.set( width / 2, height / 2 );
scale.set( 0 ); scale.set( 0 );
@@ -42,8 +42,8 @@ public class Surprise extends Image {
public void reset(int p) { public void reset(int p) {
revive(); revive();
x = (p % Level.WIDTH) * DungeonTilemap.SIZE + (DungeonTilemap.SIZE - width) / 2; x = (p % Dungeon.level.width()) * DungeonTilemap.SIZE + (DungeonTilemap.SIZE - width) / 2;
y = (p / Level.WIDTH) * DungeonTilemap.SIZE + (DungeonTilemap.SIZE - height) / 2; y = (p / Dungeon.level.width()) * DungeonTilemap.SIZE + (DungeonTilemap.SIZE - height) / 2;
time = TIME_TO_FADE; time = TIME_TO_FADE;
} }
@@ -47,7 +47,7 @@ public class Swap extends Actor {
this.ch1 = ch1; this.ch1 = ch1;
this.ch2 = ch2; this.ch2 = ch2;
delay = Level.distance( ch1.pos, ch2.pos ) * 0.1f; delay = Dungeon.level.distance( ch1.pos, ch2.pos ) * 0.1f;
eff1 = new Effect( ch1.sprite, ch1.pos, ch2.pos ); eff1 = new Effect( ch1.sprite, ch1.pos, ch2.pos );
eff2 = new Effect( ch2.sprite, ch2.pos, ch1.pos ); eff2 = new Effect( ch2.sprite, ch2.pos, ch1.pos );
@@ -41,9 +41,9 @@ public class Wound extends Image {
public void reset( int p ) { public void reset( int p ) {
revive(); revive();
x = (p % Level.WIDTH) * DungeonTilemap.SIZE + (DungeonTilemap.SIZE - width) / 2; x = (p % Dungeon.level.width()) * DungeonTilemap.SIZE + (DungeonTilemap.SIZE - width) / 2;
y = (p / Level.WIDTH) * DungeonTilemap.SIZE + (DungeonTilemap.SIZE - height) / 2; y = (p / Dungeon.level.width()) * DungeonTilemap.SIZE + (DungeonTilemap.SIZE - height) / 2;
time = TIME_TO_FADE; time = TIME_TO_FADE;
} }
@@ -37,6 +37,7 @@ import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog; import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -90,7 +91,7 @@ public class Bomb extends Item {
} }
if (Actor.findChar( cell ) != null && !(Actor.findChar( cell ) instanceof Hero) ){ if (Actor.findChar( cell ) != null && !(Actor.findChar( cell ) instanceof Hero) ){
ArrayList<Integer> candidates = new ArrayList<>(); ArrayList<Integer> candidates = new ArrayList<>();
for (int i : Level.NEIGHBOURS8) for (int i : PathFinder.NEIGHBOURS8)
if (Level.passable[cell + i]) if (Level.passable[cell + i])
candidates.add(cell + i); candidates.add(cell + i);
int newCell = candidates.isEmpty() ? cell : Random.element(candidates); int newCell = candidates.isEmpty() ? cell : Random.element(candidates);
@@ -119,9 +120,9 @@ public class Bomb extends Item {
} }
boolean terrainAffected = false; boolean terrainAffected = false;
for (int n : Level.NEIGHBOURS9) { for (int n : PathFinder.NEIGHBOURS9) {
int c = cell + n; int c = cell + n;
if (c >= 0 && c < Level.LENGTH) { if (c >= 0 && c < Dungeon.level.length()) {
if (Dungeon.visible[c]) { if (Dungeon.visible[c]) {
CellEmitter.get( c ).burst( SmokeParticle.FACTORY, 4 ); CellEmitter.get( c ).burst( SmokeParticle.FACTORY, 4 );
} }
@@ -34,6 +34,7 @@ import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.noosa.tweeners.AlphaTweener; import com.watabou.noosa.tweeners.AlphaTweener;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -97,7 +98,7 @@ public class Honeypot extends Item {
ArrayList<Integer> candidates = new ArrayList<Integer>(); ArrayList<Integer> candidates = new ArrayList<Integer>();
boolean[] passable = Level.passable; boolean[] passable = Level.passable;
for (int n : Level.NEIGHBOURS4) { for (int n : PathFinder.NEIGHBOURS4) {
int c = pos + n; int c = pos + n;
if (passable[c] && Actor.findChar( c ) == null) { if (passable[c] && Actor.findChar( c ) == null) {
candidates.add( c ); candidates.add( c );
@@ -35,6 +35,8 @@ import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet; import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet;
import com.watabou.noosa.Camera; import com.watabou.noosa.Camera;
import com.watabou.utils.Callback; import com.watabou.utils.Callback;
import com.watabou.utils.PathFinder;
public class WarriorArmor extends ClassArmor { public class WarriorArmor extends ClassArmor {
private static int LEAP_TIME = 1; private static int LEAP_TIME = 1;
@@ -74,8 +76,8 @@ public class WarriorArmor extends ClassArmor {
Dungeon.level.press(dest, curUser); Dungeon.level.press(dest, curUser);
Dungeon.observe(); Dungeon.observe();
for (int i = 0; i < Level.NEIGHBOURS8.length; i++) { for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++) {
Char mob = Actor.findChar(curUser.pos + Level.NEIGHBOURS8[i]); Char mob = Actor.findChar(curUser.pos + PathFinder.NEIGHBOURS8[i]);
if (mob != null && mob != curUser) { if (mob != null && mob != curUser) {
Buff.prolong(mob, Paralysis.class, SHOCK_TIME); Buff.prolong(mob, Paralysis.class, SHOCK_TIME);
} }
@@ -20,6 +20,7 @@
*/ */
package com.shatteredpixel.shatteredpixeldungeon.items.armor.curses; package com.shatteredpixel.shatteredpixeldungeon.items.armor.curses;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Burning; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Burning;
@@ -43,7 +44,7 @@ public class AntiEntropy extends Glyph {
if (Random.Int( 8 ) == 0) { if (Random.Int( 8 ) == 0) {
if (Level.adjacent( attacker.pos, defender.pos )) { if (Dungeon.level.adjacent( attacker.pos, defender.pos )) {
Buff.prolong(attacker, Frost.class, Frost.duration(attacker) * Random.Float(0.5f, 1f)); Buff.prolong(attacker, Frost.class, Frost.duration(attacker) * Random.Float(0.5f, 1f));
CellEmitter.get(attacker.pos).start(SnowParticle.FACTORY, 0.2f, 6); CellEmitter.get(attacker.pos).start(SnowParticle.FACTORY, 0.2f, 6);
} }
@@ -28,6 +28,7 @@ import com.shatteredpixel.shatteredpixeldungeon.effects.Splash;
import com.shatteredpixel.shatteredpixeldungeon.items.armor.Armor; import com.shatteredpixel.shatteredpixeldungeon.items.armor.Armor;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level; import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite; import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
public class Corrosion extends Armor.Glyph { public class Corrosion extends Armor.Glyph {
@@ -39,7 +40,7 @@ public class Corrosion extends Armor.Glyph {
if (Random.Int(10) == 0){ if (Random.Int(10) == 0){
int pos = defender.pos; int pos = defender.pos;
for (int i : Level.NEIGHBOURS9){ for (int i : PathFinder.NEIGHBOURS9){
Splash.at(pos+i, 0x000000, 5); Splash.at(pos+i, 0x000000, 5);
if (Actor.findChar(pos+i) != null) if (Actor.findChar(pos+i) != null)
Buff.affect(Actor.findChar(pos+i), Ooze.class); Buff.affect(Actor.findChar(pos+i), Ooze.class);
@@ -34,6 +34,7 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene; import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite; import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -48,8 +49,8 @@ public class Multiplicity extends Armor.Glyph {
if (Random.Int(20) == 0){ if (Random.Int(20) == 0){
ArrayList<Integer> spawnPoints = new ArrayList<>(); ArrayList<Integer> spawnPoints = new ArrayList<>();
for (int i = 0; i < Level.NEIGHBOURS8.length; i++) { for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++) {
int p = defender.pos + Level.NEIGHBOURS8[i]; int p = defender.pos + PathFinder.NEIGHBOURS8[i];
if (Actor.findChar( p ) == null && (Level.passable[p] || Level.avoid[p])) { if (Actor.findChar( p ) == null && (Level.passable[p] || Level.avoid[p])) {
spawnPoints.add( p ); spawnPoints.add( p );
} }
@@ -31,6 +31,7 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene; import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite; import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite.Glowing; import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite.Glowing;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -48,8 +49,8 @@ public class Multiplicity extends Glyph {
ArrayList<Integer> respawnPoints = new ArrayList<Integer>(); ArrayList<Integer> respawnPoints = new ArrayList<Integer>();
for (int i=0; i < Level.NEIGHBOURS8.length; i++) { for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++) {
int p = defender.pos + Level.NEIGHBOURS8[i]; int p = defender.pos + PathFinder.NEIGHBOURS8[i];
if (Actor.findChar( p ) == null && (Level.passable[p] || Level.avoid[p])) { if (Actor.findChar( p ) == null && (Level.passable[p] || Level.avoid[p])) {
respawnPoints.add( p ); respawnPoints.add( p );
} }
@@ -93,7 +93,7 @@ public class CapeOfThorns extends Artifact {
int deflected = Random.NormalIntRange(0, damage); int deflected = Random.NormalIntRange(0, damage);
damage -= deflected; damage -= deflected;
if (attacker != null && Level.adjacent(attacker.pos, defender.pos)) { if (attacker != null && Dungeon.level.adjacent(attacker.pos, defender.pos)) {
attacker.damage(deflected, this); attacker.damage(deflected, this);
} }
@@ -48,6 +48,7 @@ import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.shatteredpixel.shatteredpixeldungeon.windows.WndQuest; import com.shatteredpixel.shatteredpixeldungeon.windows.WndQuest;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -100,8 +101,8 @@ public class DriedRose extends Artifact {
else if (cursed) GLog.i( Messages.get(this, "cursed") ); else if (cursed) GLog.i( Messages.get(this, "cursed") );
else { else {
ArrayList<Integer> spawnPoints = new ArrayList<Integer>(); ArrayList<Integer> spawnPoints = new ArrayList<Integer>();
for (int i = 0; i < Level.NEIGHBOURS8.length; i++) { for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++) {
int p = hero.pos + Level.NEIGHBOURS8[i]; int p = hero.pos + PathFinder.NEIGHBOURS8[i];
if (Actor.findChar(p) == null && (Level.passable[p] || Level.avoid[p])) { if (Actor.findChar(p) == null && (Level.passable[p] || Level.avoid[p])) {
spawnPoints.add(p); spawnPoints.add(p);
} }
@@ -217,8 +218,8 @@ public class DriedRose extends Artifact {
ArrayList<Integer> spawnPoints = new ArrayList<Integer>(); ArrayList<Integer> spawnPoints = new ArrayList<Integer>();
for (int i = 0; i < Level.NEIGHBOURS8.length; i++) { for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++) {
int p = target.pos + Level.NEIGHBOURS8[i]; int p = target.pos + PathFinder.NEIGHBOURS8[i];
if (Actor.findChar(p) == null && (Level.passable[p] || Level.avoid[p])) { if (Actor.findChar(p) == null && (Level.passable[p] || Level.avoid[p])) {
spawnPoints.add(p); spawnPoints.add(p);
} }
@@ -347,7 +348,7 @@ public class DriedRose extends Artifact {
@Override @Override
protected boolean getCloser( int target ) { protected boolean getCloser( int target ) {
if (state == WANDERING || Level.distance(target, Dungeon.hero.pos) > 6) if (state == WANDERING || Dungeon.level.distance(target, Dungeon.hero.pos) > 6)
this.target = target = Dungeon.hero.pos; this.target = target = Dungeon.hero.pos;
return super.getCloser( target ); return super.getCloser( target );
} }
@@ -120,7 +120,7 @@ public class EtherealChains extends Artifact {
} else { } else {
final int newMobPos = newPos; final int newMobPos = newPos;
final Char affected = Actor.findChar( chain.collisionPos ); final Char affected = Actor.findChar( chain.collisionPos );
int chargeUse = Level.distance(affected.pos, newMobPos); int chargeUse = Dungeon.level.distance(affected.pos, newMobPos);
if (chargeUse > charge) { if (chargeUse > charge) {
GLog.w( Messages.get(EtherealChains.class, "no_charge") ); GLog.w( Messages.get(EtherealChains.class, "no_charge") );
return; return;
@@ -159,7 +159,7 @@ public class EtherealChains extends Artifact {
GLog.w( Messages.get(EtherealChains.class, "does_nothing") ); GLog.w( Messages.get(EtherealChains.class, "does_nothing") );
} else { } else {
final int newHeroPos = newPos; final int newHeroPos = newPos;
int chargeUse = Level.distance(curUser.pos, newHeroPos); int chargeUse = Dungeon.level.distance(curUser.pos, newHeroPos);
if (chargeUse > charge){ if (chargeUse > charge){
GLog.w( Messages.get(EtherealChains.class, "no_charge") ); GLog.w( Messages.get(EtherealChains.class, "no_charge") );
return; return;
@@ -46,6 +46,7 @@ import com.watabou.noosa.Game;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.Callback; import com.watabou.utils.Callback;
import com.watabou.utils.PathFinder;
import java.util.ArrayList; import java.util.ArrayList;
@@ -115,8 +116,8 @@ public class LloydsBeacon extends Artifact {
return; return;
} }
for (int i=0; i < Level.NEIGHBOURS8.length; i++) { for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++) {
if (Actor.findChar( hero.pos + Level.NEIGHBOURS8[i] ) != null) { if (Actor.findChar( hero.pos + PathFinder.NEIGHBOURS8[i] ) != null) {
GLog.w( Messages.get(this, "creatures") ); GLog.w( Messages.get(this, "creatures") );
return; return;
} }
@@ -75,7 +75,7 @@ public class TalismanOfForesight extends Artifact {
hero.busy(); hero.busy();
Sample.INSTANCE.play(Assets.SND_BEACON); Sample.INSTANCE.play(Assets.SND_BEACON);
charge = 0; charge = 0;
for (int i = 0; i < Level.LENGTH; i++) { for (int i = 0; i < Dungeon.level.length(); i++) {
int terr = Dungeon.level.map[i]; int terr = Dungeon.level.map[i];
if ((Terrain.flags[terr] & Terrain.SECRET) != 0) { if ((Terrain.flags[terr] & Terrain.SECRET) != 0) {
@@ -130,27 +130,27 @@ public class TalismanOfForesight extends Artifact {
int distance = 3; int distance = 3;
int cx = target.pos % Level.WIDTH; int cx = target.pos % Dungeon.level.width();
int cy = target.pos / Level.WIDTH; int cy = target.pos / Dungeon.level.width();
int ax = cx - distance; int ax = cx - distance;
if (ax < 0) { if (ax < 0) {
ax = 0; ax = 0;
} }
int bx = cx + distance; int bx = cx + distance;
if (bx >= Level.WIDTH) { if (bx >= Dungeon.level.width()) {
bx = Level.WIDTH - 1; bx = Dungeon.level.width() - 1;
} }
int ay = cy - distance; int ay = cy - distance;
if (ay < 0) { if (ay < 0) {
ay = 0; ay = 0;
} }
int by = cy + distance; int by = cy + distance;
if (by >= Level.HEIGHT) { if (by >= Dungeon.level.height()) {
by = Level.HEIGHT - 1; by = Dungeon.level.height() - 1;
} }
for (int y = ay; y <= by; y++) { for (int y = ay; y <= by; y++) {
for (int x = ax, p = ax + y * Level.WIDTH; x <= bx; x++, p++) { for (int x = ax, p = ax + y * Dungeon.level.width(); x <= bx; x++, p++) {
if (Dungeon.visible[p] && Level.secret[p] && Dungeon.level.map[p] != Terrain.SECRET_DOOR) if (Dungeon.visible[p] && Level.secret[p] && Dungeon.level.map[p] != Terrain.SECRET_DOOR)
smthFound = true; smthFound = true;
@@ -45,7 +45,7 @@ public class PotionOfFrost extends Potion {
Fire fire = (Fire)Dungeon.level.blobs.get( Fire.class ); Fire fire = (Fire)Dungeon.level.blobs.get( Fire.class );
boolean visible = false; boolean visible = false;
for (int i=0; i < Level.LENGTH; i++) { for (int i=0; i < Dungeon.level.length(); i++) {
if (PathFinder.distance[i] < Integer.MAX_VALUE) { if (PathFinder.distance[i] < Integer.MAX_VALUE) {
visible = Freezing.affect( i, fire ) || visible; visible = Freezing.affect( i, fire ) || visible;
} }
@@ -30,6 +30,7 @@ import com.shatteredpixel.shatteredpixeldungeon.effects.particles.FlameParticle;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level; import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene; import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.PathFinder;
public class PotionOfLiquidFlame extends Potion { public class PotionOfLiquidFlame extends Potion {
@@ -47,7 +48,7 @@ public class PotionOfLiquidFlame extends Potion {
Sample.INSTANCE.play( Assets.SND_SHATTER ); Sample.INSTANCE.play( Assets.SND_SHATTER );
} }
for (int offset : Level.NEIGHBOURS9){ for (int offset : PathFinder.NEIGHBOURS9){
if (Level.flamable[cell+offset] if (Level.flamable[cell+offset]
|| Actor.findChar(cell+offset) != null || Actor.findChar(cell+offset) != null
|| Dungeon.level.heaps.get(cell+offset) != null) { || Dungeon.level.heaps.get(cell+offset) != null) {
@@ -70,7 +70,7 @@ public class PotionOfPurity extends Potion {
continue; continue;
} }
for (int i=0; i < Level.LENGTH; i++) { for (int i=0; i < Dungeon.level.length(); i++) {
if (PathFinder.distance[i] < Integer.MAX_VALUE) { if (PathFinder.distance[i] < Integer.MAX_VALUE) {
int value = blob.cur[i]; int value = blob.cur[i];
@@ -34,6 +34,7 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene; import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet; import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -76,9 +77,9 @@ public class CeremonialCandle extends Item {
} }
private static void checkCandles(){ private static void checkCandles(){
Heap heapTop = Dungeon.level.heaps.get(ritualPos - Level.WIDTH); Heap heapTop = Dungeon.level.heaps.get(ritualPos - Dungeon.level.width());
Heap heapRight = Dungeon.level.heaps.get(ritualPos + 1); Heap heapRight = Dungeon.level.heaps.get(ritualPos + 1);
Heap heapBottom = Dungeon.level.heaps.get(ritualPos + Level.WIDTH); Heap heapBottom = Dungeon.level.heaps.get(ritualPos + Dungeon.level.width());
Heap heapLeft = Dungeon.level.heaps.get(ritualPos - 1); Heap heapLeft = Dungeon.level.heaps.get(ritualPos - 1);
if (heapTop != null && if (heapTop != null &&
@@ -100,7 +101,7 @@ public class CeremonialCandle extends Item {
Char ch = Actor.findChar( ritualPos ); Char ch = Actor.findChar( ritualPos );
if (ch != null) { if (ch != null) {
ArrayList<Integer> candidates = new ArrayList<>(); ArrayList<Integer> candidates = new ArrayList<>();
for (int n : Level.NEIGHBOURS8) { for (int n : PathFinder.NEIGHBOURS8) {
int cell = ritualPos + n; int cell = ritualPos + n;
if ((Level.passable[cell] || Level.avoid[cell]) && Actor.findChar( cell ) == null) { if ((Level.passable[cell] || Level.avoid[cell]) && Actor.findChar( cell ) == null) {
candidates.add( cell ); candidates.add( cell );
@@ -117,7 +118,7 @@ public class CeremonialCandle extends Item {
elemental.state = elemental.HUNTING; elemental.state = elemental.HUNTING;
GameScene.add(elemental, 1); GameScene.add(elemental, 1);
for (int i : Level.NEIGHBOURS9){ for (int i : PathFinder.NEIGHBOURS9){
CellEmitter.get(ritualPos+i).burst(ElmoParticle.FACTORY, 10); CellEmitter.get(ritualPos+i).burst(ElmoParticle.FACTORY, 10);
} }
Sample.INSTANCE.play(Assets.SND_BURNING); Sample.INSTANCE.play(Assets.SND_BURNING);
@@ -101,7 +101,7 @@ public class CorpseDust extends Item {
spawnPower -= powerNeeded; spawnPower -= powerNeeded;
int pos = 0; int pos = 0;
do{ do{
pos = Random.Int(Level.LENGTH); pos = Random.Int(Dungeon.level.length());
} while (!Dungeon.visible[pos] || !Level.passable[pos] || Actor.findChar( pos ) != null); } while (!Dungeon.visible[pos] || !Level.passable[pos] || Actor.findChar( pos ) != null);
Wraith.spawnAt(pos); Wraith.spawnAt(pos);
Sample.INSTANCE.play(Assets.SND_CURSED); Sample.INSTANCE.play(Assets.SND_CURSED);
@@ -40,6 +40,7 @@ import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.Callback; import com.watabou.utils.Callback;
import com.watabou.utils.PathFinder;
import java.util.ArrayList; import java.util.ArrayList;
@@ -96,9 +97,9 @@ public class Pickaxe extends Weapon {
return; return;
} }
for (int i=0; i < Level.NEIGHBOURS8.length; i++) { for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++) {
final int pos = hero.pos + Level.NEIGHBOURS8[i]; final int pos = hero.pos + PathFinder.NEIGHBOURS8[i];
if (Dungeon.level.map[pos] == Terrain.WALL_DECO) { if (Dungeon.level.map[pos] == Terrain.WALL_DECO) {
hero.spend( TIME_TO_MINE ); hero.spend( TIME_TO_MINE );
@@ -42,7 +42,7 @@ public class ScrollOfMagicMapping extends Scroll {
@Override @Override
protected void doRead() { protected void doRead() {
int length = Level.LENGTH; int length = Dungeon.level.length();
int[] map = Dungeon.level.map; int[] map = Dungeon.level.map;
boolean[] mapped = Dungeon.level.mapped; boolean[] mapped = Dungeon.level.mapped;
boolean[] discoverable = Level.discoverable; boolean[] discoverable = Level.discoverable;
@@ -27,6 +27,7 @@ import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.npcs.MirrorImage;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level; import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene; import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -44,8 +45,8 @@ public class ScrollOfMirrorImage extends Scroll {
ArrayList<Integer> respawnPoints = new ArrayList<Integer>(); ArrayList<Integer> respawnPoints = new ArrayList<Integer>();
for (int i=0; i < Level.NEIGHBOURS8.length; i++) { for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++) {
int p = curUser.pos + Level.NEIGHBOURS8[i]; int p = curUser.pos + PathFinder.NEIGHBOURS8[i];
if (Actor.findChar( p ) == null && (Level.passable[p] || Level.avoid[p])) { if (Actor.findChar( p ) == null && (Level.passable[p] || Level.avoid[p])) {
respawnPoints.add( p ); respawnPoints.add( p );
} }
@@ -356,7 +356,7 @@ public class CursedWand {
//great forest fire! //great forest fire!
case 0: case 0:
for (int i = 0; i < Level.LENGTH; i++){ for (int i = 0; i < Dungeon.level.length(); i++){
int c = Dungeon.level.map[i]; int c = Dungeon.level.map[i];
if (c == Terrain.EMPTY || if (c == Terrain.EMPTY ||
c == Terrain.EMBERS || c == Terrain.EMBERS ||
@@ -40,6 +40,7 @@ import com.watabou.noosa.Group;
import com.watabou.noosa.Image; import com.watabou.noosa.Image;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Callback; import com.watabou.utils.Callback;
import com.watabou.utils.PathFinder;
import com.watabou.utils.PointF; import com.watabou.utils.PointF;
import com.watabou.utils.Random; import com.watabou.utils.Random;
@@ -67,12 +68,12 @@ public class WandOfBlastWave extends DamageWand {
int damage = damageRoll(); int damage = damageRoll();
//presses all tiles in the AOE first //presses all tiles in the AOE first
for (int i : Level.NEIGHBOURS9){ for (int i : PathFinder.NEIGHBOURS9){
Dungeon.level.press(bolt.collisionPos+i, Actor.findChar(bolt.collisionPos+i)); Dungeon.level.press(bolt.collisionPos+i, Actor.findChar(bolt.collisionPos+i));
} }
//throws other chars around the center. //throws other chars around the center.
for (int i : Level.NEIGHBOURS8){ for (int i : PathFinder.NEIGHBOURS8){
Char ch = Actor.findChar(bolt.collisionPos + i); Char ch = Actor.findChar(bolt.collisionPos + i);
if (ch != null){ if (ch != null){
@@ -186,8 +187,8 @@ public class WandOfBlastWave extends DamageWand {
public void reset(int pos) { public void reset(int pos) {
revive(); revive();
x = (pos % Level.WIDTH) * DungeonTilemap.SIZE + (DungeonTilemap.SIZE - width) / 2; x = (pos % Dungeon.level.width()) * DungeonTilemap.SIZE + (DungeonTilemap.SIZE - width) / 2;
y = (pos / Level.WIDTH) * DungeonTilemap.SIZE + (DungeonTilemap.SIZE - height) / 2; y = (pos / Dungeon.level.width()) * DungeonTilemap.SIZE + (DungeonTilemap.SIZE - height) / 2;
time = TIME_TO_FADE; time = TIME_TO_FADE;
} }
@@ -39,6 +39,7 @@ import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet; import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Callback; import com.watabou.utils.Callback;
import com.watabou.utils.PathFinder;
import java.util.HashSet; import java.util.HashSet;
@@ -100,9 +101,9 @@ public class WandOfFireblast extends DamageWand {
affectedCells.add(cell); affectedCells.add(cell);
if (strength >= 1.5f) { if (strength >= 1.5f) {
visualCells.remove(cell); visualCells.remove(cell);
spreadFlames(cell + Level.NEIGHBOURS8[left(direction)], strength - 1.5f); spreadFlames(cell + PathFinder.NEIGHBOURS8[left(direction)], strength - 1.5f);
spreadFlames(cell + Level.NEIGHBOURS8[direction], strength - 1.5f); spreadFlames(cell + PathFinder.NEIGHBOURS8[direction], strength - 1.5f);
spreadFlames(cell + Level.NEIGHBOURS8[right(direction)], strength - 1.5f); spreadFlames(cell + PathFinder.NEIGHBOURS8[right(direction)], strength - 1.5f);
} else { } else {
visualCells.add(cell); visualCells.add(cell);
} }
@@ -134,8 +135,8 @@ public class WandOfFireblast extends DamageWand {
int maxDist = (int)(4 * Math.pow(1.5,(chargesPerCast()-1))); int maxDist = (int)(4 * Math.pow(1.5,(chargesPerCast()-1)));
int dist = Math.min(bolt.dist, maxDist); int dist = Math.min(bolt.dist, maxDist);
for (int i = 0; i < Level.NEIGHBOURS8.length; i++){ for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++){
if (bolt.sourcePos+Level.NEIGHBOURS8[i] == bolt.path.get(1)){ if (bolt.sourcePos+PathFinder.NEIGHBOURS8[i] == bolt.path.get(1)){
direction = i; direction = i;
break; break;
} }
@@ -146,9 +147,9 @@ public class WandOfFireblast extends DamageWand {
strength--; //as we start at dist 1, not 0. strength--; //as we start at dist 1, not 0.
affectedCells.add(c); affectedCells.add(c);
if (strength > 1) { if (strength > 1) {
spreadFlames(c + Level.NEIGHBOURS8[left(direction)], strength - 1); spreadFlames(c + PathFinder.NEIGHBOURS8[left(direction)], strength - 1);
spreadFlames(c + Level.NEIGHBOURS8[direction], strength - 1); spreadFlames(c + PathFinder.NEIGHBOURS8[direction], strength - 1);
spreadFlames(c + Level.NEIGHBOURS8[right(direction)], strength - 1); spreadFlames(c + PathFinder.NEIGHBOURS8[right(direction)], strength - 1);
} else { } else {
visualCells.add(c); visualCells.add(c);
} }
@@ -33,9 +33,11 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica; import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages; import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet; import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet;
import com.shatteredpixel.shatteredpixeldungeon.utils.BArray;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog; import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.noosa.Camera; import com.watabou.noosa.Camera;
import com.watabou.utils.Callback; import com.watabou.utils.Callback;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -94,28 +96,24 @@ public class WandOfLightning extends DamageWand {
affected.add( ch ); affected.add( ch );
for (int i : Level.NEIGHBOURS8) { int dist;
int cell = ch.pos + i; if (Level.water[ch.pos] && !ch.flying)
dist = 2;
else
dist = 1;
Char n = Actor.findChar( cell ); PathFinder.buildDistanceMap( ch.pos, BArray.not( Level.solid, null ), dist );
if (n != null && !affected.contains( n )) { for (int i = 0; i < PathFinder.distance.length; i++) {
arcs.add(new Lightning.Arc(ch.pos, n.pos)); if (PathFinder.distance[i] < Integer.MAX_VALUE){
arc(n); Char n = Actor.findChar( i );
} if (n == Dungeon.hero && PathFinder.distance[i] > 1)
} //the hero is only zapped if they are adjacent
continue;
if (Level.water[ch.pos] && !ch.flying){ else if (n != null && !affected.contains( n )) {
for (int i : Level.NEIGHBOURS8DIST2) { arcs.add(new Lightning.Arc(ch.pos, n.pos));
int cell = ch.pos + i; arc(n);
//player can only be hit by lightning from an adjacent enemy. }
if (!Level.insideMap(cell) || Actor.findChar(cell) == Dungeon.hero) continue;
Char n = Actor.findChar( ch.pos + i );
if (n != null && !affected.contains( n )) {
arcs.add(new Lightning.Arc(ch.pos, n.pos));
arc(n);
} }
}
} }
} }
@@ -41,8 +41,10 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain;
import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica; import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene; import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet; import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet;
import com.shatteredpixel.shatteredpixeldungeon.utils.BArray;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Callback; import com.watabou.utils.Callback;
import com.watabou.utils.PathFinder;
import com.watabou.utils.PointF; import com.watabou.utils.PointF;
import com.watabou.utils.Random; import com.watabou.utils.Random;
@@ -100,10 +102,8 @@ public class WandOfPrismaticLight extends DamageWand {
private void affectMap(Ballistica beam){ private void affectMap(Ballistica beam){
boolean noticed = false; boolean noticed = false;
for (int c: beam.subPath(0, beam.dist)){ for (int c: beam.subPath(0, beam.dist)){
for (int n : Level.NEIGHBOURS9DIST2){ for (int n : PathFinder.NEIGHBOURS9){
int cell = c+n; int cell = c+n;
if (!Level.insideMap(cell))
continue;
if (Level.discoverable[cell]) if (Level.discoverable[cell])
Dungeon.level.mapped[cell] = true; Dungeon.level.mapped[cell] = true;
@@ -43,6 +43,7 @@ import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Callback; import com.watabou.utils.Callback;
import com.watabou.utils.ColorMath; import com.watabou.utils.ColorMath;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -110,9 +111,9 @@ public class WandOfRegrowth extends Wand {
if (strength >= 0 && Level.passable[cell] && !Level.losBlocking[cell]){ if (strength >= 0 && Level.passable[cell] && !Level.losBlocking[cell]){
affectedCells.add(cell); affectedCells.add(cell);
if (strength >= 1.5f) { if (strength >= 1.5f) {
spreadRegrowth(cell + Level.NEIGHBOURS8[left(direction)], strength - 1.5f); spreadRegrowth(cell + PathFinder.NEIGHBOURS8[left(direction)], strength - 1.5f);
spreadRegrowth(cell + Level.NEIGHBOURS8[direction], strength - 1.5f); spreadRegrowth(cell + PathFinder.NEIGHBOURS8[direction], strength - 1.5f);
spreadRegrowth(cell + Level.NEIGHBOURS8[right(direction)], strength-1.5f); spreadRegrowth(cell + PathFinder.NEIGHBOURS8[right(direction)], strength-1.5f);
} else { } else {
visualCells.add(cell); visualCells.add(cell);
} }
@@ -187,8 +188,8 @@ public class WandOfRegrowth extends Wand {
int maxDist = Math.round(1.2f + chargesPerCast()*.8f); int maxDist = Math.round(1.2f + chargesPerCast()*.8f);
int dist = Math.min(bolt.dist, maxDist); int dist = Math.min(bolt.dist, maxDist);
for (int i = 0; i < Level.NEIGHBOURS8.length; i++){ for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++){
if (bolt.sourcePos+Level.NEIGHBOURS8[i] == bolt.path.get(1)){ if (bolt.sourcePos+PathFinder.NEIGHBOURS8[i] == bolt.path.get(1)){
direction = i; direction = i;
break; break;
} }
@@ -199,9 +200,9 @@ public class WandOfRegrowth extends Wand {
strength--; //as we start at dist 1, not 0. strength--; //as we start at dist 1, not 0.
if (!Level.losBlocking[c]) { if (!Level.losBlocking[c]) {
affectedCells.add(c); affectedCells.add(c);
spreadRegrowth(c + Level.NEIGHBOURS8[left(direction)], strength - 1); spreadRegrowth(c + PathFinder.NEIGHBOURS8[left(direction)], strength - 1);
spreadRegrowth(c + Level.NEIGHBOURS8[direction], strength - 1); spreadRegrowth(c + PathFinder.NEIGHBOURS8[direction], strength - 1);
spreadRegrowth(c + Level.NEIGHBOURS8[right(direction)], strength - 1); spreadRegrowth(c + PathFinder.NEIGHBOURS8[right(direction)], strength - 1);
} else { } else {
visualCells.add(c); visualCells.add(c);
} }
@@ -254,7 +255,7 @@ public class WandOfRegrowth extends Wand {
int nDrops = Random.NormalIntRange(2, 8); int nDrops = Random.NormalIntRange(2, 8);
ArrayList<Integer> candidates = new ArrayList<Integer>(); ArrayList<Integer> candidates = new ArrayList<Integer>();
for (int i : Level.NEIGHBOURS8){ for (int i : PathFinder.NEIGHBOURS8){
if (Level.passable[pos+i]){ if (Level.passable[pos+i]){
candidates.add(pos+i); candidates.add(pos+i);
} }
@@ -288,7 +289,7 @@ public class WandOfRegrowth extends Wand {
int nSeeds = Random.NormalIntRange(1, 5); int nSeeds = Random.NormalIntRange(1, 5);
ArrayList<Integer> candidates = new ArrayList<Integer>(); ArrayList<Integer> candidates = new ArrayList<Integer>();
for (int i : Level.NEIGHBOURS8){ for (int i : PathFinder.NEIGHBOURS8){
if (Level.passable[pos+i]){ if (Level.passable[pos+i]){
candidates.add(pos+i); candidates.add(pos+i);
} }
@@ -34,6 +34,7 @@ import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet; import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Callback; import com.watabou.utils.Callback;
import com.watabou.utils.PathFinder;
public class WandOfVenom extends Wand { public class WandOfVenom extends Wand {
@@ -49,7 +50,7 @@ public class WandOfVenom extends Wand {
((VenomGas)venomGas).setStrength(level()+1); ((VenomGas)venomGas).setStrength(level()+1);
GameScene.add(venomGas); GameScene.add(venomGas);
for (int i : Level.NEIGHBOURS9) { for (int i : PathFinder.NEIGHBOURS9) {
Char ch = Actor.findChar(bolt.collisionPos + i); Char ch = Actor.findChar(bolt.collisionPos + i);
if (ch != null) { if (ch != null) {
processSoulMark(ch, chargesPerCast()); processSoulMark(ch, chargesPerCast());
@@ -28,6 +28,7 @@ import com.shatteredpixel.shatteredpixeldungeon.items.weapon.Weapon;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level; import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap; import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite; import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -83,8 +84,8 @@ public class Shocking extends Weapon.Enchantment {
ch.sprite.flash(); ch.sprite.flash();
HashSet<Char> ns = new HashSet<Char>(); HashSet<Char> ns = new HashSet<Char>();
for (int i=0; i < Level.NEIGHBOURS8.length; i++) { for (int i = 0; i < PathFinder.NEIGHBOURS8.length; i++) {
Char n = Actor.findChar( ch.pos + Level.NEIGHBOURS8[i] ); Char n = Actor.findChar( ch.pos + PathFinder.NEIGHBOURS8[i] );
if (n != null && !affected.contains( n )) { if (n != null && !affected.contains( n )) {
arcs.add(new Lightning.Arc(ch.pos, n.pos)); arcs.add(new Lightning.Arc(ch.pos, n.pos));
hit(n, Random.Int(damage / 2, damage)); hit(n, Random.Int(damage / 2, damage));
@@ -57,7 +57,7 @@ abstract public class MissileWeapon extends Weapon {
@Override @Override
public int throwPos(Hero user, int dst) { public int throwPos(Hero user, int dst) {
if (hasEnchant(Projecting.class) if (hasEnchant(Projecting.class)
&& !Level.solid[dst] && Level.distance(user.pos, dst) <= 4){ && !Level.solid[dst] && Dungeon.level.distance(user.pos, dst) <= 4){
return dst; return dst;
} else { } else {
return super.throwPos(user, dst); return super.throwPos(user, dst);
@@ -41,6 +41,7 @@ import com.watabou.noosa.Camera;
import com.watabou.noosa.Group; import com.watabou.noosa.Group;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
public class CavesBossLevel extends Level { public class CavesBossLevel extends Level {
@@ -51,7 +52,10 @@ public class CavesBossLevel extends Level {
viewDistance = 6; viewDistance = 6;
} }
private static final int WIDTH = 32;
private static final int HEIGHT = 32;
private static final int ROOM_LEFT = WIDTH / 2 - 2; private static final int ROOM_LEFT = WIDTH / 2 - 2;
private static final int ROOM_RIGHT = WIDTH / 2 + 2; private static final int ROOM_RIGHT = WIDTH / 2 + 2;
private static final int ROOM_TOP = HEIGHT / 2 - 2; private static final int ROOM_TOP = HEIGHT / 2 - 2;
@@ -103,21 +107,21 @@ public class CavesBossLevel extends Level {
right = ROOM_RIGHT + 3; right = ROOM_RIGHT + 3;
} else { } else {
left = ROOM_LEFT - 3; left = ROOM_LEFT - 3;
right = Random.Int( ROOM_RIGHT + 3, WIDTH - 1 ); right = Random.Int( ROOM_RIGHT + 3, width() - 1 );
} }
if (Random.Int( 2 ) == 0) { if (Random.Int( 2 ) == 0) {
top = Random.Int( 2, ROOM_TOP - 3 ); top = Random.Int( 2, ROOM_TOP - 3 );
bottom = ROOM_BOTTOM + 3; bottom = ROOM_BOTTOM + 3;
} else { } else {
top = ROOM_LEFT - 3; top = ROOM_LEFT - 3;
bottom = Random.Int( ROOM_TOP + 3, HEIGHT - 1 ); bottom = Random.Int( ROOM_TOP + 3, height() - 1 );
} }
Painter.fill( this, left, top, right - left + 1, bottom - top + 1, Terrain.EMPTY ); Painter.fill( this, left, top, right - left + 1, bottom - top + 1, Terrain.EMPTY );
if (top < topMost) { if (top < topMost) {
topMost = top; topMost = top;
exit = Random.Int( left, right ) + (top - 1) * WIDTH; exit = Random.Int( left, right ) + (top - 1) * width();
} }
} }
@@ -131,21 +135,21 @@ public class CavesBossLevel extends Level {
Painter.fill( this, ROOM_LEFT, ROOM_TOP, Painter.fill( this, ROOM_LEFT, ROOM_TOP,
ROOM_RIGHT - ROOM_LEFT + 1, 1, Terrain.EMPTY_DECO ); ROOM_RIGHT - ROOM_LEFT + 1, 1, Terrain.EMPTY_DECO );
arenaDoor = Random.Int( ROOM_LEFT, ROOM_RIGHT ) + (ROOM_BOTTOM + 1) * WIDTH; arenaDoor = Random.Int( ROOM_LEFT, ROOM_RIGHT ) + (ROOM_BOTTOM + 1) * width();
map[arenaDoor] = Terrain.DOOR; map[arenaDoor] = Terrain.DOOR;
entrance = Random.Int( ROOM_LEFT + 1, ROOM_RIGHT - 1 ) + entrance = Random.Int( ROOM_LEFT + 1, ROOM_RIGHT - 1 ) +
Random.Int( ROOM_TOP + 1, ROOM_BOTTOM - 1 ) * WIDTH; Random.Int( ROOM_TOP + 1, ROOM_BOTTOM - 1 ) * width();
map[entrance] = Terrain.ENTRANCE; map[entrance] = Terrain.ENTRANCE;
boolean[] patch = Patch.generate( 0.45f, 6 ); boolean[] patch = Patch.generate( this, 0.45f, 6 );
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (map[i] == Terrain.EMPTY && patch[i]) { if (map[i] == Terrain.EMPTY && patch[i]) {
map[i] = Terrain.WATER; map[i] = Terrain.WATER;
} }
} }
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (map[i] == Terrain.EMPTY && Random.Int( 6 ) == 0) { if (map[i] == Terrain.EMPTY && Random.Int( 6 ) == 0) {
map[i] = Terrain.INACTIVE_TRAP; map[i] = Terrain.INACTIVE_TRAP;
Trap t = new ToxicTrap().reveal(); Trap t = new ToxicTrap().reveal();
@@ -160,7 +164,7 @@ public class CavesBossLevel extends Level {
@Override @Override
protected void decorate() { protected void decorate() {
for (int i=WIDTH + 1; i < LENGTH - WIDTH; i++) { for (int i=width() + 1; i < length() - width(); i++) {
if (map[i] == Terrain.EMPTY) { if (map[i] == Terrain.EMPTY) {
int n = 0; int n = 0;
if (map[i+1] == Terrain.WALL) { if (map[i+1] == Terrain.WALL) {
@@ -169,10 +173,10 @@ public class CavesBossLevel extends Level {
if (map[i-1] == Terrain.WALL) { if (map[i-1] == Terrain.WALL) {
n++; n++;
} }
if (map[i+WIDTH] == Terrain.WALL) { if (map[i+width()] == Terrain.WALL) {
n++; n++;
} }
if (map[i-WIDTH] == Terrain.WALL) { if (map[i-width()] == Terrain.WALL) {
n++; n++;
} }
if (Random.Int( 8 ) <= n) { if (Random.Int( 8 ) <= n) {
@@ -181,7 +185,7 @@ public class CavesBossLevel extends Level {
} }
} }
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (map[i] == Terrain.WALL && Random.Int( 8 ) == 0) { if (map[i] == Terrain.WALL && Random.Int( 8 ) == 0) {
map[i] = Terrain.WALL_DECO; map[i] = Terrain.WALL_DECO;
} }
@@ -189,7 +193,7 @@ public class CavesBossLevel extends Level {
int sign; int sign;
do { do {
sign = Random.Int( ROOM_LEFT, ROOM_RIGHT ) + Random.Int( ROOM_TOP, ROOM_BOTTOM ) * WIDTH; sign = Random.Int( ROOM_LEFT, ROOM_RIGHT ) + Random.Int( ROOM_TOP, ROOM_BOTTOM ) * width();
} while (sign == entrance || map[sign] == Terrain.INACTIVE_TRAP); } while (sign == entrance || map[sign] == Terrain.INACTIVE_TRAP);
map[sign] = Terrain.SIGN; map[sign] = Terrain.SIGN;
} }
@@ -208,7 +212,7 @@ public class CavesBossLevel extends Level {
if (item != null) { if (item != null) {
int pos; int pos;
do { do {
pos = Random.IntRange( ROOM_LEFT, ROOM_RIGHT ) + Random.IntRange( ROOM_TOP + 1, ROOM_BOTTOM ) * WIDTH; pos = Random.IntRange( ROOM_LEFT, ROOM_RIGHT ) + Random.IntRange( ROOM_TOP + 1, ROOM_BOTTOM ) * width();
} while (pos == entrance || map[pos] == Terrain.SIGN); } while (pos == entrance || map[pos] == Terrain.SIGN);
drop( item, pos ).type = Heap.Type.REMAINS; drop( item, pos ).type = Heap.Type.REMAINS;
} }
@@ -216,9 +220,9 @@ public class CavesBossLevel extends Level {
@Override @Override
public int randomRespawnCell() { public int randomRespawnCell() {
int cell = entrance + NEIGHBOURS8[Random.Int(8)]; int cell = entrance + PathFinder.NEIGHBOURS8[Random.Int(8)];
while (!passable[cell]){ while (!passable[cell]){
cell = entrance + NEIGHBOURS8[Random.Int(8)]; cell = entrance + PathFinder.NEIGHBOURS8[Random.Int(8)];
} }
return cell; return cell;
} }
@@ -236,7 +240,7 @@ public class CavesBossLevel extends Level {
Mob boss = Bestiary.mob( Dungeon.depth ); Mob boss = Bestiary.mob( Dungeon.depth );
boss.state = boss.WANDERING; boss.state = boss.WANDERING;
do { do {
boss.pos = Random.Int( LENGTH ); boss.pos = Random.Int( length() );
} while ( } while (
!passable[boss.pos] || !passable[boss.pos] ||
!outsideEntraceRoom( boss.pos ) || !outsideEntraceRoom( boss.pos ) ||
@@ -272,8 +276,8 @@ public class CavesBossLevel extends Level {
} }
private boolean outsideEntraceRoom( int cell ) { private boolean outsideEntraceRoom( int cell ) {
int cx = cell % WIDTH; int cx = cell % width();
int cy = cell / WIDTH; int cy = cell / width();
return cx < ROOM_LEFT-1 || cx > ROOM_RIGHT+1 || cy < ROOM_TOP-1 || cy > ROOM_BOTTOM+1; return cx < ROOM_LEFT-1 || cx > ROOM_RIGHT+1 || cy < ROOM_TOP-1 || cy > ROOM_BOTTOM+1;
} }
@@ -73,11 +73,11 @@ public class CavesLevel extends RegularLevel {
} }
protected boolean[] water() { protected boolean[] water() {
return Patch.generate( feeling == Feeling.WATER ? 0.60f : 0.45f, 6 ); return Patch.generate( this, feeling == Feeling.WATER ? 0.60f : 0.45f, 6 );
} }
protected boolean[] grass() { protected boolean[] grass() {
return Patch.generate( feeling == Feeling.GRASS ? 0.55f : 0.35f, 3 ); return Patch.generate( this, feeling == Feeling.GRASS ? 0.55f : 0.35f, 3 );
} }
@Override @Override
@@ -121,32 +121,32 @@ public class CavesLevel extends RegularLevel {
int s = room.square(); int s = room.square();
if (Random.Int( s ) > 8) { if (Random.Int( s ) > 8) {
int corner = (room.left + 1) + (room.top + 1) * WIDTH; int corner = (room.left + 1) + (room.top + 1) * width();
if (map[corner - 1] == Terrain.WALL && map[corner - WIDTH] == Terrain.WALL) { if (map[corner - 1] == Terrain.WALL && map[corner - width()] == Terrain.WALL) {
map[corner] = Terrain.WALL; map[corner] = Terrain.WALL;
traps.remove(corner); traps.remove(corner);
} }
} }
if (Random.Int( s ) > 8) { if (Random.Int( s ) > 8) {
int corner = (room.right - 1) + (room.top + 1) * WIDTH; int corner = (room.right - 1) + (room.top + 1) * width();
if (map[corner + 1] == Terrain.WALL && map[corner - WIDTH] == Terrain.WALL) { if (map[corner + 1] == Terrain.WALL && map[corner - width()] == Terrain.WALL) {
map[corner] = Terrain.WALL; map[corner] = Terrain.WALL;
traps.remove(corner); traps.remove(corner);
} }
} }
if (Random.Int( s ) > 8) { if (Random.Int( s ) > 8) {
int corner = (room.left + 1) + (room.bottom - 1) * WIDTH; int corner = (room.left + 1) + (room.bottom - 1) * width();
if (map[corner - 1] == Terrain.WALL && map[corner + WIDTH] == Terrain.WALL) { if (map[corner - 1] == Terrain.WALL && map[corner + width()] == Terrain.WALL) {
map[corner] = Terrain.WALL; map[corner] = Terrain.WALL;
traps.remove(corner); traps.remove(corner);
} }
} }
if (Random.Int( s ) > 8) { if (Random.Int( s ) > 8) {
int corner = (room.right - 1) + (room.bottom - 1) * WIDTH; int corner = (room.right - 1) + (room.bottom - 1) * width();
if (map[corner + 1] == Terrain.WALL && map[corner + WIDTH] == Terrain.WALL) { if (map[corner + 1] == Terrain.WALL && map[corner + width()] == Terrain.WALL) {
map[corner] = Terrain.WALL; map[corner] = Terrain.WALL;
traps.remove(corner); traps.remove(corner);
} }
@@ -159,7 +159,7 @@ public class CavesLevel extends RegularLevel {
} }
} }
for (int i=WIDTH + 1; i < LENGTH - WIDTH; i++) { for (int i=width() + 1; i < length() - width(); i++) {
if (map[i] == Terrain.EMPTY) { if (map[i] == Terrain.EMPTY) {
int n = 0; int n = 0;
if (map[i+1] == Terrain.WALL) { if (map[i+1] == Terrain.WALL) {
@@ -168,10 +168,10 @@ public class CavesLevel extends RegularLevel {
if (map[i-1] == Terrain.WALL) { if (map[i-1] == Terrain.WALL) {
n++; n++;
} }
if (map[i+WIDTH] == Terrain.WALL) { if (map[i+width()] == Terrain.WALL) {
n++; n++;
} }
if (map[i-WIDTH] == Terrain.WALL) { if (map[i-width()] == Terrain.WALL) {
n++; n++;
} }
if (Random.Int( 6 ) <= n) { if (Random.Int( 6 ) <= n) {
@@ -180,7 +180,7 @@ public class CavesLevel extends RegularLevel {
} }
} }
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (map[i] == Terrain.WALL && Random.Int( 12 ) == 0) { if (map[i] == Terrain.WALL && Random.Int( 12 ) == 0) {
map[i] = Terrain.WALL_DECO; map[i] = Terrain.WALL_DECO;
} }
@@ -261,7 +261,7 @@ public class CavesLevel extends RegularLevel {
} }
public static void addCavesVisuals( Level level, Group group ) { public static void addCavesVisuals( Level level, Group group ) {
for (int i=0; i < LENGTH; i++) { for (int i=0; i < level.length(); i++) {
if (level.map[i] == Terrain.WALL_DECO) { if (level.map[i] == Terrain.WALL_DECO) {
group.add( new Vein( i ) ); group.add( new Vein( i ) );
} }
@@ -36,6 +36,7 @@ import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.watabou.noosa.Group; import com.watabou.noosa.Group;
import com.watabou.noosa.tweeners.AlphaTweener; import com.watabou.noosa.tweeners.AlphaTweener;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
public class CityBossLevel extends Level { public class CityBossLevel extends Level {
@@ -49,6 +50,8 @@ public class CityBossLevel extends Level {
private static final int HALL_WIDTH = 7; private static final int HALL_WIDTH = 7;
private static final int HALL_HEIGHT = 15; private static final int HALL_HEIGHT = 15;
private static final int CHAMBER_HEIGHT = 3; private static final int CHAMBER_HEIGHT = 3;
private static final int WIDTH = 32;
private static final int LEFT = (WIDTH - HALL_WIDTH) / 2; private static final int LEFT = (WIDTH - HALL_WIDTH) / 2;
private static final int CENTER = LEFT + HALL_WIDTH / 2; private static final int CENTER = LEFT + HALL_WIDTH / 2;
@@ -95,8 +98,8 @@ public class CityBossLevel extends Level {
int y = TOP + 1; int y = TOP + 1;
while (y < TOP + HALL_HEIGHT) { while (y < TOP + HALL_HEIGHT) {
map[y * WIDTH + CENTER - 2] = Terrain.STATUE_SP; map[y * width() + CENTER - 2] = Terrain.STATUE_SP;
map[y * WIDTH + CENTER + 2] = Terrain.STATUE_SP; map[y * width() + CENTER + 2] = Terrain.STATUE_SP;
y += 2; y += 2;
} }
@@ -107,17 +110,17 @@ public class CityBossLevel extends Level {
map[i] = Terrain.EMPTY_SP; map[i] = Terrain.EMPTY_SP;
} }
exit = (TOP - 1) * WIDTH + CENTER; exit = (TOP - 1) * width() + CENTER;
map[exit] = Terrain.LOCKED_EXIT; map[exit] = Terrain.LOCKED_EXIT;
arenaDoor = (TOP + HALL_HEIGHT) * WIDTH + CENTER; arenaDoor = (TOP + HALL_HEIGHT) * width() + CENTER;
map[arenaDoor] = Terrain.DOOR; map[arenaDoor] = Terrain.DOOR;
Painter.fill( this, LEFT, TOP + HALL_HEIGHT + 1, HALL_WIDTH, CHAMBER_HEIGHT, Terrain.EMPTY ); Painter.fill( this, LEFT, TOP + HALL_HEIGHT + 1, HALL_WIDTH, CHAMBER_HEIGHT, Terrain.EMPTY );
Painter.fill( this, LEFT, TOP + HALL_HEIGHT + 1, 1, CHAMBER_HEIGHT, Terrain.BOOKSHELF ); Painter.fill( this, LEFT, TOP + HALL_HEIGHT + 1, 1, CHAMBER_HEIGHT, Terrain.BOOKSHELF );
Painter.fill( this, LEFT + HALL_WIDTH - 1, TOP + HALL_HEIGHT + 1, 1, CHAMBER_HEIGHT, Terrain.BOOKSHELF ); Painter.fill( this, LEFT + HALL_WIDTH - 1, TOP + HALL_HEIGHT + 1, 1, CHAMBER_HEIGHT, Terrain.BOOKSHELF );
entrance = (TOP + HALL_HEIGHT + 2 + Random.Int( CHAMBER_HEIGHT - 1 )) * WIDTH + LEFT + (/*1 +*/ Random.Int( HALL_WIDTH-2 )); entrance = (TOP + HALL_HEIGHT + 2 + Random.Int( CHAMBER_HEIGHT - 1 )) * width() + LEFT + (/*1 +*/ Random.Int( HALL_WIDTH-2 ));
map[entrance] = Terrain.ENTRANCE; map[entrance] = Terrain.ENTRANCE;
return true; return true;
@@ -126,7 +129,7 @@ public class CityBossLevel extends Level {
@Override @Override
protected void decorate() { protected void decorate() {
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (map[i] == Terrain.EMPTY && Random.Int( 10 ) == 0) { if (map[i] == Terrain.EMPTY && Random.Int( 10 ) == 0) {
map[i] = Terrain.EMPTY_DECO; map[i] = Terrain.EMPTY_DECO;
} else if (map[i] == Terrain.WALL && Random.Int( 8 ) == 0) { } else if (map[i] == Terrain.WALL && Random.Int( 8 ) == 0) {
@@ -134,15 +137,15 @@ public class CityBossLevel extends Level {
} }
} }
int sign = arenaDoor + WIDTH + 1; int sign = arenaDoor + width() + 1;
map[sign] = Terrain.SIGN; map[sign] = Terrain.SIGN;
} }
public static int pedestal( boolean left ) { public int pedestal( boolean left ) {
if (left) { if (left) {
return (TOP + HALL_HEIGHT / 2) * WIDTH + CENTER - 2; return (TOP + HALL_HEIGHT / 2) * width() + CENTER - 2;
} else { } else {
return (TOP + HALL_HEIGHT / 2) * WIDTH + CENTER + 2; return (TOP + HALL_HEIGHT / 2) * width() + CENTER + 2;
} }
} }
@@ -162,7 +165,7 @@ public class CityBossLevel extends Level {
do { do {
pos = pos =
Random.IntRange( LEFT + 1, LEFT + HALL_WIDTH - 2 ) + Random.IntRange( LEFT + 1, LEFT + HALL_WIDTH - 2 ) +
Random.IntRange( TOP + HALL_HEIGHT + 1, TOP + HALL_HEIGHT + CHAMBER_HEIGHT ) * WIDTH; Random.IntRange( TOP + HALL_HEIGHT + 1, TOP + HALL_HEIGHT + CHAMBER_HEIGHT ) * width();
} while (pos == entrance || map[pos] == Terrain.SIGN); } while (pos == entrance || map[pos] == Terrain.SIGN);
drop( item, pos ).type = Heap.Type.REMAINS; drop( item, pos ).type = Heap.Type.REMAINS;
} }
@@ -170,9 +173,9 @@ public class CityBossLevel extends Level {
@Override @Override
public int randomRespawnCell() { public int randomRespawnCell() {
int cell = entrance + NEIGHBOURS8[Random.Int(8)]; int cell = entrance + PathFinder.NEIGHBOURS8[Random.Int(8)];
while (!passable[cell]){ while (!passable[cell]){
cell = entrance + NEIGHBOURS8[Random.Int(8)]; cell = entrance + PathFinder.NEIGHBOURS8[Random.Int(8)];
} }
return cell; return cell;
} }
@@ -191,7 +194,7 @@ public class CityBossLevel extends Level {
boss.state = boss.WANDERING; boss.state = boss.WANDERING;
int count = 0; int count = 0;
do { do {
boss.pos = Random.Int( LENGTH ); boss.pos = Random.Int( length() );
} while ( } while (
!passable[boss.pos] || !passable[boss.pos] ||
!outsideEntraceRoom( boss.pos ) || !outsideEntraceRoom( boss.pos ) ||
@@ -227,7 +230,7 @@ public class CityBossLevel extends Level {
} }
private boolean outsideEntraceRoom( int cell ) { private boolean outsideEntraceRoom( int cell ) {
return cell / WIDTH < arenaDoor / WIDTH; return cell / width() < arenaDoor / width();
} }
@Override @Override
@@ -68,11 +68,11 @@ public class CityLevel extends RegularLevel {
} }
protected boolean[] water() { protected boolean[] water() {
return Patch.generate( feeling == Feeling.WATER ? 0.65f : 0.45f, 4 ); return Patch.generate( this, feeling == Feeling.WATER ? 0.65f : 0.45f, 4 );
} }
protected boolean[] grass() { protected boolean[] grass() {
return Patch.generate( feeling == Feeling.GRASS ? 0.60f : 0.40f, 3 ); return Patch.generate( this, feeling == Feeling.GRASS ? 0.60f : 0.40f, 3 );
} }
@Override @Override
@@ -107,7 +107,7 @@ public class CityLevel extends RegularLevel {
@Override @Override
protected void decorate() { protected void decorate() {
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (map[i] == Terrain.EMPTY && Random.Int( 10 ) == 0) { if (map[i] == Terrain.EMPTY && Random.Int( 10 ) == 0) {
map[i] = Terrain.EMPTY_DECO; map[i] = Terrain.EMPTY_DECO;
} else if (map[i] == Terrain.WALL && Random.Int( 8 ) == 0) { } else if (map[i] == Terrain.WALL && Random.Int( 8 ) == 0) {
@@ -167,7 +167,7 @@ public class CityLevel extends RegularLevel {
} }
public static void addCityVisuals( Level level, Group group ) { public static void addCityVisuals( Level level, Group group ) {
for (int i=0; i < LENGTH; i++) { for (int i=0; i < level.length(); i++) {
if (level.map[i] == Terrain.WALL_DECO) { if (level.map[i] == Terrain.WALL_DECO) {
group.add( new Smoke( i ) ); group.add( new Smoke( i ) );
} }
@@ -52,22 +52,22 @@ public class DeadEndLevel extends Level {
for (int i=2; i < SIZE; i++) { for (int i=2; i < SIZE; i++) {
for (int j=2; j < SIZE; j++) { for (int j=2; j < SIZE; j++) {
map[i * WIDTH + j] = Terrain.EMPTY; map[i * width() + j] = Terrain.EMPTY;
} }
} }
for (int i=1; i <= SIZE; i++) { for (int i=1; i <= SIZE; i++) {
map[WIDTH + i] = map[width() + i] =
map[WIDTH * SIZE + i] = map[width() * SIZE + i] =
map[WIDTH * i + 1] = map[width() * i + 1] =
map[WIDTH * i + SIZE] = map[width() * i + SIZE] =
Terrain.WATER; Terrain.WATER;
} }
entrance = SIZE * WIDTH + SIZE / 2 + 1; entrance = SIZE * width() + SIZE / 2 + 1;
map[entrance] = Terrain.ENTRANCE; map[entrance] = Terrain.ENTRANCE;
map[(SIZE / 2 + 1) * (WIDTH + 1)] = Terrain.SIGN; map[(SIZE / 2 + 1) * (width() + 1)] = Terrain.SIGN;
exit = 0; exit = 0;
@@ -76,7 +76,7 @@ public class DeadEndLevel extends Level {
@Override @Override
protected void decorate() { protected void decorate() {
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (map[i] == Terrain.EMPTY && Random.Int( 10 ) == 0) { if (map[i] == Terrain.EMPTY && Random.Int( 10 ) == 0) {
map[i] = Terrain.EMPTY_DECO; map[i] = Terrain.EMPTY_DECO;
} else if (map[i] == Terrain.WALL && Random.Int( 8 ) == 0) { } else if (map[i] == Terrain.WALL && Random.Int( 8 ) == 0) {
@@ -99,7 +99,7 @@ public class DeadEndLevel extends Level {
@Override @Override
public int randomRespawnCell() { public int randomRespawnCell() {
return entrance-WIDTH; return entrance-width();
} }
} }
@@ -36,6 +36,7 @@ import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene; import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.watabou.noosa.Group; import com.watabou.noosa.Group;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
public class HallsBossLevel extends Level { public class HallsBossLevel extends Level {
@@ -46,7 +47,10 @@ public class HallsBossLevel extends Level {
viewDistance = 3; viewDistance = 3;
} }
private static final int WIDTH = 32;
private static final int HEIGHT = 32;
private static final int ROOM_LEFT = WIDTH / 2 - 1; private static final int ROOM_LEFT = WIDTH / 2 - 1;
private static final int ROOM_RIGHT = WIDTH / 2 + 1; private static final int ROOM_RIGHT = WIDTH / 2 + 1;
private static final int ROOM_TOP = HEIGHT / 2 - 1; private static final int ROOM_TOP = HEIGHT / 2 - 1;
@@ -96,13 +100,13 @@ public class HallsBossLevel extends Level {
Painter.fill( this, 2 + i * 4, top, 4, bottom - top + 1, Terrain.EMPTY ); Painter.fill( this, 2 + i * 4, top, 4, bottom - top + 1, Terrain.EMPTY );
if (i == 2) { if (i == 2) {
exit = (i * 4 + 3) + (top - 1) * WIDTH ; exit = (i * 4 + 3) + (top - 1) * width() ;
} }
for (int j=0; j < 4; j++) { for (int j=0; j < 4; j++) {
if (Random.Int( 2 ) == 0) { if (Random.Int( 2 ) == 0) {
int y = Random.IntRange( top + 1, bottom - 1 ); int y = Random.IntRange( top + 1, bottom - 1 );
map[i*4+j + y*WIDTH] = Terrain.WALL_DECO; map[i*4+j + y*width()] = Terrain.WALL_DECO;
} }
} }
} }
@@ -115,11 +119,11 @@ public class HallsBossLevel extends Level {
ROOM_RIGHT - ROOM_LEFT + 1, ROOM_BOTTOM - ROOM_TOP + 1, Terrain.EMPTY ); ROOM_RIGHT - ROOM_LEFT + 1, ROOM_BOTTOM - ROOM_TOP + 1, Terrain.EMPTY );
entrance = Random.Int( ROOM_LEFT + 1, ROOM_RIGHT - 1 ) + entrance = Random.Int( ROOM_LEFT + 1, ROOM_RIGHT - 1 ) +
Random.Int( ROOM_TOP + 1, ROOM_BOTTOM - 1 ) * WIDTH; Random.Int( ROOM_TOP + 1, ROOM_BOTTOM - 1 ) * width();
map[entrance] = Terrain.ENTRANCE; map[entrance] = Terrain.ENTRANCE;
boolean[] patch = Patch.generate( 0.45f, 6 ); boolean[] patch = Patch.generate( this, 0.45f, 6 );
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (map[i] == Terrain.EMPTY && patch[i]) { if (map[i] == Terrain.EMPTY && patch[i]) {
map[i] = Terrain.WATER; map[i] = Terrain.WATER;
} }
@@ -131,7 +135,7 @@ public class HallsBossLevel extends Level {
@Override @Override
protected void decorate() { protected void decorate() {
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (map[i] == Terrain.EMPTY && Random.Int( 10 ) == 0) { if (map[i] == Terrain.EMPTY && Random.Int( 10 ) == 0) {
map[i] = Terrain.EMPTY_DECO; map[i] = Terrain.EMPTY_DECO;
} }
@@ -152,7 +156,7 @@ public class HallsBossLevel extends Level {
if (item != null) { if (item != null) {
int pos; int pos;
do { do {
pos = Random.IntRange( ROOM_LEFT, ROOM_RIGHT ) + Random.IntRange( ROOM_TOP + 1, ROOM_BOTTOM ) * WIDTH; pos = Random.IntRange( ROOM_LEFT, ROOM_RIGHT ) + Random.IntRange( ROOM_TOP + 1, ROOM_BOTTOM ) * width();
} while (pos == entrance || map[pos] == Terrain.SIGN); } while (pos == entrance || map[pos] == Terrain.SIGN);
drop( item, pos ).type = Heap.Type.REMAINS; drop( item, pos ).type = Heap.Type.REMAINS;
} }
@@ -161,9 +165,9 @@ public class HallsBossLevel extends Level {
@Override @Override
public int randomRespawnCell() { public int randomRespawnCell() {
if (entrance == -1) return entrance; if (entrance == -1) return entrance;
int cell = entrance + NEIGHBOURS8[Random.Int(8)]; int cell = entrance + PathFinder.NEIGHBOURS8[Random.Int(8)];
while (!passable[cell]){ while (!passable[cell]){
cell = entrance + NEIGHBOURS8[Random.Int(8)]; cell = entrance + PathFinder.NEIGHBOURS8[Random.Int(8)];
} }
return cell; return cell;
} }
@@ -179,12 +183,12 @@ public class HallsBossLevel extends Level {
seal(); seal();
for (int i=ROOM_LEFT-1; i <= ROOM_RIGHT + 1; i++) { for (int i=ROOM_LEFT-1; i <= ROOM_RIGHT + 1; i++) {
doMagic( (ROOM_TOP - 1) * WIDTH + i ); doMagic( (ROOM_TOP - 1) * width() + i );
doMagic( (ROOM_BOTTOM + 1) * WIDTH + i ); doMagic( (ROOM_BOTTOM + 1) * width() + i );
} }
for (int i=ROOM_TOP; i < ROOM_BOTTOM + 1; i++) { for (int i=ROOM_TOP; i < ROOM_BOTTOM + 1; i++) {
doMagic( i * WIDTH + ROOM_LEFT - 1 ); doMagic( i * width() + ROOM_LEFT - 1 );
doMagic( i * WIDTH + ROOM_RIGHT + 1 ); doMagic( i * width() + ROOM_RIGHT + 1 );
} }
doMagic( entrance ); doMagic( entrance );
GameScene.updateMap(); GameScene.updateMap();
@@ -193,7 +197,7 @@ public class HallsBossLevel extends Level {
Yog boss = new Yog(); Yog boss = new Yog();
do { do {
boss.pos = Random.Int( LENGTH ); boss.pos = Random.Int( length() );
} while ( } while (
!passable[boss.pos] || !passable[boss.pos] ||
Dungeon.visible[boss.pos]); Dungeon.visible[boss.pos]);
@@ -48,6 +48,7 @@ import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.watabou.noosa.Game; import com.watabou.noosa.Game;
import com.watabou.noosa.Group; import com.watabou.noosa.Group;
import com.watabou.noosa.particles.PixelParticle; import com.watabou.noosa.particles.PixelParticle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.PointF; import com.watabou.utils.PointF;
import com.watabou.utils.Random; import com.watabou.utils.Random;
@@ -81,11 +82,11 @@ public class HallsLevel extends RegularLevel {
} }
protected boolean[] water() { protected boolean[] water() {
return Patch.generate( feeling == Feeling.WATER ? 0.55f : 0.40f, 6 ); return Patch.generate( this, feeling == Feeling.WATER ? 0.55f : 0.40f, 6 );
} }
protected boolean[] grass() { protected boolean[] grass() {
return Patch.generate( feeling == Feeling.GRASS ? 0.55f : 0.30f, 3 ); return Patch.generate( this, feeling == Feeling.GRASS ? 0.55f : 0.30f, 3 );
} }
@Override @Override
@@ -107,12 +108,12 @@ public class HallsLevel extends RegularLevel {
@Override @Override
protected void decorate() { protected void decorate() {
for (int i=WIDTH + 1; i < LENGTH - WIDTH - 1; i++) { for (int i=width() + 1; i < length() - width() - 1; i++) {
if (map[i] == Terrain.EMPTY) { if (map[i] == Terrain.EMPTY) {
int count = 0; int count = 0;
for (int j=0; j < NEIGHBOURS8.length; j++) { for (int j=0; j < PathFinder.NEIGHBOURS8.length; j++) {
if ((Terrain.flags[map[i + NEIGHBOURS8[j]]] & Terrain.PASSABLE) > 0) { if ((Terrain.flags[map[i + PathFinder.NEIGHBOURS8[j]]] & Terrain.PASSABLE) > 0) {
count++; count++;
} }
} }
@@ -123,7 +124,7 @@ public class HallsLevel extends RegularLevel {
} else } else
if (map[i] == Terrain.WALL && if (map[i] == Terrain.WALL &&
map[i-1] != Terrain.WALL_DECO && map[i-WIDTH] != Terrain.WALL_DECO && map[i-1] != Terrain.WALL_DECO && map[i-width()] != Terrain.WALL_DECO &&
Random.Int( 20 ) == 0) { Random.Int( 20 ) == 0) {
map[i] = Terrain.WALL_DECO; map[i] = Terrain.WALL_DECO;
@@ -174,7 +175,7 @@ public class HallsLevel extends RegularLevel {
} }
public static void addHallsVisuals( Level level, Group group ) { public static void addHallsVisuals( Level level, Group group ) {
for (int i=0; i < LENGTH; i++) { for (int i=0; i < level.length(); i++) {
if (level.map[i] == Terrain.WATER) { if (level.map[i] == Terrain.WATER) {
group.add( new Stream( i ) ); group.add( new Stream( i ) );
} }
@@ -27,6 +27,7 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.painters.Painter;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages; import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.watabou.noosa.Group; import com.watabou.noosa.Group;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.Arrays; import java.util.Arrays;
@@ -57,7 +58,7 @@ public class LastLevel extends Level {
@Override @Override
public void create() { public void create() {
super.create(); super.create();
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
int flags = Terrain.flags[map[i]]; int flags = Terrain.flags[map[i]];
if ((flags & Terrain.PIT) != 0){ if ((flags & Terrain.PIT) != 0){
passable[i] = avoid[i] = false; passable[i] = avoid[i] = false;
@@ -82,23 +83,23 @@ public class LastLevel extends Level {
//Painter.fill( this, 2, 2, SIZE-2, SIZE-2, Terrain.EMPTY ); //Painter.fill( this, 2, 2, SIZE-2, SIZE-2, Terrain.EMPTY );
//Painter.fill( this, SIZE/2, SIZE/2, 3, 3, Terrain.EMPTY_SP ); //Painter.fill( this, SIZE/2, SIZE/2, 3, 3, Terrain.EMPTY_SP );
entrance = SIZE * WIDTH + SIZE / 2 + 1; entrance = SIZE * width() + SIZE / 2 + 1;
map[entrance] = Terrain.ENTRANCE; map[entrance] = Terrain.ENTRANCE;
pedestal = (SIZE / 2 + 1) * (WIDTH + 1) - 4*WIDTH; pedestal = (SIZE / 2 + 1) * (width() + 1) - 4*width();
map[pedestal] = Terrain.PEDESTAL; map[pedestal] = Terrain.PEDESTAL;
map[pedestal-1-WIDTH] = map[pedestal+1-WIDTH] = map[pedestal-1+WIDTH] = map[pedestal+1+WIDTH] = Terrain.STATUE_SP; map[pedestal-1-width()] = map[pedestal+1-width()] = map[pedestal-1+width()] = map[pedestal+1+width()] = Terrain.STATUE_SP;
exit = pedestal; exit = pedestal;
int pos = pedestal; int pos = pedestal;
map[pos-WIDTH] = map[pos-1] = map[pos+1] = map[pos-2] = map[pos+2] = Terrain.WATER; map[pos-width()] = map[pos-1] = map[pos+1] = map[pos-2] = map[pos+2] = Terrain.WATER;
pos+=WIDTH; pos+=width();
map[pos] = map[pos-2] = map[pos+2] = map[pos-3] = map[pos+3] = Terrain.WATER; map[pos] = map[pos-2] = map[pos+2] = map[pos-3] = map[pos+3] = Terrain.WATER;
pos+=WIDTH; pos+=width();
map[pos-3] = map[pos-2] = map[pos-1] = map[pos] = map[pos+1] = map[pos+2] = map[pos+3] = Terrain.WATER; map[pos-3] = map[pos-2] = map[pos-1] = map[pos] = map[pos+1] = map[pos+2] = map[pos+3] = Terrain.WATER;
pos+=WIDTH; pos+=width();
map[pos-2] = map[pos+2] = Terrain.WATER; map[pos-2] = map[pos+2] = Terrain.WATER;
@@ -110,7 +111,7 @@ public class LastLevel extends Level {
@Override @Override
protected void decorate() { protected void decorate() {
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (map[i] == Terrain.EMPTY && Random.Int( 10 ) == 0) { if (map[i] == Terrain.EMPTY && Random.Int( 10 ) == 0) {
map[i] = Terrain.EMPTY_DECO; map[i] = Terrain.EMPTY_DECO;
} }
@@ -132,9 +133,9 @@ public class LastLevel extends Level {
@Override @Override
public int randomRespawnCell() { public int randomRespawnCell() {
int cell = entrance + NEIGHBOURS8[Random.Int(8)]; int cell = entrance + PathFinder.NEIGHBOURS8[Random.Int(8)];
while (!passable[cell]){ while (!passable[cell]){
cell = entrance + NEIGHBOURS8[Random.Int(8)]; cell = entrance + PathFinder.NEIGHBOURS8[Random.Int(8)];
} }
return cell; return cell;
} }
@@ -181,7 +182,7 @@ public class LastLevel extends Level {
@Override @Override
public void restoreFromBundle(Bundle bundle) { public void restoreFromBundle(Bundle bundle) {
super.restoreFromBundle(bundle); super.restoreFromBundle(bundle);
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
int flags = Terrain.flags[map[i]]; int flags = Terrain.flags[map[i]];
if ((flags & Terrain.PIT) != 0){ if ((flags & Terrain.PIT) != 0){
passable[i] = avoid[i] = false; passable[i] = avoid[i] = false;
@@ -134,7 +134,7 @@ public class LastShopLevel extends RegularLevel {
@Override @Override
protected void decorate() { protected void decorate() {
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (map[i] == Terrain.EMPTY && Random.Int( 10 ) == 0) { if (map[i] == Terrain.EMPTY && Random.Int( 10 ) == 0) {
map[i] = Terrain.EMPTY_DECO; map[i] = Terrain.EMPTY_DECO;
@@ -169,7 +169,7 @@ public class LastShopLevel extends RegularLevel {
if (item != null) { if (item != null) {
int pos; int pos;
do { do {
pos = roomEntrance.random(); pos = pointToCell(roomEntrance.random());
} while (pos == entrance || map[pos] == Terrain.SIGN); } while (pos == entrance || map[pos] == Terrain.SIGN);
drop( item, pos ).type = Heap.Type.REMAINS; drop( item, pos ).type = Heap.Type.REMAINS;
} }
@@ -177,7 +177,7 @@ public class LastShopLevel extends RegularLevel {
@Override @Override
public int randomRespawnCell() { public int randomRespawnCell() {
return roomEntrance.random(); return pointToCell( roomEntrance.random() );
} }
@Override @Override
@@ -216,12 +216,12 @@ public class LastShopLevel extends RegularLevel {
@Override @Override
protected boolean[] water() { protected boolean[] water() {
return Patch.generate( 0.35f, 4 ); return Patch.generate( this, 0.35f, 4 );
} }
@Override @Override
protected boolean[] grass() { protected boolean[] grass() {
return Patch.generate( 0.30f, 3 ); return Patch.generate( this, 0.30f, 3 );
} }
@Override @Override
@@ -80,6 +80,9 @@ import com.watabou.noosa.Group;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Bundlable; import com.watabou.utils.Bundlable;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Point;
import com.watabou.utils.PointF;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import com.watabou.utils.SparseArray; import com.watabou.utils.SparseArray;
@@ -98,32 +101,11 @@ public abstract class Level implements Bundlable {
GRASS, GRASS,
DARK DARK
} }
public static final int WIDTH = 32;
public static final int HEIGHT = 32;
public static final int LENGTH = WIDTH * HEIGHT;
public static final int[] NEIGHBOURS4 = {-WIDTH, +1, +WIDTH, -1};
public static final int[] NEIGHBOURS8 = {-WIDTH, +1-WIDTH, +1, +1+WIDTH, +WIDTH, -1+WIDTH, -1, -1-WIDTH};
public static final int[] NEIGHBOURS9 = {0, -WIDTH, +1-WIDTH, +1, +1+WIDTH, +WIDTH, -1+WIDTH, -1, -1-WIDTH};
//make sure to check insideMap() when using these, as there's a risk something may be outside the map
public static final int[] NEIGHBOURS8DIST2 = {+2+2*WIDTH, +1+2*WIDTH, 2*WIDTH, -1+2*WIDTH, -2+2*WIDTH,
+2+WIDTH, +1+WIDTH, +WIDTH, -1+WIDTH, -2+WIDTH,
+2, +1, -1, -2,
+2-WIDTH, +1-WIDTH, -WIDTH, -1-WIDTH, -2-WIDTH,
+2-2*WIDTH, +1-2*WIDTH, -2*WIDTH, -1-2*WIDTH, -2-2*WIDTH};
public static final int[] NEIGHBOURS9DIST2 = {+2+2*WIDTH, +1+2*WIDTH, 2*WIDTH, -1+2*WIDTH, -2+2*WIDTH,
+2+WIDTH, +1+WIDTH, +WIDTH, -1+WIDTH, -2+WIDTH,
+2, +1, 0, -1, -2,
+2-WIDTH, +1-WIDTH, -WIDTH, -1-WIDTH, -2-WIDTH,
+2-2*WIDTH, +1-2*WIDTH, -2*WIDTH, -1-2*WIDTH, -2-2*WIDTH};
protected int width;
protected int height;
protected static final float TIME_TO_RESPAWN = 50; protected static final float TIME_TO_RESPAWN = 50;
public static boolean resizingNeeded;
public static int loadedMapSize;
public int version; public int version;
public int[] map; public int[] map;
@@ -131,19 +113,20 @@ public abstract class Level implements Bundlable {
public boolean[] mapped; public boolean[] mapped;
public int viewDistance = Dungeon.isChallenged( Challenges.DARKNESS ) ? 3: 8; public int viewDistance = Dungeon.isChallenged( Challenges.DARKNESS ) ? 3: 8;
//FIXME should not be static!
public static boolean[] fieldOfView;
public static boolean[] fieldOfView = new boolean[LENGTH]; public static boolean[] passable;
public static boolean[] losBlocking;
public static boolean[] flamable;
public static boolean[] secret;
public static boolean[] solid;
public static boolean[] avoid;
public static boolean[] water;
public static boolean[] pit;
public static boolean[] passable = new boolean[LENGTH]; public static boolean[] discoverable;
public static boolean[] losBlocking = new boolean[LENGTH];
public static boolean[] flamable = new boolean[LENGTH];
public static boolean[] secret = new boolean[LENGTH];
public static boolean[] solid = new boolean[LENGTH];
public static boolean[] avoid = new boolean[LENGTH];
public static boolean[] water = new boolean[LENGTH];
public static boolean[] pit = new boolean[LENGTH];
public static boolean[] discoverable = new boolean[LENGTH];
public Feeling feeling = Feeling.NONE; public Feeling feeling = Feeling.NONE;
@@ -187,13 +170,22 @@ public abstract class Level implements Bundlable {
private static final String FEELING = "feeling"; private static final String FEELING = "feeling";
public void create() { public void create() {
setupSize();
PathFinder.setMapSize(width(), height());
passable = new boolean[length()];
losBlocking = new boolean[length()];
flamable = new boolean[length()];
secret = new boolean[length()];
solid = new boolean[length()];
avoid = new boolean[length()];
water = new boolean[length()];
pit = new boolean[length()];
resizingNeeded = false; map = new int[length()];
visited = new boolean[length()];
map = new int[LENGTH];
visited = new boolean[LENGTH];
Arrays.fill( visited, false ); Arrays.fill( visited, false );
mapped = new boolean[LENGTH]; mapped = new boolean[length()];
Arrays.fill( mapped, false ); Arrays.fill( mapped, false );
if (!(Dungeon.bossLevel() || Dungeon.depth == 21) /*final shop floor*/) { if (!(Dungeon.bossLevel() || Dungeon.depth == 21) /*final shop floor*/) {
@@ -282,6 +274,10 @@ public abstract class Level implements Bundlable {
createMobs(); createMobs();
createItems(); createItems();
} }
protected void setupSize(){
width = height = 32;
}
public void reset() { public void reset() {
@@ -297,6 +293,13 @@ public abstract class Level implements Bundlable {
public void restoreFromBundle( Bundle bundle ) { public void restoreFromBundle( Bundle bundle ) {
version = bundle.getInt( VERSION ); version = bundle.getInt( VERSION );
if (bundle.contains("width") && bundle.contains("height")){
width = bundle.getInt("width");
height = bundle.getInt("height");
} else
width = height = 32; //default sizes
PathFinder.setMapSize(width(), height());
mobs = new HashSet<>(); mobs = new HashSet<>();
heaps = new SparseArray<>(); heaps = new SparseArray<>();
@@ -316,8 +319,6 @@ public abstract class Level implements Bundlable {
locked = bundle.getBoolean( LOCKED ); locked = bundle.getBoolean( LOCKED );
weakFloorCreated = false; weakFloorCreated = false;
adjustMapSize();
//for pre-0.3.0c saves //for pre-0.3.0c saves
if (version < 44){ if (version < 44){
@@ -327,9 +328,6 @@ public abstract class Level implements Bundlable {
Collection<Bundlable> collection = bundle.getCollection( HEAPS ); Collection<Bundlable> collection = bundle.getCollection( HEAPS );
for (Bundlable h : collection) { for (Bundlable h : collection) {
Heap heap = (Heap)h; Heap heap = (Heap)h;
if (resizingNeeded) {
heap.pos = adjustPos( heap.pos );
}
if (!heap.isEmpty()) if (!heap.isEmpty())
heaps.put( heap.pos, heap ); heaps.put( heap.pos, heap );
} }
@@ -337,27 +335,18 @@ public abstract class Level implements Bundlable {
collection = bundle.getCollection( PLANTS ); collection = bundle.getCollection( PLANTS );
for (Bundlable p : collection) { for (Bundlable p : collection) {
Plant plant = (Plant)p; Plant plant = (Plant)p;
if (resizingNeeded) {
plant.pos = adjustPos( plant.pos );
}
plants.put( plant.pos, plant ); plants.put( plant.pos, plant );
} }
collection = bundle.getCollection( TRAPS ); collection = bundle.getCollection( TRAPS );
for (Bundlable p : collection) { for (Bundlable p : collection) {
Trap trap = (Trap)p; Trap trap = (Trap)p;
if (resizingNeeded) {
trap.pos = adjustPos( trap.pos );
}
traps.put( trap.pos, trap ); traps.put( trap.pos, trap );
} }
collection = bundle.getCollection( CUSTOM_TILES ); collection = bundle.getCollection( CUSTOM_TILES );
for (Bundlable p : collection) { for (Bundlable p : collection) {
CustomTileVisual vis = (CustomTileVisual)p; CustomTileVisual vis = (CustomTileVisual)p;
if (resizingNeeded) {
//TODO: add proper resizing logic here
}
customTiles.add( vis ); customTiles.add( vis );
} }
@@ -365,9 +354,6 @@ public abstract class Level implements Bundlable {
for (Bundlable m : collection) { for (Bundlable m : collection) {
Mob mob = (Mob)m; Mob mob = (Mob)m;
if (mob != null) { if (mob != null) {
if (resizingNeeded) {
mob.pos = adjustPos( mob.pos );
}
mobs.add( mob ); mobs.add( mob );
} }
} }
@@ -389,6 +375,8 @@ public abstract class Level implements Bundlable {
@Override @Override
public void storeInBundle( Bundle bundle ) { public void storeInBundle( Bundle bundle ) {
bundle.put( VERSION, Game.versionCode ); bundle.put( VERSION, Game.versionCode );
bundle.put( "width", width );
bundle.put( "height", height );
bundle.put( MAP, map ); bundle.put( MAP, map );
bundle.put( VISITED, visited ); bundle.put( VISITED, visited );
bundle.put( MAPPED, mapped ); bundle.put( MAPPED, mapped );
@@ -407,43 +395,21 @@ public abstract class Level implements Bundlable {
public int tunnelTile() { public int tunnelTile() {
return feeling == Feeling.CHASM ? Terrain.EMPTY_SP : Terrain.EMPTY; return feeling == Feeling.CHASM ? Terrain.EMPTY_SP : Terrain.EMPTY;
} }
private void adjustMapSize() { public int width() {
// For levels saved before 1.6.3 if (width == 0)
// Seeing as shattered started on 1.7.1 this is never used, but the code may be resused in future. setupSize();
if (map.length < LENGTH) { return width;
resizingNeeded = true;
loadedMapSize = (int)Math.sqrt( map.length );
int[] map = new int[LENGTH];
Arrays.fill( map, Terrain.WALL );
boolean[] visited = new boolean[LENGTH];
Arrays.fill( visited, false );
boolean[] mapped = new boolean[LENGTH];
Arrays.fill( mapped, false );
for (int i=0; i < loadedMapSize; i++) {
System.arraycopy( this.map, i * loadedMapSize, map, i * WIDTH, loadedMapSize );
System.arraycopy( this.visited, i * loadedMapSize, visited, i * WIDTH, loadedMapSize );
System.arraycopy( this.mapped, i * loadedMapSize, mapped, i * WIDTH, loadedMapSize );
}
this.map = map;
this.visited = visited;
this.mapped = mapped;
entrance = adjustPos( entrance );
exit = adjustPos( exit );
} else {
resizingNeeded = false;
}
} }
public int adjustPos( int pos ) { public int height() {
return (pos / loadedMapSize) * WIDTH + (pos % loadedMapSize); if (height == 0)
setupSize();
return height;
}
public int length() {
return width() * height();
} }
public String tilesTex() { public String tilesTex() {
@@ -481,11 +447,11 @@ public abstract class Level implements Bundlable {
} else { } else {
visuals.clear(); visuals.clear();
} }
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (pit[i]) { if (pit[i]) {
visuals.add( new WindParticle.Wind( i ) ); visuals.add( new WindParticle.Wind( i ) );
if (i >= WIDTH && water[i-WIDTH]) { if (i >= width() && water[i-width()]) {
visuals.add( new FlowParticle.Flow( i - WIDTH ) ); visuals.add( new FlowParticle.Flow( i - width() ) );
} }
} }
} }
@@ -535,7 +501,7 @@ public abstract class Level implements Bundlable {
public int randomRespawnCell() { public int randomRespawnCell() {
int cell; int cell;
do { do {
cell = Random.Int( LENGTH ); cell = Random.Int( length() );
} while (!passable[cell] || Dungeon.visible[cell] || Actor.findChar( cell ) != null); } while (!passable[cell] || Dungeon.visible[cell] || Actor.findChar( cell ) != null);
return cell; return cell;
} }
@@ -543,7 +509,7 @@ public abstract class Level implements Bundlable {
public int randomDestination() { public int randomDestination() {
int cell; int cell;
do { do {
cell = Random.Int( LENGTH ); cell = Random.Int( length() );
} while (!passable[cell]); } while (!passable[cell]);
return cell; return cell;
} }
@@ -577,8 +543,17 @@ public abstract class Level implements Bundlable {
} }
protected void buildFlagMaps() { protected void buildFlagMaps() {
passable = new boolean[length()];
losBlocking = new boolean[length()];
flamable = new boolean[length()];
secret = new boolean[length()];
solid = new boolean[length()];
avoid = new boolean[length()];
water = new boolean[length()];
pit = new boolean[length()];
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
int flags = Terrain.flags[map[i]]; int flags = Terrain.flags[map[i]];
passable[i] = (flags & Terrain.PASSABLE) != 0; passable[i] = (flags & Terrain.PASSABLE) != 0;
losBlocking[i] = (flags & Terrain.LOS_BLOCKING) != 0; losBlocking[i] = (flags & Terrain.LOS_BLOCKING) != 0;
@@ -590,28 +565,28 @@ public abstract class Level implements Bundlable {
pit[i] = (flags & Terrain.PIT) != 0; pit[i] = (flags & Terrain.PIT) != 0;
} }
int lastRow = LENGTH - WIDTH; int lastRow = length() - width();
for (int i=0; i < WIDTH; i++) { for (int i=0; i < width(); i++) {
passable[i] = avoid[i] = false; passable[i] = avoid[i] = false;
passable[lastRow + i] = avoid[lastRow + i] = false; passable[lastRow + i] = avoid[lastRow + i] = false;
} }
for (int i=WIDTH; i < lastRow; i += WIDTH) { for (int i=width(); i < lastRow; i += width()) {
passable[i] = avoid[i] = false; passable[i] = avoid[i] = false;
passable[i + WIDTH-1] = avoid[i + WIDTH-1] = false; passable[i + width()-1] = avoid[i + width()-1] = false;
} }
for (int i=WIDTH; i < LENGTH - WIDTH; i++) { for (int i=width(); i < length() - width(); i++) {
if (water[i]) { if (water[i]) {
map[i] = getWaterTile( i ); map[i] = getWaterTile( i );
} }
if (pit[i]) { if (pit[i]) {
if (!pit[i - WIDTH]) { if (!pit[i - width()]) {
int c = map[i - WIDTH]; int c = map[i - width()];
if (c == Terrain.EMPTY_SP || c == Terrain.STATUE_SP) { if (c == Terrain.EMPTY_SP || c == Terrain.STATUE_SP) {
map[i] = Terrain.CHASM_FLOOR_SP; map[i] = Terrain.CHASM_FLOOR_SP;
} else if (water[i - WIDTH]) { } else if (water[i - width()]) {
map[i] = Terrain.CHASM_WATER; map[i] = Terrain.CHASM_WATER;
} else if ((Terrain.flags[c] & Terrain.UNSTITCHABLE) != 0) { } else if ((Terrain.flags[c] & Terrain.UNSTITCHABLE) != 0) {
map[i] = Terrain.CHASM_WALL; map[i] = Terrain.CHASM_WALL;
@@ -625,8 +600,8 @@ public abstract class Level implements Bundlable {
private int getWaterTile( int pos ) { private int getWaterTile( int pos ) {
int t = Terrain.WATER_TILES; int t = Terrain.WATER_TILES;
for (int j=0; j < NEIGHBOURS4.length; j++) { for (int j=0; j < PathFinder.NEIGHBOURS4.length; j++) {
if ((Terrain.flags[map[pos + NEIGHBOURS4[j]]] & Terrain.UNSTITCHABLE) != 0) { if ((Terrain.flags[map[pos + PathFinder.NEIGHBOURS4[j]]] & Terrain.UNSTITCHABLE) != 0) {
t += 1 << j; t += 1 << j;
} }
} }
@@ -640,8 +615,8 @@ public abstract class Level implements Bundlable {
} else { } else {
boolean flood = false; boolean flood = false;
for (int j=0; j < NEIGHBOURS4.length; j++) { for (int j = 0; j < PathFinder.NEIGHBOURS4.length; j++) {
if (water[pos + NEIGHBOURS4[j]]) { if (water[pos + PathFinder.NEIGHBOURS4[j]]) {
flood = true; flood = true;
break; break;
} }
@@ -655,13 +630,15 @@ public abstract class Level implements Bundlable {
} }
protected void cleanWalls() { protected void cleanWalls() {
for (int i=0; i < LENGTH; i++) { discoverable = new boolean[length()];
for (int i=0; i < length(); i++) {
boolean d = false; boolean d = false;
for (int j=0; j < NEIGHBOURS9.length; j++) { for (int j=0; j < PathFinder.NEIGHBOURS9.length; j++) {
int n = i + NEIGHBOURS9[j]; int n = i + PathFinder.NEIGHBOURS9[j];
if (n >= 0 && n < LENGTH && map[n] != Terrain.WALL && map[n] != Terrain.WALL_DECO) { if (n >= 0 && n < length() && map[n] != Terrain.WALL && map[n] != Terrain.WALL_DECO) {
d = true; d = true;
break; break;
} }
@@ -670,9 +647,9 @@ public abstract class Level implements Bundlable {
if (d) { if (d) {
d = false; d = false;
for (int j=0; j < NEIGHBOURS9.length; j++) { for (int j=0; j < PathFinder.NEIGHBOURS9.length; j++) {
int n = i + NEIGHBOURS9[j]; int n = i + PathFinder.NEIGHBOURS9[j];
if (n >= 0 && n < LENGTH && !pit[n]) { if (n >= 0 && n < length() && !pit[n]) {
d = true; d = true;
break; break;
} }
@@ -727,7 +704,7 @@ public abstract class Level implements Bundlable {
Dungeon.hero.buff(AlchemistsToolkit.alchemy.class) != null && Dungeon.hero.buff(AlchemistsToolkit.alchemy.class).isCursed())) { Dungeon.hero.buff(AlchemistsToolkit.alchemy.class) != null && Dungeon.hero.buff(AlchemistsToolkit.alchemy.class).isCursed())) {
int n; int n;
do { do {
n = cell + NEIGHBOURS8[Random.Int( 8 )]; n = cell + PathFinder.NEIGHBOURS8[Random.Int( 8 )];
} while (map[n] != Terrain.EMPTY_SP); } while (map[n] != Terrain.EMPTY_SP);
cell = n; cell = n;
} }
@@ -750,7 +727,7 @@ public abstract class Level implements Bundlable {
int n; int n;
do { do {
n = cell + Level.NEIGHBOURS8[Random.Int( 8 )]; n = cell + PathFinder.NEIGHBOURS8[Random.Int( 8 )];
} while (!Level.passable[n] && !Level.avoid[n]); } while (!Level.passable[n] && !Level.avoid[n]);
return drop( item, n ); return drop( item, n );
@@ -920,16 +897,16 @@ public abstract class Level implements Bundlable {
} }
public boolean[] updateFieldOfView( Char c ) { public boolean[] updateFieldOfView( Char c ) {
fieldOfView = new boolean[length()];
int cx = c.pos % WIDTH; int cx = c.pos % width();
int cy = c.pos / WIDTH; int cy = c.pos / width();
boolean sighted = c.buff( Blindness.class ) == null && c.buff( Shadows.class ) == null boolean sighted = c.buff( Blindness.class ) == null && c.buff( Shadows.class ) == null
&& c.buff( TimekeepersHourglass.timeStasis.class ) == null && c.isAlive(); && c.buff( TimekeepersHourglass.timeStasis.class ) == null && c.isAlive();
if (sighted) { if (sighted) {
ShadowCaster.castShadow( cx, cy, fieldOfView, c.viewDistance ); ShadowCaster.castShadow( cx, cy, fieldOfView, c.viewDistance );
} else {
Arrays.fill( fieldOfView, false );
} }
int sense = 1; int sense = 1;
@@ -942,17 +919,17 @@ public abstract class Level implements Bundlable {
if ((sighted && sense > 1) || !sighted) { if ((sighted && sense > 1) || !sighted) {
int ax = Math.max( 0, cx - sense ); int ax = Math.max( 0, cx - sense );
int bx = Math.min( cx + sense, WIDTH - 1 ); int bx = Math.min( cx + sense, width() - 1 );
int ay = Math.max( 0, cy - sense ); int ay = Math.max( 0, cy - sense );
int by = Math.min( cy + sense, HEIGHT - 1 ); int by = Math.min( cy + sense, height() - 1 );
int len = bx - ax + 1; int len = bx - ax + 1;
int pos = ax + ay * WIDTH; int pos = ax + ay * width();
for (int y = ay; y <= by; y++, pos+=WIDTH) { for (int y = ay; y <= by; y++, pos+=width()) {
Arrays.fill( fieldOfView, pos, pos + len, true ); Arrays.fill( fieldOfView, pos, pos + len, true );
} }
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
fieldOfView[i] &= discoverable[i]; fieldOfView[i] &= discoverable[i];
} }
} }
@@ -964,12 +941,12 @@ public abstract class Level implements Bundlable {
fieldOfView[p] = true; fieldOfView[p] = true;
fieldOfView[p + 1] = true; fieldOfView[p + 1] = true;
fieldOfView[p - 1] = true; fieldOfView[p - 1] = true;
fieldOfView[p + WIDTH + 1] = true; fieldOfView[p + width() + 1] = true;
fieldOfView[p + WIDTH - 1] = true; fieldOfView[p + width() - 1] = true;
fieldOfView[p - WIDTH + 1] = true; fieldOfView[p - width() + 1] = true;
fieldOfView[p - WIDTH - 1] = true; fieldOfView[p - width() - 1] = true;
fieldOfView[p + WIDTH] = true; fieldOfView[p + width()] = true;
fieldOfView[p - WIDTH] = true; fieldOfView[p - width()] = true;
} }
} else if (c == Dungeon.hero && ((Hero)c).heroClass == HeroClass.HUNTRESS) { } else if (c == Dungeon.hero && ((Hero)c).heroClass == HeroClass.HUNTRESS) {
for (Mob mob : mobs) { for (Mob mob : mobs) {
@@ -978,12 +955,12 @@ public abstract class Level implements Bundlable {
fieldOfView[p] = true; fieldOfView[p] = true;
fieldOfView[p + 1] = true; fieldOfView[p + 1] = true;
fieldOfView[p - 1] = true; fieldOfView[p - 1] = true;
fieldOfView[p + WIDTH + 1] = true; fieldOfView[p + width() + 1] = true;
fieldOfView[p + WIDTH - 1] = true; fieldOfView[p + width() - 1] = true;
fieldOfView[p - WIDTH + 1] = true; fieldOfView[p - width() + 1] = true;
fieldOfView[p - WIDTH - 1] = true; fieldOfView[p - width() - 1] = true;
fieldOfView[p + WIDTH] = true; fieldOfView[p + width()] = true;
fieldOfView[p - WIDTH] = true; fieldOfView[p - width()] = true;
} }
} }
} }
@@ -993,12 +970,12 @@ public abstract class Level implements Bundlable {
fieldOfView[p] = true; fieldOfView[p] = true;
fieldOfView[p + 1] = true; fieldOfView[p + 1] = true;
fieldOfView[p - 1] = true; fieldOfView[p - 1] = true;
fieldOfView[p + WIDTH + 1] = true; fieldOfView[p + width() + 1] = true;
fieldOfView[p + WIDTH - 1] = true; fieldOfView[p + width() - 1] = true;
fieldOfView[p - WIDTH + 1] = true; fieldOfView[p - width() + 1] = true;
fieldOfView[p - WIDTH - 1] = true; fieldOfView[p - width() - 1] = true;
fieldOfView[p + WIDTH] = true; fieldOfView[p + width()] = true;
fieldOfView[p - WIDTH] = true; fieldOfView[p - width()] = true;
} }
} }
} }
@@ -1010,27 +987,34 @@ public abstract class Level implements Bundlable {
return fieldOfView; return fieldOfView;
} }
public static int distance( int a, int b ) { public int distance( int a, int b ) {
int ax = a % WIDTH; int ax = a % width();
int ay = a / WIDTH; int ay = a / width();
int bx = b % WIDTH; int bx = b % width();
int by = b / WIDTH; int by = b / width();
return Math.max( Math.abs( ax - bx ), Math.abs( ay - by ) ); return Math.max( Math.abs( ax - bx ), Math.abs( ay - by ) );
} }
public static boolean adjacent( int a, int b ) { public boolean adjacent( int a, int b ) {
int diff = Math.abs( a - b ); return distance( a, b ) == 1;
return diff == 1 || diff == WIDTH || diff == WIDTH + 1 || diff == WIDTH - 1;
} }
//returns true if the input is a valid tile within the level //returns true if the input is a valid tile within the level
public static boolean insideMap( int tile ){ public boolean insideMap( int tile ){
//outside map array //outside map array
return !((tile <= -1 || tile >= LENGTH) || return !((tile < 0 || tile >= length()) ||
//top and bottom row //top and bottom row
(tile <= 31 || tile >= LENGTH - WIDTH) || (tile < width() || tile >= length() - width()) ||
//left and right column //left and right column
(tile % WIDTH == 0 || tile % WIDTH == 31)); (tile % width() == 0 || tile % width() == width()-1));
}
public Point cellToPoint( int cell ){
return new Point(cell % width(), cell / width());
}
public int pointToCell( Point p ){
return p.x + p.y*width();
} }
public String tileName( int tile ) { public String tileName( int tile ) {
@@ -20,19 +20,20 @@
*/ */
package com.shatteredpixel.shatteredpixeldungeon.levels; package com.shatteredpixel.shatteredpixeldungeon.levels;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.watabou.utils.Random; import com.watabou.utils.Random;
public class Patch { public class Patch {
private static boolean[] cur = new boolean[Level.LENGTH]; public static boolean[] generate( Level level, float seed, int nGen ) {
private static boolean[] off = new boolean[Level.LENGTH];
public static boolean[] generate( float seed, int nGen ) {
int w = Level.WIDTH; int w = level.width();
int h = Level.HEIGHT; int h = level.width();
boolean[] cur = new boolean[level.length()];
boolean[] off = new boolean[level.length()];
for (int i=0; i < Level.LENGTH; i++) { for (int i=0; i < level.length(); i++) {
off[i] = Random.Float() < seed; off[i] = Random.Float() < seed;
} }
@@ -44,6 +44,7 @@ import com.watabou.noosa.Group;
import com.watabou.noosa.audio.Sample; import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Bundlable; import com.watabou.utils.Bundlable;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -175,13 +176,13 @@ public class PrisonBossLevel extends Level {
if (ch == Dungeon.hero){ if (ch == Dungeon.hero){
//hero enters tengu's chamber //hero enters tengu's chamber
if (state == State.START if (state == State.START
&& ((Room)new Room().set(2, 25, 8, 32)).inside(cell)){ && ((Room)new Room().set(2, 25, 8, 32)).inside(cellToPoint(cell))){
progress(); progress();
} }
//hero finishes the maze //hero finishes the maze
else if (state == State.MAZE else if (state == State.MAZE
&& ((Room)new Room().set(4, 0, 7, 4)).inside(cell)){ && ((Room)new Room().set(4, 0, 7, 4)).inside(cellToPoint(cell))){
progress(); progress();
} }
} }
@@ -189,7 +190,7 @@ public class PrisonBossLevel extends Level {
@Override @Override
public int randomRespawnCell() { public int randomRespawnCell() {
return 5+2*32 + NEIGHBOURS8[Random.Int(8)]; //random cell adjacent to the entrance. return 5+2*32 + PathFinder.NEIGHBOURS8[Random.Int(8)]; //random cell adjacent to the entrance.
} }
@Override @Override
@@ -220,7 +221,7 @@ public class PrisonBossLevel extends Level {
} }
traps.clear(); traps.clear();
for (int i = 0; i < Level.LENGTH; i++){ for (int i = 0; i < Dungeon.level.length(); i++){
if (map[i] == Terrain.INACTIVE_TRAP) { if (map[i] == Terrain.INACTIVE_TRAP) {
Trap t = new SpearTrap().reveal(); Trap t = new SpearTrap().reveal();
t.active = false; t.active = false;
@@ -237,13 +238,13 @@ public class PrisonBossLevel extends Level {
cleanWalls(); cleanWalls();
exit = entrance = 0; exit = entrance = 0;
for (int i = 0; i < LENGTH; i ++) for (int i = 0; i < length(); i ++)
if (map[i] == Terrain.ENTRANCE) if (map[i] == Terrain.ENTRANCE)
entrance = i; entrance = i;
else if (map[i] == Terrain.EXIT) else if (map[i] == Terrain.EXIT)
exit = i; exit = i;
visited = mapped = new boolean[LENGTH]; visited = mapped = new boolean[length()];
for (Blob blob: blobs.values()){ for (Blob blob: blobs.values()){
blob.fullyClear(); blob.fullyClear();
} }
@@ -255,19 +256,19 @@ public class PrisonBossLevel extends Level {
private void clearEntities(Room safeArea){ private void clearEntities(Room safeArea){
for (Heap heap : heaps.values()){ for (Heap heap : heaps.values()){
if (safeArea == null || !safeArea.inside(heap.pos)){ if (safeArea == null || !safeArea.inside(cellToPoint(heap.pos))){
for (Item item : heap.items) for (Item item : heap.items)
storedItems.add(item); storedItems.add(item);
heap.destroy(); heap.destroy();
} }
} }
for (Mob mob : Dungeon.level.mobs.toArray(new Mob[Dungeon.level.mobs.size()])){ for (Mob mob : Dungeon.level.mobs.toArray(new Mob[Dungeon.level.mobs.size()])){
if (mob != tengu && (safeArea == null || !safeArea.inside(mob.pos))){ if (mob != tengu && (safeArea == null || !safeArea.inside(cellToPoint(mob.pos)))){
mob.destroy(); mob.destroy();
} }
} }
for (Plant plant : plants.values()){ for (Plant plant : plants.values()){
if (safeArea == null || !safeArea.inside(plant.pos)){ if (safeArea == null || !safeArea.inside(cellToPoint(plant.pos))){
plants.remove(plant.pos); plants.remove(plant.pos);
plant.sprite.kill(); plant.sprite.kill();
} }
@@ -328,7 +329,7 @@ public class PrisonBossLevel extends Level {
tengu.state = tengu.HUNTING; tengu.state = tengu.HUNTING;
do { do {
tengu.pos = Random.Int(LENGTH); tengu.pos = Random.Int(length());
} while (solid[tengu.pos] || distance(tengu.pos, Dungeon.hero.pos) < 8); } while (solid[tengu.pos] || distance(tengu.pos, Dungeon.hero.pos) < 8);
GameScene.add(tengu); GameScene.add(tengu);
tengu.notice(); tengu.notice();
@@ -66,11 +66,11 @@ public class PrisonLevel extends RegularLevel {
} }
protected boolean[] water() { protected boolean[] water() {
return Patch.generate( feeling == Feeling.WATER ? 0.65f : 0.45f, 4 ); return Patch.generate( this, feeling == Feeling.WATER ? 0.65f : 0.45f, 4 );
} }
protected boolean[] grass() { protected boolean[] grass() {
return Patch.generate( feeling == Feeling.GRASS ? 0.60f : 0.40f, 3 ); return Patch.generate( this, feeling == Feeling.GRASS ? 0.60f : 0.40f, 3 );
} }
@Override @Override
@@ -103,20 +103,20 @@ public class PrisonLevel extends RegularLevel {
@Override @Override
protected void decorate() { protected void decorate() {
for (int i=WIDTH + 1; i < LENGTH - WIDTH - 1; i++) { for (int i=width() + 1; i < length() - width() - 1; i++) {
if (map[i] == Terrain.EMPTY) { if (map[i] == Terrain.EMPTY) {
float c = 0.05f; float c = 0.05f;
if (map[i + 1] == Terrain.WALL && map[i + WIDTH] == Terrain.WALL) { if (map[i + 1] == Terrain.WALL && map[i + width()] == Terrain.WALL) {
c += 0.2f; c += 0.2f;
} }
if (map[i - 1] == Terrain.WALL && map[i + WIDTH] == Terrain.WALL) { if (map[i - 1] == Terrain.WALL && map[i + width()] == Terrain.WALL) {
c += 0.2f; c += 0.2f;
} }
if (map[i + 1] == Terrain.WALL && map[i - WIDTH] == Terrain.WALL) { if (map[i + 1] == Terrain.WALL && map[i - width()] == Terrain.WALL) {
c += 0.2f; c += 0.2f;
} }
if (map[i - 1] == Terrain.WALL && map[i - WIDTH] == Terrain.WALL) { if (map[i - 1] == Terrain.WALL && map[i - width()] == Terrain.WALL) {
c += 0.2f; c += 0.2f;
} }
@@ -126,19 +126,19 @@ public class PrisonLevel extends RegularLevel {
} }
} }
for (int i=0; i < WIDTH; i++) { for (int i=0; i < width(); i++) {
if (map[i] == Terrain.WALL && if (map[i] == Terrain.WALL &&
(map[i + WIDTH] == Terrain.EMPTY || map[i + WIDTH] == Terrain.EMPTY_SP) && (map[i + width()] == Terrain.EMPTY || map[i + width()] == Terrain.EMPTY_SP) &&
Random.Int( 6 ) == 0) { Random.Int( 6 ) == 0) {
map[i] = Terrain.WALL_DECO; map[i] = Terrain.WALL_DECO;
} }
} }
for (int i=WIDTH; i < LENGTH - WIDTH; i++) { for (int i=width(); i < length() - width(); i++) {
if (map[i] == Terrain.WALL && if (map[i] == Terrain.WALL &&
map[i - WIDTH] == Terrain.WALL && map[i - width()] == Terrain.WALL &&
(map[i + WIDTH] == Terrain.EMPTY || map[i + WIDTH] == Terrain.EMPTY_SP) && (map[i + width()] == Terrain.EMPTY || map[i + width()] == Terrain.EMPTY_SP) &&
Random.Int( 3 ) == 0) { Random.Int( 3 ) == 0) {
map[i] = Terrain.WALL_DECO; map[i] = Terrain.WALL_DECO;
@@ -178,7 +178,7 @@ public class PrisonLevel extends RegularLevel {
} }
public static void addPrisonVisuals(Level level, Group group){ public static void addPrisonVisuals(Level level, Group group){
for (int i=0; i < LENGTH; i++) { for (int i=0; i < level.length(); i++) {
if (level.map[i] == Terrain.WALL_DECO) { if (level.map[i] == Terrain.WALL_DECO) {
group.add( new Torch( i ) ); group.add( new Torch( i ) );
} }
@@ -40,6 +40,7 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.traps.Trap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.WornTrap; import com.shatteredpixel.shatteredpixeldungeon.levels.traps.WornTrap;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.Graph; import com.watabou.utils.Graph;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import com.watabou.utils.Rect; import com.watabou.utils.Rect;
@@ -172,7 +173,7 @@ public abstract class RegularLevel extends Level {
protected void placeSign(){ protected void placeSign(){
while (true) { while (true) {
int pos = roomEntrance.random(); int pos = pointToCell(roomEntrance.random());
if (pos != entrance && traps.get(pos) == null && findMob(pos) == null) { if (pos != entrance && traps.get(pos) == null && findMob(pos) == null) {
map[pos] = Terrain.SIGN; map[pos] = Terrain.SIGN;
break; break;
@@ -182,8 +183,8 @@ public abstract class RegularLevel extends Level {
protected boolean initRooms() { protected boolean initRooms() {
rooms = new HashSet<Room>(); rooms = new HashSet<>();
split( new Rect( 0, 0, WIDTH - 1, HEIGHT - 1 ) ); split( new Rect( 0, 0, width() - 1, height() - 1 ) );
if (rooms.size() < 8) { if (rooms.size() < 8) {
return false; return false;
@@ -296,7 +297,7 @@ public abstract class RegularLevel extends Level {
protected void paintWater() { protected void paintWater() {
boolean[] lake = water(); boolean[] lake = water();
for (int i=0; i < LENGTH; i++) { for (int i=0; i < length(); i++) {
if (map[i] == Terrain.EMPTY && lake[i]) { if (map[i] == Terrain.EMPTY && lake[i]) {
map[i] = Terrain.WATER; map[i] = Terrain.WATER;
} }
@@ -310,18 +311,18 @@ public abstract class RegularLevel extends Level {
for (Room room : rooms) { for (Room room : rooms) {
if (room.type != Type.NULL && room.type != Type.PASSAGE && room.type != Type.TUNNEL) { if (room.type != Type.NULL && room.type != Type.PASSAGE && room.type != Type.TUNNEL) {
grass[(room.left + 1) + (room.top + 1) * WIDTH] = true; grass[(room.left + 1) + (room.top + 1) * width()] = true;
grass[(room.right - 1) + (room.top + 1) * WIDTH] = true; grass[(room.right - 1) + (room.top + 1) * width()] = true;
grass[(room.left + 1) + (room.bottom - 1) * WIDTH] = true; grass[(room.left + 1) + (room.bottom - 1) * width()] = true;
grass[(room.right - 1) + (room.bottom - 1) * WIDTH] = true; grass[(room.right - 1) + (room.bottom - 1) * width()] = true;
} }
} }
} }
for (int i=WIDTH+1; i < LENGTH-WIDTH-1; i++) { for (int i=width()+1; i < length()-width()-1; i++) {
if (map[i] == Terrain.EMPTY && grass[i]) { if (map[i] == Terrain.EMPTY && grass[i]) {
int count = 1; int count = 1;
for (int n : NEIGHBOURS8) { for (int n : PathFinder.NEIGHBOURS8) {
if (grass[i + n]) { if (grass[i + n]) {
count++; count++;
} }
@@ -342,7 +343,7 @@ public abstract class RegularLevel extends Level {
LinkedList<Integer> validCells = new LinkedList<Integer>(); LinkedList<Integer> validCells = new LinkedList<Integer>();
for (int i = 0; i < LENGTH; i ++) { for (int i = 0; i < length(); i ++) {
if (map[i] == Terrain.EMPTY){ if (map[i] == Terrain.EMPTY){
if(Dungeon.depth == 1){ if(Dungeon.depth == 1){
@@ -477,7 +478,7 @@ public abstract class RegularLevel extends Level {
} }
Room.Door d = r.connected.get( n ); Room.Door d = r.connected.get( n );
int door = d.x + d.y * WIDTH; int door = d.x + d.y * width();
switch (d.type) { switch (d.type) {
case EMPTY: case EMPTY:
@@ -595,7 +596,7 @@ public abstract class RegularLevel extends Level {
Room roomToSpawn = stdRoomIter.next(); Room roomToSpawn = stdRoomIter.next();
Mob mob = Bestiary.mob( Dungeon.depth ); Mob mob = Bestiary.mob( Dungeon.depth );
mob.pos = roomToSpawn.random(); mob.pos = pointToCell(roomToSpawn.random());
if (findMob(mob.pos) == null && Level.passable[mob.pos]) { if (findMob(mob.pos) == null && Level.passable[mob.pos]) {
mobsToSpawn--; mobsToSpawn--;
@@ -604,7 +605,7 @@ public abstract class RegularLevel extends Level {
//TODO: perhaps externalize this logic into a method. Do I want to make mobs more likely to clump deeper down? //TODO: perhaps externalize this logic into a method. Do I want to make mobs more likely to clump deeper down?
if (mobsToSpawn > 0 && Random.Int(4) == 0){ if (mobsToSpawn > 0 && Random.Int(4) == 0){
mob = Bestiary.mob( Dungeon.depth ); mob = Bestiary.mob( Dungeon.depth );
mob.pos = roomToSpawn.random(); mob.pos = pointToCell(roomToSpawn.random());
if (findMob(mob.pos) == null && Level.passable[mob.pos]) { if (findMob(mob.pos) == null && Level.passable[mob.pos]) {
mobsToSpawn--; mobsToSpawn--;
@@ -631,7 +632,7 @@ public abstract class RegularLevel extends Level {
continue; continue;
} }
cell = room.random(); cell = pointToCell(room.random());
if (!Dungeon.visible[cell] && Actor.findChar( cell ) == null && Level.passable[cell]) { if (!Dungeon.visible[cell] && Actor.findChar( cell ) == null && Level.passable[cell]) {
return cell; return cell;
} }
@@ -651,7 +652,7 @@ public abstract class RegularLevel extends Level {
continue; continue;
} }
cell = room.random(); cell = pointToCell(room.random());
if (Level.passable[cell]) { if (Level.passable[cell]) {
return cell; return cell;
} }
@@ -721,7 +722,7 @@ public abstract class RegularLevel extends Level {
public Room room( int pos ) { public Room room( int pos ) {
for (Room room : rooms) { for (Room room : rooms) {
if (room.type != Type.NULL && room.inside( pos )) { if (room.type != Type.NULL && room.inside( cellToPoint(pos) )) {
return room; return room;
} }
} }
@@ -733,7 +734,7 @@ public abstract class RegularLevel extends Level {
while (true) { while (true) {
Room room = randomRoom( Room.Type.STANDARD, 1 ); Room room = randomRoom( Room.Type.STANDARD, 1 );
if (room != null) { if (room != null) {
int pos = room.random(); int pos = pointToCell(room.random());
if (passable[pos]) { if (passable[pos]) {
return pos; return pos;
} }
@@ -745,7 +746,7 @@ public abstract class RegularLevel extends Level {
public int pitCell() { public int pitCell() {
for (Room room : rooms) { for (Room room : rooms) {
if (room.type == Type.PIT) { if (room.type == Type.PIT) {
return room.random(); return pointToCell(room.random());
} }
} }
@@ -20,6 +20,7 @@
*/ */
package com.shatteredpixel.shatteredpixeldungeon.levels; package com.shatteredpixel.shatteredpixeldungeon.levels;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.ShatteredPixelDungeon; import com.shatteredpixel.shatteredpixeldungeon.ShatteredPixelDungeon;
import com.shatteredpixel.shatteredpixeldungeon.levels.painters.AltarPainter; import com.shatteredpixel.shatteredpixeldungeon.levels.painters.AltarPainter;
import com.shatteredpixel.shatteredpixeldungeon.levels.painters.ArmoryPainter; import com.shatteredpixel.shatteredpixeldungeon.levels.painters.ArmoryPainter;
@@ -133,14 +134,13 @@ public class Room extends Rect implements Graph.Node, Bundlable {
public Type type = Type.NULL; public Type type = Type.NULL;
public int random() { public Point random() {
return random( 0 ); return random( 0 );
} }
public int random( int m ) { public Point random( int m ) {
int x = Random.Int( left + 1 + m, right - m ); return new Point( Random.Int( left + 1 + m, right - m ),
int y = Random.Int( top + 1 + m, bottom - m ); Random.Int( top + 1 + m, bottom - m ));
return x + y * Level.WIDTH;
} }
public void addNeigbour( Room other ) { public void addNeigbour( Room other ) {
@@ -165,10 +165,8 @@ public class Room extends Rect implements Graph.Node, Bundlable {
return connected.values().iterator().next(); return connected.values().iterator().next();
} }
public boolean inside( int p ) { public boolean inside( Point p ) {
int x = p % Level.WIDTH; return p.x > left && p.y > top && p.x < right && p.y < bottom;
int y = p / Level.WIDTH;
return x > left && y > top && x < right && y < bottom;
} }
public Point center() { public Point center() {
@@ -176,14 +174,6 @@ public class Room extends Rect implements Graph.Node, Bundlable {
(left + right) / 2 + (((right - left) & 1) == 1 ? Random.Int( 2 ) : 0), (left + right) / 2 + (((right - left) & 1) == 1 ? Random.Int( 2 ) : 0),
(top + bottom) / 2 + (((bottom - top) & 1) == 1 ? Random.Int( 2 ) : 0) ); (top + bottom) / 2 + (((bottom - top) & 1) == 1 ? Random.Int( 2 ) : 0) );
} }
public HashSet<Integer> getCells(){
HashSet<Point> points = getPoints();
HashSet<Integer> cells = new HashSet<>();
for( Point point : points)
cells.add(point.x + point.y*Level.WIDTH);
return cells;
}
// **** Graph.Node interface **** // **** Graph.Node interface ****
@@ -34,6 +34,7 @@ import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.watabou.noosa.Group; import com.watabou.noosa.Group;
import com.watabou.utils.Bundle; import com.watabou.utils.Bundle;
import com.watabou.utils.Graph; import com.watabou.utils.Graph;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random; import com.watabou.utils.Random;
import java.util.ArrayList; import java.util.ArrayList;
@@ -159,12 +160,12 @@ public class SewerBossLevel extends RegularLevel {
paint(); paint();
//sticks the exit in the room entrance. //sticks the exit in the room entrance.
exit = roomEntrance.top * Level.WIDTH + (roomEntrance.left + roomEntrance.right) / 2; exit = roomEntrance.top * width() + (roomEntrance.left + roomEntrance.right) / 2;
map[exit] = Terrain.LOCKED_EXIT; map[exit] = Terrain.LOCKED_EXIT;
//make sure the exit is only visible in the entrance room. //make sure the exit is only visible in the entrance room.
int count = 0; int count = 0;
for (int i : NEIGHBOURS8){ for (int i : PathFinder.NEIGHBOURS8){
//exit must have exactly 3 non-wall tiles around it. //exit must have exactly 3 non-wall tiles around it.
if (map[exit+i] != Terrain.WALL) if (map[exit+i] != Terrain.WALL)
count++; count++;
@@ -180,23 +181,23 @@ public class SewerBossLevel extends RegularLevel {
} }
protected boolean[] water() { protected boolean[] water() {
return Patch.generate( 0.5f, 5 ); return Patch.generate( this, 0.5f, 5 );
} }
protected boolean[] grass() { protected boolean[] grass() {
return Patch.generate( 0.40f, 4 ); return Patch.generate( this, 0.40f, 4 );
} }
@Override @Override
protected void decorate() { protected void decorate() {
int start = roomExit.top * WIDTH + roomExit.left + 1; int start = roomExit.top * width() + roomExit.left + 1;
int end = start + roomExit.width() - 1; int end = start + roomExit.width() - 1;
for (int i=start; i < end; i++) { for (int i=start; i < end; i++) {
if (i != exit && map[i] == Terrain.WALL) { if (i != exit && map[i] == Terrain.WALL) {
map[i] = Terrain.WALL_DECO; map[i] = Terrain.WALL_DECO;
map[i + WIDTH] = Terrain.WATER; map[i + width()] = Terrain.WATER;
} else { } else {
map[i + WIDTH] = Terrain.EMPTY; map[i + width()] = Terrain.EMPTY;
} }
} }
@@ -217,7 +218,7 @@ public class SewerBossLevel extends RegularLevel {
do { do {
room = Random.element(rooms); room = Random.element(rooms);
} while (room.type != Type.STANDARD); } while (room.type != Type.STANDARD);
mob.pos = room.random(); mob.pos = pointToCell(room.random());
mobs.add( mob ); mobs.add( mob );
} }
@@ -231,7 +232,7 @@ public class SewerBossLevel extends RegularLevel {
if (item != null) { if (item != null) {
int pos; int pos;
do { do {
pos = roomEntrance.random(); pos = pointToCell(roomEntrance.random());
} while (pos == entrance || map[pos] == Terrain.SIGN); } while (pos == entrance || map[pos] == Terrain.SIGN);
drop( item, pos ).type = Heap.Type.REMAINS; drop( item, pos ).type = Heap.Type.REMAINS;
} }
@@ -239,7 +240,7 @@ public class SewerBossLevel extends RegularLevel {
@Override @Override
public int randomRespawnCell() { public int randomRespawnCell() {
return roomEntrance.random(); return pointToCell(roomEntrance.random());
} }
@@ -62,11 +62,11 @@ public class SewerLevel extends RegularLevel {
} }
protected boolean[] water() { protected boolean[] water() {
return Patch.generate( feeling == Feeling.WATER ? 0.60f : 0.45f, 5 ); return Patch.generate( this, feeling == Feeling.WATER ? 0.60f : 0.45f, 5 );
} }
protected boolean[] grass() { protected boolean[] grass() {
return Patch.generate( feeling == Feeling.GRASS ? 0.60f : 0.40f, 4 ); return Patch.generate( this, feeling == Feeling.GRASS ? 0.60f : 0.40f, 4 );
} }
@Override @Override
@@ -90,33 +90,33 @@ public class SewerLevel extends RegularLevel {
@Override @Override
protected void decorate() { protected void decorate() {
for (int i=0; i < WIDTH; i++) { for (int i=0; i < width(); i++) {
if (map[i] == Terrain.WALL && if (map[i] == Terrain.WALL &&
map[i + WIDTH] == Terrain.WATER && map[i + width()] == Terrain.WATER &&
Random.Int( 4 ) == 0) { Random.Int( 4 ) == 0) {
map[i] = Terrain.WALL_DECO; map[i] = Terrain.WALL_DECO;
} }
} }
for (int i=WIDTH; i < LENGTH - WIDTH; i++) { for (int i=width(); i < length() - width(); i++) {
if (map[i] == Terrain.WALL && if (map[i] == Terrain.WALL &&
map[i - WIDTH] == Terrain.WALL && map[i - width()] == Terrain.WALL &&
map[i + WIDTH] == Terrain.WATER && map[i + width()] == Terrain.WATER &&
Random.Int( 2 ) == 0) { Random.Int( 2 ) == 0) {
map[i] = Terrain.WALL_DECO; map[i] = Terrain.WALL_DECO;
} }
} }
for (int i=WIDTH + 1; i < LENGTH - WIDTH - 1; i++) { for (int i=width() + 1; i < length() - width() - 1; i++) {
if (map[i] == Terrain.EMPTY) { if (map[i] == Terrain.EMPTY) {
int count = int count =
(map[i + 1] == Terrain.WALL ? 1 : 0) + (map[i + 1] == Terrain.WALL ? 1 : 0) +
(map[i - 1] == Terrain.WALL ? 1 : 0) + (map[i - 1] == Terrain.WALL ? 1 : 0) +
(map[i + WIDTH] == Terrain.WALL ? 1 : 0) + (map[i + width()] == Terrain.WALL ? 1 : 0) +
(map[i - WIDTH] == Terrain.WALL ? 1 : 0); (map[i - width()] == Terrain.WALL ? 1 : 0);
if (Random.Int( 16 ) < count * count) { if (Random.Int( 16 ) < count * count) {
map[i] = Terrain.EMPTY_DECO; map[i] = Terrain.EMPTY_DECO;
@@ -129,7 +129,7 @@ public class SewerLevel extends RegularLevel {
for (Room r : roomEntrance.connected.keySet()){ for (Room r : roomEntrance.connected.keySet()){
Room.Door d = roomEntrance.connected.get(r); Room.Door d = roomEntrance.connected.get(r);
if (d.type == Room.Door.Type.REGULAR) if (d.type == Room.Door.Type.REGULAR)
map[d.x + d.y * WIDTH] = Terrain.SECRET_DOOR; map[d.x + d.y * width()] = Terrain.SECRET_DOOR;
} }
placeSign(); placeSign();
@@ -155,7 +155,7 @@ public class SewerLevel extends RegularLevel {
} }
public static void addSewerVisuals( Level level, Group group ) { public static void addSewerVisuals( Level level, Group group ) {
for (int i=0; i < LENGTH; i++) { for (int i=0; i < level.length(); i++) {
if (level.map[i] == Terrain.WALL_DECO) { if (level.map[i] == Terrain.WALL_DECO) {
group.add( new Sink( i ) ); group.add( new Sink( i ) );
} }
@@ -216,7 +216,7 @@ public class SewerLevel extends RegularLevel {
super.update(); super.update();
if ((rippleDelay -= Game.elapsed) <= 0) { if ((rippleDelay -= Game.elapsed) <= 0) {
Ripple ripple = GameScene.ripple( pos + WIDTH ); Ripple ripple = GameScene.ripple( pos + Dungeon.level.width() );
if (ripple != null) { if (ripple != null) {
ripple.y -= DungeonTilemap.SIZE / 2; ripple.y -= DungeonTilemap.SIZE / 2;
rippleDelay = Random.Float(0.2f, 0.3f); rippleDelay = Random.Float(0.2f, 0.3f);
@@ -57,7 +57,7 @@ public class ArmoryPainter extends Painter {
for (int i=0; i < n; i++) { for (int i=0; i < n; i++) {
int pos; int pos;
do { do {
pos = room.random(); pos = level.pointToCell(room.random());
} while (level.map[pos] != Terrain.EMPTY || level.heaps.get( pos ) != null); } while (level.map[pos] != Terrain.EMPTY || level.heaps.get( pos ) != null);
level.drop( prize( level ), pos ); level.drop( prize( level ), pos );
} }
@@ -26,6 +26,7 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.levels.Room; import com.shatteredpixel.shatteredpixeldungeon.levels.Room;
import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain; import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FireTrap; import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FireTrap;
import com.watabou.utils.Point;
import com.watabou.utils.Random; import com.watabou.utils.Random;
public class BlacksmithPainter extends Painter { public class BlacksmithPainter extends Painter {
@@ -39,7 +40,7 @@ public class BlacksmithPainter extends Painter {
for (int i=0; i < 2; i++) { for (int i=0; i < 2; i++) {
int pos; int pos;
do { do {
pos = room.random(); pos = level.pointToCell(room.random());
} while (level.map[pos] != Terrain.EMPTY_SP); } while (level.map[pos] != Terrain.EMPTY_SP);
level.drop( level.drop(
Generator.random( Random.oneOf( Generator.random( Random.oneOf(
@@ -55,11 +56,12 @@ public class BlacksmithPainter extends Painter {
Blacksmith npc = new Blacksmith(); Blacksmith npc = new Blacksmith();
do { do {
npc.pos = room.random( 1 ); npc.pos = level.pointToCell(room.random( 1 ));
} while (level.heaps.get( npc.pos ) != null); } while (level.heaps.get( npc.pos ) != null);
level.mobs.add( npc ); level.mobs.add( npc );
for(int cell : room.getCells()) { for(Point p : room.getPoints()) {
int cell = level.pointToCell(p);
if (level.map[cell] == Terrain.TRAP){ if (level.map[cell] == Terrain.TRAP){
level.setTrap(new FireTrap().reveal(), cell); level.setTrap(new FireTrap().reveal(), cell);
} }
@@ -35,7 +35,7 @@ public class BossExitPainter extends Painter {
door.set( Room.Door.Type.REGULAR ); door.set( Room.Door.Type.REGULAR );
} }
level.exit = room.top * Level.WIDTH + (room.left + room.right) / 2; level.exit = room.top * level.width() + (room.left + room.right) / 2;
set( level, level.exit, Terrain.LOCKED_EXIT ); set( level, level.exit, Terrain.LOCKED_EXIT );
} }
@@ -65,7 +65,7 @@ public class CryptPainter extends Painter {
cy = room.top + 2; cy = room.top + 2;
} }
level.drop( prize( level ), cx + cy * Level.WIDTH ).type = Type.TOMB; level.drop( prize( level ), cx + cy * level.width() ).type = Type.TOMB;
} }
private static Item prize( Level level ) { private static Item prize( Level level ) {
@@ -36,7 +36,7 @@ public class EntrancePainter extends Painter {
} }
do { do {
level.entrance = room.random(1); level.entrance = level.pointToCell(room.random(1));
} while (level.findMob(level.entrance) != null); } while (level.findMob(level.entrance) != null);
set( level, level.entrance, Terrain.ENTRANCE ); set( level, level.entrance, Terrain.ENTRANCE );
} }
@@ -35,7 +35,7 @@ public class ExitPainter extends Painter {
door.set( Room.Door.Type.REGULAR ); door.set( Room.Door.Type.REGULAR );
} }
level.exit = room.random( 1 ); level.exit = level.pointToCell(room.random( 1 ));
set( level, level.exit, Terrain.EXIT ); set( level, level.exit, Terrain.EXIT );
} }
@@ -42,17 +42,17 @@ public class GardenPainter extends Painter {
if (Dungeon.isChallenged(Challenges.NO_FOOD)) { if (Dungeon.isChallenged(Challenges.NO_FOOD)) {
if (Random.Int(2) == 0){ if (Random.Int(2) == 0){
level.plant(new Sungrass.Seed(), room.random()); level.plant(new Sungrass.Seed(), level.pointToCell(room.random()));
} }
} else { } else {
int bushes = Random.Int(3); int bushes = Random.Int(3);
if (bushes == 0) { if (bushes == 0) {
level.plant(new Sungrass.Seed(), room.random()); level.plant(new Sungrass.Seed(), level.pointToCell(room.random()));
} else if (bushes == 1) { } else if (bushes == 1) {
level.plant(new BlandfruitBush.Seed(), room.random()); level.plant(new BlandfruitBush.Seed(), level.pointToCell(room.random()));
} else if (Random.Int(5) == 0) { } else if (Random.Int(5) == 0) {
level.plant(new Sungrass.Seed(), room.random()); level.plant(new Sungrass.Seed(), level.pointToCell(room.random()));
level.plant(new BlandfruitBush.Seed(), room.random()); level.plant(new BlandfruitBush.Seed(), level.pointToCell(room.random()));
} }
} }
@@ -62,7 +62,7 @@ public class GardenPainter extends Painter {
} }
for (int i=room.top + 1; i < room.bottom; i++) { for (int i=room.top + 1; i < room.bottom; i++) {
for (int j=room.left + 1; j < room.right; j++) { for (int j=room.left + 1; j < room.right; j++) {
light.seed( j + Level.WIDTH * i, 1 ); light.seed( level, j + level.width() * i, 1 );
} }
} }
level.blobs.put( Foliage.class, light ); level.blobs.put( Foliage.class, light );

Some files were not shown because too many files have changed in this diff Show More