diff --git a/assets/Data/symbolism.json b/assets/Data/symbolism.json index 85defb2b..1f6227f0 100644 --- a/assets/Data/symbolism.json +++ b/assets/Data/symbolism.json @@ -9,6 +9,15 @@ } ] }, + { + "name" : "water", + "relations" : [ + { + "name" : "fire", + "strength" : -1 + } + ] + }, { "name" : "water", "relations" : [ diff --git a/src/main/java/electrosphere/engine/LoadingThread.java b/src/main/java/electrosphere/engine/LoadingThread.java index 202d3112..37a2a9d6 100644 --- a/src/main/java/electrosphere/engine/LoadingThread.java +++ b/src/main/java/electrosphere/engine/LoadingThread.java @@ -271,13 +271,13 @@ public class LoadingThread extends Thread { Actually initialize the terrain manager */ float[][] elevation; - Globals.serverTerrainManager = new ServerTerrainManager(2000,200,100,0.25f,0); + Globals.serverTerrainManager = new ServerTerrainManager(2000,50,100,0.25f,0); if(Globals.RUN_SERVER){ if(Globals.LOAD_TERRAIN){ Globals.serverTerrainManager.load(); } else { Globals.serverTerrainManager.generate(); - Globals.serverTerrainManager.save(); +// Globals.serverTerrainManager.save(); } } @@ -291,7 +291,7 @@ public class LoadingThread extends Thread { boolean found = false; for(int x = 0; x < discreteSize; x++){ for(int y = 0; y < discreteSize; y++){ - if(Globals.serverTerrainManager.getDiscreteValue(x, y)>0){ + if(Globals.serverTerrainManager.getDiscreteValue(x, y)>1000){ playerStartX = x; playerStartY = y; found = true; @@ -305,7 +305,7 @@ public class LoadingThread extends Thread { } } - Globals.spawnPoint = new Vector3f(playerStartX * chunkSize,0,playerStartY * chunkSize); + Globals.spawnPoint = new Vector3f(playerStartX * chunkSize, Globals.serverTerrainManager.getHeightAtPosition(playerStartX * chunkSize,playerStartY * chunkSize), playerStartY * chunkSize); @@ -404,6 +404,13 @@ public class LoadingThread extends Thread { } // System.out.println("undrawable"); } + + while(Globals.drawCellManager.containsPhysicsNeedingCell()){ + try { + TimeUnit.MILLISECONDS.sleep(10); + } catch (InterruptedException ex) { + } + } } diff --git a/src/main/java/electrosphere/game/client/drawcell/DrawCell.java b/src/main/java/electrosphere/game/client/drawcell/DrawCell.java index 096f412a..fa9dfdac 100644 --- a/src/main/java/electrosphere/game/client/drawcell/DrawCell.java +++ b/src/main/java/electrosphere/game/client/drawcell/DrawCell.java @@ -1,8 +1,11 @@ package electrosphere.game.client.drawcell; +import com.bulletphysics.collision.dispatch.CollisionObject; +import com.bulletphysics.dynamics.RigidBody; import electrosphere.entity.Entity; import electrosphere.entity.EntityUtils; import electrosphere.game.collision.PhysicsUtils; +import electrosphere.game.collision.collidable.Collidable; import electrosphere.game.terrain.processing.TerrainInterpolator; import electrosphere.logger.LoggerInterface; import electrosphere.main.Globals; @@ -29,6 +32,8 @@ public class DrawCell { ShaderProgram program; + CollisionObject physicsObject; + @@ -82,12 +87,21 @@ public class DrawCell { modelEntity = EntityUtils.spawnDrawableEntity(terrainModelPath); LoggerInterface.loggerRenderer.INFO("New cell @ " + cellX * dynamicInterpolationRatio + "," + cellY * dynamicInterpolationRatio); EntityUtils.getPosition(modelEntity).set(new Vector3f(cellX * dynamicInterpolationRatio, 0.0f, cellY * dynamicInterpolationRatio)); - PhysicsUtils.attachTerrainRigidBody(modelEntity,heightmap); - Globals.collisionEngine.registerPhysicsEntity(modelEntity); } public void retireCell(){ EntityUtils.cleanUpDrawableEntity(modelEntity); } + public void generatePhysics(){ + physicsObject = PhysicsUtils.attachTerrainRigidBody(modelEntity,heightmap); + Globals.collisionEngine.registerPhysicsEntity(modelEntity); +// System.out.println("generate physics"); + } + + public void destroyPhysics(){ + Globals.collisionEngine.deregisterCollidableEntity(modelEntity); + Globals.collisionEngine.deregisterRigidBody((RigidBody)physicsObject); + } + } diff --git a/src/main/java/electrosphere/game/client/drawcell/DrawCellManager.java b/src/main/java/electrosphere/game/client/drawcell/DrawCellManager.java index 6b19ed93..893190ee 100644 --- a/src/main/java/electrosphere/game/client/drawcell/DrawCellManager.java +++ b/src/main/java/electrosphere/game/client/drawcell/DrawCellManager.java @@ -35,15 +35,19 @@ public class DrawCellManager { boolean[][] drawable; boolean[][] updateable; boolean[][] hasRequested; + boolean[][] needsPhysics; + boolean[][] hasPhysics; ShaderProgram program; - int drawRadius = 5; + int drawRadius = 35; int drawStepdownInterval = 3; - int drawStepdownValue = 5; + int drawStepdownValue = 25; + + int physicsRadius = 3; int worldBoundDiscreteMin = 0; int worldBoundDiscreteMax = 0; @@ -70,6 +74,8 @@ public class DrawCellManager { drawable = new boolean[drawRadius * 2 + 1][drawRadius * 2 + 1]; updateable = new boolean[drawRadius * 2 + 1][drawRadius * 2 + 1]; hasRequested = new boolean[drawRadius * 2 + 1][drawRadius * 2 + 1]; + needsPhysics = new boolean[physicsRadius * 2 + 1][physicsRadius * 2 + 1]; + hasPhysics = new boolean[physicsRadius * 2 + 1][physicsRadius * 2 + 1]; for(int x = 0; x < drawRadius * 2 + 1; x++){ for(int y = 0; y < drawRadius * 2 + 1; y++){ valid[x][y] = false; @@ -78,6 +84,12 @@ public class DrawCellManager { hasRequested[x][y] = false; } } + for(int x = 0; x < physicsRadius * 2 + 1; x++){ + for(int y = 0; y < physicsRadius * 2 + 1; y++){ + needsPhysics[x][y] = true; + hasPhysics[x][y] = false; + } + } cellX = discreteX; cellY = discreteY; @@ -147,6 +159,9 @@ public class DrawCellManager { drawable[targetX][targetY] = false; updateable[targetX][targetY] = false; hasRequested[targetX][targetY] = false; +// if(Math.abs(physicsRadius + 1 - targetX) < physicsRadius && Math.abs(physicsRadius + 1 - targetY) < physicsRadius){ +// needsPhysics[targetX][targetY] = true; +// } } else { if(hasRequested[targetX][targetY] == false){ //client should request macro values from server @@ -190,6 +205,10 @@ public class DrawCellManager { currentCellY >= 0 && currentCellY < clientWorldData.getWorldDiscreteSize() ){ + //physics radius calculation +// if(Math.abs(physicsRadius + 1 - targetX) < physicsRadius && Math.abs(physicsRadius + 1 - targetY) < physicsRadius){ +// needsPhysics[targetX][targetY] = true; +// } //calculation for stride int dist = (int)Math.sqrt((targetX - drawRadius)*(targetX - drawRadius) + (targetY - drawRadius) * (targetY - drawRadius));//Math.abs(targetX - drawRadius) * Math.abs(targetY - drawRadius); int stride = Math.min(clientWorldData.getDynamicInterpolationRatio()/2, Math.max(1, dist / drawStepdownInterval * drawStepdownValue)); @@ -230,6 +249,9 @@ public class DrawCellManager { currentCellY >= 0 && currentCellY < clientWorldData.getWorldDiscreteSize() ){ +// if(Math.abs(drawRadius + 1 - targetX) < physicsRadius && Math.abs(drawRadius + 1 - targetY) < physicsRadius){ +// needsPhysics[targetX][targetY] = true; +// } int dist = (int)Math.sqrt((targetX - drawRadius)*(targetX - drawRadius) + (targetY - drawRadius) * (targetY - drawRadius)); //Math.abs(targetX - drawRadius) * Math.abs(targetY - drawRadius); int stride = Math.min(clientWorldData.getDynamicInterpolationRatio()/2, Math.max(1, dist / drawStepdownInterval * drawStepdownValue)); while(clientWorldData.getDynamicInterpolationRatio() % stride != 0){ @@ -280,13 +302,74 @@ public class DrawCellManager { return false; } + public boolean containsPhysicsNeedingCell(){ + for(int x = 0; x < physicsRadius * 2 + 1; x++){ + for(int y = 0; y < physicsRadius * 2 + 1; y++){ + if(needsPhysics[x][y]){ + return true; + } + } + } + return false; + } + + public void addPhysicsToCell(){ + int targetX = 0; + int targetY = 0; + boolean found = false; + for(int x = 0; x < physicsRadius * 2 + 1; x++){ + targetX = x; + for(int y = 0; y < physicsRadius * 2 + 1; y++){ + targetY = y; +// System.out.println(x + " <=>w " + y); + if(needsPhysics[x][y]){ + found = true; + break; + } + } + if(found){ + break; + } + } + + if(found){ + int currentCellX = cellX - physicsRadius + targetX; + int currentCellY = cellY - physicsRadius + targetY; + if( + currentCellX >= 0 && + currentCellX < clientWorldData.getWorldDiscreteSize() && + currentCellY >= 0 && + currentCellY < clientWorldData.getWorldDiscreteSize() + ){ +// if(Math.abs(drawRadius + 1 - targetX) < physicsRadius && Math.abs(drawRadius + 1 - targetY) < physicsRadius){ +// needsPhysics[targetX][targetY] = true; +// } +// int dist = (int)Math.sqrt((targetX - drawRadius)*(targetX - drawRadius) + (targetY - drawRadius) * (targetY - drawRadius)); //Math.abs(targetX - drawRadius) * Math.abs(targetY - drawRadius); +// int stride = Math.min(clientWorldData.getDynamicInterpolationRatio()/2, Math.max(1, dist / drawStepdownInterval * drawStepdownValue)); +// while(clientWorldData.getDynamicInterpolationRatio() % stride != 0){ +// stride = stride + 1; +// } +// if(cells[targetX][targetY + drawRadius] != null){ +// System.out.println(targetX + " - " + targetY); + cells[targetX + drawRadius - physicsRadius][targetY + drawRadius - physicsRadius].generatePhysics(); +// } else { +// System.out.println("Current cell is null: " + currentCellX + " - " + currentCellY); +// } + } + needsPhysics[targetX][targetY] = false; + hasPhysics[targetX][targetY] = true; + } + } + public void shiftChunksNegX(){ + //retire old graphics for(int y = 0; y < drawRadius * 2 + 1; y++){ if(cells[drawRadius * 2][y] != null){ cells[drawRadius * 2][y].retireCell(); } } + //shift draw array for(int x = drawRadius * 2; x > 0; x--){ for(int y = 0; y < drawRadius * 2 + 1; y++){ cells[x][y] = cells[x-1][y]; @@ -294,18 +377,39 @@ public class DrawCellManager { hasRequested[x][y] = hasRequested[x-1][y]; } } + //invalidate edge of draw array for(int y = 0; y < drawRadius * 2 + 1; y++){ valid[0][y] = false; hasRequested[0][y] = false; } + //retire physics of cells + for(int x = 0; x < physicsRadius * 2 + 1; x++){ + if(hasPhysics[x][physicsRadius * 2]){ + cells[x + drawRadius - physicsRadius][physicsRadius * 2 + drawRadius - physicsRadius].destroyPhysics(); + } + } + //shift physics array + for(int x = physicsRadius * 2; x > 0; x--){ + for(int y = 0; y < physicsRadius * 2 + 1; y++){ + needsPhysics[x][y] = needsPhysics[x-1][y]; + hasPhysics[x][y] = hasPhysics[x-1][y]; + } + } + //invalidate edge of physics array + for(int y = 0; y < physicsRadius * 2 + 1; y++){ + needsPhysics[0][y] = true; + hasPhysics[0][y] = false; + } } public void shiftChunksPosX(){ + //retire old graphics for(int y = 0; y < drawRadius * 2 + 1; y++){ if(cells[0][y] != null){ cells[0][y].retireCell(); } } + //shift draw array for(int x = 0; x < drawRadius * 2; x++){ for(int y = 0; y < drawRadius * 2 + 1; y++){ cells[x][y] = cells[x+1][y]; @@ -313,18 +417,39 @@ public class DrawCellManager { hasRequested[x][y] = hasRequested[x+1][y]; } } + //invalidate edge of draw array for(int y = 0; y < drawRadius * 2 + 1; y++){ valid[drawRadius * 2][y] = false; hasRequested[drawRadius * 2][y] = false; } + //retire physics of cells + for(int x = 0; x < physicsRadius * 2 + 1; x++){ + if(hasPhysics[x][physicsRadius * 2]){ + cells[x + drawRadius - physicsRadius][physicsRadius * 2 + drawRadius - physicsRadius].destroyPhysics(); + } + } + //shift physics array + for(int x = 0; x < physicsRadius * 2; x++){ + for(int y = 0; y < physicsRadius * 2 + 1; y++){ + needsPhysics[x][y] = needsPhysics[x+1][y]; + hasPhysics[x][y] = hasPhysics[x+1][y]; + } + } + //invalidate edge of physics array + for(int y = 0; y < physicsRadius * 2 + 1; y++){ + needsPhysics[physicsRadius * 2][y] = true; + hasPhysics[physicsRadius * 2][y] = false; + } } public void shiftChunksNegY(){ + //retire cells for(int x = 0; x < drawRadius * 2 + 1; x++){ if(cells[x][drawRadius * 2] != null){ cells[x][drawRadius * 2].retireCell(); } } + //shift draw array for(int x = 0; x < drawRadius * 2 + 1; x++){ for(int y = drawRadius * 2; y > 0; y--){ cells[x][y] = cells[x][y-1]; @@ -332,18 +457,39 @@ public class DrawCellManager { hasRequested[x][y] = hasRequested[x][y-1]; } } + //invalidate edge of draw array for(int x = 0; x < drawRadius * 2 + 1; x++){ valid[x][0] = false; hasRequested[x][0] = false; } + //retire physics of cells + for(int x = 0; x < physicsRadius * 2 + 1; x++){ + if(hasPhysics[x][physicsRadius * 2]){ + cells[x + drawRadius - physicsRadius][physicsRadius * 2 + drawRadius - physicsRadius].destroyPhysics(); + } + } + //shift physics array + for(int x = 0; x < physicsRadius * 2 + 1; x++){ + for(int y = physicsRadius * 2; y > 0; y--){ + needsPhysics[x][y] = needsPhysics[x][y-1]; + hasPhysics[x][y] = hasPhysics[x][y-1]; + } + } + //invalidate edge of physics array + for(int x = 0; x < physicsRadius * 2 + 1; x++){ + needsPhysics[x][0] = true; + hasPhysics[x][0] = false; + } } public void shiftChunksPosY(){ + //retire old graphics for(int x = 0; x < drawRadius * 2 + 1; x++){ if(cells[x][0] != null){ cells[x][0].retireCell(); } } + //shift draw array for(int x = 0; x < drawRadius * 2 + 1; x++){ for(int y = 0; y < drawRadius * 2; y++){ cells[x][y] = cells[x][y+1]; @@ -351,10 +497,29 @@ public class DrawCellManager { hasRequested[x][y] = hasRequested[x][y+1]; } } + //invalidate edge of draw array for(int x = 0; x < drawRadius * 2 + 1; x++){ valid[x][drawRadius * 2] = false; hasRequested[x][drawRadius * 2] = false; } + //retire physics of cells + for(int x = 0; x < physicsRadius * 2 + 1; x++){ + if(hasPhysics[x][0]){ + cells[x + drawRadius - physicsRadius][0 + drawRadius - physicsRadius].destroyPhysics(); + } + } + //shift physics array + for(int x = 0; x < physicsRadius * 2 + 1; x++){ + for(int y = 0; y < physicsRadius * 2; y++){ + needsPhysics[x][y] = needsPhysics[x][y+1]; + hasPhysics[x][y] = hasPhysics[x][y+1]; + } + } + //invalidate edge of physics array + for(int x = 0; x < physicsRadius * 2 + 1; x++){ + needsPhysics[x][physicsRadius * 2] = true; + hasPhysics[x][physicsRadius * 2] = false; + } } @@ -404,6 +569,8 @@ public class DrawCellManager { makeCellDrawable(); } else if(containsUpdateableCell()){ updateCellModel(); + } else if(containsPhysicsNeedingCell()){ + addPhysicsToCell(); } } // } else if(DRAW_CELL_MANAGER_FLAG_GENERATE_ARENA){ diff --git a/src/main/java/electrosphere/game/collision/CollisionEngine.java b/src/main/java/electrosphere/game/collision/CollisionEngine.java index b78c1fc8..af0a144d 100644 --- a/src/main/java/electrosphere/game/collision/CollisionEngine.java +++ b/src/main/java/electrosphere/game/collision/CollisionEngine.java @@ -395,4 +395,36 @@ public class CollisionEngine { } } + public void deregisterPhysicsObject(CollisionObject object){ + if(collisionObject.contains(object)){ + collisionObject.remove(object); + } + world.removeCollisionObject(object); + } + + public void deregisterRigidBody(RigidBody body){ + if(collisionObject.contains(body)){ + collisionObject.remove(body); + } + if((body) != null){ + body.destroy(); +// world.removeRigidBody(body); + } + } + + public void deregisterCollidableEntity(Entity e){ + if(collisionEntities.contains(e)){ + collisionEntities.remove(e); + } + if(physicsEntities.contains(e)){ + physicsEntities.remove(e); + } + if(dynamicPhysicsEntities.contains(e)){ + dynamicPhysicsEntities.remove(e); + } + if(structurePhysicsEntities.contains(e)){ + structurePhysicsEntities.remove(e); + } + } + } diff --git a/src/main/java/electrosphere/game/collision/PhysicsUtils.java b/src/main/java/electrosphere/game/collision/PhysicsUtils.java index 5b53e179..6c841ffe 100644 --- a/src/main/java/electrosphere/game/collision/PhysicsUtils.java +++ b/src/main/java/electrosphere/game/collision/PhysicsUtils.java @@ -156,7 +156,7 @@ public class PhysicsUtils { Globals.collisionEngine.registerCollisionObject(terrainRigidBody, new Collidable(terrain,Collidable.TYPE_TERRAIN)); // terrainRigidBody.getAabb(aabbMin, aabbMax); - +// // System.out.println("aabbMin: " + aabbMin + " aabbMax: " + aabbMax); diff --git a/src/main/java/electrosphere/main/Globals.java b/src/main/java/electrosphere/main/Globals.java index 07a4ad70..32468e34 100644 --- a/src/main/java/electrosphere/main/Globals.java +++ b/src/main/java/electrosphere/main/Globals.java @@ -171,7 +171,7 @@ public class Globals { public static EntityManager serverEntityManager; //terrain manager - public static boolean LOAD_TERRAIN = true; + public static boolean LOAD_TERRAIN = false; public static ServerTerrainManager serverTerrainManager; public static Vector3f spawnPoint = new Vector3f(1000,0,1000); diff --git a/src/main/java/electrosphere/net/server/ServerConnectionHandler.java b/src/main/java/electrosphere/net/server/ServerConnectionHandler.java index 3322a4c8..ec82c14d 100644 --- a/src/main/java/electrosphere/net/server/ServerConnectionHandler.java +++ b/src/main/java/electrosphere/net/server/ServerConnectionHandler.java @@ -96,7 +96,7 @@ public class ServerConnectionHandler implements Runnable { //spawn player in world Entity newPlayerCharacter = CreatureUtils.spawnBasicCreature("Human"); playerCharacterID = newPlayerCharacter.getId(); - CreatureUtils.positionCharacter(newPlayerCharacter, new Vector3f(Globals.spawnPoint.x,3,Globals.spawnPoint.z)); + CreatureUtils.positionCharacter(newPlayerCharacter, new Vector3f(Globals.spawnPoint.x,Globals.spawnPoint.y,Globals.spawnPoint.z)); //spawn player sword Entity sword = ItemUtils.spawnBasicItem("Katana"); AttachUtils.attachEntityToEntityAtBone(newPlayerCharacter, sword, "Bone.031"); diff --git a/src/main/java/electrosphere/util/worldviewer/TerrainViewer.java b/src/main/java/electrosphere/util/worldviewer/TerrainViewer.java index 7929eb00..51a0ac38 100644 --- a/src/main/java/electrosphere/util/worldviewer/TerrainViewer.java +++ b/src/main/java/electrosphere/util/worldviewer/TerrainViewer.java @@ -34,12 +34,12 @@ public class TerrainViewer { TerrainModel terrainModel; -// ServerTerrainManager terrainManager = new ServerTerrainManager(2000, 1000, 100, 0.05f, new Random().nextLong()); -// terrainManager.generate(); -// terrainModel = terrainManager.getModel(); + ServerTerrainManager terrainManager = new ServerTerrainManager(2000, 1000, 100, 0.05f, new Random().nextLong()); + terrainManager.generate(); + terrainModel = terrainManager.getModel(); // Utilities.saveObjectToBakedJsonFile("/Config/testingTerrain.json", terrainModel); - terrainModel = FileLoadingUtils.loadObjectFromAssetPath("/Config/testingTerrain.json", TerrainModel.class); +// terrainModel = FileLoadingUtils.loadObjectFromAssetPath("/Config/testingTerrain.json", TerrainModel.class); MacroSimulation simulation = new MacroSimulation();