ProjectZombie/src/projectzombie/world/World.java

251 lines
5.6 KiB
Java
Executable File

package projectzombie.world;
import java.nio.ByteBuffer;
import java.nio.FloatBuffer;
import java.util.ArrayList;
import org.lwjgl.BufferUtils;
import org.lwjgl.opengl.GL33;
import bdf.classes.IBdfClassManager;
import bdf.types.BdfArray;
import bdf.types.BdfNamedList;
import bdf.types.BdfObject;
import gl_engine.matrix.Matrix4;
import gl_engine.vec.Vec3d;
import projectzombie.Main;
import projectzombie.display.Camera;
import projectzombie.display.DisplayLighting;
import projectzombie.entity.player.EntityPlayer;
import projectzombie.model.Model;
import projectzombie.time.GameTimer;
import projectzombie.world.chunk.ChunkEventHandler;
import projectzombie.world.layer.Layer;
public class World implements IBdfClassManager
{
public static final double BIOME_SIZE = 1024;
private Layer loaded;
private ArrayList<Layer> layers = new ArrayList<Layer>();
private String path;
private int pool_vao, pool_vbo, pool_ibo;
private boolean pool_dirty = true;
private int pool_particle_count = 0;
private int pool_size = 1;
public World(String path) {
this.path = path;
}
public String getSavePath() {
return path;
}
public boolean isPoolDirty() {
return pool_dirty;
}
public void markPoolDirty() {
this.pool_dirty = true;
}
public void render(Camera camera)
{
// Render the world and the player
if(!Main.player.dead)
{
Vec3d ppos = Main.player.getPos();
Model model = Main.player.getModel();
model.setModel(Matrix4.translate(
ppos.x - Camera.camera.x - 0.5, ppos.y,
ppos.z - Camera.camera.y - 0.5));
model.render();
}
// Re-generate the particle pool if the pool has changed
if(pool_dirty)
{
pool_particle_count = loaded.getParticlePoolSize();
boolean changed = false;
if(pool_particle_count > pool_size)
{
changed = true;
while(pool_particle_count > pool_size) {
pool_size *= 2;
}
}
if(changed)
{
ByteBuffer pool = BufferUtils.createByteBuffer(pool_size * Model.SIZE * 16);
loaded.render(camera, pool.asFloatBuffer(), 0);
if(pool_vao != 0) {
GL33.glDeleteVertexArrays(pool_vao);
GL33.glDeleteBuffers(pool_vbo);
GL33.glDeleteBuffers(pool_ibo);
}
pool_vao = GL33.glGenVertexArrays();
pool_vbo = GL33.glGenBuffers();
pool_ibo = GL33.glGenBuffers();
GL33.glBindVertexArray(pool_vao);
int[] indicies = new int[pool_size * 6];
for(int i=0;i<pool_size;i++) {
indicies[i*6+0] = i*4+0;
indicies[i*6+1] = i*4+1;
indicies[i*6+2] = i*4+2;
indicies[i*6+3] = i*4+2;
indicies[i*6+4] = i*4+3;
indicies[i*6+5] = i*4+0;
}
GL33.glBindBuffer(GL33.GL_ELEMENT_ARRAY_BUFFER, pool_ibo);
GL33.glBufferData(GL33.GL_ELEMENT_ARRAY_BUFFER, indicies, GL33.GL_STATIC_DRAW);
GL33.glBindBuffer(GL33.GL_ARRAY_BUFFER, pool_vbo);
GL33.glBufferData(GL33.GL_ARRAY_BUFFER, pool, GL33.GL_DYNAMIC_DRAW);
Model.setGLArrayAttributes();
pool.clear();
}
else
{
ByteBuffer pool = BufferUtils.createByteBuffer(pool_particle_count * Model.SIZE * 16);
loaded.render(camera, pool.asFloatBuffer(), 0);
GL33.glBindVertexArray(pool_vao);
GL33.glBindBuffer(GL33.GL_ARRAY_BUFFER, pool_vbo);
GL33.glBufferSubData(GL33.GL_ARRAY_BUFFER, 0, pool);
pool.clear();
}
pool_dirty = false;
}
else
{
loaded.render(camera, null, 0);
GL33.glBindVertexArray(pool_vao);
}
GL33.glUniformMatrix4fv(Main.window.glsl_model, true, Matrix4.identity().getArray());
GL33.glDrawElements(GL33.GL_TRIANGLES, pool_particle_count*6, GL33.GL_UNSIGNED_INT, 0);
}
public void tickEntities() {
loaded.tickEntities();
}
public void spawnRandomEntities() {
loaded.spawnRandomEntities();
}
public void setLayer(int id)
{
ChunkEventHandler.loaded = false;
DisplayLighting.clearLighting();
DisplayLighting.setDirty();
if(this.loaded != null) {
this.loaded.free();
}
this.loaded = layers.get(id);
}
public void removeLayer(int id) {
layers.remove(id).free();
}
public int addLayer(Layer layer) {
int id = layers.size();
layers.add(layer);
layer.id = id;
return id;
}
public Layer getLayer() {
return loaded;
}
@Override
public void BdfClassLoad(BdfObject bdf)
{
BdfNamedList nl = bdf.getNamedList();
// Get the layers and the loaded layer
BdfArray layers_bdf = nl.get("layers").getArray();
for(BdfObject o : layers_bdf) {
layers.add(new Layer(o));
}
int loaded_id = nl.get("loaded").getInteger();
setLayer(loaded_id);
// Load the player data
BdfArray players = nl.get("players").getArray();
Main.player = new EntityPlayer(players.get(0));
// Set the games time
GameTimer.setTime(nl.get("time").getLong());
}
@Override
public void BdfClassSave(BdfObject bdf)
{
BdfNamedList nl = bdf.getNamedList();
// Get the current loaded layer
int loaded_id = -1;
for(int i=0;i<layers.size();i++) {
if(layers.get(i) == loaded) {
loaded_id = i;
}
}
// Save layer data
BdfArray layers_bdf = new BdfArray();
nl.set("loaded", BdfObject.withInteger(loaded_id));
nl.set("layers", BdfObject.withArray(layers_bdf));
for(Layer l : layers) {
BdfObject o = new BdfObject();
l.BdfClassSave(o);
layers_bdf.add(o);
}
// Save player data
BdfArray players = new BdfArray();
nl.set("players", BdfObject.withArray(players));
BdfObject player = new BdfObject();
Main.player.BdfClassSave(player);
players.add(player);
// Save the game timer
nl.set("time", BdfObject.withLong(GameTimer.getTime()));
}
public void free()
{
for(Layer layer : layers) {
layer.free();
}
}
}