From 239af5e7ab134c077d9ddb20bbe7870ca3e62b09 Mon Sep 17 00:00:00 2001 From: austin Date: Sat, 30 Nov 2024 20:22:18 -0500 Subject: [PATCH] multichunk fluidsim --- .../fluid/manager/ServerFluidChunk.java | 40 +++++++++++++++ .../fluid/manager/ServerFluidManager.java | 49 ++++++++++++++++++- 2 files changed, 88 insertions(+), 1 deletion(-) diff --git a/src/main/java/electrosphere/server/fluid/manager/ServerFluidChunk.java b/src/main/java/electrosphere/server/fluid/manager/ServerFluidChunk.java index 766b6cbd..3d01b16a 100644 --- a/src/main/java/electrosphere/server/fluid/manager/ServerFluidChunk.java +++ b/src/main/java/electrosphere/server/fluid/manager/ServerFluidChunk.java @@ -427,4 +427,44 @@ public class ServerFluidChunk { return updated; } + /** + * Gets the neighbor index given an offset in each dimension + * @param x The x coordinate + * @param y The y coordinate + * @param z The z coordinate + * @return The neighbor index + */ + public static final int getNeighborIndex(int x, int y, int z){ + return x + y * 3 + z * 3 * 3; + } + + /** + * Sets the neighbor of this chunk + * @param x The x coordinate + * @param y The y coordinate + * @param z The z coordinate + * @param neighbor The neighbor ServerFluidChunk + */ + public void setNeighbor(int x, int y, int z, ServerFluidChunk neighbor){ + if(neighbor == null){ + bWeights[getNeighborIndex(x,y,z)] = null; + b0Weights[getNeighborIndex(x,y,z)] = null; + bVelocityX[getNeighborIndex(x,y,z)] = null; + bVelocityY[getNeighborIndex(x,y,z)] = null; + bVelocityZ[getNeighborIndex(x,y,z)] = null; + b0VelocityX[getNeighborIndex(x,y,z)] = null; + b0VelocityY[getNeighborIndex(x,y,z)] = null; + b0VelocityZ[getNeighborIndex(x,y,z)] = null; + } else { + bWeights[getNeighborIndex(x,y,z)] = neighbor.bWeights[CENTER_BUFF]; + b0Weights[getNeighborIndex(x,y,z)] = neighbor.b0Weights[CENTER_BUFF]; + bVelocityX[getNeighborIndex(x,y,z)] = neighbor.bVelocityX[CENTER_BUFF]; + bVelocityY[getNeighborIndex(x,y,z)] = neighbor.bVelocityY[CENTER_BUFF]; + bVelocityZ[getNeighborIndex(x,y,z)] = neighbor.bVelocityZ[CENTER_BUFF]; + b0VelocityX[getNeighborIndex(x,y,z)] = neighbor.b0VelocityX[CENTER_BUFF]; + b0VelocityY[getNeighborIndex(x,y,z)] = neighbor.b0VelocityY[CENTER_BUFF]; + b0VelocityZ[getNeighborIndex(x,y,z)] = neighbor.b0VelocityZ[CENTER_BUFF]; + } + } + } diff --git a/src/main/java/electrosphere/server/fluid/manager/ServerFluidManager.java b/src/main/java/electrosphere/server/fluid/manager/ServerFluidManager.java index 78de3e9c..236a3548 100644 --- a/src/main/java/electrosphere/server/fluid/manager/ServerFluidManager.java +++ b/src/main/java/electrosphere/server/fluid/manager/ServerFluidManager.java @@ -222,7 +222,7 @@ public class ServerFluidManager { } //generate if it does not exist if(returnedChunk == null){ - returnedChunk = chunkGenerator.generateChunk(worldX, worldY, worldZ); + returnedChunk = this.generateChunk(worldX, worldY, worldZ); } chunkCache.put(key, returnedChunk); chunkCacheContents.add(key); @@ -307,6 +307,53 @@ public class ServerFluidManager { Globals.profiler.endCpuSample(); } + /** + * Generates a fluid chunk + * @param worldX The world x position + * @param worldY The world y position + * @param worldZ The world z position + * @return The fluid chunk + */ + private ServerFluidChunk generateChunk(int worldX, int worldY, int worldZ){ + lock.lock(); + ServerFluidChunk rVal = chunkGenerator.generateChunk(worldX, worldY, worldZ); + this.linkNeighbors(rVal, worldX, worldY, worldZ); + lock.unlock(); + return rVal; + } + + /** + * Links the world position to all its neighboring fluid chunks + * @param current The chunk to link + * @param worldX The world x position + * @param worldY The world y position + * @param worldZ The world z position + */ + private void linkNeighbors(ServerFluidChunk current, int worldX, int worldY, int worldZ){ + String key = this.getKey(worldX,worldY,worldZ); + for(int i = -1; i < 2; i++){ + for(int j = -1; j < 2; j++){ + for(int k = -1; k < 2; k++){ + if(i == j && j == k && k == 0){ + continue; + } + if( + 0 <= worldX + i && worldX + i < this.parent.getWorldSizeDiscrete() && + 0 <= worldY + j && worldY + j < this.parent.getWorldSizeDiscrete() && + 0 <= worldZ + k && worldZ + k < this.parent.getWorldSizeDiscrete() + ){ + key = this.getKey(worldX + i,worldY +j,worldZ + k); + ServerFluidChunk neighbor = this.chunkCache.get(key); + current.setNeighbor(i+1,j+1,k+1,neighbor); + if(neighbor != null){ + neighbor.setNeighbor(1-i,1-j,1-k,current); + } + } + } + } + } + } + /** * Gets the broadcast queue * @return The broadcast queue