ProjectZombie/src/shootergame/world/chunk/Chunk.java

193 lines
4.6 KiB
Java

package shootergame.world.chunk;
import java.util.ArrayList;
import java.util.Random;
import shootergame.display.Camera;
import shootergame.entity.Entity;
import shootergame.entity.EntityAlive;
import shootergame.init.Tiles;
import shootergame.tiles.Tile;
import shootergame.util.math.MathHelpers;
import shootergame.util.math.range.Range2i;
import shootergame.util.math.vec.Vec2d;
import shootergame.util.math.vec.Vec2i;
import shootergame.world.layer.Layer;
public class Chunk
{
public static final Range2i CHUNK_SIZE = new Range2i(16, 16);
public static final Chunk CHUNK_EMPTY = new ChunkEmpty();
public static final int CHUNK_INDEX = CHUNK_SIZE.mx * CHUNK_SIZE.my;
public static final int SIMULATION_DISTANCE = 5;
private Tile tiles_back[] = new Tile[CHUNK_INDEX];
private Tile tiles_front[] = new Tile[CHUNK_INDEX];
private ArrayList<Entity> entities = new ArrayList<Entity>();
private Random rand;
private Layer layer;
private Vec2i c_pos;
public Chunk(Layer layer, Vec2i c_pos, Random rand)
{
// Set some specified values
this.rand = rand;
this.layer = layer;
this.c_pos = c_pos;
// Loop over all the tiles in the chunk
for(int i=0;i<CHUNK_INDEX;i++)
{
// Make all these tiles void
tiles_back[i] = Tiles.VOID;
tiles_front[i] = Tiles.VOID;
}
}
public void render(Camera camera)
{
// Loop over all the tiles
for(int i=0;i<CHUNK_INDEX;i++)
{
// Get the tile pos
Vec2i t_pos = Vec2i.fromId(CHUNK_SIZE, i);
// Render the tiles
tiles_back[i].doRender(new Vec2d(t_pos.x + c_pos.x * 16, t_pos.y + c_pos.y * 16), camera);
tiles_front[i].doRender(new Vec2d(t_pos.x + c_pos.x * 16, t_pos.y + c_pos.y * 16), camera);
}
// Render all the entities
for(int i=0;i<entities.size();i++) {
Entity e = entities.get(i);
e.doRender(e.pos, camera);
}
}
public void spawnEntity(Entity e) {
entities.add(e);
}
public void tickEntities()
{
// Loop over every entitiy
for(int i=0;i<entities.size();i++)
{
// Get the entity and tick it
Entity e = entities.get(i);
e.tick(this, layer);
}
}
public void checkEntities()
{
// Loop over every entity
for(int i=0;i<entities.size();i++)
{
// Get the entitiy
Entity e = entities.get(i);
// is this entity alive
if(e instanceof EntityAlive)
{
// Get the alive entity
EntityAlive ea = (EntityAlive)e;
// Kill the entity if it should be dead and continue to the next loop iteration
if(ea.getHealth() < 0) {
entities.remove(i);
continue;
}
}
// Has the entity left the chunk
int cx = c_pos.x * CHUNK_SIZE.mx;
int cy = c_pos.y * CHUNK_SIZE.my;
double px = e.pos.x;
double py = e.pos.y;
if(px > cx + CHUNK_SIZE.mx || px < cx || py > cy + CHUNK_SIZE.my || py < cy)
{
// Process the entity by layer and remove the entity from the array
layer.spawnEntity(e);
entities.remove(i);
i -= 1;
}
}
}
public void setBackTile(Tile tile, Vec2i pos)
{
// Get the id
Vec2i cpos = new Vec2i(0, 0);
cpos.x = MathHelpers.mod(pos.x, CHUNK_SIZE.mx);
cpos.y = MathHelpers.mod(pos.y, CHUNK_SIZE.my);
int id = cpos.getId(CHUNK_SIZE);
// Set the back tile
this.tiles_back[id] = tile;
}
public void setFrontTile(Tile tile, Vec2i pos)
{
// Get the id
Vec2i cpos = new Vec2i(0, 0);
cpos.x = MathHelpers.mod(pos.x, CHUNK_SIZE.mx);
cpos.y = MathHelpers.mod(pos.y, CHUNK_SIZE.my);
int id = cpos.getId(CHUNK_SIZE);
// Set the front tile
this.tiles_front[id] = tile;
}
public Tile getBackTile(Vec2i pos)
{
// Get the id
Vec2i cpos = new Vec2i(0, 0);
cpos.x = MathHelpers.mod(pos.x, CHUNK_SIZE.mx);
cpos.y = MathHelpers.mod(pos.y, CHUNK_SIZE.my);
int id = cpos.getId(CHUNK_SIZE);
// Send back the back tile
return this.tiles_back[id];
}
public Tile getFrontTile(Vec2i pos)
{
// Get the id
Vec2i cpos = new Vec2i(0, 0);
cpos.x = MathHelpers.mod(pos.x, CHUNK_SIZE.mx);
cpos.y = MathHelpers.mod(pos.y, CHUNK_SIZE.my);
int id = cpos.getId(CHUNK_SIZE);
// Send back the front tile
return this.tiles_front[id];
}
public void killEntity(Entity e) {
entities.remove(e);
}
public ArrayList<Entity> getNearbyEntities(Vec2d pos, double distance)
{
// Get the list of entities to send back
ArrayList<Entity> nearby_entities = new ArrayList<Entity>();
// Loop over the entities
for(Entity e : entities)
{
if(
e.pos.x + distance > pos.x &&
e.pos.x - distance < pos.x &&
e.pos.y + distance > pos.y &&
e.pos.y - distance < pos.y
) {
nearby_entities.add(e);
}
}
// Send back the entities
return nearby_entities;
}
}