package electrosphere.client.fluid.cache; import java.util.HashSet; import java.util.Set; import org.joml.Vector3i; import electrosphere.server.terrain.manager.ServerTerrainChunk; /** * A container of data about a chunk of fluid */ public class FluidChunkData { //The size of a chunk in virtual data public static final int CHUNK_SIZE = ServerTerrainChunk.CHUNK_DIMENSION; //The size of the data passed into marching cubes/transvoxel algorithm to get a fully connected and seamless chunk public static final int CHUNK_DATA_GENERATOR_SIZE = ServerTerrainChunk.CHUNK_DATA_GENERATOR_SIZE; //What type of fluid is in this voxel, eg stone vs dirt vs grass, etc int[][][] voxelType; //How much of that fluid type is in this voxel float[][][] voxelWeight; //the list of positions modified since the last call to resetModifiedPositions //Used in DrawCell to keep track of which positions to invalidate Set modifiedSinceLastGeneration = new HashSet(); /** * Gets the voxel type array in this container * @return The voxel type array */ public int[][][] getVoxelType(){ return voxelType; } /** * Sets the voxel type array in this container * @param voxelType The voxel type array */ public void setVoxelType(int[][][] voxelType){ //mark changed cells if(this.voxelType != null){ for(int x = 0; x < CHUNK_SIZE; x++){ for(int y = 0; y < CHUNK_SIZE; y++){ for(int z = 0; z < CHUNK_SIZE; z++){ if(voxelType[x][y][z] != this.voxelType[x][y][z]){ String key = getVoxelPositionKey(new Vector3i(x,y,z)); if(!modifiedSinceLastGeneration.contains(key)){ modifiedSinceLastGeneration.add(key); } } } } } } //update data this.voxelType = voxelType; } /** * Gets the voxel weight array in this container * @return The voxel weight array */ public float[][][] getVoxelWeight(){ return voxelWeight; } /** * Sets the voxel weight array in this container * @param voxelWeight The voxel weight array */ public void setVoxelWeight(float[][][] voxelWeight){ //mark changed cells if(this.voxelWeight != null){ for(int x = 0; x < CHUNK_SIZE; x++){ for(int y = 0; y < CHUNK_SIZE; y++){ for(int z = 0; z < CHUNK_SIZE; z++){ if(voxelWeight[x][y][z] != this.voxelWeight[x][y][z]){ String key = getVoxelPositionKey(new Vector3i(x,y,z)); if(!modifiedSinceLastGeneration.contains(key)){ modifiedSinceLastGeneration.add(key); } } } } } } //update data this.voxelWeight = voxelWeight; } /** * Updates the value of a single voxel in the chunk * @param localX The local position X * @param localY The local position Y * @param localZ The local position Z * @param weight The weight to set it to * @param type The type to set the voxel to */ public void updatePosition(int localX, int localY, int localZ, float weight, int type){ voxelWeight[localX][localY][localZ] = weight; voxelType[localX][localY][localZ] = type; //store as modified in cache String key = getVoxelPositionKey(new Vector3i(localX,localY,localZ)); if(!modifiedSinceLastGeneration.contains(key)){ modifiedSinceLastGeneration.add(key); } } /** * Gets the weight of a voxel at a poisiton * @param localPosition The local position * @return The weight of the specified voxel */ public float getWeight(Vector3i localPosition){ return voxelWeight[localPosition.x][localPosition.y][localPosition.z]; } /** * Gets the type of a voxel at a position * @param localPosition The local position * @return The type of the specified voxel */ public int getType(Vector3i localPosition){ return voxelType[localPosition.x][localPosition.y][localPosition.z]; } /** * Resets the cache of modified positions */ public void resetModifiedPositions(){ this.modifiedSinceLastGeneration.clear(); } /** * Gets the set of all modified positions since the last call to resetModifiedPositions * @return The set of all modified positions */ public Set getModifiedPositions(){ Set rVal = new HashSet(); for(String key : modifiedSinceLastGeneration){ String[] split = key.split("_"); rVal.add(new Vector3i(Integer.parseInt(split[0]),Integer.parseInt(split[1]),Integer.parseInt(split[2]))); } return rVal; } /** * Gets a key for the modifiedSinceLastGeneration set based on a voxel position * @param position The voxel position * @return The key */ private String getVoxelPositionKey(Vector3i position){ return position.x + "_" + position.y + "_" + position.z; } }