From c571e62658634213c8441fa25af871459946419f Mon Sep 17 00:00:00 2001 From: "alexander.pickering" Date: Sat, 20 Sep 2014 15:07:39 -0400 Subject: [PATCH] Modified jumping control to stop "flying" up block-stairs --- src/localplayer.cpp | 89 ++++++++++++++++++++++++++------------------- src/localplayer.h | 5 ++- src/player.cpp | 6 ++- src/player.h | 13 ++++--- 4 files changed, 65 insertions(+), 48 deletions(-) diff --git a/src/localplayer.cpp b/src/localplayer.cpp index 1a238cb47..aaf9a57f0 100644 --- a/src/localplayer.cpp +++ b/src/localplayer.cpp @@ -29,6 +29,13 @@ with this program; if not, write to the Free Software Foundation, Inc., #include "map.h" #include "util/numeric.h" +// +#include + +using namespace std; +// + + /* LocalPlayer */ @@ -54,7 +61,8 @@ LocalPlayer::LocalPlayer(IGameDef *gamedef): m_old_node_below_type("air"), m_need_to_get_new_sneak_node(true), m_can_jump(false), - m_cao(NULL) + m_cao(NULL), + m_jumptime(0.0) { // Initialize hp to 0, so that no hearts will be shown if server // doesn't support health points @@ -99,7 +107,7 @@ void LocalPlayer::move(f32 dtime, Environment *env, f32 pos_max_d, /* Collision detection */ - + /* Check if player is in liquid (the oscillating value) */ @@ -177,7 +185,7 @@ void LocalPlayer::move(f32 dtime, Environment *env, f32 pos_max_d, v3f lwn_f = intToFloat(m_sneak_node, BS); position.X = rangelim(position.X, lwn_f.X-maxd, lwn_f.X+maxd); position.Z = rangelim(position.Z, lwn_f.Z-maxd, lwn_f.Z+maxd); - + if(!is_climbing) { f32 min_y = lwn_f.Y + 0.5*BS; @@ -207,7 +215,7 @@ void LocalPlayer::move(f32 dtime, Environment *env, f32 pos_max_d, */ bool touching_ground_was = touching_ground; touching_ground = result.touching_ground; - + //bool standing_on_unloaded = result.standing_on_unloaded; /* @@ -258,7 +266,7 @@ void LocalPlayer::move(f32 dtime, Environment *env, f32 pos_max_d, f32 max_axis_distance_f = MYMAX( fabs(player_p2df.X-node_p2df.X), fabs(player_p2df.Y-node_p2df.Y)); - + if(distance_f > min_distance_f || max_axis_distance_f > 0.5*BS + sneak_max + 0.1*BS) continue; @@ -284,7 +292,7 @@ void LocalPlayer::move(f32 dtime, Environment *env, f32 pos_max_d, min_distance_f = distance_f; new_sneak_node = p; } - + bool sneak_node_found = (min_distance_f < 100000.0*BS*0.9); m_sneak_node = new_sneak_node; @@ -297,12 +305,12 @@ void LocalPlayer::move(f32 dtime, Environment *env, f32 pos_max_d, if(sneak_node_found && control.sneak) touching_ground = true; } - + /* Set new position */ setPosition(position); - + /* Report collisions */ @@ -324,6 +332,7 @@ void LocalPlayer::move(f32 dtime, Environment *env, f32 pos_max_d, touching_ground = false; MtEvent *e = new SimpleTriggerEvent("PlayerJump"); m_gamedef->event()->put(e); + cout << "Jumped because " << m_jumptime << " is less than " << env->getTimeOfDay() << "\n"; } if(!touching_ground_was && touching_ground){ @@ -350,13 +359,18 @@ void LocalPlayer::move(f32 dtime, Environment *env, f32 pos_max_d, */ m_old_node_below = floatToInt(position - v3f(0,BS/2,0), BS); m_old_node_below_type = nodemgr->get(map->getNodeNoEx(m_old_node_below)).name; - + /* Check properties of the node on which the player is standing */ const ContentFeatures &f = nodemgr->get(map->getNodeNoEx(getStandingNodePos())); // Determine if jumping is possible - m_can_jump = touching_ground && !in_liquid; + m_can_jump = touching_ground && !in_liquid && (m_jumptime <= env->getTimeOfDay()); + if(!touching_ground){ + m_jumptime = env->getTimeOfDay()+movement_jump_dealy; + } + //cout << m_jumptime << ":" << (env->getTimeOfDay()) << ":" << m_can_jump << "\n"; + if(itemgroup_get(f.groups, "disable_jump")) m_can_jump = false; } @@ -383,10 +397,10 @@ void LocalPlayer::applyControl(float dtime) v3f move_direction = v3f(0,0,1); move_direction.rotateXZBy(getYaw()); - + v3f speedH = v3f(0,0,0); // Horizontal (X, Z) v3f speedV = v3f(0,0,0); // Vertical (Y) - + bool fly_allowed = m_gamedef->checkLocalPrivilege("fly"); bool fast_allowed = m_gamedef->checkLocalPrivilege("fast"); @@ -398,7 +412,7 @@ void LocalPlayer::applyControl(float dtime) // Whether superspeed mode is used or not bool superspeed = false; - + if(g_settings->getBool("always_fly_fast") && free_move && fast_move) superspeed = true; @@ -408,7 +422,7 @@ void LocalPlayer::applyControl(float dtime) // If free movement and fast movement, always move fast if(free_move && fast_move) superspeed = true; - + // Auxiliary button 1 (E) if(control.aux1) { @@ -478,30 +492,29 @@ void LocalPlayer::applyControl(float dtime) speedV.Y = -movement_speed_climb; } } - } +} + if(continuous_forward) + speedH += move_direction; - if(continuous_forward) - speedH += move_direction; - - if(control.up) - { - if(continuous_forward) - superspeed = true; - else - speedH += move_direction; - } - if(control.down) - { - speedH -= move_direction; - } - if(control.left) - { - speedH += move_direction.crossProduct(v3f(0,1,0)); - } - if(control.right) - { - speedH += move_direction.crossProduct(v3f(0,-1,0)); - } + if(control.up) + { + if(continuous_forward) + superspeed = true; + else + speedH += move_direction; + } + if(control.down) + { + speedH -= move_direction; + } + if(control.left) + { + speedH += move_direction.crossProduct(v3f(0,1,0)); + } + if(control.right) + { + speedH += move_direction.crossProduct(v3f(0,-1,0)); + } if(control.jump) { if(free_move) @@ -531,7 +544,7 @@ void LocalPlayer::applyControl(float dtime) { speedJ.Y = movement_speed_jump * physics_override_jump; setSpeed(speedJ); - + MtEvent *e = new SimpleTriggerEvent("PlayerJump"); m_gamedef->event()->put(e); } diff --git a/src/localplayer.h b/src/localplayer.h index bfe476b70..1b7361a81 100644 --- a/src/localplayer.h +++ b/src/localplayer.h @@ -39,13 +39,13 @@ public: { return true; } - + ClientActiveObject *parent; bool isAttached; v3f overridePosition; - + void move(f32 dtime, Environment *env, f32 pos_max_d); void move(f32 dtime, Environment *env, f32 pos_max_d, std::list *collision_info); @@ -91,6 +91,7 @@ private: std::string m_old_node_below_type; // Whether recalculation of the sneak node is needed bool m_need_to_get_new_sneak_node; + f32 m_jumptime; bool m_can_jump; GenericCAO* m_cao; diff --git a/src/player.cpp b/src/player.cpp index 40d403952..0f3037949 100644 --- a/src/player.cpp +++ b/src/player.cpp @@ -53,6 +53,7 @@ Player::Player(IGameDef *gamedef): m_last_pos(0,0,0), m_last_hp(PLAYER_MAX_HP), m_last_inventory(gamedef->idef()) + m_jumping_dir(0,0,0); { updateName(""); inventory.clear(); @@ -83,6 +84,7 @@ Player::Player(IGameDef *gamedef): movement_liquid_fluidity_smooth = 0.5 * BS; movement_liquid_sink = 10 * BS; movement_gravity = 9.81 * BS; + movement_jump_dealy = 0.3 * BS; // Movement overrides are multipliers and must be 1 by default physics_override_speed = 1; @@ -114,7 +116,7 @@ void Player::accelerateHorizontal(v3f target_speed, f32 max_increase) f32 dl = d_wanted.getLength(); if(dl > max_increase) dl = max_increase; - + v3f d = d_wanted.normalize() * dl; m_speed.X += d.X; @@ -195,7 +197,7 @@ void Player::serialize(std::ostream &os) void Player::deSerialize(std::istream &is, std::string playername) { Settings args; - + for(;;) { if(is.eof()) diff --git a/src/player.h b/src/player.h index 93197d374..1c6d79e81 100644 --- a/src/player.h +++ b/src/player.h @@ -113,7 +113,7 @@ public: { m_speed = speed; } - + void accelerateHorizontal(v3f target_speed, f32 max_increase); void accelerateVertical(v3f target_speed, f32 max_increase); @@ -250,7 +250,7 @@ public: bool is_climbing; bool swimming_vertical; bool camera_barely_in_ceiling; - + u8 light; Inventory inventory; @@ -267,6 +267,7 @@ public: f32 movement_liquid_fluidity_smooth; f32 movement_liquid_sink; f32 movement_gravity; + f32 movement_jump_dealy; float physics_override_speed; float physics_override_jump; @@ -285,15 +286,15 @@ public: u16 peer_id; std::string inventory_formspec; - + PlayerControl control; PlayerControl getPlayerControl() { return control; } - + u32 keyPressed; - + HudElement* getHud(u32 id); u32 addHud(HudElement* hud); @@ -342,7 +343,7 @@ public: void setPlayerSAO(PlayerSAO *sao) { m_sao = sao; } void setPosition(const v3f &position); - + private: PlayerSAO *m_sao; };