Search in sources :

Example 26 with Tile

use of io.anuke.mindustry.world.Tile in project Mindustry by Anuken.

the class Save15 method write.

@Override
public void write(DataOutputStream stream) throws IOException {
    // --META--
    // version id
    stream.writeInt(version);
    // last saved
    stream.writeLong(TimeUtils.millis());
    // --GENERAL STATE--
    // gamemode
    stream.writeByte(state.mode.ordinal());
    // map ID
    stream.writeByte(world.getMap().id);
    // wave
    stream.writeInt(state.wave);
    // wave countdown
    stream.writeFloat(state.wavetime);
    stream.writeByte(state.difficulty.ordinal());
    // --BLOCK HEADER--
    stream.writeInt(Block.getAllBlocks().size);
    for (int i = 0; i < Block.getAllBlocks().size; i++) {
        Block block = Block.getAllBlocks().get(i);
        writeString(stream, block.name);
        stream.writeShort(block.id);
    }
    if (!headless) {
        // player x/y
        stream.writeFloat(player.x);
        stream.writeFloat(player.y);
        // player health
        stream.writeInt(player.health);
        // amount of weapons
        stream.writeByte(control.upgrades().getWeapons().size - 1);
        // start at 1, because the first weapon is always the starter - ignore that
        for (int i = 1; i < control.upgrades().getWeapons().size; i++) {
            // weapon ordinal
            stream.writeByte(control.upgrades().getWeapons().get(i).id);
        }
    } else {
        stream.writeFloat(world.getSpawnX());
        stream.writeFloat(world.getSpawnY());
        stream.writeInt(150);
        stream.writeByte(0);
    }
    // --INVENTORY--
    int l = state.inventory.getItems().length;
    int itemsize = 0;
    for (int i = 0; i < l; i++) {
        if (state.inventory.getItems()[i] > 0) {
            itemsize++;
        }
    }
    // amount of items
    stream.writeByte(itemsize);
    for (int i = 0; i < l; i++) {
        if (state.inventory.getItems()[i] > 0) {
            // item ID
            stream.writeByte(i);
            // item amount
            stream.writeInt(state.inventory.getItems()[i]);
        }
    }
    // --ENEMIES--
    EntityContainer<Enemy> enemies = enemyGroup.all();
    // enemy amount
    stream.writeInt(enemies.size());
    for (int i = 0; i < enemies.size(); i++) {
        Enemy enemy = enemies.get(i);
        // type
        stream.writeByte(enemy.type.id);
        // lane
        stream.writeByte(enemy.lane);
        // x
        stream.writeFloat(enemy.x);
        // y
        stream.writeFloat(enemy.y);
        // tier
        stream.writeByte(enemy.tier);
        // health
        stream.writeShort(enemy.health);
    }
    // --MAP DATA--
    // seed
    stream.writeInt(world.getSeed());
    int totalblocks = 0;
    int totalrocks = 0;
    for (int x = 0; x < world.width(); x++) {
        for (int y = 0; y < world.height(); y++) {
            Tile tile = world.tile(x, y);
            if (tile != null && tile.breakable()) {
                if (tile.block() instanceof Rock) {
                    totalrocks++;
                } else {
                    totalblocks++;
                }
            }
        }
    }
    // amount of rocks
    stream.writeInt(totalrocks);
    // write all rocks
    for (int x = 0; x < world.width(); x++) {
        for (int y = 0; y < world.height(); y++) {
            Tile tile = world.tile(x, y);
            if (tile != null && tile.block() instanceof Rock) {
                stream.writeInt(tile.packedPosition());
            }
        }
    }
    // write all blocks
    stream.writeInt(totalblocks);
    for (int x = 0; x < world.width(); x++) {
        for (int y = 0; y < world.height(); y++) {
            Tile tile = world.tile(x, y);
            if (tile != null && tile.breakable() && !(tile.block() instanceof Rock)) {
                // tile pos
                stream.writeInt(x + y * world.width());
                // block ID
                stream.writeInt(tile.block().id);
                if (tile.block() instanceof BlockPart)
                    stream.writeByte(tile.link);
                if (tile.entity != null) {
                    // rotation
                    stream.writeByte(tile.getRotation());
                    // health
                    stream.writeShort((short) tile.entity.health);
                    byte amount = 0;
                    for (int i = 0; i < tile.entity.items.length; i++) {
                        if (tile.entity.items[i] > 0)
                            amount++;
                    }
                    // amount of items
                    stream.writeByte(amount);
                    for (int i = 0; i < tile.entity.items.length; i++) {
                        if (tile.entity.items[i] > 0) {
                            // item ID
                            stream.writeByte(i);
                            // item amount
                            stream.writeInt(tile.entity.items[i]);
                        }
                    }
                    tile.entity.write(stream);
                }
            }
        }
    }
}
Also used : BlockPart(io.anuke.mindustry.world.blocks.types.BlockPart) Rock(io.anuke.mindustry.world.blocks.types.Rock) Enemy(io.anuke.mindustry.entities.enemies.Enemy) Block(io.anuke.mindustry.world.Block) Tile(io.anuke.mindustry.world.Tile)

Example 27 with Tile

use of io.anuke.mindustry.world.Tile in project Mindustry by Anuken.

the class Pathfind method findClosest.

/**
 *Finds the closest tile to a position, in an array of tiles.
 */
private int findClosest(Tile[] tiles, float x, float y) {
    int cindex = -2;
    float dst = Float.MAX_VALUE;
    for (int i = 0; i < tiles.length - 1; i++) {
        Tile tile = tiles[i];
        Tile next = tiles[i + 1];
        float d = pointLineDist(tile.worldx(), tile.worldy(), next.worldx(), next.worldy(), x, y);
        if (d < dst) {
            dst = d;
            cindex = i;
        }
    }
    return cindex + 1;
}
Also used : Tile(io.anuke.mindustry.world.Tile) SpawnPoint(io.anuke.mindustry.game.SpawnPoint)

Example 28 with Tile

use of io.anuke.mindustry.world.Tile in project Mindustry by Anuken.

the class Pathfind method find.

/**
 *Finds the position on the path an enemy should move to.
 * If the path is not yet calculated, this returns the enemy's position (i. e. "don't move")
 * @param enemy The enemy to find a path for
 * @return The position the enemy should move to.
 */
public Vector2 find(Enemy enemy) {
    // TODO fix -1/-2 node usage
    if (enemy.node == -1 || enemy.node == -2) {
        findNode(enemy);
    }
    if (enemy.node == -2) {
        enemy.node = -1;
    }
    if (enemy.node < 0 || world.getSpawns().get(enemy.lane).pathTiles == null) {
        return vector.set(enemy.x, enemy.y);
    }
    Tile[] path = world.getSpawns().get(enemy.lane).pathTiles;
    if (enemy.node >= path.length) {
        enemy.node = -1;
        return vector.set(enemy.x, enemy.y);
    }
    if (enemy.node <= -1) {
        return vector.set(enemy.x, enemy.y);
    }
    // TODO documentation on what this does
    Tile prev = path[enemy.node - 1];
    Tile target = path[enemy.node];
    // a bridge has been broken, re-path
    if (!world.passable(target.x, target.y)) {
        remakePath();
        return vector.set(enemy.x, enemy.y);
    }
    float projectLen = Vector2.dst(prev.worldx(), prev.worldy(), target.worldx(), target.worldy()) / 6f;
    Vector2 projection = projectPoint(prev.worldx(), prev.worldy(), target.worldx(), target.worldy(), enemy.x, enemy.y);
    boolean canProject = true;
    if (projectLen < 8 || !onLine(projection, prev.worldx(), prev.worldy(), target.worldx(), target.worldy())) {
        canProject = false;
    } else {
        projection.add(v1.set(projectLen, 0).rotate(Angles.angle(prev.worldx(), prev.worldy(), target.worldx(), target.worldy())));
    }
    float dst = Vector2.dst(enemy.x, enemy.y, target.worldx(), target.worldy());
    float nlinedist = enemy.node >= path.length - 1 ? 9999 : pointLineDist(path[enemy.node].worldx(), path[enemy.node].worldy(), path[enemy.node + 1].worldx(), path[enemy.node + 1].worldy(), enemy.x, enemy.y);
    if (dst < 8 || nlinedist < 8) {
        if (enemy.node <= path.length - 2)
            enemy.node++;
        target = path[enemy.node];
    }
    if (canProject && projection.dst(enemy.x, enemy.y) < Vector2.dst(target.x, target.y, enemy.x, enemy.y)) {
        vector.set(projection);
    } else {
        vector.set(target.worldx(), target.worldy());
    }
    // near the core, stop
    if (enemy.node == path.length - 1) {
        vector.set(target.worldx(), target.worldy());
    }
    return vector;
}
Also used : Vector2(com.badlogic.gdx.math.Vector2) Tile(io.anuke.mindustry.world.Tile)

Example 29 with Tile

use of io.anuke.mindustry.world.Tile in project Mindustry by Anuken.

the class Pathfind method findNode.

/**
 *For an enemy that was just loaded from a save, find the node in the path it should be following.
 */
void findNode(Enemy enemy) {
    if (enemy.lane >= world.getSpawns().size || enemy.lane < 0) {
        enemy.lane = 0;
    }
    if (world.getSpawns().get(enemy.lane).pathTiles == null) {
        return;
    }
    Tile[] path = world.getSpawns().get(enemy.lane).pathTiles;
    int closest = findClosest(path, enemy.x, enemy.y);
    closest = Mathf.clamp(closest, 1, path.length - 1);
    if (closest == -1) {
        return;
    }
    enemy.node = closest;
}
Also used : Tile(io.anuke.mindustry.world.Tile) SpawnPoint(io.anuke.mindustry.game.SpawnPoint)

Example 30 with Tile

use of io.anuke.mindustry.world.Tile in project Mindustry by Anuken.

the class Logic method runWave.

public void runWave() {
    if (state.lastUpdated < state.wave + 1) {
        world.pathfinder().resetPaths();
        state.lastUpdated = state.wave + 1;
    }
    for (EnemySpawn spawn : spawns) {
        Array<SpawnPoint> spawns = world.getSpawns();
        for (int lane = 0; lane < spawns.size; lane++) {
            int fl = lane;
            Tile tile = spawns.get(lane).start;
            int spawnamount = spawn.evaluate(state.wave, lane);
            for (int i = 0; i < spawnamount; i++) {
                float range = 12f;
                Timers.runTask(i * 5f, () -> {
                    Enemy enemy = new Enemy(spawn.type);
                    enemy.set(tile.worldx() + Mathf.range(range), tile.worldy() + Mathf.range(range));
                    enemy.lane = fl;
                    enemy.tier = spawn.tier(state.wave, fl);
                    enemy.add();
                    Effects.effect(Fx.spawn, enemy);
                    state.enemies++;
                });
            }
        }
    }
    state.wave++;
    state.wavetime = wavespace * state.difficulty.timeScaling;
    state.extrawavetime = maxwavespace * state.difficulty.maxTimeScaling;
    Events.fire(WaveEvent.class);
}
Also used : EnemySpawn(io.anuke.mindustry.game.EnemySpawn) Enemy(io.anuke.mindustry.entities.enemies.Enemy) Tile(io.anuke.mindustry.world.Tile) SpawnPoint(io.anuke.mindustry.game.SpawnPoint) SpawnPoint(io.anuke.mindustry.game.SpawnPoint)

Aggregations

Tile (io.anuke.mindustry.world.Tile)45 Enemy (io.anuke.mindustry.entities.enemies.Enemy)10 Item (io.anuke.mindustry.resource.Item)7 SpawnPoint (io.anuke.mindustry.game.SpawnPoint)6 Block (io.anuke.mindustry.world.Block)6 Vector2 (com.badlogic.gdx.math.Vector2)5 IOException (java.io.IOException)5 Array (com.badlogic.gdx.utils.Array)4 Player (io.anuke.mindustry.entities.Player)3 BlockPart (io.anuke.mindustry.world.blocks.types.BlockPart)3 PowerAcceptor (io.anuke.mindustry.world.blocks.types.PowerAcceptor)3 Rock (io.anuke.mindustry.world.blocks.types.Rock)3 IntMap (com.badlogic.gdx.utils.IntMap)2 LiquidBlock (io.anuke.mindustry.world.blocks.types.LiquidBlock)2 StaticBlock (io.anuke.mindustry.world.blocks.types.StaticBlock)2 GridPoint2 (com.badlogic.gdx.math.GridPoint2)1 Rectangle (com.badlogic.gdx.math.Rectangle)1 Vars (io.anuke.mindustry.Vars)1 TileEntity (io.anuke.mindustry.entities.TileEntity)1 Difficulty (io.anuke.mindustry.game.Difficulty)1