PlayerSAO/LocalPlayer refactor: (#4612)
* Create UnitSAO, a common part between PlayerSAO & LuaEntitySAO * Move breath to PlayerSAO & LocalPlayer * Migrate m_yaw from (Remote)Player & LuaEntitySAO to UnitSAO * Migrate m_yaw from Player to LocalPlayer for client * Move some functions outside of player class to PlayerSAO/RemotePlayer or LocalPlayer depending on which class needs it * Move pitch to LocalPlayer & PlayerSAO * Move m_position from Player to LocalPlayer * Move camera_barely_in_ceiling to LocalPlayer as it's used only there * use PlayerSAO::m_base_position for Server side positions * remove a unused variable * ServerActiveObject::setPos now uses const ref * use ServerEnv::loadPlayer unconditionnaly as it creates RemotePlayer only if it's not already loaded * Move hp from Player to LocalPlayer * Move m_hp from LuaEntitySAO to UnitSAO * Use m_hp from PlayerSAO/UnitSAO instead of RemotePlayermutilcraft-mt53
parent
d43326021a
commit
9d25242c5c
|
@ -29,7 +29,7 @@ with this program; if not, write to the Free Software Foundation, Inc.,
|
||||||
#include "environment.h"
|
#include "environment.h"
|
||||||
#include "map.h"
|
#include "map.h"
|
||||||
#include "emerge.h"
|
#include "emerge.h"
|
||||||
#include "serverobject.h" // TODO this is used for cleanup of only
|
#include "content_sao.h" // TODO this is used for cleanup of only
|
||||||
#include "log.h"
|
#include "log.h"
|
||||||
#include "util/srp.h"
|
#include "util/srp.h"
|
||||||
|
|
||||||
|
@ -82,6 +82,10 @@ void RemoteClient::GetNextBlocks (
|
||||||
if (player == NULL)
|
if (player == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
PlayerSAO *sao = player->getPlayerSAO();
|
||||||
|
if (sao == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
// Won't send anything if already sending
|
// Won't send anything if already sending
|
||||||
if(m_blocks_sending.size() >= g_settings->getU16
|
if(m_blocks_sending.size() >= g_settings->getU16
|
||||||
("max_simultaneous_block_sends_per_client"))
|
("max_simultaneous_block_sends_per_client"))
|
||||||
|
@ -90,7 +94,7 @@ void RemoteClient::GetNextBlocks (
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
v3f playerpos = player->getPosition();
|
v3f playerpos = sao->getBasePosition();
|
||||||
v3f playerspeed = player->getSpeed();
|
v3f playerspeed = player->getSpeed();
|
||||||
v3f playerspeeddir(0,0,0);
|
v3f playerspeeddir(0,0,0);
|
||||||
if(playerspeed.getLength() > 1.0*BS)
|
if(playerspeed.getLength() > 1.0*BS)
|
||||||
|
@ -103,10 +107,10 @@ void RemoteClient::GetNextBlocks (
|
||||||
v3s16 center = getNodeBlockPos(center_nodepos);
|
v3s16 center = getNodeBlockPos(center_nodepos);
|
||||||
|
|
||||||
// Camera position and direction
|
// Camera position and direction
|
||||||
v3f camera_pos = player->getEyePosition();
|
v3f camera_pos = sao->getEyePosition();
|
||||||
v3f camera_dir = v3f(0,0,1);
|
v3f camera_dir = v3f(0,0,1);
|
||||||
camera_dir.rotateYZBy(player->getPitch());
|
camera_dir.rotateYZBy(sao->getPitch());
|
||||||
camera_dir.rotateXZBy(player->getYaw());
|
camera_dir.rotateXZBy(sao->getYaw());
|
||||||
|
|
||||||
/*infostream<<"camera_dir=("<<camera_dir.X<<","<<camera_dir.Y<<","
|
/*infostream<<"camera_dir=("<<camera_dir.X<<","<<camera_dir.Y<<","
|
||||||
<<camera_dir.Z<<")"<<std::endl;*/
|
<<camera_dir.Z<<")"<<std::endl;*/
|
||||||
|
|
|
@ -367,7 +367,7 @@ collisionMoveResult collisionMoveSimple(Environment *env, IGameDef *gamedef,
|
||||||
#endif
|
#endif
|
||||||
{
|
{
|
||||||
ServerEnvironment *s_env = dynamic_cast<ServerEnvironment*>(env);
|
ServerEnvironment *s_env = dynamic_cast<ServerEnvironment*>(env);
|
||||||
if (s_env != 0) {
|
if (s_env != NULL) {
|
||||||
f32 distance = speed_f->getLength();
|
f32 distance = speed_f->getLength();
|
||||||
std::vector<u16> s_objects;
|
std::vector<u16> s_objects;
|
||||||
s_env->getObjectsInsideRadius(s_objects, *pos_f, distance * 1.5);
|
s_env->getObjectsInsideRadius(s_objects, *pos_f, distance * 1.5);
|
||||||
|
|
|
@ -118,14 +118,12 @@ LuaEntitySAO proto_LuaEntitySAO(NULL, v3f(0,0,0), "_prototype", "");
|
||||||
|
|
||||||
LuaEntitySAO::LuaEntitySAO(ServerEnvironment *env, v3f pos,
|
LuaEntitySAO::LuaEntitySAO(ServerEnvironment *env, v3f pos,
|
||||||
const std::string &name, const std::string &state):
|
const std::string &name, const std::string &state):
|
||||||
ServerActiveObject(env, pos),
|
UnitSAO(env, pos),
|
||||||
m_init_name(name),
|
m_init_name(name),
|
||||||
m_init_state(state),
|
m_init_state(state),
|
||||||
m_registered(false),
|
m_registered(false),
|
||||||
m_hp(-1),
|
|
||||||
m_velocity(0,0,0),
|
m_velocity(0,0,0),
|
||||||
m_acceleration(0,0,0),
|
m_acceleration(0,0,0),
|
||||||
m_yaw(0),
|
|
||||||
m_properties_sent(true),
|
m_properties_sent(true),
|
||||||
m_last_sent_yaw(0),
|
m_last_sent_yaw(0),
|
||||||
m_last_sent_position(0,0,0),
|
m_last_sent_position(0,0,0),
|
||||||
|
@ -664,16 +662,6 @@ v3f LuaEntitySAO::getAcceleration()
|
||||||
return m_acceleration;
|
return m_acceleration;
|
||||||
}
|
}
|
||||||
|
|
||||||
void LuaEntitySAO::setYaw(float yaw)
|
|
||||||
{
|
|
||||||
m_yaw = yaw;
|
|
||||||
}
|
|
||||||
|
|
||||||
float LuaEntitySAO::getYaw()
|
|
||||||
{
|
|
||||||
return m_yaw;
|
|
||||||
}
|
|
||||||
|
|
||||||
void LuaEntitySAO::setTextureMod(const std::string &mod)
|
void LuaEntitySAO::setTextureMod(const std::string &mod)
|
||||||
{
|
{
|
||||||
std::string str = gob_cmd_set_texture_mod(mod);
|
std::string str = gob_cmd_set_texture_mod(mod);
|
||||||
|
@ -762,10 +750,9 @@ bool LuaEntitySAO::collideWithObjects(){
|
||||||
|
|
||||||
// No prototype, PlayerSAO does not need to be deserialized
|
// No prototype, PlayerSAO does not need to be deserialized
|
||||||
|
|
||||||
PlayerSAO::PlayerSAO(ServerEnvironment *env_, RemotePlayer *player_, u16 peer_id_,
|
PlayerSAO::PlayerSAO(ServerEnvironment *env_, u16 peer_id_, bool is_singleplayer):
|
||||||
const std::set<std::string> &privs, bool is_singleplayer):
|
UnitSAO(env_, v3f(0,0,0)),
|
||||||
ServerActiveObject(env_, v3f(0,0,0)),
|
m_player(NULL),
|
||||||
m_player(player_),
|
|
||||||
m_peer_id(peer_id_),
|
m_peer_id(peer_id_),
|
||||||
m_inventory(NULL),
|
m_inventory(NULL),
|
||||||
m_damage(0),
|
m_damage(0),
|
||||||
|
@ -777,7 +764,6 @@ PlayerSAO::PlayerSAO(ServerEnvironment *env_, RemotePlayer *player_, u16 peer_id
|
||||||
m_position_not_sent(false),
|
m_position_not_sent(false),
|
||||||
m_armor_groups_sent(false),
|
m_armor_groups_sent(false),
|
||||||
m_properties_sent(true),
|
m_properties_sent(true),
|
||||||
m_privs(privs),
|
|
||||||
m_is_singleplayer(is_singleplayer),
|
m_is_singleplayer(is_singleplayer),
|
||||||
m_animation_speed(0),
|
m_animation_speed(0),
|
||||||
m_animation_blend(0),
|
m_animation_blend(0),
|
||||||
|
@ -786,6 +772,8 @@ PlayerSAO::PlayerSAO(ServerEnvironment *env_, RemotePlayer *player_, u16 peer_id
|
||||||
m_bone_position_sent(false),
|
m_bone_position_sent(false),
|
||||||
m_attachment_parent_id(0),
|
m_attachment_parent_id(0),
|
||||||
m_attachment_sent(false),
|
m_attachment_sent(false),
|
||||||
|
m_breath(PLAYER_MAX_BREATH),
|
||||||
|
m_pitch(0),
|
||||||
// public
|
// public
|
||||||
m_physics_override_speed(1),
|
m_physics_override_speed(1),
|
||||||
m_physics_override_jump(1),
|
m_physics_override_jump(1),
|
||||||
|
@ -794,10 +782,7 @@ PlayerSAO::PlayerSAO(ServerEnvironment *env_, RemotePlayer *player_, u16 peer_id
|
||||||
m_physics_override_sneak_glitch(true),
|
m_physics_override_sneak_glitch(true),
|
||||||
m_physics_override_sent(false)
|
m_physics_override_sent(false)
|
||||||
{
|
{
|
||||||
assert(m_player); // pre-condition
|
|
||||||
assert(m_peer_id != 0); // pre-condition
|
assert(m_peer_id != 0); // pre-condition
|
||||||
setBasePosition(m_player->getPosition());
|
|
||||||
m_inventory = &m_player->inventory;
|
|
||||||
m_armor_groups["fleshy"] = 100;
|
m_armor_groups["fleshy"] = 100;
|
||||||
|
|
||||||
m_prop.hp_max = PLAYER_MAX_HP;
|
m_prop.hp_max = PLAYER_MAX_HP;
|
||||||
|
@ -816,6 +801,7 @@ PlayerSAO::PlayerSAO(ServerEnvironment *env_, RemotePlayer *player_, u16 peer_id
|
||||||
// end of default appearance
|
// end of default appearance
|
||||||
m_prop.is_visible = true;
|
m_prop.is_visible = true;
|
||||||
m_prop.makes_footstep_sound = true;
|
m_prop.makes_footstep_sound = true;
|
||||||
|
m_hp = PLAYER_MAX_HP;
|
||||||
}
|
}
|
||||||
|
|
||||||
PlayerSAO::~PlayerSAO()
|
PlayerSAO::~PlayerSAO()
|
||||||
|
@ -824,6 +810,14 @@ PlayerSAO::~PlayerSAO()
|
||||||
delete m_inventory;
|
delete m_inventory;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void PlayerSAO::initialize(RemotePlayer *player, const std::set<std::string> &privs)
|
||||||
|
{
|
||||||
|
assert(player);
|
||||||
|
m_player = player;
|
||||||
|
m_privs = privs;
|
||||||
|
m_inventory = &m_player->inventory;
|
||||||
|
}
|
||||||
|
|
||||||
std::string PlayerSAO::getDescription()
|
std::string PlayerSAO::getDescription()
|
||||||
{
|
{
|
||||||
return std::string("player ") + m_player->getName();
|
return std::string("player ") + m_player->getName();
|
||||||
|
@ -833,10 +827,10 @@ std::string PlayerSAO::getDescription()
|
||||||
void PlayerSAO::addedToEnvironment(u32 dtime_s)
|
void PlayerSAO::addedToEnvironment(u32 dtime_s)
|
||||||
{
|
{
|
||||||
ServerActiveObject::addedToEnvironment(dtime_s);
|
ServerActiveObject::addedToEnvironment(dtime_s);
|
||||||
ServerActiveObject::setBasePosition(m_player->getPosition());
|
ServerActiveObject::setBasePosition(m_base_position);
|
||||||
m_player->setPlayerSAO(this);
|
m_player->setPlayerSAO(this);
|
||||||
m_player->peer_id = m_peer_id;
|
m_player->peer_id = m_peer_id;
|
||||||
m_last_good_position = m_player->getPosition();
|
m_last_good_position = m_base_position;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Called before removing from environment
|
// Called before removing from environment
|
||||||
|
@ -844,9 +838,9 @@ void PlayerSAO::removingFromEnvironment()
|
||||||
{
|
{
|
||||||
ServerActiveObject::removingFromEnvironment();
|
ServerActiveObject::removingFromEnvironment();
|
||||||
if (m_player->getPlayerSAO() == this) {
|
if (m_player->getPlayerSAO() == this) {
|
||||||
m_player->setPlayerSAO(NULL);
|
|
||||||
m_player->peer_id = 0;
|
m_player->peer_id = 0;
|
||||||
m_env->savePlayer(m_player);
|
m_env->savePlayer(m_player);
|
||||||
|
m_player->setPlayerSAO(NULL);
|
||||||
m_env->removePlayer(m_player);
|
m_env->removePlayer(m_player);
|
||||||
for (UNORDERED_SET<u32>::iterator it = m_attached_particle_spawners.begin();
|
for (UNORDERED_SET<u32>::iterator it = m_attached_particle_spawners.begin();
|
||||||
it != m_attached_particle_spawners.end(); ++it) {
|
it != m_attached_particle_spawners.end(); ++it) {
|
||||||
|
@ -870,8 +864,8 @@ std::string PlayerSAO::getClientInitializationData(u16 protocol_version)
|
||||||
os<<serializeString(m_player->getName()); // name
|
os<<serializeString(m_player->getName()); // name
|
||||||
writeU8(os, 1); // is_player
|
writeU8(os, 1); // is_player
|
||||||
writeS16(os, getId()); //id
|
writeS16(os, getId()); //id
|
||||||
writeV3F1000(os, m_player->getPosition() + v3f(0,BS*1,0));
|
writeV3F1000(os, m_base_position + v3f(0,BS*1,0));
|
||||||
writeF1000(os, m_player->getYaw());
|
writeF1000(os, m_yaw);
|
||||||
writeS16(os, getHP());
|
writeS16(os, getHP());
|
||||||
|
|
||||||
writeU8(os, 6 + m_bone_position.size() + m_attachment_child_ids.size()); // number of messages stuffed in here
|
writeU8(os, 6 + m_bone_position.size() + m_attachment_child_ids.size()); // number of messages stuffed in here
|
||||||
|
@ -900,8 +894,8 @@ std::string PlayerSAO::getClientInitializationData(u16 protocol_version)
|
||||||
writeU8(os, 0); // version
|
writeU8(os, 0); // version
|
||||||
os<<serializeString(m_player->getName()); // name
|
os<<serializeString(m_player->getName()); // name
|
||||||
writeU8(os, 1); // is_player
|
writeU8(os, 1); // is_player
|
||||||
writeV3F1000(os, m_player->getPosition() + v3f(0,BS*1,0));
|
writeV3F1000(os, m_base_position + v3f(0,BS*1,0));
|
||||||
writeF1000(os, m_player->getYaw());
|
writeF1000(os, m_yaw);
|
||||||
writeS16(os, getHP());
|
writeS16(os, getHP());
|
||||||
writeU8(os, 2); // number of messages stuffed in here
|
writeU8(os, 2); // number of messages stuffed in here
|
||||||
os<<serializeLongString(getPropertyPacket()); // message 1
|
os<<serializeLongString(getPropertyPacket()); // message 1
|
||||||
|
@ -947,7 +941,7 @@ void PlayerSAO::step(float dtime, bool send_recommended)
|
||||||
m_attachment_bone = "";
|
m_attachment_bone = "";
|
||||||
m_attachment_position = v3f(0,0,0);
|
m_attachment_position = v3f(0,0,0);
|
||||||
m_attachment_rotation = v3f(0,0,0);
|
m_attachment_rotation = v3f(0,0,0);
|
||||||
m_player->setPosition(m_last_good_position);
|
setBasePosition(m_last_good_position);
|
||||||
((Server*)m_env->getGameDef())->SendMovePlayer(m_peer_id);
|
((Server*)m_env->getGameDef())->SendMovePlayer(m_peer_id);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -969,14 +963,13 @@ void PlayerSAO::step(float dtime, bool send_recommended)
|
||||||
|
|
||||||
// Each frame, parent position is copied if the object is attached, otherwise it's calculated normally
|
// Each frame, parent position is copied if the object is attached, otherwise it's calculated normally
|
||||||
// If the object gets detached this comes into effect automatically from the last known origin
|
// If the object gets detached this comes into effect automatically from the last known origin
|
||||||
if(isAttached())
|
if (isAttached()) {
|
||||||
{
|
|
||||||
v3f pos = m_env->getActiveObject(m_attachment_parent_id)->getBasePosition();
|
v3f pos = m_env->getActiveObject(m_attachment_parent_id)->getBasePosition();
|
||||||
m_last_good_position = pos;
|
m_last_good_position = pos;
|
||||||
m_player->setPosition(pos);
|
setBasePosition(pos);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(send_recommended == false)
|
if (!send_recommended)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// If the object is attached client-side, don't waste bandwidth sending its position to clients
|
// If the object is attached client-side, don't waste bandwidth sending its position to clients
|
||||||
|
@ -988,12 +981,12 @@ void PlayerSAO::step(float dtime, bool send_recommended)
|
||||||
if(isAttached()) // Just in case we ever do send attachment position too
|
if(isAttached()) // Just in case we ever do send attachment position too
|
||||||
pos = m_env->getActiveObject(m_attachment_parent_id)->getBasePosition();
|
pos = m_env->getActiveObject(m_attachment_parent_id)->getBasePosition();
|
||||||
else
|
else
|
||||||
pos = m_player->getPosition() + v3f(0,BS*1,0);
|
pos = m_base_position + v3f(0,BS*1,0);
|
||||||
std::string str = gob_cmd_update_position(
|
std::string str = gob_cmd_update_position(
|
||||||
pos,
|
pos,
|
||||||
v3f(0,0,0),
|
v3f(0,0,0),
|
||||||
v3f(0,0,0),
|
v3f(0,0,0),
|
||||||
m_player->getYaw(),
|
m_yaw,
|
||||||
true,
|
true,
|
||||||
false,
|
false,
|
||||||
update_interval
|
update_interval
|
||||||
|
@ -1003,7 +996,7 @@ void PlayerSAO::step(float dtime, bool send_recommended)
|
||||||
m_messages_out.push(aom);
|
m_messages_out.push(aom);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(m_armor_groups_sent == false) {
|
if (!m_armor_groups_sent) {
|
||||||
m_armor_groups_sent = true;
|
m_armor_groups_sent = true;
|
||||||
std::string str = gob_cmd_update_armor_groups(
|
std::string str = gob_cmd_update_armor_groups(
|
||||||
m_armor_groups);
|
m_armor_groups);
|
||||||
|
@ -1012,7 +1005,7 @@ void PlayerSAO::step(float dtime, bool send_recommended)
|
||||||
m_messages_out.push(aom);
|
m_messages_out.push(aom);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(m_physics_override_sent == false){
|
if (!m_physics_override_sent) {
|
||||||
m_physics_override_sent = true;
|
m_physics_override_sent = true;
|
||||||
std::string str = gob_cmd_update_physics_override(m_physics_override_speed,
|
std::string str = gob_cmd_update_physics_override(m_physics_override_speed,
|
||||||
m_physics_override_jump, m_physics_override_gravity,
|
m_physics_override_jump, m_physics_override_gravity,
|
||||||
|
@ -1022,7 +1015,7 @@ void PlayerSAO::step(float dtime, bool send_recommended)
|
||||||
m_messages_out.push(aom);
|
m_messages_out.push(aom);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(m_animation_sent == false){
|
if (!m_animation_sent) {
|
||||||
m_animation_sent = true;
|
m_animation_sent = true;
|
||||||
std::string str = gob_cmd_update_animation(
|
std::string str = gob_cmd_update_animation(
|
||||||
m_animation_range, m_animation_speed, m_animation_blend, m_animation_loop);
|
m_animation_range, m_animation_speed, m_animation_blend, m_animation_loop);
|
||||||
|
@ -1055,16 +1048,20 @@ void PlayerSAO::step(float dtime, bool send_recommended)
|
||||||
|
|
||||||
void PlayerSAO::setBasePosition(const v3f &position)
|
void PlayerSAO::setBasePosition(const v3f &position)
|
||||||
{
|
{
|
||||||
|
if (m_player && position != m_base_position)
|
||||||
|
m_player->setDirty(true);
|
||||||
|
|
||||||
// This needs to be ran for attachments too
|
// This needs to be ran for attachments too
|
||||||
ServerActiveObject::setBasePosition(position);
|
ServerActiveObject::setBasePosition(position);
|
||||||
m_position_not_sent = true;
|
m_position_not_sent = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void PlayerSAO::setPos(v3f pos)
|
void PlayerSAO::setPos(const v3f &pos)
|
||||||
{
|
{
|
||||||
if(isAttached())
|
if(isAttached())
|
||||||
return;
|
return;
|
||||||
m_player->setPosition(pos);
|
|
||||||
|
setBasePosition(pos);
|
||||||
// Movement caused by this command is always valid
|
// Movement caused by this command is always valid
|
||||||
m_last_good_position = pos;
|
m_last_good_position = pos;
|
||||||
((Server*)m_env->getGameDef())->SendMovePlayer(m_peer_id);
|
((Server*)m_env->getGameDef())->SendMovePlayer(m_peer_id);
|
||||||
|
@ -1074,22 +1071,34 @@ void PlayerSAO::moveTo(v3f pos, bool continuous)
|
||||||
{
|
{
|
||||||
if(isAttached())
|
if(isAttached())
|
||||||
return;
|
return;
|
||||||
m_player->setPosition(pos);
|
|
||||||
|
setBasePosition(pos);
|
||||||
// Movement caused by this command is always valid
|
// Movement caused by this command is always valid
|
||||||
m_last_good_position = pos;
|
m_last_good_position = pos;
|
||||||
((Server*)m_env->getGameDef())->SendMovePlayer(m_peer_id);
|
((Server*)m_env->getGameDef())->SendMovePlayer(m_peer_id);
|
||||||
}
|
}
|
||||||
|
|
||||||
void PlayerSAO::setYaw(float yaw)
|
void PlayerSAO::setYaw(const float yaw, bool send_data)
|
||||||
{
|
{
|
||||||
m_player->setYaw(yaw);
|
if (m_player && yaw != m_yaw)
|
||||||
((Server*)m_env->getGameDef())->SendMovePlayer(m_peer_id);
|
m_player->setDirty(true);
|
||||||
|
|
||||||
|
UnitSAO::setYaw(yaw);
|
||||||
|
|
||||||
|
// Datas should not be sent at player initialization
|
||||||
|
if (send_data)
|
||||||
|
((Server*)m_env->getGameDef())->SendMovePlayer(m_peer_id);
|
||||||
}
|
}
|
||||||
|
|
||||||
void PlayerSAO::setPitch(float pitch)
|
void PlayerSAO::setPitch(const float pitch, bool send_data)
|
||||||
{
|
{
|
||||||
m_player->setPitch(pitch);
|
if (m_player && pitch != m_pitch)
|
||||||
((Server*)m_env->getGameDef())->SendMovePlayer(m_peer_id);
|
m_player->setDirty(true);
|
||||||
|
|
||||||
|
m_pitch = pitch;
|
||||||
|
|
||||||
|
if (send_data)
|
||||||
|
((Server*)m_env->getGameDef())->SendMovePlayer(m_peer_id);
|
||||||
}
|
}
|
||||||
|
|
||||||
int PlayerSAO::punch(v3f dir,
|
int PlayerSAO::punch(v3f dir,
|
||||||
|
@ -1153,15 +1162,10 @@ int PlayerSAO::punch(v3f dir,
|
||||||
return hitparams.wear;
|
return hitparams.wear;
|
||||||
}
|
}
|
||||||
|
|
||||||
void PlayerSAO::rightClick(ServerActiveObject *clicker)
|
void PlayerSAO::rightClick(ServerActiveObject *)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
s16 PlayerSAO::getHP() const
|
|
||||||
{
|
|
||||||
return m_player->hp;
|
|
||||||
}
|
|
||||||
|
|
||||||
s16 PlayerSAO::readDamage()
|
s16 PlayerSAO::readDamage()
|
||||||
{
|
{
|
||||||
s16 damage = m_damage;
|
s16 damage = m_damage;
|
||||||
|
@ -1169,12 +1173,16 @@ s16 PlayerSAO::readDamage()
|
||||||
return damage;
|
return damage;
|
||||||
}
|
}
|
||||||
|
|
||||||
void PlayerSAO::setHP(s16 hp)
|
void PlayerSAO::setHP(s16 hp, bool direct)
|
||||||
{
|
{
|
||||||
s16 oldhp = m_player->hp;
|
if (direct) {
|
||||||
|
m_hp = hp;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
s16 hp_change = m_env->getScriptIface()->on_player_hpchange(this,
|
s16 oldhp = m_hp;
|
||||||
hp - oldhp);
|
|
||||||
|
s16 hp_change = m_env->getScriptIface()->on_player_hpchange(this, hp - oldhp);
|
||||||
if (hp_change == 0)
|
if (hp_change == 0)
|
||||||
return;
|
return;
|
||||||
hp = oldhp + hp_change;
|
hp = oldhp + hp_change;
|
||||||
|
@ -1184,11 +1192,11 @@ void PlayerSAO::setHP(s16 hp)
|
||||||
else if (hp > PLAYER_MAX_HP)
|
else if (hp > PLAYER_MAX_HP)
|
||||||
hp = PLAYER_MAX_HP;
|
hp = PLAYER_MAX_HP;
|
||||||
|
|
||||||
if(hp < oldhp && g_settings->getBool("enable_damage") == false) {
|
if (hp < oldhp && !g_settings->getBool("enable_damage")) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
m_player->hp = hp;
|
m_hp = hp;
|
||||||
|
|
||||||
if (oldhp > hp)
|
if (oldhp > hp)
|
||||||
m_damage += (oldhp - hp);
|
m_damage += (oldhp - hp);
|
||||||
|
@ -1198,14 +1206,12 @@ void PlayerSAO::setHP(s16 hp)
|
||||||
m_properties_sent = false;
|
m_properties_sent = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
u16 PlayerSAO::getBreath() const
|
void PlayerSAO::setBreath(const u16 breath)
|
||||||
{
|
{
|
||||||
return m_player->getBreath();
|
if (m_player && breath != m_breath)
|
||||||
}
|
m_player->setDirty(true);
|
||||||
|
|
||||||
void PlayerSAO::setBreath(u16 breath)
|
m_breath = breath;
|
||||||
{
|
|
||||||
m_player->setBreath(breath);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void PlayerSAO::setArmorGroups(const ItemGroupList &armor_groups)
|
void PlayerSAO::setArmorGroups(const ItemGroupList &armor_groups)
|
||||||
|
@ -1355,7 +1361,7 @@ bool PlayerSAO::checkMovementCheat()
|
||||||
{
|
{
|
||||||
if (isAttached() || m_is_singleplayer ||
|
if (isAttached() || m_is_singleplayer ||
|
||||||
g_settings->getBool("disable_anticheat")) {
|
g_settings->getBool("disable_anticheat")) {
|
||||||
m_last_good_position = m_player->getPosition();
|
m_last_good_position = m_base_position;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1382,7 +1388,7 @@ bool PlayerSAO::checkMovementCheat()
|
||||||
// Tolerance. The lag pool does this a bit.
|
// Tolerance. The lag pool does this a bit.
|
||||||
//player_max_speed *= 2.5;
|
//player_max_speed *= 2.5;
|
||||||
|
|
||||||
v3f diff = (m_player->getPosition() - m_last_good_position);
|
v3f diff = (m_base_position - m_last_good_position);
|
||||||
float d_vert = diff.Y;
|
float d_vert = diff.Y;
|
||||||
diff.Y = 0;
|
diff.Y = 0;
|
||||||
float d_horiz = diff.getLength();
|
float d_horiz = diff.getLength();
|
||||||
|
@ -1392,27 +1398,26 @@ bool PlayerSAO::checkMovementCheat()
|
||||||
required_time = d_vert / player_max_speed; // Moving upwards
|
required_time = d_vert / player_max_speed; // Moving upwards
|
||||||
|
|
||||||
if (m_move_pool.grab(required_time)) {
|
if (m_move_pool.grab(required_time)) {
|
||||||
m_last_good_position = m_player->getPosition();
|
m_last_good_position = m_base_position;
|
||||||
} else {
|
} else {
|
||||||
actionstream << "Player " << m_player->getName()
|
actionstream << "Player " << m_player->getName()
|
||||||
<< " moved too fast; resetting position"
|
<< " moved too fast; resetting position"
|
||||||
<< std::endl;
|
<< std::endl;
|
||||||
m_player->setPosition(m_last_good_position);
|
setBasePosition(m_last_good_position);
|
||||||
cheated = true;
|
cheated = true;
|
||||||
}
|
}
|
||||||
return cheated;
|
return cheated;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool PlayerSAO::getCollisionBox(aabb3f *toset) {
|
bool PlayerSAO::getCollisionBox(aabb3f *toset)
|
||||||
//update collision box
|
{
|
||||||
*toset = m_player->getCollisionbox();
|
*toset = aabb3f(-BS * 0.30, 0.0, -BS * 0.30, BS * 0.30, BS * 1.75, BS * 0.30);
|
||||||
|
|
||||||
toset->MinEdge += m_base_position;
|
toset->MinEdge += m_base_position;
|
||||||
toset->MaxEdge += m_base_position;
|
toset->MaxEdge += m_base_position;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool PlayerSAO::collideWithObjects(){
|
bool PlayerSAO::collideWithObjects()
|
||||||
|
{
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
|
@ -23,12 +23,35 @@ with this program; if not, write to the Free Software Foundation, Inc.,
|
||||||
#include "serverobject.h"
|
#include "serverobject.h"
|
||||||
#include "itemgroup.h"
|
#include "itemgroup.h"
|
||||||
#include "object_properties.h"
|
#include "object_properties.h"
|
||||||
|
#include "constants.h"
|
||||||
|
|
||||||
|
class UnitSAO: public ServerActiveObject
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
UnitSAO(ServerEnvironment *env, v3f pos):
|
||||||
|
ServerActiveObject(env, pos),
|
||||||
|
m_hp(-1), m_yaw(0) {}
|
||||||
|
virtual ~UnitSAO() {}
|
||||||
|
|
||||||
|
virtual void setYaw(const float yaw) { m_yaw = yaw; }
|
||||||
|
float getYaw() const { return m_yaw; };
|
||||||
|
f32 getRadYaw() const { return m_yaw * core::DEGTORAD; }
|
||||||
|
// Deprecated
|
||||||
|
f32 getRadYawDep() const { return (m_yaw + 90.) * core::DEGTORAD; }
|
||||||
|
|
||||||
|
s16 getHP() const { return m_hp; }
|
||||||
|
// Use a function, if isDead can be defined by other conditions
|
||||||
|
bool isDead() const { return m_hp == 0; }
|
||||||
|
protected:
|
||||||
|
s16 m_hp;
|
||||||
|
float m_yaw;
|
||||||
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
LuaEntitySAO needs some internals exposed.
|
LuaEntitySAO needs some internals exposed.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
class LuaEntitySAO : public ServerActiveObject
|
class LuaEntitySAO : public UnitSAO
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
LuaEntitySAO(ServerEnvironment *env, v3f pos,
|
LuaEntitySAO(ServerEnvironment *env, v3f pos,
|
||||||
|
@ -74,8 +97,7 @@ public:
|
||||||
v3f getVelocity();
|
v3f getVelocity();
|
||||||
void setAcceleration(v3f acceleration);
|
void setAcceleration(v3f acceleration);
|
||||||
v3f getAcceleration();
|
v3f getAcceleration();
|
||||||
void setYaw(float yaw);
|
|
||||||
float getYaw();
|
|
||||||
void setTextureMod(const std::string &mod);
|
void setTextureMod(const std::string &mod);
|
||||||
void setSprite(v2s16 p, int num_frames, float framelength,
|
void setSprite(v2s16 p, int num_frames, float framelength,
|
||||||
bool select_horiz_by_yawpitch);
|
bool select_horiz_by_yawpitch);
|
||||||
|
@ -91,10 +113,9 @@ private:
|
||||||
bool m_registered;
|
bool m_registered;
|
||||||
struct ObjectProperties m_prop;
|
struct ObjectProperties m_prop;
|
||||||
|
|
||||||
s16 m_hp;
|
|
||||||
v3f m_velocity;
|
v3f m_velocity;
|
||||||
v3f m_acceleration;
|
v3f m_acceleration;
|
||||||
float m_yaw;
|
|
||||||
ItemGroupList m_armor_groups;
|
ItemGroupList m_armor_groups;
|
||||||
|
|
||||||
bool m_properties_sent;
|
bool m_properties_sent;
|
||||||
|
@ -158,11 +179,10 @@ public:
|
||||||
|
|
||||||
class RemotePlayer;
|
class RemotePlayer;
|
||||||
|
|
||||||
class PlayerSAO : public ServerActiveObject
|
class PlayerSAO : public UnitSAO
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
PlayerSAO(ServerEnvironment *env_, RemotePlayer *player_, u16 peer_id_,
|
PlayerSAO(ServerEnvironment *env_, u16 peer_id_, bool is_singleplayer);
|
||||||
const std::set<std::string> &privs, bool is_singleplayer);
|
|
||||||
~PlayerSAO();
|
~PlayerSAO();
|
||||||
ActiveObjectType getType() const
|
ActiveObjectType getType() const
|
||||||
{ return ACTIVEOBJECT_TYPE_PLAYER; }
|
{ return ACTIVEOBJECT_TYPE_PLAYER; }
|
||||||
|
@ -182,10 +202,14 @@ public:
|
||||||
bool isAttached();
|
bool isAttached();
|
||||||
void step(float dtime, bool send_recommended);
|
void step(float dtime, bool send_recommended);
|
||||||
void setBasePosition(const v3f &position);
|
void setBasePosition(const v3f &position);
|
||||||
void setPos(v3f pos);
|
void setPos(const v3f &pos);
|
||||||
void moveTo(v3f pos, bool continuous);
|
void moveTo(v3f pos, bool continuous);
|
||||||
void setYaw(float);
|
void setYaw(const float yaw, bool send_data = true);
|
||||||
void setPitch(float);
|
void setPitch(const float pitch, bool send_data = true);
|
||||||
|
f32 getPitch() const { return m_pitch; }
|
||||||
|
f32 getRadPitch() const { return m_pitch * core::DEGTORAD; }
|
||||||
|
// Deprecated
|
||||||
|
f32 getRadPitchDep() const { return -1.0 * m_pitch * core::DEGTORAD; }
|
||||||
|
|
||||||
/*
|
/*
|
||||||
Interaction interface
|
Interaction interface
|
||||||
|
@ -196,11 +220,10 @@ public:
|
||||||
ServerActiveObject *puncher,
|
ServerActiveObject *puncher,
|
||||||
float time_from_last_punch);
|
float time_from_last_punch);
|
||||||
void rightClick(ServerActiveObject *clicker);
|
void rightClick(ServerActiveObject *clicker);
|
||||||
s16 getHP() const;
|
void setHP(s16 hp, bool direct = false);
|
||||||
void setHP(s16 hp);
|
|
||||||
s16 readDamage();
|
s16 readDamage();
|
||||||
u16 getBreath() const;
|
u16 getBreath() const { return m_breath; }
|
||||||
void setBreath(u16 breath);
|
void setBreath(const u16 breath);
|
||||||
void setArmorGroups(const ItemGroupList &armor_groups);
|
void setArmorGroups(const ItemGroupList &armor_groups);
|
||||||
ItemGroupList getArmorGroups();
|
ItemGroupList getArmorGroups();
|
||||||
void setAnimation(v2f frame_range, float frame_speed, float frame_blend, bool frame_loop);
|
void setAnimation(v2f frame_range, float frame_speed, float frame_blend, bool frame_loop);
|
||||||
|
@ -283,6 +306,11 @@ public:
|
||||||
bool getCollisionBox(aabb3f *toset);
|
bool getCollisionBox(aabb3f *toset);
|
||||||
bool collideWithObjects();
|
bool collideWithObjects();
|
||||||
|
|
||||||
|
void initialize(RemotePlayer *player, const std::set<std::string> &privs);
|
||||||
|
|
||||||
|
v3f getEyePosition() const { return m_base_position + getEyeOffset(); }
|
||||||
|
v3f getEyeOffset() const { return v3f(0, BS * 1.625f, 0); }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::string getPropertyPacket();
|
std::string getPropertyPacket();
|
||||||
|
|
||||||
|
@ -326,8 +354,8 @@ private:
|
||||||
v3f m_attachment_position;
|
v3f m_attachment_position;
|
||||||
v3f m_attachment_rotation;
|
v3f m_attachment_rotation;
|
||||||
bool m_attachment_sent;
|
bool m_attachment_sent;
|
||||||
|
u16 m_breath;
|
||||||
|
f32 m_pitch;
|
||||||
public:
|
public:
|
||||||
float m_physics_override_speed;
|
float m_physics_override_speed;
|
||||||
float m_physics_override_jump;
|
float m_physics_override_jump;
|
||||||
|
|
|
@ -608,9 +608,8 @@ void ServerEnvironment::saveLoadedPlayers()
|
||||||
for (std::vector<RemotePlayer *>::iterator it = m_players.begin();
|
for (std::vector<RemotePlayer *>::iterator it = m_players.begin();
|
||||||
it != m_players.end();
|
it != m_players.end();
|
||||||
++it) {
|
++it) {
|
||||||
RemotePlayer *player = static_cast<RemotePlayer*>(*it);
|
if ((*it)->checkModified()) {
|
||||||
if (player->checkModified()) {
|
(*it)->save(players_path, m_gamedef);
|
||||||
player->save(players_path, m_gamedef);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -623,7 +622,7 @@ void ServerEnvironment::savePlayer(RemotePlayer *player)
|
||||||
player->save(players_path, m_gamedef);
|
player->save(players_path, m_gamedef);
|
||||||
}
|
}
|
||||||
|
|
||||||
RemotePlayer *ServerEnvironment::loadPlayer(const std::string &playername)
|
RemotePlayer *ServerEnvironment::loadPlayer(const std::string &playername, PlayerSAO *sao)
|
||||||
{
|
{
|
||||||
bool newplayer = false;
|
bool newplayer = false;
|
||||||
bool found = false;
|
bool found = false;
|
||||||
|
@ -641,7 +640,8 @@ RemotePlayer *ServerEnvironment::loadPlayer(const std::string &playername)
|
||||||
std::ifstream is(path.c_str(), std::ios_base::binary);
|
std::ifstream is(path.c_str(), std::ios_base::binary);
|
||||||
if (!is.good())
|
if (!is.good())
|
||||||
continue;
|
continue;
|
||||||
player->deSerialize(is, path);
|
|
||||||
|
player->deSerialize(is, path, sao);
|
||||||
is.close();
|
is.close();
|
||||||
|
|
||||||
if (player->getName() == playername) {
|
if (player->getName() == playername) {
|
||||||
|
@ -657,11 +657,13 @@ RemotePlayer *ServerEnvironment::loadPlayer(const std::string &playername)
|
||||||
<< " not found" << std::endl;
|
<< " not found" << std::endl;
|
||||||
if (newplayer)
|
if (newplayer)
|
||||||
delete player;
|
delete player;
|
||||||
|
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (newplayer)
|
if (newplayer) {
|
||||||
addPlayer(player);
|
addPlayer(player);
|
||||||
|
}
|
||||||
player->setModified(false);
|
player->setModified(false);
|
||||||
return player;
|
return player;
|
||||||
}
|
}
|
||||||
|
@ -1271,12 +1273,16 @@ void ServerEnvironment::step(float dtime)
|
||||||
i != m_players.end(); ++i) {
|
i != m_players.end(); ++i) {
|
||||||
RemotePlayer *player = dynamic_cast<RemotePlayer *>(*i);
|
RemotePlayer *player = dynamic_cast<RemotePlayer *>(*i);
|
||||||
assert(player);
|
assert(player);
|
||||||
|
|
||||||
// Ignore disconnected players
|
// Ignore disconnected players
|
||||||
if (player->peer_id == 0)
|
if (player->peer_id == 0)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
PlayerSAO *playersao = player->getPlayerSAO();
|
||||||
|
assert(playersao);
|
||||||
|
|
||||||
v3s16 blockpos = getNodeBlockPos(
|
v3s16 blockpos = getNodeBlockPos(
|
||||||
floatToInt(player->getPosition(), BS));
|
floatToInt(playersao->getBasePosition(), BS));
|
||||||
players_blockpos.push_back(blockpos);
|
players_blockpos.push_back(blockpos);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1584,7 +1590,7 @@ u16 ServerEnvironment::addActiveObject(ServerActiveObject *object)
|
||||||
Finds out what new objects have been added to
|
Finds out what new objects have been added to
|
||||||
inside a radius around a position
|
inside a radius around a position
|
||||||
*/
|
*/
|
||||||
void ServerEnvironment::getAddedActiveObjects(RemotePlayer *player, s16 radius,
|
void ServerEnvironment::getAddedActiveObjects(PlayerSAO *playersao, s16 radius,
|
||||||
s16 player_radius,
|
s16 player_radius,
|
||||||
std::set<u16> ¤t_objects,
|
std::set<u16> ¤t_objects,
|
||||||
std::queue<u16> &added_objects)
|
std::queue<u16> &added_objects)
|
||||||
|
@ -1594,7 +1600,6 @@ void ServerEnvironment::getAddedActiveObjects(RemotePlayer *player, s16 radius,
|
||||||
|
|
||||||
if (player_radius_f < 0)
|
if (player_radius_f < 0)
|
||||||
player_radius_f = 0;
|
player_radius_f = 0;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
Go through the object list,
|
Go through the object list,
|
||||||
- discard m_removed objects,
|
- discard m_removed objects,
|
||||||
|
@ -1602,20 +1607,21 @@ void ServerEnvironment::getAddedActiveObjects(RemotePlayer *player, s16 radius,
|
||||||
- discard objects that are found in current_objects.
|
- discard objects that are found in current_objects.
|
||||||
- add remaining objects to added_objects
|
- add remaining objects to added_objects
|
||||||
*/
|
*/
|
||||||
for(ActiveObjectMap::iterator i = m_active_objects.begin();
|
for (ActiveObjectMap::iterator i = m_active_objects.begin();
|
||||||
i != m_active_objects.end(); ++i) {
|
i != m_active_objects.end(); ++i) {
|
||||||
u16 id = i->first;
|
u16 id = i->first;
|
||||||
|
|
||||||
// Get object
|
// Get object
|
||||||
ServerActiveObject *object = i->second;
|
ServerActiveObject *object = i->second;
|
||||||
if(object == NULL)
|
if (object == NULL)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
// Discard if removed or deactivating
|
// Discard if removed or deactivating
|
||||||
if(object->m_removed || object->m_pending_deactivation)
|
if(object->m_removed || object->m_pending_deactivation)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
f32 distance_f = object->getBasePosition().getDistanceFrom(player->getPosition());
|
f32 distance_f = object->getBasePosition().
|
||||||
|
getDistanceFrom(playersao->getBasePosition());
|
||||||
if (object->getType() == ACTIVEOBJECT_TYPE_PLAYER) {
|
if (object->getType() == ACTIVEOBJECT_TYPE_PLAYER) {
|
||||||
// Discard if too far
|
// Discard if too far
|
||||||
if (distance_f > player_radius_f && player_radius_f != 0)
|
if (distance_f > player_radius_f && player_radius_f != 0)
|
||||||
|
@ -1637,7 +1643,7 @@ void ServerEnvironment::getAddedActiveObjects(RemotePlayer *player, s16 radius,
|
||||||
Finds out what objects have been removed from
|
Finds out what objects have been removed from
|
||||||
inside a radius around a position
|
inside a radius around a position
|
||||||
*/
|
*/
|
||||||
void ServerEnvironment::getRemovedActiveObjects(RemotePlayer *player, s16 radius,
|
void ServerEnvironment::getRemovedActiveObjects(PlayerSAO *playersao, s16 radius,
|
||||||
s16 player_radius,
|
s16 player_radius,
|
||||||
std::set<u16> ¤t_objects,
|
std::set<u16> ¤t_objects,
|
||||||
std::queue<u16> &removed_objects)
|
std::queue<u16> &removed_objects)
|
||||||
|
@ -1647,7 +1653,6 @@ void ServerEnvironment::getRemovedActiveObjects(RemotePlayer *player, s16 radius
|
||||||
|
|
||||||
if (player_radius_f < 0)
|
if (player_radius_f < 0)
|
||||||
player_radius_f = 0;
|
player_radius_f = 0;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
Go through current_objects; object is removed if:
|
Go through current_objects; object is removed if:
|
||||||
- object is not found in m_active_objects (this is actually an
|
- object is not found in m_active_objects (this is actually an
|
||||||
|
@ -1675,7 +1680,7 @@ void ServerEnvironment::getRemovedActiveObjects(RemotePlayer *player, s16 radius
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
f32 distance_f = object->getBasePosition().getDistanceFrom(player->getPosition());
|
f32 distance_f = object->getBasePosition().getDistanceFrom(playersao->getBasePosition());
|
||||||
if (object->getType() == ACTIVEOBJECT_TYPE_PLAYER) {
|
if (object->getType() == ACTIVEOBJECT_TYPE_PLAYER) {
|
||||||
if (distance_f <= player_radius_f || player_radius_f == 0)
|
if (distance_f <= player_radius_f || player_radius_f == 0)
|
||||||
continue;
|
continue;
|
||||||
|
|
|
@ -54,6 +54,7 @@ class ClientMap;
|
||||||
class GameScripting;
|
class GameScripting;
|
||||||
class Player;
|
class Player;
|
||||||
class RemotePlayer;
|
class RemotePlayer;
|
||||||
|
class PlayerSAO;
|
||||||
|
|
||||||
class Environment
|
class Environment
|
||||||
{
|
{
|
||||||
|
@ -315,7 +316,7 @@ public:
|
||||||
// Save players
|
// Save players
|
||||||
void saveLoadedPlayers();
|
void saveLoadedPlayers();
|
||||||
void savePlayer(RemotePlayer *player);
|
void savePlayer(RemotePlayer *player);
|
||||||
RemotePlayer *loadPlayer(const std::string &playername);
|
RemotePlayer *loadPlayer(const std::string &playername, PlayerSAO *sao);
|
||||||
void addPlayer(RemotePlayer *player);
|
void addPlayer(RemotePlayer *player);
|
||||||
void removePlayer(RemotePlayer *player);
|
void removePlayer(RemotePlayer *player);
|
||||||
|
|
||||||
|
@ -362,7 +363,7 @@ public:
|
||||||
Find out what new objects have been added to
|
Find out what new objects have been added to
|
||||||
inside a radius around a position
|
inside a radius around a position
|
||||||
*/
|
*/
|
||||||
void getAddedActiveObjects(RemotePlayer *player, s16 radius,
|
void getAddedActiveObjects(PlayerSAO *playersao, s16 radius,
|
||||||
s16 player_radius,
|
s16 player_radius,
|
||||||
std::set<u16> ¤t_objects,
|
std::set<u16> ¤t_objects,
|
||||||
std::queue<u16> &added_objects);
|
std::queue<u16> &added_objects);
|
||||||
|
@ -371,7 +372,7 @@ public:
|
||||||
Find out what new objects have been removed from
|
Find out what new objects have been removed from
|
||||||
inside a radius around a position
|
inside a radius around a position
|
||||||
*/
|
*/
|
||||||
void getRemovedActiveObjects(RemotePlayer *player, s16 radius,
|
void getRemovedActiveObjects(PlayerSAO *playersao, s16 radius,
|
||||||
s16 player_radius,
|
s16 player_radius,
|
||||||
std::set<u16> ¤t_objects,
|
std::set<u16> ¤t_objects,
|
||||||
std::queue<u16> &removed_objects);
|
std::queue<u16> &removed_objects);
|
||||||
|
|
|
@ -35,6 +35,7 @@ with this program; if not, write to the Free Software Foundation, Inc.,
|
||||||
LocalPlayer::LocalPlayer(Client *gamedef, const char *name):
|
LocalPlayer::LocalPlayer(Client *gamedef, const char *name):
|
||||||
Player(name, gamedef->idef()),
|
Player(name, gamedef->idef()),
|
||||||
parent(0),
|
parent(0),
|
||||||
|
hp(PLAYER_MAX_HP),
|
||||||
got_teleported(false),
|
got_teleported(false),
|
||||||
isAttached(false),
|
isAttached(false),
|
||||||
touching_ground(false),
|
touching_ground(false),
|
||||||
|
@ -62,6 +63,7 @@ LocalPlayer::LocalPlayer(Client *gamedef, const char *name):
|
||||||
light_color(255,255,255,255),
|
light_color(255,255,255,255),
|
||||||
hurt_tilt_timer(0.0f),
|
hurt_tilt_timer(0.0f),
|
||||||
hurt_tilt_strength(0.0f),
|
hurt_tilt_strength(0.0f),
|
||||||
|
m_position(0,0,0),
|
||||||
m_sneak_node(32767,32767,32767),
|
m_sneak_node(32767,32767,32767),
|
||||||
m_sneak_node_exists(false),
|
m_sneak_node_exists(false),
|
||||||
m_need_to_get_new_sneak_node(true),
|
m_need_to_get_new_sneak_node(true),
|
||||||
|
@ -69,6 +71,11 @@ LocalPlayer::LocalPlayer(Client *gamedef, const char *name):
|
||||||
m_old_node_below(32767,32767,32767),
|
m_old_node_below(32767,32767,32767),
|
||||||
m_old_node_below_type("air"),
|
m_old_node_below_type("air"),
|
||||||
m_can_jump(false),
|
m_can_jump(false),
|
||||||
|
m_breath(PLAYER_MAX_BREATH),
|
||||||
|
m_yaw(0),
|
||||||
|
m_pitch(0),
|
||||||
|
camera_barely_in_ceiling(false),
|
||||||
|
m_collisionbox(-BS * 0.30, 0.0, -BS * 0.30, BS * 0.30, BS * 1.75, BS * 0.30),
|
||||||
m_cao(NULL),
|
m_cao(NULL),
|
||||||
m_gamedef(gamedef)
|
m_gamedef(gamedef)
|
||||||
{
|
{
|
||||||
|
|
|
@ -40,6 +40,7 @@ public:
|
||||||
|
|
||||||
ClientActiveObject *parent;
|
ClientActiveObject *parent;
|
||||||
|
|
||||||
|
u16 hp;
|
||||||
bool got_teleported;
|
bool got_teleported;
|
||||||
bool isAttached;
|
bool isAttached;
|
||||||
bool touching_ground;
|
bool touching_ground;
|
||||||
|
@ -99,10 +100,45 @@ public:
|
||||||
|
|
||||||
u32 maxHudId() const { return hud.size(); }
|
u32 maxHudId() const { return hud.size(); }
|
||||||
|
|
||||||
|
u16 getBreath() const { return m_breath; }
|
||||||
|
void setBreath(u16 breath) { m_breath = breath; }
|
||||||
|
|
||||||
|
v3s16 getLightPosition() const
|
||||||
|
{
|
||||||
|
return floatToInt(m_position + v3f(0,BS+BS/2,0), BS);
|
||||||
|
}
|
||||||
|
|
||||||
|
void setYaw(f32 yaw)
|
||||||
|
{
|
||||||
|
m_yaw = yaw;
|
||||||
|
}
|
||||||
|
|
||||||
|
f32 getYaw() const { return m_yaw; }
|
||||||
|
|
||||||
|
void setPitch(f32 pitch)
|
||||||
|
{
|
||||||
|
m_pitch = pitch;
|
||||||
|
}
|
||||||
|
|
||||||
|
f32 getPitch() const { return m_pitch; }
|
||||||
|
|
||||||
|
void setPosition(const v3f &position)
|
||||||
|
{
|
||||||
|
m_position = position;
|
||||||
|
}
|
||||||
|
|
||||||
|
v3f getPosition() const { return m_position; }
|
||||||
|
v3f getEyePosition() const { return m_position + getEyeOffset(); }
|
||||||
|
v3f getEyeOffset() const
|
||||||
|
{
|
||||||
|
float eye_height = camera_barely_in_ceiling ? 1.5f : 1.625f;
|
||||||
|
return v3f(0, BS * eye_height, 0);
|
||||||
|
}
|
||||||
private:
|
private:
|
||||||
void accelerateHorizontal(const v3f &target_speed, const f32 max_increase);
|
void accelerateHorizontal(const v3f &target_speed, const f32 max_increase);
|
||||||
void accelerateVertical(const v3f &target_speed, const f32 max_increase);
|
void accelerateVertical(const v3f &target_speed, const f32 max_increase);
|
||||||
|
|
||||||
|
v3f m_position;
|
||||||
// This is used for determining the sneaking range
|
// This is used for determining the sneaking range
|
||||||
v3s16 m_sneak_node;
|
v3s16 m_sneak_node;
|
||||||
// Whether the player is allowed to sneak
|
// Whether the player is allowed to sneak
|
||||||
|
@ -117,6 +153,11 @@ private:
|
||||||
v3s16 m_old_node_below;
|
v3s16 m_old_node_below;
|
||||||
std::string m_old_node_below_type;
|
std::string m_old_node_below_type;
|
||||||
bool m_can_jump;
|
bool m_can_jump;
|
||||||
|
u16 m_breath;
|
||||||
|
f32 m_yaw;
|
||||||
|
f32 m_pitch;
|
||||||
|
bool camera_barely_in_ceiling;
|
||||||
|
aabb3f m_collisionbox;
|
||||||
|
|
||||||
GenericCAO* m_cao;
|
GenericCAO* m_cao;
|
||||||
Client *m_gamedef;
|
Client *m_gamedef;
|
||||||
|
|
|
@ -634,7 +634,6 @@ void Client::handleCommand_AnnounceMedia(NetworkPacket* pkt)
|
||||||
m_media_downloader->addFile(name, sha1_raw);
|
m_media_downloader->addFile(name, sha1_raw);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<std::string> remote_media;
|
|
||||||
try {
|
try {
|
||||||
std::string str;
|
std::string str;
|
||||||
|
|
||||||
|
|
|
@ -809,13 +809,6 @@ void Server::handleCommand_PlayerPos(NetworkPacket* pkt)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// If player is dead we don't care of this packet
|
|
||||||
if (player->isDead()) {
|
|
||||||
verbosestream << "TOSERVER_PLAYERPOS: " << player->getName()
|
|
||||||
<< " is dead. Ignoring packet";
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
PlayerSAO *playersao = player->getPlayerSAO();
|
PlayerSAO *playersao = player->getPlayerSAO();
|
||||||
if (playersao == NULL) {
|
if (playersao == NULL) {
|
||||||
errorstream << "Server::ProcessData(): Canceling: "
|
errorstream << "Server::ProcessData(): Canceling: "
|
||||||
|
@ -825,10 +818,17 @@ void Server::handleCommand_PlayerPos(NetworkPacket* pkt)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
player->setPosition(position);
|
// If player is dead we don't care of this packet
|
||||||
|
if (playersao->isDead()) {
|
||||||
|
verbosestream << "TOSERVER_PLAYERPOS: " << player->getName()
|
||||||
|
<< " is dead. Ignoring packet";
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
playersao->setBasePosition(position);
|
||||||
player->setSpeed(speed);
|
player->setSpeed(speed);
|
||||||
player->setPitch(pitch);
|
playersao->setPitch(pitch, false);
|
||||||
player->setYaw(yaw);
|
playersao->setYaw(yaw, false);
|
||||||
player->keyPressed = keyPressed;
|
player->keyPressed = keyPressed;
|
||||||
player->control.up = (keyPressed & 1);
|
player->control.up = (keyPressed & 1);
|
||||||
player->control.down = (keyPressed & 2);
|
player->control.down = (keyPressed & 2);
|
||||||
|
@ -1100,7 +1100,7 @@ void Server::handleCommand_Damage(NetworkPacket* pkt)
|
||||||
|
|
||||||
if (g_settings->getBool("enable_damage")) {
|
if (g_settings->getBool("enable_damage")) {
|
||||||
actionstream << player->getName() << " damaged by "
|
actionstream << player->getName() << " damaged by "
|
||||||
<< (int)damage << " hp at " << PP(player->getPosition() / BS)
|
<< (int)damage << " hp at " << PP(playersao->getBasePosition() / BS)
|
||||||
<< std::endl;
|
<< std::endl;
|
||||||
|
|
||||||
playersao->setHP(playersao->getHP() - damage);
|
playersao->setHP(playersao->getHP() - damage);
|
||||||
|
@ -1124,16 +1124,6 @@ void Server::handleCommand_Breath(NetworkPacket* pkt)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* If player is dead, we don't need to update the breath
|
|
||||||
* He is dead !
|
|
||||||
*/
|
|
||||||
if (player->isDead()) {
|
|
||||||
verbosestream << "TOSERVER_BREATH: " << player->getName()
|
|
||||||
<< " is dead. Ignoring packet";
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
PlayerSAO *playersao = player->getPlayerSAO();
|
PlayerSAO *playersao = player->getPlayerSAO();
|
||||||
if (playersao == NULL) {
|
if (playersao == NULL) {
|
||||||
|
@ -1144,6 +1134,16 @@ void Server::handleCommand_Breath(NetworkPacket* pkt)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* If player is dead, we don't need to update the breath
|
||||||
|
* He is dead !
|
||||||
|
*/
|
||||||
|
if (playersao->isDead()) {
|
||||||
|
verbosestream << "TOSERVER_BREATH: " << player->getName()
|
||||||
|
<< " is dead. Ignoring packet";
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
playersao->setBreath(breath);
|
playersao->setBreath(breath);
|
||||||
SendPlayerBreath(pkt->getPeerId());
|
SendPlayerBreath(pkt->getPeerId());
|
||||||
}
|
}
|
||||||
|
@ -1264,13 +1264,16 @@ void Server::handleCommand_Respawn(NetworkPacket* pkt)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!player->isDead())
|
PlayerSAO *playersao = player->getPlayerSAO();
|
||||||
|
assert(playersao);
|
||||||
|
|
||||||
|
if (!playersao->isDead())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
RespawnPlayer(pkt->getPeerId());
|
RespawnPlayer(pkt->getPeerId());
|
||||||
|
|
||||||
actionstream << player->getName() << " respawns at "
|
actionstream << player->getName() << " respawns at "
|
||||||
<< PP(player->getPosition()/BS) << std::endl;
|
<< PP(playersao->getBasePosition() / BS) << std::endl;
|
||||||
|
|
||||||
// ActiveObject is added to environment in AsyncRunStep after
|
// ActiveObject is added to environment in AsyncRunStep after
|
||||||
// the previous addition has been successfully removed
|
// the previous addition has been successfully removed
|
||||||
|
@ -1322,9 +1325,9 @@ void Server::handleCommand_Interact(NetworkPacket* pkt)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (player->isDead()) {
|
if (playersao->isDead()) {
|
||||||
verbosestream << "TOSERVER_INTERACT: " << player->getName()
|
verbosestream << "TOSERVER_INTERACT: " << player->getName()
|
||||||
<< " is dead. Ignoring packet";
|
<< " is dead. Ignoring packet";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1455,7 +1458,7 @@ void Server::handleCommand_Interact(NetworkPacket* pkt)
|
||||||
ToolCapabilities toolcap =
|
ToolCapabilities toolcap =
|
||||||
punchitem.getToolCapabilities(m_itemdef);
|
punchitem.getToolCapabilities(m_itemdef);
|
||||||
v3f dir = (pointed_object->getBasePosition() -
|
v3f dir = (pointed_object->getBasePosition() -
|
||||||
(player->getPosition() + player->getEyeOffset())
|
(playersao->getBasePosition() + playersao->getEyeOffset())
|
||||||
).normalize();
|
).normalize();
|
||||||
float time_from_last_punch =
|
float time_from_last_punch =
|
||||||
playersao->resetTimeFromLastPunch();
|
playersao->resetTimeFromLastPunch();
|
||||||
|
|
|
@ -30,18 +30,11 @@ with this program; if not, write to the Free Software Foundation, Inc.,
|
||||||
|
|
||||||
|
|
||||||
Player::Player(const char *name, IItemDefManager *idef):
|
Player::Player(const char *name, IItemDefManager *idef):
|
||||||
camera_barely_in_ceiling(false),
|
|
||||||
inventory(idef),
|
inventory(idef),
|
||||||
hp(PLAYER_MAX_HP),
|
|
||||||
peer_id(PEER_ID_INEXISTENT),
|
peer_id(PEER_ID_INEXISTENT),
|
||||||
keyPressed(0),
|
keyPressed(0),
|
||||||
// protected
|
// protected
|
||||||
m_breath(PLAYER_MAX_BREATH),
|
m_speed(0,0,0)
|
||||||
m_pitch(0),
|
|
||||||
m_yaw(0),
|
|
||||||
m_speed(0,0,0),
|
|
||||||
m_position(0,0,0),
|
|
||||||
m_collisionbox(-BS*0.30,0.0,-BS*0.30,BS*0.30,BS*1.75,BS*0.30)
|
|
||||||
{
|
{
|
||||||
strlcpy(m_name, name, PLAYERNAME_SIZE);
|
strlcpy(m_name, name, PLAYERNAME_SIZE);
|
||||||
|
|
||||||
|
@ -90,11 +83,6 @@ Player::~Player()
|
||||||
clearHud();
|
clearHud();
|
||||||
}
|
}
|
||||||
|
|
||||||
v3s16 Player::getLightPosition() const
|
|
||||||
{
|
|
||||||
return floatToInt(m_position + v3f(0,BS+BS/2,0), BS);
|
|
||||||
}
|
|
||||||
|
|
||||||
u32 Player::addHud(HudElement *toadd)
|
u32 Player::addHud(HudElement *toadd)
|
||||||
{
|
{
|
||||||
MutexAutoLock lock(m_mutex);
|
MutexAutoLock lock(m_mutex);
|
||||||
|
|
50
src/player.h
50
src/player.h
|
@ -129,49 +129,7 @@ public:
|
||||||
m_speed = speed;
|
m_speed = speed;
|
||||||
}
|
}
|
||||||
|
|
||||||
v3f getPosition()
|
|
||||||
{
|
|
||||||
return m_position;
|
|
||||||
}
|
|
||||||
|
|
||||||
v3s16 getLightPosition() const;
|
|
||||||
|
|
||||||
v3f getEyeOffset()
|
|
||||||
{
|
|
||||||
float eye_height = camera_barely_in_ceiling ? 1.5f : 1.625f;
|
|
||||||
return v3f(0, BS * eye_height, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
v3f getEyePosition()
|
|
||||||
{
|
|
||||||
return m_position + getEyeOffset();
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void setPosition(const v3f &position)
|
|
||||||
{
|
|
||||||
m_position = position;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void setPitch(f32 pitch)
|
|
||||||
{
|
|
||||||
m_pitch = pitch;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void setYaw(f32 yaw)
|
|
||||||
{
|
|
||||||
m_yaw = yaw;
|
|
||||||
}
|
|
||||||
|
|
||||||
f32 getPitch() const { return m_pitch; }
|
|
||||||
f32 getYaw() const { return m_yaw; }
|
|
||||||
u16 getBreath() const { return m_breath; }
|
|
||||||
|
|
||||||
virtual void setBreath(u16 breath) { m_breath = breath; }
|
|
||||||
|
|
||||||
f32 getRadPitch() const { return m_pitch * core::DEGTORAD; }
|
|
||||||
f32 getRadYaw() const { return m_yaw * core::DEGTORAD; }
|
|
||||||
const char *getName() const { return m_name; }
|
const char *getName() const { return m_name; }
|
||||||
aabb3f getCollisionbox() const { return m_collisionbox; }
|
|
||||||
|
|
||||||
u32 getFreeHudID()
|
u32 getFreeHudID()
|
||||||
{
|
{
|
||||||
|
@ -183,7 +141,6 @@ public:
|
||||||
return size;
|
return size;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool camera_barely_in_ceiling;
|
|
||||||
v3f eye_offset_first;
|
v3f eye_offset_first;
|
||||||
v3f eye_offset_third;
|
v3f eye_offset_third;
|
||||||
|
|
||||||
|
@ -205,8 +162,6 @@ public:
|
||||||
v2s32 local_animations[4];
|
v2s32 local_animations[4];
|
||||||
float local_animation_speed;
|
float local_animation_speed;
|
||||||
|
|
||||||
u16 hp;
|
|
||||||
|
|
||||||
u16 peer_id;
|
u16 peer_id;
|
||||||
|
|
||||||
std::string inventory_formspec;
|
std::string inventory_formspec;
|
||||||
|
@ -225,12 +180,7 @@ public:
|
||||||
s32 hud_hotbar_itemcount;
|
s32 hud_hotbar_itemcount;
|
||||||
protected:
|
protected:
|
||||||
char m_name[PLAYERNAME_SIZE];
|
char m_name[PLAYERNAME_SIZE];
|
||||||
u16 m_breath;
|
|
||||||
f32 m_pitch;
|
|
||||||
f32 m_yaw;
|
|
||||||
v3f m_speed;
|
v3f m_speed;
|
||||||
v3f m_position;
|
|
||||||
aabb3f m_collisionbox;
|
|
||||||
|
|
||||||
std::vector<HudElement *> hud;
|
std::vector<HudElement *> hud;
|
||||||
private:
|
private:
|
||||||
|
|
|
@ -96,7 +96,7 @@ void RemotePlayer::save(std::string savedir, IGameDef *gamedef)
|
||||||
infostream << "Failed to open " << path << std::endl;
|
infostream << "Failed to open " << path << std::endl;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
testplayer.deSerialize(is, path);
|
testplayer.deSerialize(is, path, NULL);
|
||||||
is.close();
|
is.close();
|
||||||
if (strcmp(testplayer.getName(), m_name) == 0) {
|
if (strcmp(testplayer.getName(), m_name) == 0) {
|
||||||
// Open file and serialize
|
// Open file and serialize
|
||||||
|
@ -115,37 +115,46 @@ void RemotePlayer::save(std::string savedir, IGameDef *gamedef)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
void RemotePlayer::deSerialize(std::istream &is, const std::string &playername)
|
void RemotePlayer::deSerialize(std::istream &is, const std::string &playername,
|
||||||
|
PlayerSAO *sao)
|
||||||
{
|
{
|
||||||
Settings args;
|
Settings args;
|
||||||
|
|
||||||
if (!args.parseConfigLines(is, "PlayerArgsEnd")) {
|
if (!args.parseConfigLines(is, "PlayerArgsEnd")) {
|
||||||
throw SerializationError("PlayerArgsEnd of player " +
|
throw SerializationError("PlayerArgsEnd of player " + playername + " not found!");
|
||||||
playername + " not found!");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
m_dirty = true;
|
m_dirty = true;
|
||||||
//args.getS32("version"); // Version field value not used
|
//args.getS32("version"); // Version field value not used
|
||||||
std::string name = args.get("name");
|
std::string name = args.get("name");
|
||||||
strlcpy(m_name, name.c_str(), PLAYERNAME_SIZE);
|
strlcpy(m_name, name.c_str(), PLAYERNAME_SIZE);
|
||||||
setPitch(args.getFloat("pitch"));
|
|
||||||
setYaw(args.getFloat("yaw"));
|
|
||||||
setPosition(args.getV3F("position"));
|
|
||||||
try {
|
|
||||||
hp = args.getS32("hp");
|
|
||||||
} catch(SettingNotFoundException &e) {
|
|
||||||
hp = PLAYER_MAX_HP;
|
|
||||||
}
|
|
||||||
|
|
||||||
try {
|
if (sao) {
|
||||||
m_breath = args.getS32("breath");
|
try {
|
||||||
} catch(SettingNotFoundException &e) {
|
sao->setHP(args.getS32("hp"), true);
|
||||||
m_breath = PLAYER_MAX_BREATH;
|
} catch(SettingNotFoundException &e) {
|
||||||
|
sao->setHP(PLAYER_MAX_HP, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
sao->setBasePosition(args.getV3F("position"));
|
||||||
|
} catch (SettingNotFoundException &e) {}
|
||||||
|
|
||||||
|
try {
|
||||||
|
sao->setPitch(args.getFloat("pitch"), false);
|
||||||
|
} catch (SettingNotFoundException &e) {}
|
||||||
|
try {
|
||||||
|
sao->setYaw(args.getFloat("yaw"), false);
|
||||||
|
} catch (SettingNotFoundException &e) {}
|
||||||
|
|
||||||
|
try {
|
||||||
|
sao->setBreath(args.getS32("breath"));
|
||||||
|
} catch (SettingNotFoundException &e) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
inventory.deSerialize(is);
|
inventory.deSerialize(is);
|
||||||
|
|
||||||
if(inventory.getList("craftpreview") == NULL) {
|
if (inventory.getList("craftpreview") == NULL) {
|
||||||
// Convert players without craftpreview
|
// Convert players without craftpreview
|
||||||
inventory.addList("craftpreview", 1);
|
inventory.addList("craftpreview", 1);
|
||||||
|
|
||||||
|
@ -167,11 +176,14 @@ void RemotePlayer::serialize(std::ostream &os)
|
||||||
args.setS32("version", 1);
|
args.setS32("version", 1);
|
||||||
args.set("name", m_name);
|
args.set("name", m_name);
|
||||||
//args.set("password", m_password);
|
//args.set("password", m_password);
|
||||||
args.setFloat("pitch", m_pitch);
|
|
||||||
args.setFloat("yaw", m_yaw);
|
if (m_sao) {
|
||||||
args.setV3F("position", m_position);
|
args.setS32("hp", m_sao->getHP());
|
||||||
args.setS32("hp", hp);
|
args.setV3F("position", m_sao->getBasePosition());
|
||||||
args.setS32("breath", m_breath);
|
args.setFloat("pitch", m_sao->getPitch());
|
||||||
|
args.setFloat("yaw", m_sao->getYaw());
|
||||||
|
args.setS32("breath", m_sao->getBreath());
|
||||||
|
}
|
||||||
|
|
||||||
args.writeLines(os);
|
args.writeLines(os);
|
||||||
|
|
||||||
|
@ -180,16 +192,6 @@ void RemotePlayer::serialize(std::ostream &os)
|
||||||
inventory.serialize(os);
|
inventory.serialize(os);
|
||||||
}
|
}
|
||||||
|
|
||||||
void RemotePlayer::setPosition(const v3f &position)
|
|
||||||
{
|
|
||||||
if (position != m_position)
|
|
||||||
m_dirty = true;
|
|
||||||
|
|
||||||
Player::setPosition(position);
|
|
||||||
if(m_sao)
|
|
||||||
m_sao->setBasePosition(position);
|
|
||||||
}
|
|
||||||
|
|
||||||
const RemotePlayerChatResult RemotePlayer::canSendChatMessage()
|
const RemotePlayerChatResult RemotePlayer::canSendChatMessage()
|
||||||
{
|
{
|
||||||
// Rate limit messages
|
// Rate limit messages
|
||||||
|
|
|
@ -40,11 +40,10 @@ public:
|
||||||
virtual ~RemotePlayer() {}
|
virtual ~RemotePlayer() {}
|
||||||
|
|
||||||
void save(std::string savedir, IGameDef *gamedef);
|
void save(std::string savedir, IGameDef *gamedef);
|
||||||
void deSerialize(std::istream &is, const std::string &playername);
|
void deSerialize(std::istream &is, const std::string &playername, PlayerSAO *sao);
|
||||||
|
|
||||||
PlayerSAO *getPlayerSAO() { return m_sao; }
|
PlayerSAO *getPlayerSAO() { return m_sao; }
|
||||||
void setPlayerSAO(PlayerSAO *sao) { m_sao = sao; }
|
void setPlayerSAO(PlayerSAO *sao) { m_sao = sao; }
|
||||||
void setPosition(const v3f &position);
|
|
||||||
|
|
||||||
const RemotePlayerChatResult canSendChatMessage();
|
const RemotePlayerChatResult canSendChatMessage();
|
||||||
|
|
||||||
|
@ -67,9 +66,6 @@ public:
|
||||||
*ratio = m_day_night_ratio;
|
*ratio = m_day_night_ratio;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Use a function, if isDead can be defined by other conditions
|
|
||||||
bool isDead() const { return hp == 0; }
|
|
||||||
|
|
||||||
void setHotbarImage(const std::string &name)
|
void setHotbarImage(const std::string &name)
|
||||||
{
|
{
|
||||||
hud_hotbar_image = name;
|
hud_hotbar_image = name;
|
||||||
|
@ -90,12 +86,6 @@ public:
|
||||||
return hud_hotbar_selected_image;
|
return hud_hotbar_selected_image;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Deprecated
|
|
||||||
f32 getRadPitchDep() const { return -1.0 * m_pitch * core::DEGTORAD; }
|
|
||||||
|
|
||||||
// Deprecated
|
|
||||||
f32 getRadYawDep() const { return (m_yaw + 90.) * core::DEGTORAD; }
|
|
||||||
|
|
||||||
void setSky(const video::SColor &bgcolor, const std::string &type,
|
void setSky(const video::SColor &bgcolor, const std::string &type,
|
||||||
const std::vector<std::string> ¶ms)
|
const std::vector<std::string> ¶ms)
|
||||||
{
|
{
|
||||||
|
@ -121,27 +111,6 @@ public:
|
||||||
inventory.setModified(x);
|
inventory.setModified(x);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void setBreath(u16 breath)
|
|
||||||
{
|
|
||||||
if (breath != m_breath)
|
|
||||||
m_dirty = true;
|
|
||||||
Player::setBreath(breath);
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void setPitch(f32 pitch)
|
|
||||||
{
|
|
||||||
if (pitch != m_pitch)
|
|
||||||
m_dirty = true;
|
|
||||||
Player::setPitch(pitch);
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void setYaw(f32 yaw)
|
|
||||||
{
|
|
||||||
if (yaw != m_yaw)
|
|
||||||
m_dirty = true;
|
|
||||||
Player::setYaw(yaw);
|
|
||||||
}
|
|
||||||
|
|
||||||
void setLocalAnimations(v2s32 frames[4], float frame_speed)
|
void setLocalAnimations(v2s32 frames[4], float frame_speed)
|
||||||
{
|
{
|
||||||
for (int i = 0; i < 4; i++)
|
for (int i = 0; i < 4; i++)
|
||||||
|
@ -156,6 +125,8 @@ public:
|
||||||
*frame_speed = local_animation_speed;
|
*frame_speed = local_animation_speed;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void setDirty(bool dirty) { m_dirty = true; }
|
||||||
|
|
||||||
u16 protocol_version;
|
u16 protocol_version;
|
||||||
private:
|
private:
|
||||||
/*
|
/*
|
||||||
|
|
|
@ -1013,11 +1013,11 @@ int ObjectRef::l_get_look_dir(lua_State *L)
|
||||||
{
|
{
|
||||||
NO_MAP_LOCK_REQUIRED;
|
NO_MAP_LOCK_REQUIRED;
|
||||||
ObjectRef *ref = checkobject(L, 1);
|
ObjectRef *ref = checkobject(L, 1);
|
||||||
RemotePlayer *player = getplayer(ref);
|
PlayerSAO* co = getplayersao(ref);
|
||||||
if (player == NULL) return 0;
|
if (co == NULL) return 0;
|
||||||
// Do it
|
// Do it
|
||||||
float pitch = player->getRadPitchDep();
|
float pitch = co->getRadPitchDep();
|
||||||
float yaw = player->getRadYawDep();
|
float yaw = co->getRadYawDep();
|
||||||
v3f v(cos(pitch)*cos(yaw), sin(pitch), cos(pitch)*sin(yaw));
|
v3f v(cos(pitch)*cos(yaw), sin(pitch), cos(pitch)*sin(yaw));
|
||||||
push_v3f(L, v);
|
push_v3f(L, v);
|
||||||
return 1;
|
return 1;
|
||||||
|
@ -1033,10 +1033,10 @@ int ObjectRef::l_get_look_pitch(lua_State *L)
|
||||||
"Deprecated call to get_look_pitch, use get_look_vertical instead");
|
"Deprecated call to get_look_pitch, use get_look_vertical instead");
|
||||||
|
|
||||||
ObjectRef *ref = checkobject(L, 1);
|
ObjectRef *ref = checkobject(L, 1);
|
||||||
RemotePlayer *player = getplayer(ref);
|
PlayerSAO* co = getplayersao(ref);
|
||||||
if (player == NULL) return 0;
|
if (co == NULL) return 0;
|
||||||
// Do it
|
// Do it
|
||||||
lua_pushnumber(L, player->getRadPitchDep());
|
lua_pushnumber(L, co->getRadPitchDep());
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1050,10 +1050,10 @@ int ObjectRef::l_get_look_yaw(lua_State *L)
|
||||||
"Deprecated call to get_look_yaw, use get_look_horizontal instead");
|
"Deprecated call to get_look_yaw, use get_look_horizontal instead");
|
||||||
|
|
||||||
ObjectRef *ref = checkobject(L, 1);
|
ObjectRef *ref = checkobject(L, 1);
|
||||||
RemotePlayer *player = getplayer(ref);
|
PlayerSAO* co = getplayersao(ref);
|
||||||
if (player == NULL) return 0;
|
if (co == NULL) return 0;
|
||||||
// Do it
|
// Do it
|
||||||
lua_pushnumber(L, player->getRadYawDep());
|
lua_pushnumber(L, co->getRadYawDep());
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1062,10 +1062,10 @@ int ObjectRef::l_get_look_vertical(lua_State *L)
|
||||||
{
|
{
|
||||||
NO_MAP_LOCK_REQUIRED;
|
NO_MAP_LOCK_REQUIRED;
|
||||||
ObjectRef *ref = checkobject(L, 1);
|
ObjectRef *ref = checkobject(L, 1);
|
||||||
RemotePlayer *player = getplayer(ref);
|
PlayerSAO* co = getplayersao(ref);
|
||||||
if (player == NULL) return 0;
|
if (co == NULL) return 0;
|
||||||
// Do it
|
// Do it
|
||||||
lua_pushnumber(L, player->getRadPitch());
|
lua_pushnumber(L, co->getRadPitch());
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1074,10 +1074,10 @@ int ObjectRef::l_get_look_horizontal(lua_State *L)
|
||||||
{
|
{
|
||||||
NO_MAP_LOCK_REQUIRED;
|
NO_MAP_LOCK_REQUIRED;
|
||||||
ObjectRef *ref = checkobject(L, 1);
|
ObjectRef *ref = checkobject(L, 1);
|
||||||
RemotePlayer *player = getplayer(ref);
|
PlayerSAO* co = getplayersao(ref);
|
||||||
if (player == NULL) return 0;
|
if (co == NULL) return 0;
|
||||||
// Do it
|
// Do it
|
||||||
lua_pushnumber(L, player->getRadYaw());
|
lua_pushnumber(L, co->getRadYaw());
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -701,11 +701,15 @@ void Server::AsyncRunStep(bool initial_step)
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
PlayerSAO *playersao = player->getPlayerSAO();
|
||||||
|
if (playersao == NULL)
|
||||||
|
continue;
|
||||||
|
|
||||||
std::queue<u16> removed_objects;
|
std::queue<u16> removed_objects;
|
||||||
std::queue<u16> added_objects;
|
std::queue<u16> added_objects;
|
||||||
m_env->getRemovedActiveObjects(player, radius, player_radius,
|
m_env->getRemovedActiveObjects(playersao, radius, player_radius,
|
||||||
client->m_known_objects, removed_objects);
|
client->m_known_objects, removed_objects);
|
||||||
m_env->getAddedActiveObjects(player, radius, player_radius,
|
m_env->getAddedActiveObjects(playersao, radius, player_radius,
|
||||||
client->m_known_objects, added_objects);
|
client->m_known_objects, added_objects);
|
||||||
|
|
||||||
// Ignore if nothing happened
|
// Ignore if nothing happened
|
||||||
|
@ -1108,7 +1112,7 @@ PlayerSAO* Server::StageTwoClientInit(u16 peer_id)
|
||||||
SendPlayerBreath(peer_id);
|
SendPlayerBreath(peer_id);
|
||||||
|
|
||||||
// Show death screen if necessary
|
// Show death screen if necessary
|
||||||
if (player->isDead())
|
if (playersao->isDead())
|
||||||
SendDeathscreen(peer_id, false, v3f(0,0,0));
|
SendDeathscreen(peer_id, false, v3f(0,0,0));
|
||||||
|
|
||||||
// Note things in chat if not in simple singleplayer mode
|
// Note things in chat if not in simple singleplayer mode
|
||||||
|
@ -1860,18 +1864,18 @@ void Server::SendMovePlayer(u16 peer_id)
|
||||||
DSTACK(FUNCTION_NAME);
|
DSTACK(FUNCTION_NAME);
|
||||||
RemotePlayer *player = m_env->getPlayer(peer_id);
|
RemotePlayer *player = m_env->getPlayer(peer_id);
|
||||||
assert(player);
|
assert(player);
|
||||||
|
PlayerSAO *sao = player->getPlayerSAO();
|
||||||
|
assert(sao);
|
||||||
|
|
||||||
NetworkPacket pkt(TOCLIENT_MOVE_PLAYER, sizeof(v3f) + sizeof(f32) * 2, peer_id);
|
NetworkPacket pkt(TOCLIENT_MOVE_PLAYER, sizeof(v3f) + sizeof(f32) * 2, peer_id);
|
||||||
pkt << player->getPosition() << player->getPitch() << player->getYaw();
|
pkt << sao->getBasePosition() << sao->getPitch() << sao->getYaw();
|
||||||
|
|
||||||
{
|
{
|
||||||
v3f pos = player->getPosition();
|
v3f pos = sao->getBasePosition();
|
||||||
f32 pitch = player->getPitch();
|
|
||||||
f32 yaw = player->getYaw();
|
|
||||||
verbosestream << "Server: Sending TOCLIENT_MOVE_PLAYER"
|
verbosestream << "Server: Sending TOCLIENT_MOVE_PLAYER"
|
||||||
<< " pos=(" << pos.X << "," << pos.Y << "," << pos.Z << ")"
|
<< " pos=(" << pos.X << "," << pos.Y << "," << pos.Z << ")"
|
||||||
<< " pitch=" << pitch
|
<< " pitch=" << sao->getPitch()
|
||||||
<< " yaw=" << yaw
|
<< " yaw=" << sao->getYaw()
|
||||||
<< std::endl;
|
<< std::endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1984,8 +1988,12 @@ s32 Server::playSound(const SimpleSoundSpec &spec,
|
||||||
if (!player)
|
if (!player)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
PlayerSAO *sao = player->getPlayerSAO();
|
||||||
|
if (!sao)
|
||||||
|
continue;
|
||||||
|
|
||||||
if (pos_exists) {
|
if (pos_exists) {
|
||||||
if(player->getPosition().getDistanceFrom(pos) >
|
if(sao->getBasePosition().getDistanceFrom(pos) >
|
||||||
params.max_hear_distance)
|
params.max_hear_distance)
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -2044,14 +2052,17 @@ void Server::sendRemoveNode(v3s16 p, u16 ignore_id,
|
||||||
pkt << p;
|
pkt << p;
|
||||||
|
|
||||||
std::vector<u16> clients = m_clients.getClientIDs();
|
std::vector<u16> clients = m_clients.getClientIDs();
|
||||||
for(std::vector<u16>::iterator i = clients.begin();
|
for (std::vector<u16>::iterator i = clients.begin(); i != clients.end(); ++i) {
|
||||||
i != clients.end(); ++i) {
|
|
||||||
if (far_players) {
|
if (far_players) {
|
||||||
// Get player
|
// Get player
|
||||||
if (RemotePlayer *player = m_env->getPlayer(*i)) {
|
if (RemotePlayer *player = m_env->getPlayer(*i)) {
|
||||||
|
PlayerSAO *sao = player->getPlayerSAO();
|
||||||
|
if (!sao)
|
||||||
|
continue;
|
||||||
|
|
||||||
// If player is far away, only set modified blocks not sent
|
// If player is far away, only set modified blocks not sent
|
||||||
v3f player_pos = player->getPosition();
|
v3f player_pos = sao->getBasePosition();
|
||||||
if(player_pos.getDistanceFrom(p_f) > maxd) {
|
if (player_pos.getDistanceFrom(p_f) > maxd) {
|
||||||
far_players->push_back(*i);
|
far_players->push_back(*i);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -2071,14 +2082,16 @@ void Server::sendAddNode(v3s16 p, MapNode n, u16 ignore_id,
|
||||||
v3f p_f = intToFloat(p, BS);
|
v3f p_f = intToFloat(p, BS);
|
||||||
|
|
||||||
std::vector<u16> clients = m_clients.getClientIDs();
|
std::vector<u16> clients = m_clients.getClientIDs();
|
||||||
for(std::vector<u16>::iterator i = clients.begin();
|
for(std::vector<u16>::iterator i = clients.begin(); i != clients.end(); ++i) {
|
||||||
i != clients.end(); ++i) {
|
if (far_players) {
|
||||||
|
|
||||||
if(far_players) {
|
|
||||||
// Get player
|
// Get player
|
||||||
if (RemotePlayer *player = m_env->getPlayer(*i)) {
|
if (RemotePlayer *player = m_env->getPlayer(*i)) {
|
||||||
|
PlayerSAO *sao = player->getPlayerSAO();
|
||||||
|
if (!sao)
|
||||||
|
continue;
|
||||||
|
|
||||||
// If player is far away, only set modified blocks not sent
|
// If player is far away, only set modified blocks not sent
|
||||||
v3f player_pos = player->getPosition();
|
v3f player_pos = sao->getBasePosition();
|
||||||
if(player_pos.getDistanceFrom(p_f) > maxd) {
|
if(player_pos.getDistanceFrom(p_f) > maxd) {
|
||||||
far_players->push_back(*i);
|
far_players->push_back(*i);
|
||||||
continue;
|
continue;
|
||||||
|
@ -3426,10 +3439,9 @@ PlayerSAO* Server::emergePlayer(const char *name, u16 peer_id, u16 proto_version
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Load player if it isn't already loaded
|
// Create a new player active object
|
||||||
if (!player) {
|
PlayerSAO *playersao = new PlayerSAO(m_env, peer_id, isSingleplayer());
|
||||||
player = m_env->loadPlayer(name);
|
player = m_env->loadPlayer(name, playersao);
|
||||||
}
|
|
||||||
|
|
||||||
// Create player if it doesn't exist
|
// Create player if it doesn't exist
|
||||||
if (!player) {
|
if (!player) {
|
||||||
|
@ -3438,8 +3450,7 @@ PlayerSAO* Server::emergePlayer(const char *name, u16 peer_id, u16 proto_version
|
||||||
// Set player position
|
// Set player position
|
||||||
infostream<<"Server: Finding spawn place for player \""
|
infostream<<"Server: Finding spawn place for player \""
|
||||||
<<name<<"\""<<std::endl;
|
<<name<<"\""<<std::endl;
|
||||||
v3f pos = findSpawnPos();
|
playersao->setBasePosition(findSpawnPos());
|
||||||
player->setPosition(pos);
|
|
||||||
|
|
||||||
// Make sure the player is saved
|
// Make sure the player is saved
|
||||||
player->setModified(true);
|
player->setModified(true);
|
||||||
|
@ -3450,18 +3461,14 @@ PlayerSAO* Server::emergePlayer(const char *name, u16 peer_id, u16 proto_version
|
||||||
// If the player exists, ensure that they respawn inside legal bounds
|
// If the player exists, ensure that they respawn inside legal bounds
|
||||||
// This fixes an assert crash when the player can't be added
|
// This fixes an assert crash when the player can't be added
|
||||||
// to the environment
|
// to the environment
|
||||||
if (objectpos_over_limit(player->getPosition())) {
|
if (objectpos_over_limit(playersao->getBasePosition())) {
|
||||||
actionstream << "Respawn position for player \""
|
actionstream << "Respawn position for player \""
|
||||||
<< name << "\" outside limits, resetting" << std::endl;
|
<< name << "\" outside limits, resetting" << std::endl;
|
||||||
v3f pos = findSpawnPos();
|
playersao->setBasePosition(findSpawnPos());
|
||||||
player->setPosition(pos);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Create a new player active object
|
playersao->initialize(player, getPlayerEffectivePrivs(player->getName()));
|
||||||
PlayerSAO *playersao = new PlayerSAO(m_env, player, peer_id,
|
|
||||||
getPlayerEffectivePrivs(player->getName()),
|
|
||||||
isSingleplayer());
|
|
||||||
|
|
||||||
player->protocol_version = proto_version;
|
player->protocol_version = proto_version;
|
||||||
|
|
||||||
|
|
|
@ -85,7 +85,7 @@ public:
|
||||||
Some more dynamic interface
|
Some more dynamic interface
|
||||||
*/
|
*/
|
||||||
|
|
||||||
virtual void setPos(v3f pos)
|
virtual void setPos(const v3f &pos)
|
||||||
{ setBasePosition(pos); }
|
{ setBasePosition(pos); }
|
||||||
// continuous: if true, object does not stop immediately at pos
|
// continuous: if true, object does not stop immediately at pos
|
||||||
virtual void moveTo(v3f pos, bool continuous)
|
virtual void moveTo(v3f pos, bool continuous)
|
||||||
|
|
|
@ -46,11 +46,14 @@ void TestPlayer::runTests(IGameDef *gamedef)
|
||||||
void TestPlayer::testSave(IGameDef *gamedef)
|
void TestPlayer::testSave(IGameDef *gamedef)
|
||||||
{
|
{
|
||||||
RemotePlayer rplayer("testplayer_save", gamedef->idef());
|
RemotePlayer rplayer("testplayer_save", gamedef->idef());
|
||||||
rplayer.setBreath(10);
|
PlayerSAO sao(NULL, 1, false);
|
||||||
rplayer.hp = 8;
|
sao.initialize(&rplayer, std::set<std::string>());
|
||||||
rplayer.setYaw(0.1f);
|
rplayer.setPlayerSAO(&sao);
|
||||||
rplayer.setPitch(0.6f);
|
sao.setBreath(10);
|
||||||
rplayer.setPosition(v3f(450.2f, -15.7f, 68.1f));
|
sao.setHP(8, true);
|
||||||
|
sao.setYaw(0.1f, false);
|
||||||
|
sao.setPitch(0.6f, false);
|
||||||
|
sao.setBasePosition(v3f(450.2f, -15.7f, 68.1f));
|
||||||
rplayer.save(".", gamedef);
|
rplayer.save(".", gamedef);
|
||||||
UASSERT(fs::PathExists("testplayer_save"));
|
UASSERT(fs::PathExists("testplayer_save"));
|
||||||
}
|
}
|
||||||
|
@ -58,24 +61,28 @@ void TestPlayer::testSave(IGameDef *gamedef)
|
||||||
void TestPlayer::testLoad(IGameDef *gamedef)
|
void TestPlayer::testLoad(IGameDef *gamedef)
|
||||||
{
|
{
|
||||||
RemotePlayer rplayer("testplayer_load", gamedef->idef());
|
RemotePlayer rplayer("testplayer_load", gamedef->idef());
|
||||||
rplayer.setBreath(10);
|
PlayerSAO sao(NULL, 1, false);
|
||||||
rplayer.hp = 8;
|
sao.initialize(&rplayer, std::set<std::string>());
|
||||||
rplayer.setYaw(0.1f);
|
rplayer.setPlayerSAO(&sao);
|
||||||
rplayer.setPitch(0.6f);
|
sao.setBreath(10);
|
||||||
rplayer.setPosition(v3f(450.2f, -15.7f, 68.1f));
|
sao.setHP(8, true);
|
||||||
|
sao.setYaw(0.1f, false);
|
||||||
|
sao.setPitch(0.6f, false);
|
||||||
|
sao.setBasePosition(v3f(450.2f, -15.7f, 68.1f));
|
||||||
rplayer.save(".", gamedef);
|
rplayer.save(".", gamedef);
|
||||||
UASSERT(fs::PathExists("testplayer_load"));
|
UASSERT(fs::PathExists("testplayer_load"));
|
||||||
|
|
||||||
RemotePlayer rplayer_load("testplayer_load", gamedef->idef());
|
RemotePlayer rplayer_load("testplayer_load", gamedef->idef());
|
||||||
|
PlayerSAO sao_load(NULL, 2, false);
|
||||||
std::ifstream is("testplayer_load", std::ios_base::binary);
|
std::ifstream is("testplayer_load", std::ios_base::binary);
|
||||||
UASSERT(is.good());
|
UASSERT(is.good());
|
||||||
rplayer_load.deSerialize(is, "testplayer_load");
|
rplayer_load.deSerialize(is, "testplayer_load", &sao_load);
|
||||||
is.close();
|
is.close();
|
||||||
|
|
||||||
UASSERT(strcmp(rplayer_load.getName(), "testplayer_load") == 0);
|
UASSERT(strcmp(rplayer_load.getName(), "testplayer_load") == 0);
|
||||||
UASSERT(rplayer.getBreath() == 10);
|
UASSERT(sao_load.getBreath() == 10);
|
||||||
UASSERT(rplayer.hp == 8);
|
UASSERT(sao_load.getHP() == 8);
|
||||||
UASSERT(rplayer.getYaw() == 0.1f);
|
UASSERT(sao_load.getYaw() == 0.1f);
|
||||||
UASSERT(rplayer.getPitch() == 0.6f);
|
UASSERT(sao_load.getPitch() == 0.6f);
|
||||||
UASSERT(rplayer.getPosition() == v3f(450.2f, -15.7f, 68.1f));
|
UASSERT(sao_load.getBasePosition() == v3f(450.2f, -15.7f, 68.1f));
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue