improve airplane movement + fix camera calculation

This commit is contained in:
austin 2023-01-01 23:53:58 -05:00
parent a5c9158875
commit 5874cac33b
16 changed files with 195 additions and 26 deletions

View File

@ -1,5 +1,6 @@
package electrosphere.controls;
import org.joml.Quaternionf;
import org.joml.Vector3d;
import org.joml.Vector3f;
@ -12,7 +13,8 @@ import electrosphere.renderer.ui.events.MouseEvent;
public class CameraHandler {
float mouseSensitivity = .1f;
float mouseSensitivityHorizontal = .1f;
float mouseSensitivityVertical = .08f;
float cameraSpeed;
float yaw = 150;
float pitch = 50;
@ -22,14 +24,14 @@ public class CameraHandler {
public void handleMouseEvent(MouseEvent event){
if(Globals.controlHandler != null && !Globals.controlHandler.isMouseVisible()){
yaw = yaw + event.getDeltaX() * mouseSensitivity;
pitch = pitch - event.getDeltaY() * mouseSensitivity;
yaw = yaw + event.getDeltaX() * mouseSensitivityHorizontal;
pitch = pitch - event.getDeltaY() * mouseSensitivityVertical;
if (pitch > 100.0f) {
pitch = 100.0f;
if (pitch >= 89.9f) {
pitch = 89.9f;
}
if (pitch < -99.0f) {
pitch = -99.0f;
if (pitch <= -89.9f) {
pitch = -89.9f;
}
}
@ -64,20 +66,33 @@ public class CameraHandler {
CameraEntityUtils.setCameraPitch(Globals.playerCamera, pitch);
CameraEntityUtils.setCameraYaw(Globals.playerCamera, yaw);
// System.out.println(pitch);
// if(Globals.playerCharacter != null){
// Vector3d charPos = EntityUtils.getPosition(Globals.playerCharacter);
// CameraEntityUtils.setCameraCenter(Globals.playerCamera, new Vector3f((float)charPos.x,(float)charPos.y,(float)charPos.z));
// }
cameraRotationVector.x = 0 + (float) Math.cos(yaw / 180.0f * Math.PI) * 1;
cameraRotationVector.y = 0 + (float) Math.sin(pitch / 180.0f * Math.PI) * 1;
cameraRotationVector.z = 0 + (float) Math.sin(yaw / 180.0f * Math.PI) * 1;
Quaternionf pitchQuat = new Quaternionf().fromAxisAngleDeg(new Vector3f(1,0,0), -pitch);
Quaternionf yawQuat = new Quaternionf().fromAxisAngleDeg(new Vector3f(0,1,0), -yaw);
// float yawRad = yaw / 180.0f * (float)Math.PI;
// float pitchRad = pitch / 180.0f * (float)Math.PI;
// float rollRad = 0.0f;
// pitchQuat.mul(yawQuat);
cameraRotationVector = pitchQuat.transform(new Vector3f(0,0,1));
cameraRotationVector = yawQuat.transform(cameraRotationVector);
cameraRotationVector.normalize();
// cameraRotationVector.x = 0 + (float) Math.cos(yaw / 180.0f * Math.PI) * 1;
// cameraRotationVector.y = 0 + (float) Math.sin(pitch / 180.0f * Math.PI) * 1;
// cameraRotationVector.z = 0 + (float) Math.sin(yaw / 180.0f * Math.PI) * 1;
// cameraRotationVector.normalize();
// System.out.println(yaw + " " + pitch);
}
//update view matrix offset
float xFactor = (float)Math.cos(yaw / 180.0f * Math.PI);
float yFactor = (float)Math.sin(yaw / 180.0f * Math.PI);
// Vector3f radialOffset = CameraEntityUtils.getOrbitalCameraRadialOffset(Globals.playerCamera);
Vector3f radialOffset = CameraEntityUtils.getOrbitalCameraRadialOffset(Globals.playerCamera);
Vector3f trueOffset = new Vector3f(radialOffset).mul(xFactor,1.0f,yFactor);
CameraEntityUtils.setOrbitalCameraRadialOffset(Globals.playerCamera, trueOffset);
// float cam_Player_Orbit_Magnitude = CameraEntityUtils.getCameraOrbitRadius(Globals.playerCamera);

View File

@ -75,8 +75,8 @@ import electrosphere.audio.AudioUtils;
import electrosphere.controls.Control.ControlMethod;
import electrosphere.controls.Control.ControlType;
import electrosphere.entity.Entity;
import electrosphere.entity.state.AttackTree;
import electrosphere.entity.state.BehaviorTree;
import electrosphere.entity.state.attack.AttackTree;
import electrosphere.entity.state.equip.EquipState;
import electrosphere.entity.state.inventory.InventoryUtils;
import electrosphere.entity.state.inventory.UnrelationalInventoryState;

View File

@ -623,7 +623,7 @@ public class LoadingThread extends Thread {
Player Camera
*/
Globals.playerCamera = CameraEntityUtils.spawnPlayerEntityTrackingCameraEntity(new Vector3f(1,0,1), new Vector3f(0,0,1));
Globals.playerCamera = CameraEntityUtils.spawnPlayerEntityAirplaneTrackingCameraEntity(new Vector3f(1,0,1), new Vector3f(0,0,1));

View File

@ -1,11 +1,12 @@
package electrosphere.entity.state;
import electrosphere.entity.state.attack.AttackTree;
import electrosphere.entity.state.attack.AttackTree.AttackTreeState;
import electrosphere.entity.state.movement.AirplaneMovementTree;
import electrosphere.entity.state.movement.GroundMovementTree;
import electrosphere.entity.Entity;
import electrosphere.entity.EntityDataStrings;
import electrosphere.entity.EntityUtils;
import electrosphere.entity.state.AttackTree.AttackTreeState;
import electrosphere.entity.state.movement.GroundMovementTree.MovementTreeState;
import electrosphere.entity.types.creature.CreatureUtils;
import electrosphere.main.Globals;

View File

@ -1,8 +1,9 @@
package electrosphere.entity.state;
package electrosphere.entity.state.attack;
import electrosphere.entity.Entity;
import electrosphere.entity.EntityDataStrings;
import electrosphere.entity.EntityUtils;
import electrosphere.entity.state.BehaviorTree;
import electrosphere.entity.state.collidable.Impulse;
import electrosphere.entity.state.equip.EquipState;
import electrosphere.entity.state.movement.GroundMovementTree;

View File

@ -0,0 +1,55 @@
package electrosphere.entity.state.attack;
import electrosphere.entity.Entity;
import electrosphere.entity.state.BehaviorTree;
public class ShooterTree implements BehaviorTree {
public static enum ShooterTreeState {
ATTACK,
COOLDOWN,
IDLE,
}
ShooterTreeState state;
Entity parent;
int ammoAvailable;
int ammoMax;
public ShooterTree(Entity parent){
this.parent = parent;
}
@Override
public void simulate() {
// TODO Auto-generated method stub
switch(state){
case ATTACK: {
//
} break;
case COOLDOWN: {
//
} break;
case IDLE: {
//
} break;
}
}
public void fire(){
boolean canFire = true;
if(ammoAvailable <= 0){
canFire = false;
}
if(state != ShooterTreeState.IDLE){
canFire = false;
}
if(canFire){
//fire
System.out.println("Fire!");
}
}
}

View File

@ -29,6 +29,14 @@ public class AirplaneMovementTree implements BehaviorTree {
float minVelocity = 0;
float maxRotationSpeed = 1.0f;
//The yaw value last simulation frame
float previousYaw = 270;
//how much we're rolling currently
float rollVal = 0;
// the factor to increment rollVal by while swinging the camera around
float rollFactor = 0.05f;
static final double STATE_DIFFERENCE_HARD_UPDATE_THRESHOLD = 1.0;
static final double STATE_DIFFERENCE_SOFT_UPDATE_THRESHOLD = 0.2;
static final double SOFT_UPDATE_MULTIPLIER = 0.1;
@ -45,6 +53,8 @@ public class AirplaneMovementTree implements BehaviorTree {
//used to filter out packets before the most recent one
long lastUpdateTime = 0;
float pitchCalculationTolerance = 0.99f;
/**
* Constructs an airplane movement tree
@ -173,9 +183,34 @@ public class AirplaneMovementTree implements BehaviorTree {
void updateRotation(Quaternionf rotation, Vector3d rotationVector){
if(Globals.RUN_CLIENT && this.parent == Globals.playerEntity){
Vector3f cameraEyeVector = CameraEntityUtils.getCameraEye(Globals.playerCamera);
float pitch = CameraEntityUtils.getCameraPitch(Globals.playerCamera) / 180 * (float)Math.PI;
float yaw = -(CameraEntityUtils.getCameraYaw(Globals.playerCamera) + 180) / 180 * (float)Math.PI;
float deltaYaw = yaw - previousYaw;
if(deltaYaw > 0){
rollVal += -rollFactor;
}
if(deltaYaw < 0){
rollVal += rollFactor;
}
Quaternionf yawQuat = new Quaternionf().fromAxisAngleRad(new Vector3f(0,1,0), yaw);
Quaternionf pitchQuat = new Quaternionf().fromAxisAngleRad(new Vector3f(1,0,0), pitch);
Quaternionf rollQuat = new Quaternionf().fromAxisAngleRad(new Vector3f(0,0,1), rollVal);
rotation.slerp(yawQuat.mul(pitchQuat).mul(rollQuat),0.1f);
//rotate thrust vector
rotationVector.set(new Vector3f((float)rotationVector.x,(float)rotationVector.y,(float)rotationVector.z).mul(1.0f - this.maxRotationSpeed).add(new Vector3f(cameraEyeVector).mul(-this.maxRotationSpeed)));
rotation.set(new Quaternionf().rotationTo(new Vector3f(0,0,1), new Vector3f((float)rotationVector.x,(float)rotationVector.y,(float)rotationVector.z)).normalize());
// rotation.slerp(new Quaternionf().rotationTo(new Vector3f((float)rotationVector.x,(float)rotationVector.y,(float)rotationVector.z), cameraEyeVector), this.maxRotationSpeed);
rollVal = rollVal * 0.9f;
previousYaw = yaw;
}
}

View File

@ -10,9 +10,9 @@ import electrosphere.entity.types.creature.CreatureUtils;
import electrosphere.entity.Entity;
import electrosphere.entity.EntityDataStrings;
import electrosphere.entity.EntityUtils;
import electrosphere.entity.state.AttackTree;
import electrosphere.entity.state.BehaviorTree;
import electrosphere.entity.state.AttackTree.AttackTreeState;
import electrosphere.entity.state.attack.AttackTree;
import electrosphere.entity.state.attack.AttackTree.AttackTreeState;
import electrosphere.entity.state.movement.SprintTree.SprintTreeState;
import electrosphere.game.collision.CollisionEngine;
import electrosphere.game.collision.PhysicsUtils;

View File

@ -75,6 +75,29 @@ public class CameraEntityUtils {
Globals.entityManager.registerBehaviorTree(entityTrackingTree);
return rVal;
}
public static Entity spawnPlayerEntityAirplaneTrackingCameraEntity(Vector3f center, Vector3f eye){
Entity rVal = new Entity();
Globals.entityManager.registerEntity(rVal);
rVal.putData(EntityDataStrings.DATA_STRING_CAMERA_TYPE, EntityDataStrings.DATA_STRING_CAMERA_TYPE_ORBIT);
rVal.putData(EntityDataStrings.DATA_STRING_CAMERA_CENTER, center);
rVal.putData(EntityDataStrings.DATA_STRING_CAMERA_EYE, eye);
rVal.putData(EntityDataStrings.DATA_STRING_CAMERA_ORBIT_DISTANCE, 2.0f);
rVal.putData(EntityDataStrings.CAMERA_ORBIT_RADIAL_OFFSET, new Vector3f(0,0.45f,0));
rVal.putData(EntityDataStrings.CAMERA_PITCH, 0.0f);
rVal.putData(EntityDataStrings.CAMERA_YAW, 0.0f);
BehaviorTree entityTrackingTree = new BehaviorTree() {
@Override
public void simulate() {
if(Globals.playerEntity != null){
Vector3d entityPos = EntityUtils.getPosition(Globals.playerEntity);
CameraEntityUtils.setCameraCenter(rVal, new Vector3f((float)entityPos.x,(float)entityPos.y,(float)entityPos.z).add(getOrbitalCameraRadialOffset(rVal)));
}
}
};
Globals.entityManager.registerBehaviorTree(entityTrackingTree);
return rVal;
}
public static Entity getOrbitalCameraTarget(Entity camera){
return (Entity)camera.getData(EntityDataStrings.DATA_STRING_CAMERA_ORBIT_TARGET);
@ -138,8 +161,12 @@ public class CameraEntityUtils {
Vector3f cameraCenter = new Vector3f(0,0,0);//getViewMatrixCenterOffset(camera);
Vector3f cameraEye = new Vector3f(cameraCenter).add(getCameraEye(camera));
Vector3f cameraUp = new Vector3f(0,1.0f,0);
// System.out.println("eye: " + cameraEye);
// System.out.println("center: " + cameraCenter);
//!!before you make the same mistake I made, cameraEye is NOT NECESSARILY normalized/unit vector
//the orbital distance and offset are included in this vector
//TODO: refactor this to some other matrix of transforms or something??
cameraEye = new Vector3f(getCameraEye(camera));
// System.out.println("eye: " + cameraEye);
// System.out.println("center: " + cameraCenter);
// System.out.println("up: " + cameraUp);
Matrix4f rVal = new Matrix4f().setLookAt(
cameraEye, //eye

View File

@ -12,9 +12,9 @@ import electrosphere.entity.state.movement.JumpTree;
import electrosphere.entity.types.hitbox.HitboxData;
import electrosphere.entity.types.hitbox.HitboxUtils;
import electrosphere.game.data.creature.type.CreatureType;
import electrosphere.entity.state.AttackTree;
import electrosphere.entity.state.BehaviorTree;
import electrosphere.entity.state.IdleTree;
import electrosphere.entity.state.attack.AttackTree;
import electrosphere.entity.state.collidable.CollidableTree;
import electrosphere.entity.state.equip.EquipState;
import electrosphere.entity.state.gravity.GravityTree;

View File

@ -18,4 +18,13 @@ public class DebugVisualizerUtils {
return rVal;
}
public static Entity spawnUpdatingVectorVisualizer(Vector3d position, Vector3d direction){
Entity rVal = EntityUtils.spawnDrawableEntity("Models/unitcube.fbx");
Vector3d pos = new Vector3d(position).add(new Vector3d(direction).normalize().mul(0.3));
EntityUtils.getPosition(rVal).set(pos);
EntityUtils.getScale(rVal).set(0.05f,0.3f,0.05f);
EntityUtils.getRotation(rVal).rotateTo(new Vector3f(0,1,0), new Vector3f((float)direction.x,(float)direction.y,(float)direction.z));
return rVal;
}
}

View File

@ -3,7 +3,7 @@ package electrosphere.game.server.ai.creature;
import electrosphere.entity.Entity;
import electrosphere.entity.EntityDataStrings;
import electrosphere.entity.EntityUtils;
import electrosphere.entity.state.AttackTree;
import electrosphere.entity.state.attack.AttackTree;
import electrosphere.entity.state.movement.GroundMovementTree;
import electrosphere.entity.state.movement.GroundMovementTree.MovementRelativeFacing;
import electrosphere.entity.types.creature.CreatureUtils;

View File

@ -3,7 +3,7 @@ package electrosphere.game.server.ai.creature;
import electrosphere.entity.Entity;
import electrosphere.entity.EntityDataStrings;
import electrosphere.entity.EntityUtils;
import electrosphere.entity.state.AttackTree;
import electrosphere.entity.state.attack.AttackTree;
import electrosphere.entity.state.equip.EquipState;
import electrosphere.entity.state.movement.GroundMovementTree;
import electrosphere.entity.state.movement.GroundMovementTree.MovementRelativeFacing;

View File

@ -4,11 +4,11 @@ import electrosphere.entity.types.attach.AttachUtils;
import electrosphere.entity.Entity;
import electrosphere.entity.EntityDataStrings;
import electrosphere.entity.EntityUtils;
import electrosphere.entity.state.AttackTree;
import electrosphere.entity.state.BehaviorTree;
import electrosphere.entity.state.IdleTree;
import electrosphere.entity.state.movement.GroundMovementTree;
import electrosphere.entity.state.ParticleTree;
import electrosphere.entity.state.attack.AttackTree;
import electrosphere.entity.state.collidable.CollidableTree;
import electrosphere.entity.state.gravity.GravityTree;
import electrosphere.entity.types.creature.CreatureUtils;

View File

@ -64,7 +64,7 @@ public class CharacterProtocol {
// System.out.println(EntityUtils.getRotation(newPlayerCharacter).set(0,1,0,1).normalize());
Globals.dataCellManager.addPlayerToGroundCells(playerObject);
Globals.dataCellManager.movePlayerGroundCells(playerObject, Globals.serverWorldData.convertRealToChunkSpace(Globals.spawnPoint.x), Globals.serverWorldData.convertRealToChunkSpace(Globals.spawnPoint.z));
IronSightTree.attachIronSightTree(newPlayerEntity);
// IronSightTree.attachIronSightTree(newPlayerEntity);
// //spawn player sword
// Entity sword = ItemUtils.spawnBasicItem("Katana");
// AttachUtils.attachEntityToEntityAtBone(newPlayerCharacter, sword, "Bone.031");

View File

@ -0,0 +1,26 @@
package electrosphere.util;
import org.joml.Quaternionf;
import org.joml.Vector3d;
import org.joml.Vector3f;
public class TransformUtils {
public Quaternionf calculateQuaternionFromPoints(Vector3d origin, Vector3d direction){
return new Quaternionf().rotateTo(new Vector3f(0,1,0), new Vector3f((float)(direction.x-origin.x),(float)(direction.y-origin.y),(float)(direction.z-origin.z)));
}
public Quaternionf calculateQuaternionFromPoints(Vector3d direction){
return new Quaternionf().rotateTo(new Vector3f(0,1,0), new Vector3f((float)direction.x,(float)direction.y,(float)direction.z));
}
public Quaternionf calculateQuaternionFromPoints(Vector3f origin, Vector3f direction){
return new Quaternionf().rotateTo(new Vector3f(0,1,0), new Vector3f(direction.x-origin.x,direction.y-origin.y,direction.z-origin.z));
}
public Quaternionf calculateQuaternionFromPoints(Vector3f direction){
return new Quaternionf().rotateTo(new Vector3f(0,1,0), new Vector3f(direction));
}
}