Fix terrain editing
All checks were successful
studiorailgun/Renderer/pipeline/head This commit looks good
All checks were successful
studiorailgun/Renderer/pipeline/head This commit looks good
This commit is contained in:
parent
a34dc4a4dc
commit
5fee2d06af
@ -1132,6 +1132,8 @@ Disable tunnel noise to align foliage better + adjust manual value for foliage p
|
|||||||
(11/23/2024)
|
(11/23/2024)
|
||||||
Clean up top level folder
|
Clean up top level folder
|
||||||
Break out dependency documentation into a dedicated file
|
Break out dependency documentation into a dedicated file
|
||||||
|
Fix terrain editing
|
||||||
|
Fix foliage not updating at edited chunk
|
||||||
|
|
||||||
|
|
||||||
# TODO
|
# TODO
|
||||||
@ -1168,6 +1170,7 @@ Bug Fixes
|
|||||||
- Fix particles not spawning in correct positions
|
- Fix particles not spawning in correct positions
|
||||||
- Fix flickering when applying yoga signal (may need to rethink arch here)
|
- Fix flickering when applying yoga signal (may need to rethink arch here)
|
||||||
- Fix virtual scrollables not working
|
- Fix virtual scrollables not working
|
||||||
|
- Fix foliage flickering on edit
|
||||||
|
|
||||||
Startup Performance
|
Startup Performance
|
||||||
- Allow texture map to bind multiple model paths to a single set of mesh->textures
|
- Allow texture map to bind multiple model paths to a single set of mesh->textures
|
||||||
|
|||||||
@ -154,6 +154,31 @@ public class ClientWorldData {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Converts a relative voxel position to its absolute voxel equivalent
|
||||||
|
* @param voxelPos The relative voxel position
|
||||||
|
* @param worldPos The position of the chunk
|
||||||
|
* @return The absolute voxel position ie the voxel-aligned position not clamped to the current chunk
|
||||||
|
*/
|
||||||
|
public Vector3i convertRelativeVoxelToAbsoluteVoxelSpace(Vector3i voxelPos, Vector3i worldPos){
|
||||||
|
return new Vector3i(
|
||||||
|
worldPos.x * ServerTerrainChunk.CHUNK_DIMENSION + voxelPos.x,
|
||||||
|
worldPos.y * ServerTerrainChunk.CHUNK_DIMENSION + voxelPos.y,
|
||||||
|
worldPos.z * ServerTerrainChunk.CHUNK_DIMENSION + voxelPos.z
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Converts a relative voxel position to its absolute voxel equivalent
|
||||||
|
* @param voxelPos The relative voxel position
|
||||||
|
* @param worldPos The position of the chunk
|
||||||
|
* @return The absolute voxel position ie the voxel-aligned position not clamped to the current chunk
|
||||||
|
*/
|
||||||
|
public int convertRelativeVoxelToAbsoluteVoxelSpace(int voxelPos, int worldPos){
|
||||||
|
return worldPos * ServerTerrainChunk.CHUNK_DIMENSION + voxelPos;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Converts a world space vector to a real space vector
|
* Converts a world space vector to a real space vector
|
||||||
* @param position The world space vector
|
* @param position The world space vector
|
||||||
|
|||||||
@ -14,6 +14,11 @@ import electrosphere.entity.Entity;
|
|||||||
*/
|
*/
|
||||||
public class ScriptClientVoxelUtils {
|
public class ScriptClientVoxelUtils {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Increment to edit terrain by
|
||||||
|
*/
|
||||||
|
static final float EDIT_INCREMENT = 0.1f;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Applies the current voxel palette where the player's cursor is looking
|
* Applies the current voxel palette where the player's cursor is looking
|
||||||
*/
|
*/
|
||||||
@ -29,7 +34,7 @@ public class ScriptClientVoxelUtils {
|
|||||||
Vector3d centerPos = new Vector3d(CameraEntityUtils.getCameraCenter(camera));
|
Vector3d centerPos = new Vector3d(CameraEntityUtils.getCameraCenter(camera));
|
||||||
Vector3d cursorPos = collisionEngine.rayCastPosition(new Vector3d(centerPos), new Vector3d(eyePos).mul(-1.0), CollisionEngine.DEFAULT_INTERACT_DISTANCE);
|
Vector3d cursorPos = collisionEngine.rayCastPosition(new Vector3d(centerPos), new Vector3d(eyePos).mul(-1.0), CollisionEngine.DEFAULT_INTERACT_DISTANCE);
|
||||||
if(Globals.clientSelectedVoxelType != null){
|
if(Globals.clientSelectedVoxelType != null){
|
||||||
TerrainEditing.editTerrain(cursorPos, 1.1f, Globals.clientSelectedVoxelType.getId(), 0.1f);
|
TerrainEditing.editTerrain(cursorPos, 1.1f, Globals.clientSelectedVoxelType.getId(), EDIT_INCREMENT);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -159,7 +159,7 @@ public class ChunkData {
|
|||||||
voxelWeight[localX][localY][localZ] = weight;
|
voxelWeight[localX][localY][localZ] = weight;
|
||||||
voxelType[localX][localY][localZ] = type;
|
voxelType[localX][localY][localZ] = type;
|
||||||
//store as modified in cache
|
//store as modified in cache
|
||||||
String key = getVoxelPositionKey(new Vector3i(localX,localY,localZ));
|
String key = this.getVoxelPositionKey(new Vector3i(localX,localY,localZ));
|
||||||
if(!modifiedSinceLastGeneration.contains(key)){
|
if(!modifiedSinceLastGeneration.contains(key)){
|
||||||
modifiedSinceLastGeneration.add(key);
|
modifiedSinceLastGeneration.add(key);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -799,8 +799,11 @@ public class ClientDrawCellManager {
|
|||||||
* @param worldY The world y position
|
* @param worldY The world y position
|
||||||
* @param worldZ The world z position
|
* @param worldZ The world z position
|
||||||
*/
|
*/
|
||||||
public void markUpdateable(float worldX, float worldY, float worldZ){
|
public void markUpdateable(int worldX, int worldY, int worldZ){
|
||||||
throw new Error("Unimplemented");
|
DrawCell drawCell = this.getDrawCell(worldX, worldY, worldZ);
|
||||||
|
drawCell.ejectChunkData();
|
||||||
|
drawCell.setHasGenerated(false);
|
||||||
|
drawCell.setHasRequested(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@ -175,10 +175,11 @@ public class DrawCell {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Entity toDelete = this.modelEntity;
|
||||||
modelEntity = TerrainChunk.clientCreateTerrainChunkEntity(
|
modelEntity = TerrainChunk.clientCreateTerrainChunkEntity(
|
||||||
this.chunkData,
|
this.chunkData,
|
||||||
this.notifyTarget,
|
this.notifyTarget,
|
||||||
this.modelEntity,
|
toDelete,
|
||||||
lod,
|
lod,
|
||||||
atlas,
|
atlas,
|
||||||
this.hasPolygons()
|
this.hasPolygons()
|
||||||
@ -555,6 +556,13 @@ public class DrawCell {
|
|||||||
this.failedGenerationAttempts = this.failedGenerationAttempts + attempts;
|
this.failedGenerationAttempts = this.failedGenerationAttempts + attempts;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Ejects the chunk data
|
||||||
|
*/
|
||||||
|
public void ejectChunkData(){
|
||||||
|
this.chunkData = null;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets whether this draw cell is homogenous or not
|
* Gets whether this draw cell is homogenous or not
|
||||||
* @return true if it is homogenous, false otherwise
|
* @return true if it is homogenous, false otherwise
|
||||||
|
|||||||
@ -19,7 +19,6 @@ import electrosphere.client.terrain.cache.ChunkData;
|
|||||||
import electrosphere.engine.Globals;
|
import electrosphere.engine.Globals;
|
||||||
import electrosphere.entity.ClientEntityUtils;
|
import electrosphere.entity.ClientEntityUtils;
|
||||||
import electrosphere.entity.Entity;
|
import electrosphere.entity.Entity;
|
||||||
import electrosphere.entity.EntityCreationUtils;
|
|
||||||
import electrosphere.entity.EntityUtils;
|
import electrosphere.entity.EntityUtils;
|
||||||
import electrosphere.entity.btree.BehaviorTree;
|
import electrosphere.entity.btree.BehaviorTree;
|
||||||
import electrosphere.renderer.OpenGLState;
|
import electrosphere.renderer.OpenGLState;
|
||||||
@ -267,7 +266,6 @@ public class FoliageCell {
|
|||||||
this.chunkData = new TransvoxelChunkData(currentChunk.getVoxelWeight(), currentChunk.getVoxelType(), 0);
|
this.chunkData = new TransvoxelChunkData(currentChunk.getVoxelWeight(), currentChunk.getVoxelType(), 0);
|
||||||
}
|
}
|
||||||
this.generate();
|
this.generate();
|
||||||
this.setHasGenerated(true);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -276,9 +274,6 @@ public class FoliageCell {
|
|||||||
*/
|
*/
|
||||||
protected void generate(){
|
protected void generate(){
|
||||||
boolean shouldGenerate = false;
|
boolean shouldGenerate = false;
|
||||||
if(!Globals.clientDrawCellManager.hasGeneratedPhysics(worldPos.x, worldPos.y, worldPos.z)){
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
ChunkData data = Globals.clientTerrainManager.getChunkDataAtWorldPoint(worldPos,ChunkData.NO_STRIDE);
|
ChunkData data = Globals.clientTerrainManager.getChunkDataAtWorldPoint(worldPos,ChunkData.NO_STRIDE);
|
||||||
if(data == null){
|
if(data == null){
|
||||||
return;
|
return;
|
||||||
@ -315,9 +310,12 @@ public class FoliageCell {
|
|||||||
if(shouldGenerate){
|
if(shouldGenerate){
|
||||||
Entity oldEntity = this.modelEntity;
|
Entity oldEntity = this.modelEntity;
|
||||||
//create entity
|
//create entity
|
||||||
this.modelEntity = EntityCreationUtils.createClientSpatialEntity();
|
this.modelEntity = FoliageModel.clientCreateFoliageChunkEntity(foliageTypesSupported,scale,this.getRealPos(),worldPos,voxelPos,notifyTarget,oldEntity);
|
||||||
FoliageModel.clientCreateFoliageChunkEntity(foliageTypesSupported,scale,this.modelEntity,this.getRealPos(),worldPos,voxelPos,notifyTarget,oldEntity);
|
|
||||||
} else {
|
} else {
|
||||||
|
if(this.modelEntity != null){
|
||||||
|
ClientEntityUtils.destroyEntity(this.modelEntity);
|
||||||
|
this.modelEntity = null;
|
||||||
|
}
|
||||||
this.homogenous = true;
|
this.homogenous = true;
|
||||||
}
|
}
|
||||||
this.hasGenerated = true;
|
this.hasGenerated = true;
|
||||||
@ -650,6 +648,13 @@ public class FoliageCell {
|
|||||||
this.failedGenerationAttempts = this.failedGenerationAttempts + attempts;
|
this.failedGenerationAttempts = this.failedGenerationAttempts + attempts;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Ejects the chunk data
|
||||||
|
*/
|
||||||
|
public void ejectChunkData(){
|
||||||
|
this.chunkData = null;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets whether this foliage cell is homogenous or not
|
* Gets whether this foliage cell is homogenous or not
|
||||||
* @return true if it is homogenous, false otherwise
|
* @return true if it is homogenous, false otherwise
|
||||||
|
|||||||
@ -723,9 +723,18 @@ public class FoliageCellManager {
|
|||||||
* @param worldX The world x position
|
* @param worldX The world x position
|
||||||
* @param worldY The world y position
|
* @param worldY The world y position
|
||||||
* @param worldZ The world z position
|
* @param worldZ The world z position
|
||||||
|
* @param voxelX The voxel x position
|
||||||
|
* @param voxelY The voxel y position
|
||||||
|
* @param voxelZ The voxel z position
|
||||||
*/
|
*/
|
||||||
public void markUpdateable(float worldX, float worldY, float worldZ){
|
public void markUpdateable(int worldX, int worldY, int worldZ, int voxelX, int voxelY, int voxelZ){
|
||||||
throw new Error("Unimplemented");
|
int absVoxelX = Globals.clientWorldData.convertRelativeVoxelToAbsoluteVoxelSpace(voxelX,worldX);
|
||||||
|
int absVoxelY = Globals.clientWorldData.convertRelativeVoxelToAbsoluteVoxelSpace(voxelY,worldY);
|
||||||
|
int absVoxelZ = Globals.clientWorldData.convertRelativeVoxelToAbsoluteVoxelSpace(voxelZ,worldZ);
|
||||||
|
FoliageCell foliageCell = this.getFoliageCell(absVoxelX, absVoxelY, absVoxelZ);
|
||||||
|
foliageCell.ejectChunkData();
|
||||||
|
foliageCell.setHasGenerated(false);
|
||||||
|
foliageCell.setHasRequested(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@ -137,7 +137,6 @@ public class FoliageModel {
|
|||||||
public static Entity clientCreateFoliageChunkEntity(
|
public static Entity clientCreateFoliageChunkEntity(
|
||||||
List<String> foliageTypesSupported,
|
List<String> foliageTypesSupported,
|
||||||
int scale,
|
int scale,
|
||||||
Entity modelEntity,
|
|
||||||
Vector3d realPos,
|
Vector3d realPos,
|
||||||
Vector3i worldPos,
|
Vector3i worldPos,
|
||||||
Vector3i voxelPos,
|
Vector3i voxelPos,
|
||||||
@ -218,11 +217,17 @@ public class FoliageModel {
|
|||||||
QueuedTexture queuedAsset = new QueuedTexture(buffer,textureWidth,textureHeight);
|
QueuedTexture queuedAsset = new QueuedTexture(buffer,textureWidth,textureHeight);
|
||||||
Globals.assetManager.queuedAsset(queuedAsset);
|
Globals.assetManager.queuedAsset(queuedAsset);
|
||||||
|
|
||||||
TextureInstancedActor.attachTextureInstancedActor(modelEntity, foliageType.getGraphicsTemplate().getModel().getPath(), vertexPath, fragmentPath, queuedAsset, drawCount, textureHeight);
|
TextureInstancedActor.attachTextureInstancedActor(rVal, foliageType.getGraphicsTemplate().getModel().getPath(), vertexPath, fragmentPath, queuedAsset, drawCount, textureHeight);
|
||||||
ClientEntityUtils.initiallyPositionEntity(modelEntity, realPos, new Quaterniond());
|
ClientEntityUtils.initiallyPositionEntity(rVal, realPos, new Quaterniond());
|
||||||
EntityUtils.getScale(modelEntity).set(1,1,1);
|
EntityUtils.getScale(rVal).set(1,1,1);
|
||||||
//add ambient foliage behavior tree
|
//add ambient foliage behavior tree
|
||||||
AmbientFoliage.attachAmbientFoliageTree(modelEntity, 1.0f, foliageType.getGrowthModel().getGrowthRate());
|
AmbientFoliage.attachAmbientFoliageTree(rVal, 1.0f, foliageType.getGrowthModel().getGrowthRate());
|
||||||
|
}
|
||||||
|
if(toDelete != null){
|
||||||
|
ClientEntityUtils.destroyEntity(toDelete);
|
||||||
|
}
|
||||||
|
if(notifyTarget != null){
|
||||||
|
notifyTarget.alertToGeneration();
|
||||||
}
|
}
|
||||||
} catch (Error e){
|
} catch (Error e){
|
||||||
LoggerInterface.loggerEngine.ERROR(e);
|
LoggerInterface.loggerEngine.ERROR(e);
|
||||||
|
|||||||
@ -10,6 +10,7 @@ import electrosphere.entity.state.attach.AttachUtils;
|
|||||||
import electrosphere.entity.state.hitbox.HitboxCollectionState;
|
import electrosphere.entity.state.hitbox.HitboxCollectionState;
|
||||||
import electrosphere.entity.types.collision.CollisionObjUtils;
|
import electrosphere.entity.types.collision.CollisionObjUtils;
|
||||||
import electrosphere.renderer.actor.ActorUtils;
|
import electrosphere.renderer.actor.ActorUtils;
|
||||||
|
import electrosphere.renderer.actor.instance.TextureInstancedActor;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Client only entity utility functions
|
* Client only entity utility functions
|
||||||
@ -55,6 +56,12 @@ public class ClientEntityUtils {
|
|||||||
//deregister all behavior trees
|
//deregister all behavior trees
|
||||||
EntityUtils.cleanUpEntity(entity);
|
EntityUtils.cleanUpEntity(entity);
|
||||||
|
|
||||||
|
//instanced actor
|
||||||
|
if(TextureInstancedActor.getTextureInstancedActor(entity) != null){
|
||||||
|
TextureInstancedActor actor = TextureInstancedActor.getTextureInstancedActor(entity);
|
||||||
|
actor.free();
|
||||||
|
}
|
||||||
|
|
||||||
if(Globals.clientSceneWrapper != null){
|
if(Globals.clientSceneWrapper != null){
|
||||||
Globals.clientSceneWrapper.getScene().deregisterEntity(entity);
|
Globals.clientSceneWrapper.getScene().deregisterEntity(entity);
|
||||||
Globals.clientSceneWrapper.deregisterTranslationMapping(entity);
|
Globals.clientSceneWrapper.deregisterTranslationMapping(entity);
|
||||||
|
|||||||
@ -107,13 +107,67 @@ public class TerrainProtocol implements ClientProtocolTemplate<TerrainMessage> {
|
|||||||
//
|
//
|
||||||
//mark all relevant drawcells as updateable
|
//mark all relevant drawcells as updateable
|
||||||
for(Vector3i worldPosToUpdate : positionsToUpdate){
|
for(Vector3i worldPosToUpdate : positionsToUpdate){
|
||||||
if(Globals.clientTerrainManager.containsChunkDataAtWorldPoint(worldPosToUpdate.x, worldPosToUpdate.y, worldPosToUpdate.z, ChunkData.NO_STRIDE)){
|
if(
|
||||||
ChunkData data = Globals.clientTerrainManager.getChunkDataAtWorldPoint(worldPosToUpdate.x, worldPosToUpdate.y, worldPosToUpdate.z, ChunkData.NO_STRIDE);
|
worldPosToUpdate.x >= 0 && worldPosToUpdate.x < Globals.clientWorldData.getWorldDiscreteSize() &&
|
||||||
if(data != null){
|
worldPosToUpdate.y >= 0 && worldPosToUpdate.y < Globals.clientWorldData.getWorldDiscreteSize() &&
|
||||||
Globals.clientDrawCellManager.markUpdateable(worldPosToUpdate.x, worldPosToUpdate.y, worldPosToUpdate.z);
|
worldPosToUpdate.z >= 0 && worldPosToUpdate.z < Globals.clientWorldData.getWorldDiscreteSize()
|
||||||
|
){
|
||||||
|
//
|
||||||
|
//mark terrain chunk for update
|
||||||
|
Globals.clientDrawCellManager.markUpdateable(worldPosToUpdate.x, worldPosToUpdate.y, worldPosToUpdate.z);
|
||||||
|
|
||||||
|
//
|
||||||
|
//update foliage manager
|
||||||
|
Globals.foliageCellManager.markUpdateable(
|
||||||
|
worldPosToUpdate.x, worldPosToUpdate.y, worldPosToUpdate.z,
|
||||||
|
message.getvoxelX(), message.getvoxelY(), message.getvoxelZ()
|
||||||
|
);
|
||||||
|
if(message.getvoxelX() > 0){
|
||||||
|
Globals.foliageCellManager.markUpdateable(
|
||||||
|
worldPosToUpdate.x, worldPosToUpdate.y, worldPosToUpdate.z,
|
||||||
|
message.getvoxelX() - 1, message.getvoxelY(), message.getvoxelZ()
|
||||||
|
);
|
||||||
|
if(message.getvoxelY() > 0){
|
||||||
|
Globals.foliageCellManager.markUpdateable(
|
||||||
|
worldPosToUpdate.x, worldPosToUpdate.y, worldPosToUpdate.z,
|
||||||
|
message.getvoxelX() - 1, message.getvoxelY() - 1, message.getvoxelZ()
|
||||||
|
);
|
||||||
|
if(message.getvoxelZ() > 0){
|
||||||
|
Globals.foliageCellManager.markUpdateable(
|
||||||
|
worldPosToUpdate.x, worldPosToUpdate.y, worldPosToUpdate.z,
|
||||||
|
message.getvoxelX() - 1, message.getvoxelY() - 1, message.getvoxelZ() - 1
|
||||||
|
);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if(message.getvoxelZ() > 0){
|
||||||
|
Globals.foliageCellManager.markUpdateable(
|
||||||
|
worldPosToUpdate.x, worldPosToUpdate.y, worldPosToUpdate.z,
|
||||||
|
message.getvoxelX() - 1, message.getvoxelY(), message.getvoxelZ() - 1
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if(message.getvoxelY() > 0){
|
||||||
|
Globals.foliageCellManager.markUpdateable(
|
||||||
|
worldPosToUpdate.x, worldPosToUpdate.y, worldPosToUpdate.z,
|
||||||
|
message.getvoxelX(), message.getvoxelY() - 1, message.getvoxelZ()
|
||||||
|
);
|
||||||
|
if(message.getvoxelZ() > 0){
|
||||||
|
Globals.foliageCellManager.markUpdateable(
|
||||||
|
worldPosToUpdate.x, worldPosToUpdate.y, worldPosToUpdate.z,
|
||||||
|
message.getvoxelX(), message.getvoxelY() - 1, message.getvoxelZ() - 1
|
||||||
|
);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if(message.getvoxelZ() > 0){
|
||||||
|
Globals.foliageCellManager.markUpdateable(
|
||||||
|
worldPosToUpdate.x, worldPosToUpdate.y, worldPosToUpdate.z,
|
||||||
|
message.getvoxelX(), message.getvoxelY(), message.getvoxelZ() - 1
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// Globals.clientFoliageManager.evaluateChunk(worldPos);
|
|
||||||
}
|
}
|
||||||
} break;
|
} break;
|
||||||
case SENDFLUIDDATA: {
|
case SENDFLUIDDATA: {
|
||||||
|
|||||||
@ -28,13 +28,13 @@ public class TerrainProtocol implements ServerProtocolTemplate<TerrainMessage> {
|
|||||||
public TerrainMessage handleAsyncMessage(ServerConnectionHandler connectionHandler, TerrainMessage message) {
|
public TerrainMessage handleAsyncMessage(ServerConnectionHandler connectionHandler, TerrainMessage message) {
|
||||||
switch(message.getMessageSubtype()){
|
switch(message.getMessageSubtype()){
|
||||||
case REQUESTCHUNKDATA: {
|
case REQUESTCHUNKDATA: {
|
||||||
sendWorldSubChunkAsync(connectionHandler,
|
TerrainProtocol.sendWorldSubChunkAsync(connectionHandler,
|
||||||
message.getworldX(), message.getworldY(), message.getworldZ()
|
message.getworldX(), message.getworldY(), message.getworldZ()
|
||||||
);
|
);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
case REQUESTREDUCEDCHUNKDATA: {
|
case REQUESTREDUCEDCHUNKDATA: {
|
||||||
sendWorldSubChunkAsyncStrided(connectionHandler,
|
TerrainProtocol.sendWorldSubChunkAsyncStrided(connectionHandler,
|
||||||
message.getworldX(), message.getworldY(), message.getworldZ(), message.getchunkResolution()
|
message.getworldX(), message.getworldY(), message.getworldZ(), message.getchunkResolution()
|
||||||
);
|
);
|
||||||
return null;
|
return null;
|
||||||
@ -49,25 +49,25 @@ public class TerrainProtocol implements ServerProtocolTemplate<TerrainMessage> {
|
|||||||
public void handleSyncMessage(ServerConnectionHandler connectionHandler, TerrainMessage message) {
|
public void handleSyncMessage(ServerConnectionHandler connectionHandler, TerrainMessage message) {
|
||||||
switch(message.getMessageSubtype()){
|
switch(message.getMessageSubtype()){
|
||||||
case REQUESTMETADATA: {
|
case REQUESTMETADATA: {
|
||||||
sendWorldMetadata(connectionHandler);
|
TerrainProtocol.sendWorldMetadata(connectionHandler);
|
||||||
} break;
|
} break;
|
||||||
case REQUESTCHUNKDATA: {
|
case REQUESTCHUNKDATA: {
|
||||||
LoggerInterface.loggerNetworking.DEBUG("(Server) Received request for terrain " + message.getworldX() + " " + message.getworldY() + " " + message.getworldZ());
|
LoggerInterface.loggerNetworking.DEBUG("(Server) Received request for terrain " + message.getworldX() + " " + message.getworldY() + " " + message.getworldZ());
|
||||||
// System.out.println("Received request for terrain " + message.getworldX() + " " + message.getworldY() + " " + message.getworldZ());
|
// System.out.println("Received request for terrain " + message.getworldX() + " " + message.getworldY() + " " + message.getworldZ());
|
||||||
sendWorldSubChunk(connectionHandler,
|
TerrainProtocol.sendWorldSubChunk(connectionHandler,
|
||||||
message.getworldX(), message.getworldY(), message.getworldZ()
|
message.getworldX(), message.getworldY(), message.getworldZ()
|
||||||
);
|
);
|
||||||
} break;
|
} break;
|
||||||
case REQUESTEDITVOXEL: {
|
case REQUESTEDITVOXEL: {
|
||||||
attemptTerrainEdit(connectionHandler, message);
|
TerrainProtocol.attemptTerrainEdit(connectionHandler, message);
|
||||||
} break;
|
} break;
|
||||||
case REQUESTUSETERRAINPALETTE: {
|
case REQUESTUSETERRAINPALETTE: {
|
||||||
attemptUseTerrainEditPalette(connectionHandler, message);
|
TerrainProtocol.attemptUseTerrainEditPalette(connectionHandler, message);
|
||||||
} break;
|
} break;
|
||||||
case REQUESTFLUIDDATA: {
|
case REQUESTFLUIDDATA: {
|
||||||
LoggerInterface.loggerNetworking.DEBUG("(Server) Received request for fluid " + message.getworldX() + " " + message.getworldY() + " " + message.getworldZ());
|
LoggerInterface.loggerNetworking.DEBUG("(Server) Received request for fluid " + message.getworldX() + " " + message.getworldY() + " " + message.getworldZ());
|
||||||
// System.out.println("Received request for fluid " + message.getworldX() + " " + message.getworldY() + " " + message.getworldZ());
|
// System.out.println("Received request for fluid " + message.getworldX() + " " + message.getworldY() + " " + message.getworldZ());
|
||||||
sendWorldFluidSubChunk(connectionHandler,
|
TerrainProtocol.sendWorldFluidSubChunk(connectionHandler,
|
||||||
message.getworldX(), message.getworldY(), message.getworldZ()
|
message.getworldX(), message.getworldY(), message.getworldZ()
|
||||||
);
|
);
|
||||||
} break;
|
} break;
|
||||||
|
|||||||
@ -185,4 +185,13 @@ public class TextureInstancedActor {
|
|||||||
model.setWorldPos(worldPos);
|
model.setWorldPos(worldPos);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Frees the texture instanced actor
|
||||||
|
*/
|
||||||
|
public void free(){
|
||||||
|
if(this.queuedTexture != null && this.queuedTexture.getTexture() != null){
|
||||||
|
Globals.assetManager.queueTextureForDeletion(this.queuedTexture.getTexture().getPath());
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -653,8 +653,6 @@ public class GriddedDataCellManager implements DataCellManager, VoxelCellManager
|
|||||||
*/
|
*/
|
||||||
public void editChunk(Vector3i worldPosition, Vector3i voxelPosition, float weight, int type) {
|
public void editChunk(Vector3i worldPosition, Vector3i voxelPosition, float weight, int type) {
|
||||||
terrainEditLock.acquireUninterruptibly();
|
terrainEditLock.acquireUninterruptibly();
|
||||||
//update terrain
|
|
||||||
serverTerrainManager.deformTerrainAtLocationToValue(worldPosition, voxelPosition, weight, type);
|
|
||||||
List<Vector3i> worldPositionsToUpdate = new LinkedList<Vector3i>();
|
List<Vector3i> worldPositionsToUpdate = new LinkedList<Vector3i>();
|
||||||
worldPositionsToUpdate.add(worldPosition);
|
worldPositionsToUpdate.add(worldPosition);
|
||||||
if(voxelPosition.x < 1){
|
if(voxelPosition.x < 1){
|
||||||
@ -664,32 +662,45 @@ public class GriddedDataCellManager implements DataCellManager, VoxelCellManager
|
|||||||
if(voxelPosition.z < 1){
|
if(voxelPosition.z < 1){
|
||||||
worldPositionsToUpdate.add(new Vector3i(worldPosition).sub(1,1,1));
|
worldPositionsToUpdate.add(new Vector3i(worldPosition).sub(1,1,1));
|
||||||
}
|
}
|
||||||
} else {
|
|
||||||
if(voxelPosition.z < 1){
|
|
||||||
worldPositionsToUpdate.add(new Vector3i(worldPosition).sub(1,0,1));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
} else {
|
if(voxelPosition.z < 1){
|
||||||
if(voxelPosition.y < 1){
|
worldPositionsToUpdate.add(new Vector3i(worldPosition).sub(1,0,1));
|
||||||
worldPositionsToUpdate.add(new Vector3i(worldPosition).sub(0,1,0));
|
|
||||||
if(voxelPosition.z < 1){
|
|
||||||
worldPositionsToUpdate.add(new Vector3i(worldPosition).sub(0,1,1));
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if(voxelPosition.z < 1){
|
|
||||||
worldPositionsToUpdate.add(new Vector3i(worldPosition).sub(0,0,1));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if(voxelPosition.y < 1){
|
||||||
|
worldPositionsToUpdate.add(new Vector3i(worldPosition).sub(0,1,0));
|
||||||
|
if(voxelPosition.z < 1){
|
||||||
|
worldPositionsToUpdate.add(new Vector3i(worldPosition).sub(0,1,1));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(voxelPosition.z < 1){
|
||||||
|
worldPositionsToUpdate.add(new Vector3i(worldPosition).sub(0,0,1));
|
||||||
|
}
|
||||||
//update all loaded cells
|
//update all loaded cells
|
||||||
for(Vector3i toUpdate : worldPositionsToUpdate){
|
for(Vector3i toUpdate : worldPositionsToUpdate){
|
||||||
ServerDataCell cell = groundDataCells.get(getServerDataCellKey(toUpdate));
|
if(
|
||||||
if(cell != null){
|
toUpdate.x >= 0 && toUpdate.x < this.serverWorldData.getWorldSizeDiscrete() &&
|
||||||
this.createTerrainPhysicsEntities(toUpdate);
|
toUpdate.y >= 0 && toUpdate.y < this.serverWorldData.getWorldSizeDiscrete() &&
|
||||||
cell.broadcastNetworkMessage(TerrainMessage.constructUpdateVoxelMessage(
|
toUpdate.z >= 0 && toUpdate.z < this.serverWorldData.getWorldSizeDiscrete()
|
||||||
worldPosition.x, worldPosition.y, worldPosition.z,
|
){
|
||||||
voxelPosition.x, voxelPosition.y, voxelPosition.z,
|
//update terrain
|
||||||
weight, type));
|
int localVoxelX = voxelPosition.x + (ServerTerrainChunk.CHUNK_DATA_GENERATOR_SIZE - 1) * (worldPosition.x - toUpdate.x);
|
||||||
|
int localVoxelY = voxelPosition.y + (ServerTerrainChunk.CHUNK_DATA_GENERATOR_SIZE - 1) * (worldPosition.y - toUpdate.y);
|
||||||
|
int localVoxelZ = voxelPosition.z + (ServerTerrainChunk.CHUNK_DATA_GENERATOR_SIZE - 1) * (worldPosition.z - toUpdate.z);
|
||||||
|
serverTerrainManager.deformTerrainAtLocationToValue(toUpdate, new Vector3i(localVoxelX, localVoxelY, localVoxelZ), weight, type);
|
||||||
|
|
||||||
|
//update anything loaded
|
||||||
|
ServerDataCell cell = groundDataCells.get(this.getServerDataCellKey(toUpdate));
|
||||||
|
if(cell != null){
|
||||||
|
//update physics
|
||||||
|
this.createTerrainPhysicsEntities(toUpdate);
|
||||||
|
|
||||||
|
//broadcast update
|
||||||
|
cell.broadcastNetworkMessage(TerrainMessage.constructUpdateVoxelMessage(
|
||||||
|
toUpdate.x, toUpdate.y, toUpdate.z,
|
||||||
|
localVoxelX, localVoxelY, localVoxelZ,
|
||||||
|
weight, type));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
terrainEditLock.release();
|
terrainEditLock.release();
|
||||||
|
|||||||
@ -223,7 +223,7 @@ public class WorldOctTree <T> {
|
|||||||
){
|
){
|
||||||
throw new Error("Trying to search for node outside tree range!");
|
throw new Error("Trying to search for node outside tree range!");
|
||||||
}
|
}
|
||||||
WorldOctTreeNode<T> searchResult = recursiveSearchUnsafe(root,position,maxLevel);
|
WorldOctTreeNode<T> searchResult = this.recursiveSearchUnsafe(root,position,maxLevel);
|
||||||
if(!returnNonLeaf && !searchResult.isLeaf()){
|
if(!returnNonLeaf && !searchResult.isLeaf()){
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user