package electrosphere.entity.state.movement; import org.joml.Vector3d; import org.ode4j.math.DVector3C; import org.ode4j.ode.DBody; import electrosphere.collision.PhysicsEntityUtils; import electrosphere.collision.collidable.Collidable; import electrosphere.entity.Entity; import electrosphere.entity.EntityDataStrings; import electrosphere.entity.EntityUtils; import electrosphere.entity.btree.BehaviorTree; import electrosphere.entity.state.collidable.Impulse; import electrosphere.entity.state.gravity.GravityUtils; import electrosphere.entity.types.collision.CollisionObjUtils; import electrosphere.renderer.actor.Actor; public class ServerJumpTree implements BehaviorTree { static enum JumpState { INACTIVE, ACTIVE, AWAITING_LAND, } JumpState state = JumpState.INACTIVE; String animationJump = "Armature|Jump"; Entity parent; int jumpFrames = 0; int currentFrame = 0; float jumpForce = 10.0f; float currentJumpForce = jumpForce; static final float jumpFalloff = 0.99f; public ServerJumpTree(Entity parent, int jumpFrames, float jumpForce){ this.parent = parent; this.jumpFrames = jumpFrames; this.jumpForce = jumpForce; } public void start(){ if(state == JumpState.INACTIVE){ state = JumpState.ACTIVE; currentFrame = 0; currentJumpForce = jumpForce; GravityUtils.serverAttemptActivateGravity(parent); } } @Override public void simulate(float deltaTime) { Actor entityActor = EntityUtils.getActor(parent); switch(state){ case ACTIVE: if(entityActor != null){ String animationToPlay = determineCorrectAnimation(); if(!entityActor.isPlayingAnimation() || !entityActor.isPlayingAnimation(animationToPlay)){ entityActor.playAnimation(animationToPlay,1); entityActor.incrementAnimationTime(0.0001); } } currentFrame++; currentJumpForce = currentJumpForce * jumpFalloff; //stop body falling if it is DBody body = PhysicsEntityUtils.getDBody(parent); DVector3C linearVelocity = body.getLinearVel(); body.setLinearVel(linearVelocity.get0(), 0, linearVelocity.get2()); //push parent up body.addForce(0, currentJumpForce, 0); //potentially disable if(currentFrame >= jumpFrames){ state = JumpState.AWAITING_LAND; GravityUtils.serverAttemptActivateGravity(parent); } break; case INACTIVE: break; case AWAITING_LAND: break; } } public static ServerJumpTree getServerJumpTree(Entity parent){ return (ServerJumpTree)parent.getData(EntityDataStrings.SERVER_JUMP_TREE); } public void land(){ if(state != JumpState.INACTIVE && currentFrame > 2){ state = JumpState.INACTIVE; } } public boolean isJumping(){ return state == JumpState.ACTIVE; } String determineCorrectAnimation(){ return animationJump; } public void setAnimationJump(String animationName){ animationJump = animationName; } }