server fluid storage conversion
All checks were successful
studiorailgun/Renderer/pipeline/head This commit looks good

This commit is contained in:
austin 2024-11-30 13:23:20 -05:00
parent 2d8b172f16
commit 72e6a6d0cb
6 changed files with 117 additions and 73 deletions

View File

@ -1195,6 +1195,7 @@ Fix viewport loading
(11/30/2024) (11/30/2024)
Water spawner firing on repeat Water spawner firing on repeat
Convert server side fluid storage to using buffers

View File

@ -399,41 +399,39 @@ public class TerrainProtocol implements ServerProtocolTemplate<TerrainMessage> {
//The length along each access of the chunk data. Typically, should be at least 17. //The length along each access of the chunk data. Typically, should be at least 17.
//Because CHUNK_SIZE is 16, 17 adds the necessary extra value. Each chunk needs the value of the immediately following position to generate //Because CHUNK_SIZE is 16, 17 adds the necessary extra value. Each chunk needs the value of the immediately following position to generate
//chunk data that connects seamlessly to the next chunk. //chunk data that connects seamlessly to the next chunk.
int xWidth = chunk.getWeights().length; int dataLength = chunk.getWeights().limit();
int yWidth = chunk.getWeights()[0].length;
int zWidth = chunk.getWeights()[0][0].length;
ByteBuffer buffer = ByteBuffer.allocate(xWidth*yWidth*zWidth*(4+4+4+4)); ByteBuffer buffer = ByteBuffer.allocate(dataLength*(4+4+4+4));
FloatBuffer floatView = buffer.asFloatBuffer(); FloatBuffer floatView = buffer.asFloatBuffer();
for(int x = 0; x < xWidth; x++){ for(int x = 0; x < ServerTerrainChunk.CHUNK_DIMENSION; x++){
for(int y = 0; y < yWidth; y++){ for(int y = 0; y < ServerTerrainChunk.CHUNK_DIMENSION; y++){
for(int z = 0; z < zWidth; z++){ for(int z = 0; z < ServerTerrainChunk.CHUNK_DIMENSION; z++){
floatView.put(chunk.getWeights()[x][y][z]); floatView.put(chunk.getWeight(x, y, z));
} }
} }
} }
for(int x = 0; x < xWidth; x++){ for(int x = 0; x < ServerTerrainChunk.CHUNK_DIMENSION; x++){
for(int y = 0; y < yWidth; y++){ for(int y = 0; y < ServerTerrainChunk.CHUNK_DIMENSION; y++){
for(int z = 0; z < zWidth; z++){ for(int z = 0; z < ServerTerrainChunk.CHUNK_DIMENSION; z++){
floatView.put(chunk.getVelocityX()[x][y][z]); floatView.put(chunk.getVelocityX(x, y, z));
} }
} }
} }
for(int x = 0; x < xWidth; x++){ for(int x = 0; x < ServerTerrainChunk.CHUNK_DIMENSION; x++){
for(int y = 0; y < yWidth; y++){ for(int y = 0; y < ServerTerrainChunk.CHUNK_DIMENSION; y++){
for(int z = 0; z < zWidth; z++){ for(int z = 0; z < ServerTerrainChunk.CHUNK_DIMENSION; z++){
floatView.put(chunk.getVelocityY()[x][y][z]); floatView.put(chunk.getVelocityY(x, y, z));
} }
} }
} }
for(int x = 0; x < xWidth; x++){ for(int x = 0; x < ServerTerrainChunk.CHUNK_DIMENSION; x++){
for(int y = 0; y < yWidth; y++){ for(int y = 0; y < ServerTerrainChunk.CHUNK_DIMENSION; y++){
for(int z = 0; z < zWidth; z++){ for(int z = 0; z < ServerTerrainChunk.CHUNK_DIMENSION; z++){
floatView.put(chunk.getVelocityZ()[x][y][z]); floatView.put(chunk.getVelocityZ(x, y, z));
} }
} }
} }

View File

@ -105,39 +105,35 @@ public class FluidDiskMap {
ByteBuffer buffer = ByteBuffer.wrap(rawData); ByteBuffer buffer = ByteBuffer.wrap(rawData);
FloatBuffer floatView = buffer.asFloatBuffer(); FloatBuffer floatView = buffer.asFloatBuffer();
int DIM = ServerTerrainChunk.CHUNK_DIMENSION; int DIM = ServerTerrainChunk.CHUNK_DIMENSION;
float[][][] weights = new float[DIM][DIM][DIM]; rVal = new ServerFluidChunk(worldX, worldY, worldZ);
float[][][] velocityX = new float[DIM][DIM][DIM];
float[][][] velocityY = new float[DIM][DIM][DIM];
float[][][] velocityZ = new float[DIM][DIM][DIM];
for(int x = 0; x < DIM; x++){ for(int x = 0; x < DIM; x++){
for(int y = 0; y < DIM; y++){ for(int y = 0; y < DIM; y++){
for(int z = 0; z < DIM; z++){ for(int z = 0; z < DIM; z++){
weights[x][y][z] = floatView.get(); rVal.setWeight(x, y, z, floatView.get());
} }
} }
} }
for(int x = 0; x < DIM; x++){ for(int x = 0; x < DIM; x++){
for(int y = 0; y < DIM; y++){ for(int y = 0; y < DIM; y++){
for(int z = 0; z < DIM; z++){ for(int z = 0; z < DIM; z++){
velocityX[x][y][z] = floatView.get(); rVal.setVelocityX(x, y, z, floatView.get());
} }
} }
} }
for(int x = 0; x < DIM; x++){ for(int x = 0; x < DIM; x++){
for(int y = 0; y < DIM; y++){ for(int y = 0; y < DIM; y++){
for(int z = 0; z < DIM; z++){ for(int z = 0; z < DIM; z++){
velocityY[x][y][z] = floatView.get(); rVal.setVelocityY(x, y, z, floatView.get());
} }
} }
} }
for(int x = 0; x < DIM; x++){ for(int x = 0; x < DIM; x++){
for(int y = 0; y < DIM; y++){ for(int y = 0; y < DIM; y++){
for(int z = 0; z < DIM; z++){ for(int z = 0; z < DIM; z++){
velocityZ[x][y][z] = floatView.get(); rVal.setVelocityZ(x, y, z, floatView.get());
} }
} }
} }
rVal = new ServerFluidChunk(worldX, worldY, worldZ, weights, velocityX, velocityY, velocityZ);
} }
} }
return rVal; return rVal;
@ -158,38 +154,34 @@ public class FluidDiskMap {
fileName = chunkKey + ".dat"; fileName = chunkKey + ".dat";
} }
//generate binary for the file //generate binary for the file
float[][][] weights = fluidChunk.getWeights();
float[][][] velocityX = fluidChunk.getVelocityX();
float[][][] velocityY = fluidChunk.getVelocityY();
float[][][] velocityZ = fluidChunk.getVelocityZ();
int DIM = ServerTerrainChunk.CHUNK_DIMENSION; int DIM = ServerTerrainChunk.CHUNK_DIMENSION;
ByteBuffer buffer = ByteBuffer.allocate(DIM * DIM * DIM * 4 + DIM * DIM * DIM * 4 + DIM * DIM * DIM * 4 + DIM * DIM * DIM * 4); ByteBuffer buffer = ByteBuffer.allocate(DIM * DIM * DIM * 4 + DIM * DIM * DIM * 4 + DIM * DIM * DIM * 4 + DIM * DIM * DIM * 4);
FloatBuffer floatView = buffer.asFloatBuffer(); FloatBuffer floatView = buffer.asFloatBuffer();
for(int x = 0; x < DIM; x++){ for(int x = 0; x < DIM; x++){
for(int y = 0; y < DIM; y++){ for(int y = 0; y < DIM; y++){
for(int z = 0; z < DIM; z++){ for(int z = 0; z < DIM; z++){
floatView.put(weights[x][y][z]); floatView.put(fluidChunk.getWeight(x, y, z));
} }
} }
} }
for(int x = 0; x < DIM; x++){ for(int x = 0; x < DIM; x++){
for(int y = 0; y < DIM; y++){ for(int y = 0; y < DIM; y++){
for(int z = 0; z < DIM; z++){ for(int z = 0; z < DIM; z++){
floatView.put(velocityX[x][y][z]); floatView.put(fluidChunk.getVelocityX(x,y,z));
} }
} }
} }
for(int x = 0; x < DIM; x++){ for(int x = 0; x < DIM; x++){
for(int y = 0; y < DIM; y++){ for(int y = 0; y < DIM; y++){
for(int z = 0; z < DIM; z++){ for(int z = 0; z < DIM; z++){
floatView.put(velocityY[x][y][z]); floatView.put(fluidChunk.getVelocityY(x,y,z));
} }
} }
} }
for(int x = 0; x < DIM; x++){ for(int x = 0; x < DIM; x++){
for(int y = 0; y < DIM; y++){ for(int y = 0; y < DIM; y++){
for(int z = 0; z < DIM; z++){ for(int z = 0; z < DIM; z++){
floatView.put(velocityZ[x][y][z]); floatView.put(fluidChunk.getVelocityZ(x,y,z));
} }
} }
} }

View File

@ -2,17 +2,12 @@ package electrosphere.server.fluid.generation;
import electrosphere.server.fluid.manager.ServerFluidChunk; import electrosphere.server.fluid.manager.ServerFluidChunk;
import electrosphere.server.fluid.models.FluidModel; import electrosphere.server.fluid.models.FluidModel;
import electrosphere.server.terrain.manager.ServerTerrainChunk;
public class DefaultFluidGenerator implements FluidGenerator { public class DefaultFluidGenerator implements FluidGenerator {
@Override @Override
public ServerFluidChunk generateChunk(int worldX, int worldY, int worldZ) { public ServerFluidChunk generateChunk(int worldX, int worldY, int worldZ) {
float[][][] weights = new float[ServerTerrainChunk.CHUNK_DIMENSION][ServerTerrainChunk.CHUNK_DIMENSION][ServerTerrainChunk.CHUNK_DIMENSION]; ServerFluidChunk chunk = new ServerFluidChunk(worldX, worldY, worldZ);
float[][][] velocityX = new float[ServerTerrainChunk.CHUNK_DIMENSION][ServerTerrainChunk.CHUNK_DIMENSION][ServerTerrainChunk.CHUNK_DIMENSION];
float[][][] velocityY = new float[ServerTerrainChunk.CHUNK_DIMENSION][ServerTerrainChunk.CHUNK_DIMENSION][ServerTerrainChunk.CHUNK_DIMENSION];
float[][][] velocityZ = new float[ServerTerrainChunk.CHUNK_DIMENSION][ServerTerrainChunk.CHUNK_DIMENSION][ServerTerrainChunk.CHUNK_DIMENSION];
ServerFluidChunk chunk = new ServerFluidChunk(worldX, worldY, worldZ, weights, velocityX, velocityY, velocityZ);
return chunk; return chunk;
} }

View File

@ -1,8 +1,13 @@
package electrosphere.server.fluid.manager; package electrosphere.server.fluid.manager;
import java.nio.FloatBuffer;
import org.joml.Vector3f; import org.joml.Vector3f;
import org.joml.Vector3i; import org.joml.Vector3i;
import org.lwjgl.BufferUtils;
import electrosphere.server.terrain.manager.ServerTerrainChunk;
/** /**
@ -12,19 +17,19 @@ public class ServerFluidChunk {
int worldX, worldY, worldZ; int worldX, worldY, worldZ;
float[][][] weights; FloatBuffer weights;
float[][][] velocityX; FloatBuffer velocityX;
float[][][] velocityY; FloatBuffer velocityY;
float[][][] velocityZ; FloatBuffer velocityZ;
public ServerFluidChunk( public ServerFluidChunk(
int worldX, int worldX,
int worldY, int worldY,
int worldZ, int worldZ,
float[][][] weights, FloatBuffer weights,
float[][][] velocityX, FloatBuffer velocityX,
float[][][] velocityY, FloatBuffer velocityY,
float[][][] velocityZ FloatBuffer velocityZ
) { ) {
this.worldX = worldX; this.worldX = worldX;
this.worldY = worldY; this.worldY = worldY;
@ -35,6 +40,20 @@ public class ServerFluidChunk {
this.velocityZ = velocityZ; this.velocityZ = velocityZ;
} }
public ServerFluidChunk(
int worldX,
int worldY,
int worldZ
) {
this.worldX = worldX;
this.worldY = worldY;
this.worldZ = worldZ;
this.weights = BufferUtils.createFloatBuffer(ServerTerrainChunk.CHUNK_DIMENSION * ServerTerrainChunk.CHUNK_DIMENSION * ServerTerrainChunk.CHUNK_DIMENSION);
this.velocityX = BufferUtils.createFloatBuffer(ServerTerrainChunk.CHUNK_DIMENSION * ServerTerrainChunk.CHUNK_DIMENSION * ServerTerrainChunk.CHUNK_DIMENSION);
this.velocityY = BufferUtils.createFloatBuffer(ServerTerrainChunk.CHUNK_DIMENSION * ServerTerrainChunk.CHUNK_DIMENSION * ServerTerrainChunk.CHUNK_DIMENSION);
this.velocityZ = BufferUtils.createFloatBuffer(ServerTerrainChunk.CHUNK_DIMENSION * ServerTerrainChunk.CHUNK_DIMENSION * ServerTerrainChunk.CHUNK_DIMENSION);
}
public int getWorldX() { public int getWorldX() {
return worldX; return worldX;
} }
@ -55,7 +74,7 @@ public class ServerFluidChunk {
return new Vector3i(worldX,worldY,worldZ); return new Vector3i(worldX,worldY,worldZ);
} }
public float[][][] getWeights() { public FloatBuffer getWeights() {
return weights; return weights;
} }
@ -76,7 +95,7 @@ public class ServerFluidChunk {
* @return The weight of the specified voxel * @return The weight of the specified voxel
*/ */
public float getWeight(int x, int y, int z){ public float getWeight(int x, int y, int z){
return weights[x][y][z]; return weights.get(this.IX(x,y,z));
} }
/** /**
@ -87,54 +106,94 @@ public class ServerFluidChunk {
* @param weight The weight * @param weight The weight
*/ */
public void setWeight(int x, int y, int z, float weight){ public void setWeight(int x, int y, int z, float weight){
weights[x][y][z] = weight; weights.put(this.IX(x,y,z),weight);
} }
//get velocity x //get velocity x
public float[][][] getVelocityX() { public FloatBuffer getVelocityX() {
return velocityX; return velocityX;
} }
public float getVelocityX(int x, int y, int z){
return velocityX.get(this.IX(x, y, z));
}
//set velocity x //set velocity x
public void setVelocityX(float[][][] velocityX) { public void setVelocityX(FloatBuffer velocityX) {
this.velocityX = velocityX; this.velocityX = velocityX;
} }
public void setVelocityX(int x, int y, int z, float velocity){
this.velocityX.put(this.IX(x,y,z),velocity);
}
//get velocity y //get velocity y
public float[][][] getVelocityY() { public FloatBuffer getVelocityY() {
return velocityY; return velocityY;
} }
public float getVelocityY(int x, int y, int z){
return velocityY.get(this.IX(x, y, z));
}
//set velocity y //set velocity y
public void setVelocityY(float[][][] velocityY) { public void setVelocityY(FloatBuffer velocityY) {
this.velocityY = velocityY; this.velocityY = velocityY;
} }
public void setVelocityY(int x, int y, int z, float velocity){
this.velocityY.put(this.IX(x,y,z),velocity);
}
//get velocity z //get velocity z
public float[][][] getVelocityZ() { public FloatBuffer getVelocityZ() {
return velocityZ; return velocityZ;
} }
public float getVelocityZ(int x, int y, int z){
return velocityZ.get(this.IX(x, y, z));
}
//set velocity z //set velocity z
public void setVelocityZ(float[][][] velocityZ) { public void setVelocityZ(FloatBuffer velocityZ) {
this.velocityZ = velocityZ; this.velocityZ = velocityZ;
} }
public void setVelocityZ(int x, int y, int z, float velocity){
this.velocityZ.put(this.IX(x,y,z),velocity);
}
//get a velocity at a given x, y and z as a Vector3f //get a velocity at a given x, y and z as a Vector3f
public Vector3f getVelocity(int x, int y, int z){ public Vector3f getVelocity(int x, int y, int z){
return new Vector3f(velocityX[x][y][z],velocityY[x][y][z],velocityZ[x][y][z]); int index = this.IX(x,y,z);
return new Vector3f(
velocityX.get(index),
velocityY.get(index),
velocityZ.get(index)
);
} }
//set a velocity at a given x, y, and z given three ints //set a velocity at a given x, y, and z given three ints
public void setVelocity(int x, int y, int z, float velX, float velY, float velZ){ public void setVelocity(int x, int y, int z, float velX, float velY, float velZ){
velocityX[x][y][z] = velX; int index = this.IX(x,y,z);
velocityY[x][y][z] = velY; velocityX.put(index, velX);
velocityZ[x][y][z] = velZ; velocityY.put(index, velY);
velocityZ.put(index, velZ);
}
/**
* Gets the inddex into the buffer
* @param x The x position
* @param y The y position
* @param z The z position
* @return The index
*/
public int IX(int x, int y, int z){
return x * ServerTerrainChunk.CHUNK_DIMENSION * ServerTerrainChunk.CHUNK_DIMENSION + y * ServerTerrainChunk.CHUNK_DIMENSION + z;
} }
} }

View File

@ -16,7 +16,6 @@ public class FluidCellularAutomataSimulator implements ServerFluidSimulator {
@Override @Override
public boolean simulate(ServerFluidChunk fluidChunk, ServerTerrainChunk terrainChunk, int worldX, int worldY, int worldZ) { public boolean simulate(ServerFluidChunk fluidChunk, ServerTerrainChunk terrainChunk, int worldX, int worldY, int worldZ) {
float[][][] weights = fluidChunk.getWeights();
float[][][] terrainWeights = terrainChunk.getWeights(); float[][][] terrainWeights = terrainChunk.getWeights();
//if true, alerts the server data cell to broadcast a new update message to all clients within it //if true, alerts the server data cell to broadcast a new update message to all clients within it
@ -25,13 +24,13 @@ public class FluidCellularAutomataSimulator implements ServerFluidSimulator {
for(int x = 0; x < ServerTerrainChunk.CHUNK_DIMENSION; x++){ for(int x = 0; x < ServerTerrainChunk.CHUNK_DIMENSION; x++){
for(int y = 0; y < ServerTerrainChunk.CHUNK_DIMENSION; y++){ for(int y = 0; y < ServerTerrainChunk.CHUNK_DIMENSION; y++){
for(int z = 0; z < ServerTerrainChunk.CHUNK_DIMENSION; z++){ for(int z = 0; z < ServerTerrainChunk.CHUNK_DIMENSION; z++){
if(weights[x][y][z] <= 0){ if(fluidChunk.getWeight(x, y, z) <= 0){
continue; continue;
} else { } else {
if(y > 0 && weights[x][y-1][z] < MAX_WEIGHT){ if(y > 0 && fluidChunk.getWeight(x, y - 1, z) < MAX_WEIGHT){
update = true; update = true;
weights[x][y][z] -= GRAVITY_DIFF; fluidChunk.setWeight(x, y, z, fluidChunk.getWeight(x, y, z) - GRAVITY_DIFF);
weights[x][y-1][z] += GRAVITY_DIFF; fluidChunk.setWeight(x, y - 1, z, fluidChunk.getWeight(x, y - 1, z) + GRAVITY_DIFF);
} else { } else {
//propagate sideways //propagate sideways
int[] offsetX = new int[]{-1,1,0,0}; int[] offsetX = new int[]{-1,1,0,0};
@ -43,12 +42,12 @@ public class FluidCellularAutomataSimulator implements ServerFluidSimulator {
realZ > 0 && realZ < ServerTerrainChunk.CHUNK_DIMENSION - 1 realZ > 0 && realZ < ServerTerrainChunk.CHUNK_DIMENSION - 1
){ ){
if( if(
weights[realX][y][realZ] < weights[x][y][z] && fluidChunk.getWeight(realX, y, realZ) < fluidChunk.getWeight(x, y, z) &&
terrainWeights[realX][y][realZ] < MAX_WEIGHT terrainWeights[realX][y][realZ] < MAX_WEIGHT
){ ){
update = true; update = true;
weights[x][y][z] -= GRAVITY_DIFF; fluidChunk.setWeight(x, y, z, fluidChunk.getWeight(x, y, z) - GRAVITY_DIFF);
weights[realX][y][realZ] += GRAVITY_DIFF; fluidChunk.setWeight(realX, y, realZ, fluidChunk.getWeight(realX, y, realZ) + GRAVITY_DIFF);
} }
} }
} }