mirror of https://github.com/OpenTTD/OpenTTD
(svn r19345) -Feature: Realistic acceleration for road vehicles.
parent
e770b3d6bb
commit
c958c2c31f
|
@ -1083,6 +1083,9 @@ STR_CONFIG_SETTING_MAMMOTHTRAINS :{LTBLUE}Enable
|
|||
STR_CONFIG_SETTING_TRAIN_ACCELERATION_MODEL :{LTBLUE}Train acceleration model: {ORANGE}{STRING1}
|
||||
STR_CONFIG_SETTING_TRAIN_ACCELERATION_MODEL_ORIGINAL :Original
|
||||
STR_CONFIG_SETTING_TRAIN_ACCELERATION_MODEL_REALISTIC :Realistic
|
||||
STR_CONFIG_SETTING_ROAD_VEHICLE_ACCELERATION_MODEL :{LTBLUE}Road vehicle acceleration model: {ORANGE}{STRING1}
|
||||
STR_CONFIG_SETTING_ROAD_VEHICLE_ACCELERATION_MODEL_ORIGINAL :Original
|
||||
STR_CONFIG_SETTING_ROAD_VEHICLE_ACCELERATION_MODEL_REALISTIC :Realistic
|
||||
STR_CONFIG_SETTING_TRAIN_SLOPE_STEEPNESS :{LTBLUE}Slope steepness for trains {ORANGE}{STRING1}%
|
||||
STR_CONFIG_SETTING_FORBID_90_DEG :{LTBLUE}Forbid trains and ships to make 90 deg turns: {ORANGE}{STRING1} {LTBLUE} (not with OPF)
|
||||
STR_CONFIG_SETTING_JOINSTATIONS :{LTBLUE}Join train stations built next to each other: {ORANGE}{STRING1}
|
||||
|
|
|
@ -133,6 +133,8 @@ struct RoadVehicle : public GroundVehicle<RoadVehicle, VEH_ROAD> {
|
|||
|
||||
bool IsBus() const;
|
||||
|
||||
int GetCurrentMaxSpeed() const;
|
||||
|
||||
/**
|
||||
* Check if vehicle is a front engine
|
||||
* @return Returns true if vehicle is a front engine
|
||||
|
|
|
@ -287,6 +287,8 @@ CommandCost CmdBuildRoadVeh(TileIndex tile, DoCommandFlag flags, uint32 p1, uint
|
|||
u->InvalidateNewGRFCache();
|
||||
}
|
||||
RoadVehUpdateCache(v);
|
||||
/* Initialize cached values for realistic acceleration. */
|
||||
if (_settings_game.vehicle.roadveh_acceleration_model != AM_ORIGINAL) v->CargoChanged();
|
||||
|
||||
VehicleMove(v, false);
|
||||
|
||||
|
@ -431,6 +433,7 @@ void RoadVehicle::MarkDirty()
|
|||
for (Vehicle *v = this; v != NULL; v = v->Next()) {
|
||||
v->UpdateViewport(false, false);
|
||||
}
|
||||
this->CargoChanged();
|
||||
}
|
||||
|
||||
void RoadVehicle::UpdateDeltaXY(Direction direction)
|
||||
|
@ -456,6 +459,29 @@ void RoadVehicle::UpdateDeltaXY(Direction direction)
|
|||
this->z_extent = 6;
|
||||
}
|
||||
|
||||
/**
|
||||
* Calculates the maximum speed of the vehicle under its current conditions.
|
||||
* @return Maximum speed of the vehicle.
|
||||
*/
|
||||
FORCEINLINE int RoadVehicle::GetCurrentMaxSpeed() const
|
||||
{
|
||||
if (_settings_game.vehicle.roadveh_acceleration_model == AM_ORIGINAL) return this->max_speed;
|
||||
|
||||
int max_speed = this->max_speed;
|
||||
|
||||
/* Limit speed to 50% while reversing, 75% in curves. */
|
||||
for (const RoadVehicle *u = this; u != NULL; u = u->Next()) {
|
||||
if (this->state <= RVSB_TRACKDIR_MASK && IsReversingRoadTrackdir((Trackdir)this->state)) {
|
||||
max_speed = this->max_speed / 2;
|
||||
break;
|
||||
} else if ((u->direction & 1) == 0) {
|
||||
max_speed = this->max_speed * 3 / 4;
|
||||
}
|
||||
}
|
||||
|
||||
return max_speed;
|
||||
}
|
||||
|
||||
static void DeleteLastRoadVeh(RoadVehicle *v)
|
||||
{
|
||||
Vehicle *u = v;
|
||||
|
@ -725,17 +751,20 @@ static void RoadVehArrivesAt(const RoadVehicle *v, Station *st)
|
|||
static int RoadVehAccelerate(RoadVehicle *v)
|
||||
{
|
||||
uint oldspeed = v->cur_speed;
|
||||
uint accel = 256 + (v->overtaking != 0 ? 256 : 0);
|
||||
uint accel = v->overtaking != 0 ? 256 : 0;
|
||||
accel += (_settings_game.vehicle.roadveh_acceleration_model == AM_ORIGINAL) ? 256 : v->GetAcceleration();
|
||||
uint spd = v->subspeed + accel;
|
||||
|
||||
v->subspeed = (uint8)spd;
|
||||
|
||||
int tempmax = v->max_speed;
|
||||
if (v->cur_speed > v->max_speed) {
|
||||
int tempmax = v->GetCurrentMaxSpeed();
|
||||
if (v->cur_speed > tempmax) {
|
||||
tempmax = v->cur_speed - (v->cur_speed / 10) - 1;
|
||||
}
|
||||
|
||||
v->cur_speed = spd = Clamp(v->cur_speed + ((int)spd >> 8), 0, tempmax);
|
||||
/* Force a minimum speed of 1 km/h when realistic acceleration is on. */
|
||||
int min_speed = (_settings_game.vehicle.roadveh_acceleration_model == AM_ORIGINAL) ? 0 : 4;
|
||||
v->cur_speed = spd = Clamp(v->cur_speed + ((int)spd >> 8), min_speed, tempmax);
|
||||
|
||||
/* Apply bridge speed limit */
|
||||
if (v->state == RVSB_WORMHOLE && !(v->vehstatus & VS_HIDDEN)) {
|
||||
|
@ -873,7 +902,7 @@ static void RoadVehCheckOvertake(RoadVehicle *v, RoadVehicle *u)
|
|||
|
||||
static void RoadZPosAffectSpeed(RoadVehicle *v, byte old_z)
|
||||
{
|
||||
if (old_z == v->z_pos) return;
|
||||
if (old_z == v->z_pos || _settings_game.vehicle.roadveh_acceleration_model != AM_ORIGINAL) return;
|
||||
|
||||
if (old_z < v->z_pos) {
|
||||
v->cur_speed = v->cur_speed * 232 / 256; // slow down by ~10%
|
||||
|
@ -1317,7 +1346,7 @@ again:
|
|||
}
|
||||
if (new_dir != v->direction) {
|
||||
v->direction = new_dir;
|
||||
v->cur_speed -= v->cur_speed >> 2;
|
||||
if (_settings_game.vehicle.roadveh_acceleration_model == AM_ORIGINAL) v->cur_speed -= v->cur_speed >> 2;
|
||||
}
|
||||
v->x_pos = x;
|
||||
v->y_pos = y;
|
||||
|
@ -1382,7 +1411,7 @@ again:
|
|||
|
||||
if (new_dir != v->direction) {
|
||||
v->direction = new_dir;
|
||||
v->cur_speed -= v->cur_speed >> 2;
|
||||
if (_settings_game.vehicle.roadveh_acceleration_model == AM_ORIGINAL) v->cur_speed -= v->cur_speed >> 2;
|
||||
}
|
||||
|
||||
v->x_pos = x;
|
||||
|
@ -1434,7 +1463,7 @@ again:
|
|||
Direction old_dir = v->direction;
|
||||
if (new_dir != old_dir) {
|
||||
v->direction = new_dir;
|
||||
v->cur_speed -= (v->cur_speed >> 2);
|
||||
if (_settings_game.vehicle.roadveh_acceleration_model == AM_ORIGINAL) v->cur_speed -= v->cur_speed >> 2;
|
||||
if (old_dir != v->state) {
|
||||
/* The vehicle is in a road stop */
|
||||
v->UpdateInclination(false, true);
|
||||
|
@ -1731,6 +1760,7 @@ CommandCost CmdRefitRoadVeh(TileIndex tile, DoCommandFlag flags, uint32 p1, uint
|
|||
if (flags & DC_EXEC) {
|
||||
RoadVehicle *front = v->First();
|
||||
RoadVehUpdateCache(front);
|
||||
if (_settings_game.vehicle.roadveh_acceleration_model != AM_ORIGINAL) front->CargoChanged();
|
||||
SetWindowDirty(WC_VEHICLE_DETAILS, front->index);
|
||||
SetWindowDirty(WC_VEHICLE_DEPOT, front->tile);
|
||||
InvalidateWindowClassesData(WC_ROADVEH_LIST, 0);
|
||||
|
|
|
@ -324,6 +324,9 @@ void AfterLoadVehicles(bool part_of_load)
|
|||
RoadVehicle *rv = RoadVehicle::From(v);
|
||||
if (rv->IsRoadVehFront()) {
|
||||
RoadVehUpdateCache(rv);
|
||||
if (_settings_game.vehicle.roadveh_acceleration_model != AM_ORIGINAL) {
|
||||
rv->CargoChanged();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -64,6 +64,7 @@
|
|||
#include "company_base.h"
|
||||
#include "engine_base.h"
|
||||
#include "smallmap_gui.h"
|
||||
#include "roadveh.h"
|
||||
|
||||
#include "void_map.h"
|
||||
#include "station_base.h"
|
||||
|
@ -774,6 +775,25 @@ static bool TrainSlopeSteepnessChanged(int32 p1)
|
|||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* This function updates realistic acceleration caches when the setting "Road vehicle acceleration model" is set.
|
||||
* @param p1 Callback parameter
|
||||
* @return Always true
|
||||
*/
|
||||
static bool RoadVehAccelerationModelChanged(int32 p1)
|
||||
{
|
||||
if (_settings_game.vehicle.roadveh_acceleration_model != AM_ORIGINAL) {
|
||||
RoadVehicle *rv;
|
||||
FOR_ALL_ROADVEHICLES(rv) {
|
||||
if (rv->IsRoadVehFront()) {
|
||||
rv->CargoChanged();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool DragSignalsDensityChanged(int32)
|
||||
{
|
||||
InvalidateWindowData(WC_BUILD_SIGNAL, 0);
|
||||
|
|
|
@ -1465,6 +1465,7 @@ static SettingEntry _settings_vehicles[] = {
|
|||
SettingEntry("vehicle.plane_crashes"),
|
||||
SettingEntry("order.timetabling"),
|
||||
SettingEntry("vehicle.dynamic_engines"),
|
||||
SettingEntry("vehicle.roadveh_acceleration_model"),
|
||||
};
|
||||
/** Vehicles sub-page */
|
||||
static SettingsPage _settings_vehicles_page = {_settings_vehicles, lengthof(_settings_vehicles)};
|
||||
|
|
|
@ -310,6 +310,7 @@ struct OrderSettings {
|
|||
struct VehicleSettings {
|
||||
bool mammoth_trains; ///< allow very long trains
|
||||
uint8 train_acceleration_model; ///< realistic acceleration for trains
|
||||
uint8 roadveh_acceleration_model; ///< realistic acceleration for road vehicles
|
||||
uint8 train_slope_steepness; ///< Steepness of hills for trains when using realistic acceleration
|
||||
bool wagon_speed_limits; ///< enable wagon speed limits
|
||||
bool disable_elrails; ///< when true, the elrails are disabled
|
||||
|
|
|
@ -23,6 +23,7 @@ static bool DeleteSelectStationWindow(int32 p1);
|
|||
static bool UpdateConsists(int32 p1);
|
||||
static bool CheckInterval(int32 p1);
|
||||
static bool TrainAccelerationModelChanged(int32 p1);
|
||||
static bool RoadVehAccelerationModelChanged(int32 p1);
|
||||
static bool TrainSlopeSteepnessChanged(int32 p1);
|
||||
static bool DragSignalsDensityChanged(int32);
|
||||
static bool TownFoundingChanged(int32 p1);
|
||||
|
@ -371,6 +372,7 @@ const SettingDesc _settings[] = {
|
|||
SDT_CONDVAR(GameSettings, economy.found_town, SLE_UINT8,128, SL_MAX_VERSION, 0,MS,TF_FORBIDDEN,TF_BEGIN,TF_END - 1, 1, STR_CONFIG_SETTING_TOWN_FOUNDING, TownFoundingChanged),
|
||||
|
||||
SDT_VAR(GameSettings, vehicle.train_acceleration_model, SLE_UINT8, 0,MS, 0, 0, 1, 1, STR_CONFIG_SETTING_TRAIN_ACCELERATION_MODEL, TrainAccelerationModelChanged),
|
||||
SDT_CONDVAR(GameSettings, vehicle.roadveh_acceleration_model, SLE_UINT8,139, SL_MAX_VERSION, 0,MS, 0, 0, 1, 1, STR_CONFIG_SETTING_ROAD_VEHICLE_ACCELERATION_MODEL, RoadVehAccelerationModelChanged),
|
||||
SDT_CONDVAR(GameSettings, vehicle.train_slope_steepness, SLE_UINT8,133, SL_MAX_VERSION, 0, 0, 3, 0, 10, 1, STR_CONFIG_SETTING_TRAIN_SLOPE_STEEPNESS, TrainSlopeSteepnessChanged),
|
||||
SDT_BOOL(GameSettings, pf.forbid_90_deg, 0, 0, false, STR_CONFIG_SETTING_FORBID_90_DEG, NULL),
|
||||
SDT_BOOL(GameSettings, vehicle.mammoth_trains, 0,NN, true, STR_CONFIG_SETTING_MAMMOTHTRAINS, NULL),
|
||||
|
|
|
@ -1477,9 +1477,13 @@ static VehicleEnterTileStatus VehicleEnter_TunnelBridge(Vehicle *v, TileIndex ti
|
|||
ClrBit(t->gv_flags, GVF_GOINGDOWN_BIT);
|
||||
} break;
|
||||
|
||||
case VEH_ROAD:
|
||||
RoadVehicle::From(v)->state = RVSB_WORMHOLE;
|
||||
break;
|
||||
case VEH_ROAD: {
|
||||
RoadVehicle *rv = RoadVehicle::From(v);
|
||||
rv->state = RVSB_WORMHOLE;
|
||||
/* There are no slopes inside bridges / tunnels. */
|
||||
ClrBit(rv->gv_flags, GVF_GOINGUP_BIT);
|
||||
ClrBit(rv->gv_flags, GVF_GOINGDOWN_BIT);
|
||||
} break;
|
||||
|
||||
case VEH_SHIP:
|
||||
Ship::From(v)->state = TRACK_BIT_WORMHOLE;
|
||||
|
|
Loading…
Reference in New Issue