Respawn system
This commit is contained in:
parent
2764522b16
commit
6a3bedf808
@ -157,6 +157,7 @@
|
||||
{
|
||||
"messageName" : "Kill",
|
||||
"data" : [
|
||||
"time",
|
||||
"entityID"
|
||||
]
|
||||
},
|
||||
|
||||
@ -1,27 +1,46 @@
|
||||
package electrosphere.entity.state.life;
|
||||
|
||||
import java.util.concurrent.CopyOnWriteArrayList;
|
||||
|
||||
import org.joml.Vector3d;
|
||||
|
||||
import electrosphere.entity.Entity;
|
||||
import electrosphere.entity.EntityUtils;
|
||||
import electrosphere.entity.state.BehaviorTree;
|
||||
import electrosphere.entity.types.creature.CreatureUtils;
|
||||
import electrosphere.game.data.creature.type.CreatureType;
|
||||
import electrosphere.game.data.creature.type.HealthSystem;
|
||||
import electrosphere.main.Globals;
|
||||
import electrosphere.main.Main;
|
||||
import electrosphere.net.parser.net.message.CharacterMessage;
|
||||
import electrosphere.net.parser.net.message.EntityMessage;
|
||||
import electrosphere.renderer.actor.Actor;
|
||||
|
||||
public class LifeState {
|
||||
public class LifeState implements BehaviorTree {
|
||||
|
||||
|
||||
public static enum LifeStateEnum {
|
||||
ALIVE,
|
||||
DYING,
|
||||
DEAD,
|
||||
}
|
||||
|
||||
LifeStateEnum state = LifeStateEnum.ALIVE;
|
||||
|
||||
Entity parent;
|
||||
|
||||
boolean isAlive;
|
||||
boolean isInvincible;
|
||||
int lifeCurrent;
|
||||
int lifeMax;
|
||||
int iFrameMaxCount;
|
||||
int iFrameCurrent;
|
||||
|
||||
int deathFrameCurrent = -1;
|
||||
|
||||
CopyOnWriteArrayList<EntityMessage> networkMessageQueue = new CopyOnWriteArrayList<EntityMessage>();
|
||||
|
||||
public LifeState(Entity parent, HealthSystem system){
|
||||
this.parent = parent;
|
||||
isAlive = true;
|
||||
isInvincible = false;
|
||||
lifeMax = system.getMaxHealth();
|
||||
lifeCurrent = lifeMax;
|
||||
@ -29,9 +48,8 @@ public class LifeState {
|
||||
iFrameCurrent = 0;
|
||||
}
|
||||
|
||||
public LifeState(Entity parent, boolean isAlive, boolean isInvincible, int lifeCurrent, int lifeMax, int iFrameMaxCount) {
|
||||
public LifeState(Entity parent, boolean isInvincible, int lifeCurrent, int lifeMax, int iFrameMaxCount) {
|
||||
this.parent = parent;
|
||||
this.isAlive = isAlive;
|
||||
this.isInvincible = isInvincible;
|
||||
this.lifeCurrent = lifeCurrent;
|
||||
this.lifeMax = lifeMax;
|
||||
@ -39,7 +57,7 @@ public class LifeState {
|
||||
}
|
||||
|
||||
public boolean isIsAlive() {
|
||||
return isAlive;
|
||||
return state == LifeStateEnum.ALIVE;
|
||||
}
|
||||
|
||||
public boolean isIsInvincible() {
|
||||
@ -54,8 +72,8 @@ public class LifeState {
|
||||
return lifeMax;
|
||||
}
|
||||
|
||||
public void setIsAlive(boolean isAlive) {
|
||||
this.isAlive = isAlive;
|
||||
public void setState(LifeStateEnum state) {
|
||||
this.state = state;
|
||||
}
|
||||
|
||||
public void setIsInvincible(boolean isInvincible) {
|
||||
@ -92,15 +110,16 @@ public class LifeState {
|
||||
isInvincible = true;
|
||||
if(lifeCurrent < 0){
|
||||
lifeCurrent = 0;
|
||||
isAlive = false;
|
||||
if(Globals.RUN_SERVER){
|
||||
state = LifeStateEnum.DYING;
|
||||
Vector3d position = EntityUtils.getPosition(parent);
|
||||
Globals.dataCellManager.sendNetworkMessageToChunk(
|
||||
EntityMessage.constructKillMessage(
|
||||
parent.getId()
|
||||
),
|
||||
Globals.serverWorldData.convertRealToChunkSpace(position.x),
|
||||
Globals.serverWorldData.convertRealToChunkSpace(position.z)
|
||||
EntityMessage.constructKillMessage(
|
||||
Main.getCurrentFrame(),
|
||||
parent.getId()
|
||||
),
|
||||
Globals.serverWorldData.convertRealToChunkSpace(position.x),
|
||||
Globals.serverWorldData.convertRealToChunkSpace(position.z)
|
||||
);
|
||||
}
|
||||
} else {
|
||||
@ -110,18 +129,81 @@ public class LifeState {
|
||||
}
|
||||
|
||||
public void revive(){
|
||||
isAlive = true;
|
||||
state = LifeStateEnum.ALIVE;
|
||||
isInvincible = false;
|
||||
lifeCurrent = lifeMax;
|
||||
}
|
||||
|
||||
public void simulate(){
|
||||
if(iFrameCurrent > 0){
|
||||
iFrameCurrent--;
|
||||
if(iFrameCurrent == 0){
|
||||
isInvincible = false;
|
||||
for(EntityMessage message : networkMessageQueue){
|
||||
networkMessageQueue.remove(message);
|
||||
long updateTime = message.gettime();
|
||||
switch(message.getMessageSubtype()){
|
||||
case KILL:
|
||||
//start death
|
||||
if(Globals.RUN_CLIENT){
|
||||
state = LifeStateEnum.DYING;
|
||||
lifeCurrent = 0;
|
||||
int frameskip = (int)(Main.getCurrentFrame() - message.gettime());
|
||||
deathFrameCurrent = frameskip;
|
||||
}
|
||||
break;
|
||||
case ATTACHENTITYTOENTITY:
|
||||
case ATTACKUPDATE:
|
||||
case CREATE:
|
||||
case DESTROY:
|
||||
case SETBEHAVIORTREE:
|
||||
case SETPOSITION:
|
||||
case SETPROPERTY:
|
||||
case MOVE:
|
||||
case SETFACING:
|
||||
case MOVEUPDATE:
|
||||
//silently ignore
|
||||
break;
|
||||
}
|
||||
}
|
||||
switch(state){
|
||||
case ALIVE:
|
||||
if(iFrameCurrent > 0){
|
||||
iFrameCurrent--;
|
||||
if(iFrameCurrent == 0){
|
||||
isInvincible = false;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case DYING:
|
||||
CreatureType creatureType = Globals.gameConfigCurrent.getCreatureTypeLoader().getCreature(CreatureUtils.getType(parent));
|
||||
if(deathFrameCurrent > creatureType.getHealthSystem().getDeathFrames()){
|
||||
state = LifeStateEnum.DEAD;
|
||||
}
|
||||
Actor entityActor = EntityUtils.getActor(parent);
|
||||
if(entityActor != null){
|
||||
String animationToPlay = creatureType.getHealthSystem().getDeathAnimation();
|
||||
if(
|
||||
!entityActor.isPlayingAnimation() || !entityActor.isPlayingAnimation(animationToPlay)
|
||||
){
|
||||
entityActor.playAnimation(animationToPlay,1);
|
||||
entityActor.incrementAnimationTime(0.01);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case DEAD:
|
||||
if(Globals.RUN_CLIENT && parent == Globals.playerEntity){
|
||||
if(!Globals.RUN_SERVER){
|
||||
//destroy current (client) world stuff
|
||||
//only if not also running server
|
||||
}
|
||||
//submit respawn request
|
||||
Globals.clientConnection.queueOutgoingMessage(
|
||||
CharacterMessage.constructRequestSpawnCharacterMessage()
|
||||
);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
public void addNetworkMessage(EntityMessage networkMessage) {
|
||||
networkMessageQueue.add(networkMessage);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@ -7,6 +7,8 @@ package electrosphere.game.data.creature.type;
|
||||
public class HealthSystem {
|
||||
int maxHealth;
|
||||
int onDamageIFrames;
|
||||
int deathFrames;
|
||||
String deathAnimation;
|
||||
|
||||
public int getMaxHealth() {
|
||||
return maxHealth;
|
||||
@ -16,10 +18,19 @@ public class HealthSystem {
|
||||
return onDamageIFrames;
|
||||
}
|
||||
|
||||
public int getDeathFrames(){
|
||||
return deathFrames;
|
||||
}
|
||||
|
||||
public String getDeathAnimation(){
|
||||
return deathAnimation;
|
||||
}
|
||||
|
||||
public HealthSystem clone(){
|
||||
HealthSystem rVal = new HealthSystem();
|
||||
rVal.maxHealth = maxHealth;
|
||||
rVal.onDamageIFrames = onDamageIFrames;
|
||||
rVal.deathFrames = deathFrames;
|
||||
return rVal;
|
||||
}
|
||||
|
||||
|
||||
@ -462,12 +462,14 @@ public class EntityMessage extends NetworkMessage {
|
||||
public static EntityMessage parseKillMessage(List<Byte> byteStream){
|
||||
EntityMessage rVal = new EntityMessage(EntityMessageType.KILL);
|
||||
stripPacketHeader(byteStream);
|
||||
rVal.settime(ByteStreamUtils.popLongFromByteQueue(byteStream));
|
||||
rVal.setentityID(ByteStreamUtils.popIntFromByteQueue(byteStream));
|
||||
return rVal;
|
||||
}
|
||||
|
||||
public static EntityMessage constructKillMessage(int entityID){
|
||||
public static EntityMessage constructKillMessage(long time,int entityID){
|
||||
EntityMessage rVal = new EntityMessage(EntityMessageType.KILL);
|
||||
rVal.settime(time);
|
||||
rVal.setentityID(entityID);
|
||||
rVal.serialize();
|
||||
return rVal;
|
||||
@ -786,14 +788,18 @@ public class EntityMessage extends NetworkMessage {
|
||||
}
|
||||
break;
|
||||
case KILL:
|
||||
rawBytes = new byte[2+4];
|
||||
rawBytes = new byte[2+8+4];
|
||||
//message header
|
||||
rawBytes[0] = TypeBytes.MESSAGE_TYPE_ENTITY;
|
||||
//entity messaage header
|
||||
rawBytes[1] = TypeBytes.ENTITY_MESSAGE_TYPE_KILL;
|
||||
intValues = ByteStreamUtils.serializeLongToBytes(time);
|
||||
for(int i = 0; i < 8; i++){
|
||||
rawBytes[2+i] = intValues[i];
|
||||
}
|
||||
intValues = ByteStreamUtils.serializeIntToBytes(entityID);
|
||||
for(int i = 0; i < 4; i++){
|
||||
rawBytes[2+i] = intValues[i];
|
||||
rawBytes[10+i] = intValues[i];
|
||||
}
|
||||
break;
|
||||
case DESTROY:
|
||||
|
||||
@ -34,7 +34,7 @@ Message categories
|
||||
public static final byte ENTITY_MESSAGE_TYPE_MOVEUPDATE_SIZE = 74;
|
||||
public static final byte ENTITY_MESSAGE_TYPE_ATTACKUPDATE_SIZE = 74;
|
||||
public static final byte ENTITY_MESSAGE_TYPE_MOVE_SIZE = 38;
|
||||
public static final byte ENTITY_MESSAGE_TYPE_KILL_SIZE = 6;
|
||||
public static final byte ENTITY_MESSAGE_TYPE_KILL_SIZE = 14;
|
||||
public static final byte ENTITY_MESSAGE_TYPE_DESTROY_SIZE = 6;
|
||||
public static final byte ENTITY_MESSAGE_TYPE_SETBEHAVIORTREE_SIZE = 22;
|
||||
public static final byte ENTITY_MESSAGE_TYPE_SETPROPERTY_SIZE = 22;
|
||||
|
||||
Loading…
Reference in New Issue
Block a user