Implemented subtile flags merging from tile layers

Implemented subtile flags merging from tile layers
Fixed algebra calculating Chunk#numTiles
Hacked MapGenerator to function with test DS1
This commit is contained in:
Collin Smith 2021-08-07 00:29:22 -07:00
parent db51859edc
commit fa45d5d4b7
4 changed files with 55 additions and 26 deletions

View File

@ -39,6 +39,7 @@ public class Chunk extends BBox implements Poolable, Disposable {
.add(24 * 24)
.add(32 * 32)
.add(64 * 64)
.scl(NUM_SUBTILES)
.build();
public int layers;
@ -50,7 +51,7 @@ public class Chunk extends BBox implements Poolable, Disposable {
Chunk chunk = pool.obtain();
chunk.asBox(x, y, width, height);
chunk.layers = 0;
chunk.numTiles = width * height / SUBTILE_SIZE;
chunk.numTiles = width * height / NUM_SUBTILES;
chunk.flags = bytePools.obtain(width * height);
return chunk;
}
@ -87,6 +88,35 @@ public class Chunk extends BBox implements Poolable, Disposable {
return this;
}
public Chunk updateFlags() {
for (int i = 0; i < MAX_LAYERS; i++) {
if ((layers & (1 << i)) == 0) continue;
Tile[] tiles = this.tiles[i];
for (int y = 0, j = 0; y <= height; y += SUBTILE_SIZE) {
for (int x = 0; x <= width; x += SUBTILE_SIZE) {
mergeFlags(flags, width, tiles[j++].flags, x, y);
}
}
// TODO:
// update only takes into account chunk tiles, but needs to account for
// ds1 tile overrides.
}
return this;
}
static void mergeFlags(byte[] dst, int width, byte[] flags, int x, int y) {
int dXY, i = 0;
for (int dy = 0; dy < SUBTILE_SIZE; dy++) {
// flags are stored in reversed row order: 20..24,15..19,10..14,5..9,0..4
dXY = (y + SUBTILE_SIZE - 1 - dy) * width + x;
for (int dx = 0; dx < SUBTILE_SIZE; dx++) {
dst[dXY++] |= flags[i++];
}
}
}
Tile[] tiles(int layer) {
Tile[] tiles = this.tiles[layer];
if (tiles == null) throw new IllegalArgumentException("layer(" + layer + ") does not exist!");
@ -119,27 +149,5 @@ public class Chunk extends BBox implements Poolable, Disposable {
x + (i % width),
y + (i / width));
}
// int chunkWidth = width / SUBTILE_SIZE;
// Tile[] tiles = this.tiles[4];
// if (tiles == null) return; // TODO: remove when above is corrected
// for (int i = 0, s = numTiles; i < s; i++) {
// Tile tile = tiles[i];
// if (tile == null) continue;
// drawDebugSubtile(tile, pixmap,
// x + (i % chunkWidth) * SUBTILE_SIZE,
// y + (i / chunkWidth) * SUBTILE_SIZE);
// }
}
void drawDebugSubtile(Tile tile, Pixmap pixmap, int x, int y) {
// pixmap.drawPixel(x, y);
// TODO: apply tile offset + subtile offset of flags id
byte[] flags = tile.flags;
for (int i = 0; i < NUM_SUBTILES; i++) {
byte flag = flags[i];
if (flag == 0) continue;
pixmap.drawPixel(x + (i % SUBTILE_SIZE), y + (i / SUBTILE_SIZE));
}
}
}

View File

@ -1,5 +1,9 @@
package com.riiablo.map2;
import org.apache.commons.lang3.StringUtils;
import com.riiablo.logger.LogManager;
import com.riiablo.logger.Logger;
import com.riiablo.map2.DT1.Tile;
import com.riiablo.map2.random.Random;
import com.riiablo.map2.random.Seed;
@ -8,6 +12,8 @@ import com.riiablo.map2.util.ZoneGraph;
import static com.riiablo.map2.DT1.Tile.SUBTILE_SIZE;
public class MapGenerator {
private static final Logger log = LogManager.getLogger(MapGenerator.class);
public TileGenerator tileGenerator = new TileGenerator();
final Random random = new Random();
@ -35,7 +41,10 @@ public class MapGenerator {
void copyPrefab(Chunk chunk, DS1 ds1) {
if (ds1.width != chunk.width / SUBTILE_SIZE) throw new IllegalArgumentException("ds1 width(" + ds1.width + ") != chunk width(" + chunk.width + ")");
if (ds1.height != chunk.height / SUBTILE_SIZE) throw new IllegalArgumentException("ds1 height(" + ds1.height + ") != chunk height(" + chunk.height + ")");
chunk.init(ds1.layers);
// chunk.init(ds1.layers);
chunk.init(1 << 4);
log.debugf("layers: %s", StringUtils.reverse(StringUtils.leftPad(Integer.toBinaryString(chunk.layers), 8, '0')));
int[] cells = ds1.floors;
Tile[] tiles = chunk.tiles(4);
for (int i = 0, s = ds1.floorLen; i < s; i++) {
@ -44,6 +53,7 @@ public class MapGenerator {
Orientation.FLOOR,
DS1.Cell.mainIndex(cell),
DS1.Cell.subIndex(cell));
// TODO: merge cell flags for stuff like unwalkable tiles
}
// cells = ds1.walls;
@ -55,6 +65,8 @@ public class MapGenerator {
// DS1.Cell.mainIndex(cell),
// DS1.Cell.subIndex(cell));
// }
chunk.updateFlags();
}
void copyPrefab(Chunk chunk, DS1 ds1,

View File

@ -43,7 +43,7 @@ public class BucketPool<E> {
return pool.obtain();
} catch (NoSuchElementException t) {
E instance = ArrayPool.create(clazz, length);
log.debugf("obtain custom-sized array instance: 0x%h %s length %d",
log.debugf("obtain custom-sized array instance: 0x%h %s.length=%d",
System.identityHashCode(instance),
clazz.getSimpleName(),
length);
@ -58,7 +58,7 @@ public class BucketPool<E> {
Pool<E> pool = get(length);
pool.free(o);
} catch (NoSuchElementException t) {
log.debugf("free custom-sized array instance: 0x%h %s length %d",
log.debugf("free custom-sized array instance: 0x%h %s.length=%d",
System.identityHashCode(o),
clazz.getSimpleName(),
length);
@ -91,6 +91,14 @@ public class BucketPool<E> {
return this;
}
public Builder<E> scl(int factor) {
int[] arr = lengths.items;
for (int i = 0, s = lengths.size; i < s; i++) {
arr[i] *= factor;
}
return this;
}
public BucketPool<E> build() {
return new BucketPool<>(clazz, lengths.items, 0, lengths.size);
}

View File

@ -102,6 +102,7 @@ public class MapDebugger extends Tool {
public void create() {
Gdx.app.setLogLevel(Application.LOG_DEBUG);
LogManager.setLevel(MapDebugger.class.getName(), Level.DEBUG);
LogManager.setLevel("com.riiablo.map2", Level.DEBUG);
Riiablo.home = Gdx.files.absolute(Riiablo.home.path());
Riiablo.mpqs = new MPQFileHandleResolver();