diff --git a/core/src/com/riiablo/Files.java b/core/src/com/riiablo/Files.java index 38b86ae2..2b9422e7 100644 --- a/core/src/com/riiablo/Files.java +++ b/core/src/com/riiablo/Files.java @@ -19,6 +19,7 @@ import com.riiablo.codec.excel.Levels; import com.riiablo.codec.excel.LowQualityItems; import com.riiablo.codec.excel.LvlPrest; import com.riiablo.codec.excel.LvlTypes; +import com.riiablo.codec.excel.LvlWarp; import com.riiablo.codec.excel.MagicPrefix; import com.riiablo.codec.excel.MagicSuffix; import com.riiablo.codec.excel.Misc; @@ -45,79 +46,81 @@ public class Files { public final Obj obj; public final Speech speech; - public final Armor armor; - public final ArmType ArmType; - public final BodyLocs bodylocs; - public final Colors colors; - public final Composit Composit; - public final CompCode compcode; - public final Inventory inventory; - public final ItemStatCost ItemStatCost; - public final ItemTypes ItemTypes; - public final Levels Levels; + public final Armor armor; + public final ArmType ArmType; + public final BodyLocs bodylocs; + public final Colors colors; + public final Composit Composit; + public final CompCode compcode; + public final Inventory inventory; + public final ItemStatCost ItemStatCost; + public final ItemTypes ItemTypes; + public final Levels Levels; public final LowQualityItems LowQualityItems; - public final LvlPrest LvlPrest; - public final LvlTypes LvlTypes; - public final Misc misc; - public final MagicPrefix MagicPrefix; - public final MagicSuffix MagicSuffix; - public final MonMode MonMode; - public final MonStats monstats; - public final MonStats2 monstats2; - public final Objects objects; - public final ObjMode ObjMode; - public final PlrMode PlrMode; - public final PlrType PlrType; - public final QualityItems QualityItems; - public final RarePrefix RarePrefix; - public final RareSuffix RareSuffix; - public final Runes Runes; - public final SetItems SetItems; - public final Sounds Sounds; - public final UniqueItems UniqueItems; - //public final UniquePrefix UniquePrefix; - //public final UniqueSuffix UniqueSuffix; - public final WeaponClass WeaponClass; - public final Weapons weapons; + public final LvlPrest LvlPrest; + public final LvlTypes LvlTypes; + public final LvlWarp LvlWarp; + public final Misc misc; + public final MagicPrefix MagicPrefix; + public final MagicSuffix MagicSuffix; + public final MonMode MonMode; + public final MonStats monstats; + public final MonStats2 monstats2; + public final Objects objects; + public final ObjMode ObjMode; + public final PlrMode PlrMode; + public final PlrType PlrType; + public final QualityItems QualityItems; + public final RarePrefix RarePrefix; + public final RareSuffix RareSuffix; + public final Runes Runes; + public final SetItems SetItems; + public final Sounds Sounds; + public final UniqueItems UniqueItems; + //public final UniquePrefix UniquePrefix; + //public final UniqueSuffix UniqueSuffix; + public final WeaponClass WeaponClass; + public final Weapons weapons; public Files(AssetManager assets) { obj = loadInternal(Obj.class);//loadObj(); speech = loadInternal(Speech.class); - armor = load(assets, Armor.class); - ArmType = load(assets, ArmType.class); - bodylocs = load(assets, BodyLocs.class); - colors = load(assets, Colors.class); - Composit = load(assets, Composit.class); - compcode = load(assets, CompCode.class); - inventory = load(assets, Inventory.class); - ItemStatCost = load(assets, ItemStatCost.class); - ItemTypes = load(assets, ItemTypes.class); - Levels = load(assets, Levels.class); + armor = load(assets, Armor.class); + ArmType = load(assets, ArmType.class); + bodylocs = load(assets, BodyLocs.class); + colors = load(assets, Colors.class); + Composit = load(assets, Composit.class); + compcode = load(assets, CompCode.class); + inventory = load(assets, Inventory.class); + ItemStatCost = load(assets, ItemStatCost.class); + ItemTypes = load(assets, ItemTypes.class); + Levels = load(assets, Levels.class); LowQualityItems = load(assets, LowQualityItems.class); - LvlPrest = load(assets, LvlPrest.class); - LvlTypes = load(assets, LvlTypes.class); - misc = load(assets, Misc.class); - MagicPrefix = load(assets, MagicPrefix.class, Excel.EXPANSION); - MagicSuffix = load(assets, MagicSuffix.class, Excel.EXPANSION); - MonMode = load(assets, MonMode.class); - monstats = load(assets, MonStats.class, Excel.EXPANSION); - monstats2 = load(assets, MonStats2.class, Excel.EXPANSION); - RarePrefix = load(assets, RarePrefix.class, Excel.EXPANSION); - RareSuffix = load(assets, RareSuffix.class, Excel.EXPANSION); - Runes = load(assets, Runes.class); - objects = load(assets, Objects.class); - ObjMode = load(assets, ObjMode.class); - PlrMode = load(assets, PlrMode.class); - PlrType = load(assets, PlrType.class); - QualityItems = load(assets, QualityItems.class); - SetItems = load(assets, SetItems.class, Excel.EXPANSION); - Sounds = load(assets, Sounds.class); - UniqueItems = load(assets, UniqueItems.class, Excel.EXPANSION); - //UniquePrefix = load(assets, UniquePrefix.class); - //UniqueSuffix = load(assets, UniqueSuffix.class); - WeaponClass = load(assets, WeaponClass.class); - weapons = load(assets, Weapons.class); + LvlPrest = load(assets, LvlPrest.class); + LvlTypes = load(assets, LvlTypes.class); + LvlWarp = load(assets, LvlWarp.class, Excel.EXPANSION); + misc = load(assets, Misc.class); + MagicPrefix = load(assets, MagicPrefix.class, Excel.EXPANSION); + MagicSuffix = load(assets, MagicSuffix.class, Excel.EXPANSION); + MonMode = load(assets, MonMode.class); + monstats = load(assets, MonStats.class, Excel.EXPANSION); + monstats2 = load(assets, MonStats2.class, Excel.EXPANSION); + RarePrefix = load(assets, RarePrefix.class, Excel.EXPANSION); + RareSuffix = load(assets, RareSuffix.class, Excel.EXPANSION); + Runes = load(assets, Runes.class); + objects = load(assets, Objects.class); + ObjMode = load(assets, ObjMode.class); + PlrMode = load(assets, PlrMode.class); + PlrType = load(assets, PlrType.class); + QualityItems = load(assets, QualityItems.class); + SetItems = load(assets, SetItems.class, Excel.EXPANSION); + Sounds = load(assets, Sounds.class); + UniqueItems = load(assets, UniqueItems.class, Excel.EXPANSION); + //UniquePrefix = load(assets, UniquePrefix.class); + //UniqueSuffix = load(assets, UniqueSuffix.class); + WeaponClass = load(assets, WeaponClass.class); + weapons = load(assets, Weapons.class); } @Deprecated diff --git a/core/src/com/riiablo/codec/excel/LvlWarp.java b/core/src/com/riiablo/codec/excel/LvlWarp.java new file mode 100644 index 00000000..18fa9880 --- /dev/null +++ b/core/src/com/riiablo/codec/excel/LvlWarp.java @@ -0,0 +1,27 @@ +package com.riiablo.codec.excel; + +public class LvlWarp extends Excel { + public static class Entry extends Excel.Entry { + @Override + public String toString() { + return Name; + } + + @Column public String Name; + @Column + @Key + public int Id; + @Column public int SelectX; + @Column public int SelectY; + @Column public int SelectDX; + @Column public int SelectDY; + @Column public int ExitWalkX; + @Column public int ExitWalkY; + @Column public int OffsetX; + @Column public int OffsetY; + @Column public boolean LitVersion; + @Column public int Tiles; + @Column public String Direction; + @Column public boolean Beta; + } +} diff --git a/core/src/com/riiablo/entity/Entity.java b/core/src/com/riiablo/entity/Entity.java index 64be5c24..8c9f5506 100644 --- a/core/src/com/riiablo/entity/Entity.java +++ b/core/src/com/riiablo/entity/Entity.java @@ -89,6 +89,9 @@ public abstract class Entity { } }, ITM("ITEMS", + new String[] {"NU"}, + new String[] {"NIL"}), + WRP("WARPS", new String[] {"NU"}, new String[] {"NIL"}); @@ -558,7 +561,7 @@ public abstract class Entity { public void setOver(boolean b) { if (over != b) { over = b; - animation.setHighlighted(b); + if (animation != null) animation.setHighlighted(b); } } diff --git a/core/src/com/riiablo/entity/Warp.java b/core/src/com/riiablo/entity/Warp.java new file mode 100644 index 00000000..012d1f3b --- /dev/null +++ b/core/src/com/riiablo/entity/Warp.java @@ -0,0 +1,103 @@ +package com.riiablo.entity; + +import com.badlogic.gdx.graphics.Color; +import com.badlogic.gdx.graphics.glutils.ShapeRenderer; +import com.badlogic.gdx.math.Vector2; +import com.badlogic.gdx.utils.Align; +import com.riiablo.Riiablo; +import com.riiablo.codec.excel.Levels; +import com.riiablo.codec.excel.LvlWarp; +import com.riiablo.codec.util.BBox; +import com.riiablo.graphics.PaletteIndexedBatch; +import com.riiablo.map.Map; + +import static com.riiablo.map.DT1.Tile; + +public class Warp extends Entity { + + public final Map map; + public final Map.Zone zone; + public final int index; + + public final LvlWarp.Entry warp; + public final Levels.Entry dstLevel; + + public final Vector2 pixelLoc; + + BBox box; + + public Warp(Map map, Map.Zone zone, int index, int x, int y) { + super(Type.WRP, "warp", null); + this.map = map; + this.zone = zone; + this.index = index; + + int dst = zone.level.Vis[index]; + assert dst > 0 : "Warp to unknown level!"; + int wrp = zone.level.Warp[index]; + assert wrp >= 0 : "Invalid warp"; + + dstLevel = Riiablo.files.Levels.get(dst); + name(dstLevel.LevelWarp); + + warp = Riiablo.files.LvlWarp.get(wrp); + position.set(x, y).add(warp.OffsetX, warp.OffsetY); + + box = new BBox(); + box.xMin = warp.SelectX; + box.yMin = warp.SelectY; + box.width = warp.SelectDX; + box.height = warp.SelectDY; + box.xMax = box.width + box.xMin; + box.yMax = box.height + box.yMin; + + pixelLoc = new Vector2(); + pixelLoc.x = +(position.x * Tile.SUBTILE_WIDTH50) - (position.y * Tile.SUBTILE_WIDTH50); + pixelLoc.y = -(position.x * Tile.SUBTILE_HEIGHT50) - (position.y * Tile.SUBTILE_HEIGHT50); + + /** + * TODO: warp.LitVersion determines whether or not warp has special highlighted tiles + * warp.Tile is added to subindex of tile to find corresponding highlighted tiles (if warp.LitVersion set) + */ + } + + @Override + public boolean isSelectable() { + return true; + } + + @Override + public float getLabelOffset() { + return 0; + } + + @Override + public boolean contains(Vector2 coords) { + float x = pixelLoc.x + box.xMin; + float y = pixelLoc.y - box.yMax; + return x <= coords.x && coords.x <= x + box.width + && y <= coords.y && coords.y <= y + box.height; + } + + @Override + protected void updateCOF() { + + } + + @Override + public void draw(PaletteIndexedBatch batch) { + label.setPosition(pixelLoc.x, pixelLoc.y + getLabelOffset() + label.getHeight() / 2, Align.center); + } + + @Override + public void drawShadow(PaletteIndexedBatch batch) { + + } + + @Override + public void drawDebugStatus(PaletteIndexedBatch batch, ShapeRenderer shapes) { + super.drawDebugStatus(batch, shapes); + shapes.setColor(Color.GREEN); + shapes.rect(pixelLoc.x + box.xMin, pixelLoc.y - box.yMax, box.width, box.height); + } +} diff --git a/core/src/com/riiablo/map/Map.java b/core/src/com/riiablo/map/Map.java index 74d4d664..2325562d 100644 --- a/core/src/com/riiablo/map/Map.java +++ b/core/src/com/riiablo/map/Map.java @@ -25,6 +25,7 @@ import com.riiablo.codec.excel.Levels; import com.riiablo.codec.excel.LvlPrest; import com.riiablo.codec.excel.LvlTypes; import com.riiablo.entity.Entity; +import com.riiablo.entity.Warp; import org.apache.commons.lang3.builder.ToStringBuilder; @@ -136,6 +137,25 @@ public class Map implements Disposable { public static final int CORPSE_LOCATION = DT1.Tile.Index.create(Orientation.SPECIAL_10, 32, 0); public static final int TP_LOCATION = DT1.Tile.Index.create(Orientation.SPECIAL_10, 33, 0); + + static IntSet WARPS; + static { + WARPS = new IntSet(); + WARPS.addAll( + VIS_0_00, VIS_0_01, VIS_0_02, VIS_0_03, VIS_0_04, VIS_0_05, VIS_0_06, VIS_0_07, VIS_0_08, VIS_0_09, VIS_0_10, + VIS_1_11, VIS_1_12, VIS_1_13, VIS_1_14, VIS_1_15, VIS_1_16, VIS_1_17, VIS_1_18, VIS_1_19, + VIS_2_20, VIS_2_21, VIS_2_22, VIS_2_23, VIS_2_24, VIS_2_25, VIS_2_26, VIS_2_27, VIS_2_28, VIS_2_29, + VIS_3_30, VIS_3_31, VIS_3_32, VIS_3_33, VIS_3_34, VIS_3_35, VIS_3_36, + VIS_4_37, VIS_4_38, VIS_4_39, VIS_4_40, VIS_4_41, + VIS_5_81, VIS_5_42, VIS_5_43, + VIS_6_44, VIS_6_45, VIS_6_82, + VIS_7_46, VIS_7_83); + } + + public static int getWarpIndex(DS1.Cell cell) { + return cell.mainIndex; + } + static IntSet POPPADS; static { POPPADS = new IntSet(); @@ -345,6 +365,9 @@ public class Map implements Disposable { zone.presets[6][zone.gridsY - 2] = Preset.of(Riiablo.files.LvlPrest.get(47), 1); + // ID_VIS_5_42 + zone.presets[5][zone.gridsY - 2] = Preset.of(Riiablo.files.LvlPrest.get(52), 0); + zone.generator = new Zone.Generator() { @Override public void generate(Zone zone, DT1s dt1s, int tx, int ty) { @@ -585,7 +608,7 @@ public class Map implements Disposable { } public static class Zone { - static final Array EMPTY_ARRAY = new Array<>(0); + static final Array EMPTY_ENTITY_ARRAY = new Array<>(0); int x, y; int width, height; @@ -623,7 +646,7 @@ public class Map implements Disposable { gridsY = tilesY / gridSizeY; presets = new Preset[gridsX][gridsY]; flags = new byte[width][height]; - entities = EMPTY_ARRAY; + entities = EMPTY_ENTITY_ARRAY; } /** @@ -644,13 +667,13 @@ public class Map implements Disposable { height = gridsY * DT1.Tile.SUBTILE_SIZE; presets = new Preset[gridsX][gridsY]; flags = new byte[width][height]; - entities = EMPTY_ARRAY; + entities = EMPTY_ENTITY_ARRAY; } private void loadEntities(DS1 ds1, int gridX, int gridY) { final int x = this.x + (gridX * DT1.Tile.SUBTILE_SIZE); final int y = this.y + (gridY * DT1.Tile.SUBTILE_SIZE); - if (entities == EMPTY_ARRAY) entities = new Array<>(); + if (entities == EMPTY_ENTITY_ARRAY) entities = new Array<>(); for (int i = 0; i < ds1.numObjects; i++) { DS1.Object obj = ds1.objects[i]; Entity entity = Entity.create(map, this, ds1, obj); @@ -660,6 +683,14 @@ public class Map implements Disposable { } } + private void addWarp(Tile tile, int warpX, int warpY) { + final int x = this.x + (warpX * DT1.Tile.SUBTILE_SIZE); + final int y = this.y + (warpY * DT1.Tile.SUBTILE_SIZE); + if (entities == EMPTY_ENTITY_ARRAY) entities = new Array<>(); + Warp warp = new Warp(map, this, tile.cell.mainIndex, x, y); + entities.add(warp); + } + public void setPosition(int x, int y) { this.x = x; this.y = y; @@ -904,7 +935,7 @@ public class Map implements Disposable { DS1.Cell cell = ds1.walls[ptr]; if (Orientation.isSpecial(cell.orientation)) { - zone.tiles[layer][tx][ty] = Tile.of(dt1s, cell); + Tile tile = zone.tiles[layer][tx][ty] = Tile.of(dt1s, cell); if (ID.POPPADS.contains(cell.id)) { if (popPads == null) popPads = new IntMap<>(); PopPad popPad = popPads.get(cell.id); @@ -914,6 +945,8 @@ public class Map implements Disposable { popPad.setEnd( x * DT1.Tile.SUBTILE_SIZE + DT1.Tile.SUBTILE_SIZE + preset.PopPad, y * DT1.Tile.SUBTILE_SIZE + DT1.Tile.SUBTILE_SIZE + preset.PopPad); + } else if (ID.WARPS.contains(cell.id)) { + zone.addWarp(tile, tx, ty); } } diff --git a/core/src/com/riiablo/map/MapRenderer.java b/core/src/com/riiablo/map/MapRenderer.java index ed48455c..448d18e3 100644 --- a/core/src/com/riiablo/map/MapRenderer.java +++ b/core/src/com/riiablo/map/MapRenderer.java @@ -495,9 +495,42 @@ public class MapRenderer { for (x = 0; x < size; x++) { Map.Zone zone = map.getZone(stx, sty); if (zone != null) { - //buildCaches(zone, stx, sty); drawLowerWalls(batch, zone, tx, ty, px, py); drawFloors(batch, zone, tx, ty, px, py); + } + + tx++; + stx += Tile.SUBTILE_SIZE; + px += Tile.WIDTH50; + py -= Tile.HEIGHT50; + } + + startY2++; + if (y >= tilesX - 1) { + startX2++; + startPy2 -= Tile.HEIGHT; + } else { + startX2--; + startPx2 -= Tile.WIDTH; + } + } + + startX2 = startX; + startY2 = startY; + startPx2 = startPx; + startPy2 = startPy; + for (y = 0; y < viewBuffer.length; y++) { + int tx = startX2; + int ty = startY2; + int stx = tx * Tile.SUBTILE_SIZE; + int sty = ty * Tile.SUBTILE_SIZE; + int px = startPx2; + int py = startPy2; + int size = viewBuffer[y]; + for (x = 0; x < size; x++) { + Map.Zone zone = map.getZone(stx, sty); + if (zone != null) { + //buildCaches(zone, stx, sty); drawShadows(batch, zone, tx, ty, px, py, cache[y][x]); }