diff --git a/data/kart_characteristics.xml b/data/kart_characteristics.xml index 3407aa5ee..250b23a11 100644 --- a/data/kart_characteristics.xml +++ b/data/kart_characteristics.xml @@ -66,7 +66,7 @@ speed 10 the radius is 7.5 etc. The actual turn radius is piece-wise linearly interpolated. This allows for tighter turning at lower speeds, and also avoids that - the kart becomes too hard to control at high speed (speeds of + the kart becomes too hard to control at high speed (speeds higher than 25 can only be reached with powerups). time-full-steer: This is the amount of change in steering depending on current steering. So if the steering is between 0 and 0.5, @@ -84,7 +84,8 @@ time-reset-steer="0.1" /> - - + @@ -205,9 +207,9 @@ - + + boost="8 4" /> - + - + + min-collect-time="2.5" max-collect-time="8" add-power="300" min-speed="8" + max-speed-increase="3" duration-factor="1" fade-out-time="2" /> - + - + - + @@ -356,44 +360,40 @@ - - - - - - + + + + + + + - - - - - - + + + + + + + - - + + + - - - - + + + diff --git a/src/karts/abstract_characteristic.cpp b/src/karts/abstract_characteristic.cpp index af7ba896c..778812c0a 100644 --- a/src/karts/abstract_characteristic.cpp +++ b/src/karts/abstract_characteristic.cpp @@ -201,6 +201,8 @@ AbstractCharacteristic::ValueType AbstractCharacteristic::getType( return TYPE_FLOAT; case NITRO_ENGINE_FORCE: return TYPE_FLOAT; + case NITRO_ENGINE_MULT: + return TYPE_FLOAT; case NITRO_CONSUMPTION: return TYPE_FLOAT; case NITRO_SMALL_CONTAINER: @@ -437,6 +439,8 @@ std::string AbstractCharacteristic::getName(CharacteristicType type) return "NITRO_DURATION"; case NITRO_ENGINE_FORCE: return "NITRO_ENGINE_FORCE"; + case NITRO_ENGINE_MULT: + return "NITRO_ENGINE_MULT"; case NITRO_CONSUMPTION: return "NITRO_CONSUMPTION"; case NITRO_SMALL_CONTAINER: @@ -1395,6 +1399,18 @@ float AbstractCharacteristic::getNitroEngineForce() const return result; } // getNitroEngineForce +// ---------------------------------------------------------------------------- +float AbstractCharacteristic::getNitroEngineMult() const +{ + float result; + bool is_set = false; + process(NITRO_ENGINE_MULT, &result, &is_set); + if (!is_set) + Log::fatal("AbstractCharacteristic", "Can't get characteristic %s", + getName(NITRO_ENGINE_MULT).c_str()); + return result; +} // getNitroEngineMult + // ---------------------------------------------------------------------------- float AbstractCharacteristic::getNitroConsumption() const { diff --git a/src/karts/abstract_characteristic.hpp b/src/karts/abstract_characteristic.hpp index f4fb2406c..23cbd60c7 100644 --- a/src/karts/abstract_characteristic.hpp +++ b/src/karts/abstract_characteristic.hpp @@ -185,6 +185,7 @@ public: // Nitro NITRO_DURATION, NITRO_ENGINE_FORCE, + NITRO_ENGINE_MULT, NITRO_CONSUMPTION, NITRO_SMALL_CONTAINER, NITRO_BIG_CONTAINER, @@ -354,6 +355,7 @@ public: float getNitroDuration() const; float getNitroEngineForce() const; + float getNitroEngineMult() const; float getNitroConsumption() const; float getNitroSmallContainer() const; float getNitroBigContainer() const; diff --git a/src/karts/kart.cpp b/src/karts/kart.cpp index a7f330744..ab4300f74 100644 --- a/src/karts/kart.cpp +++ b/src/karts/kart.cpp @@ -2651,6 +2651,54 @@ void Kart::updateEngineSFX(float dt) } } // updateEngineSFX + + +//----------------------------------------------------------------------------- +/** Reduces the engine power according to speed + * + * TODO : find where the physics already apply a linear force decrease + * TODO : While this work fine, it should ideally be in physics + * However, the function use some kart properties and parachute + * effect needs to be applied, so keep both working if moving + * \param engine_power : the engine power on which to apply the decrease + */ +float Kart::applyAirFriction(float engine_power) +{ + //The physics already do that a certain amount of engine force is needed to keep going + //at a given speed (~39,33 engine force = 1 speed for a mass of 350) + //But it's either too slow to accelerate to a target speed or makes it + //too easy to accelerate farther. + //Instead of making increasing gears have enormous power gaps, apply friction + + float mass_factor = m_kart_properties->getMass()/350.0f; + float compense_linear_slowdown = 39.33f*getSpeed()*mass_factor; + + engine_power += compense_linear_slowdown; + + // The result will always be a positive number + float friction_intensity = fabsf(getSpeed()); + + // Not a pure quadratic evolution as it would be too brutal + friction_intensity *= sqrt(friction_intensity)*5; + + // Apply parachute physics + // Currently, all karts have the same base friction + // If this is changed, a compensation needs to be added here + if(m_attachment->getType()==Attachment::ATTACH_PARACHUTE) + friction_intensity *= m_kart_properties->getParachuteFriction(); + + if (friction_intensity < 0.0f) friction_intensity = 0.0f; + + // We substract the friction from the engine power + // 1)This is the logical behavior + // 2)That way, engine boosts remain useful at high speed + // 3)It helps heavier karts, who have an higher engine power + + engine_power-=friction_intensity; + + return engine_power; +} //applyAirFriction + //----------------------------------------------------------------------------- /** Sets the engine power. It considers the engine specs, items that influence * the available power, and braking/steering. @@ -2661,9 +2709,11 @@ void Kart::updateEnginePowerAndBrakes(int ticks) updateNitro(ticks); float engine_power = getActualWheelForce(); - // apply parachute physics if relevant - if(m_attachment->getType()==Attachment::ATTACH_PARACHUTE) - engine_power*=0.2f; + // apply nitro boost if relevant + if(getSpeedIncreaseTicksLeft(MaxSpeed::MS_INCREASE_NITRO) > 0) + { + engine_power*= m_kart_properties->getNitroEngineMult(); + } // apply bubblegum physics if relevant if (m_bubblegum_ticks > 0) @@ -2689,6 +2739,9 @@ void Kart::updateEnginePowerAndBrakes(int ticks) m_kart_properties->getSkidVisualTime() == 0) engine_power *= 0.5f; + // This also applies parachute physics if relevant + engine_power = applyAirFriction(engine_power); + applyEngineForce(engine_power*m_controls.getAccel()); // Either all or no brake is set, so test only one to avoid @@ -2698,14 +2751,20 @@ void Kart::updateEnginePowerAndBrakes(int ticks) m_vehicle->setAllBrakes(0); m_brake_ticks = 0; } - else - { // not accelerating + else // not accelerating + { + //The engine power is still guaranteed >= 0 at this point + float braking_power = engine_power; + + // This also applies parachute physics if relevant + engine_power = applyAirFriction(engine_power); + if(m_controls.getBrake()) { // check if the player is currently only slowing down // or moving backwards if(m_speed > 0.0f) { // Still going forward while braking - applyEngineForce(-engine_power*2.5f); + applyEngineForce(engine_power-braking_power*3); m_brake_ticks += ticks; // Apply the brakes - include the time dependent brake increase float f = 1.0f + stk_config->ticks2Time(m_brake_ticks) @@ -2723,7 +2782,7 @@ void Kart::updateEnginePowerAndBrakes(int ticks) // The backwards acceleration is artificially increased to // allow players to get "unstuck" quicker if they hit e.g. // a wall. - applyEngineForce(-engine_power*2.5f); + applyEngineForce(engine_power-braking_power*3); } else // -m_speed >= max speed on this terrain { @@ -2732,13 +2791,13 @@ void Kart::updateEnginePowerAndBrakes(int ticks) } // m_speed <00 } - else // !m_brake + else // no braking and no acceleration { m_brake_ticks = 0; - // lift the foot from throttle, brakes with 10% engine_power + // lift the foot from throttle, let friction slow it down assert(!std::isnan(m_controls.getAccel())); assert(!std::isnan(engine_power)); - applyEngineForce(-m_controls.getAccel()*engine_power*0.1f); + applyEngineForce(engine_power-braking_power); // If not giving power (forward or reverse gear), and speed is low // we are "parking" the kart, so in battle mode we can ambush people @@ -2746,7 +2805,7 @@ void Kart::updateEnginePowerAndBrakes(int ticks) m_vehicle->setAllBrakes(20.0f); else m_vehicle->setAllBrakes(0); - } // !m_brake + } // no braking and no acceleration } // not accelerating } // updateEnginePowerAndBrakes diff --git a/src/karts/kart.hpp b/src/karts/kart.hpp index 569880fe2..6cc09be44 100644 --- a/src/karts/kart.hpp +++ b/src/karts/kart.hpp @@ -264,6 +264,7 @@ protected: void updateEngineSFX(float dt); void updateSpeed(); void updateNitro(int ticks); + float applyAirFriction (float engine_power); float getActualWheelForce(); void playCrashSFX(const Material* m, AbstractKart *k); void loadData(RaceManager::KartType type, bool animatedModel); diff --git a/src/karts/kart_properties.cpp b/src/karts/kart_properties.cpp index 5463c33ad..0b1763e94 100644 --- a/src/karts/kart_properties.cpp +++ b/src/karts/kart_properties.cpp @@ -1017,6 +1017,12 @@ float KartProperties::getNitroEngineForce() const return m_cached_characteristic->getNitroEngineForce(); } // getNitroEngineForce +// ---------------------------------------------------------------------------- +float KartProperties::getNitroEngineMult() const +{ + return m_cached_characteristic->getNitroEngineMult(); +} // getNitroEngineMult + // ---------------------------------------------------------------------------- float KartProperties::getNitroConsumption() const { diff --git a/src/karts/kart_properties.hpp b/src/karts/kart_properties.hpp index 30ce89463..70fdce83b 100644 --- a/src/karts/kart_properties.hpp +++ b/src/karts/kart_properties.hpp @@ -469,6 +469,7 @@ public: float getNitroDuration() const; float getNitroEngineForce() const; + float getNitroEngineMult() const; float getNitroConsumption() const; float getNitroSmallContainer() const; float getNitroBigContainer() const; diff --git a/src/karts/skidding.cpp b/src/karts/skidding.cpp index e81fc28f7..512210bea 100644 --- a/src/karts/skidding.cpp +++ b/src/karts/skidding.cpp @@ -545,7 +545,7 @@ void Skidding::update(int ticks, bool is_on_ground, MaxSpeed::MS_INCREASE_RED_SKIDDING; m_kart->m_max_speed-> instantSpeedIncrease(bonus_cat, - bonus_speed, bonus_speed, + bonus_speed, bonus_speed/2, bonus_force, stk_config->time2Ticks(bonus_time), /*fade-out-time*/ stk_config->time2Ticks(1.0f)); diff --git a/src/karts/xml_characteristic.cpp b/src/karts/xml_characteristic.cpp index 2e9a34676..9a4e9f95e 100644 --- a/src/karts/xml_characteristic.cpp +++ b/src/karts/xml_characteristic.cpp @@ -545,6 +545,8 @@ void XmlCharacteristic::load(const XMLNode *node) &m_values[NITRO_DURATION]); sub_node->get("engine-force", &m_values[NITRO_ENGINE_FORCE]); + sub_node->get("engine-mult", + &m_values[NITRO_ENGINE_MULT]); sub_node->get("consumption", &m_values[NITRO_CONSUMPTION]); sub_node->get("small-container",