mirror of https://github.com/OpenTTD/OpenTTD
(svn r25170) [1.3] -Backport from trunk:
- Fix: Original train and rv acceleration did no longer respect bridge speed limits [FS#5523] (r25167) - Fix: [Win32] Do not statically link to SHGetFolderPath as it may not exist, and improve its emulation [FS#5522] (r25155, r25153) - Fix: [Win32] Do not store invalid paths in the search path list (r25154) - Fix: Remove stray reservation from savegames affected by FS#5510 et al. upon loading [FS#5520] (r25152) - Fix: [Script] XXBase::Chance function did not work for large values (>65535) [FS#5517] (r25148)release/1.3
parent
283ab728f2
commit
7daff778f9
|
@ -173,7 +173,7 @@ static FT_Error GetFontByFaceName(const char *font_name, FT_Face *face)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!SUCCEEDED(SHGetFolderPath(NULL, CSIDL_FONTS, NULL, SHGFP_TYPE_CURRENT, vbuffer))) {
|
if (!SUCCEEDED(OTTDSHGetFolderPath(NULL, CSIDL_FONTS, NULL, SHGFP_TYPE_CURRENT, vbuffer))) {
|
||||||
DEBUG(freetype, 0, "SHGetFolderPath cannot return fonts directory");
|
DEBUG(freetype, 0, "SHGetFolderPath cannot return fonts directory");
|
||||||
goto folder_error;
|
goto folder_error;
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,6 +17,7 @@
|
||||||
#include "../../fios.h"
|
#include "../../fios.h"
|
||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
#include <fcntl.h>
|
#include <fcntl.h>
|
||||||
|
#include <regstr.h>
|
||||||
#include <shlobj.h> /* SHGetFolderPath */
|
#include <shlobj.h> /* SHGetFolderPath */
|
||||||
#include <Shellapi.h>
|
#include <Shellapi.h>
|
||||||
#include "win32.h"
|
#include "win32.h"
|
||||||
|
@ -505,19 +506,25 @@ void DetermineBasePaths(const char *exe)
|
||||||
char tmp[MAX_PATH];
|
char tmp[MAX_PATH];
|
||||||
TCHAR path[MAX_PATH];
|
TCHAR path[MAX_PATH];
|
||||||
#ifdef WITH_PERSONAL_DIR
|
#ifdef WITH_PERSONAL_DIR
|
||||||
SHGetFolderPath(NULL, CSIDL_PERSONAL, NULL, SHGFP_TYPE_CURRENT, path);
|
if (SUCCEEDED(OTTDSHGetFolderPath(NULL, CSIDL_PERSONAL, NULL, SHGFP_TYPE_CURRENT, path))) {
|
||||||
strecpy(tmp, WIDE_TO_MB_BUFFER(path, tmp, lengthof(tmp)), lastof(tmp));
|
strecpy(tmp, WIDE_TO_MB_BUFFER(path, tmp, lengthof(tmp)), lastof(tmp));
|
||||||
AppendPathSeparator(tmp, MAX_PATH);
|
AppendPathSeparator(tmp, MAX_PATH);
|
||||||
ttd_strlcat(tmp, PERSONAL_DIR, MAX_PATH);
|
ttd_strlcat(tmp, PERSONAL_DIR, MAX_PATH);
|
||||||
AppendPathSeparator(tmp, MAX_PATH);
|
AppendPathSeparator(tmp, MAX_PATH);
|
||||||
_searchpaths[SP_PERSONAL_DIR] = strdup(tmp);
|
_searchpaths[SP_PERSONAL_DIR] = strdup(tmp);
|
||||||
|
} else {
|
||||||
|
_searchpaths[SP_PERSONAL_DIR] = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
SHGetFolderPath(NULL, CSIDL_COMMON_DOCUMENTS, NULL, SHGFP_TYPE_CURRENT, path);
|
if (SUCCEEDED(OTTDSHGetFolderPath(NULL, CSIDL_COMMON_DOCUMENTS, NULL, SHGFP_TYPE_CURRENT, path))) {
|
||||||
strecpy(tmp, WIDE_TO_MB_BUFFER(path, tmp, lengthof(tmp)), lastof(tmp));
|
strecpy(tmp, WIDE_TO_MB_BUFFER(path, tmp, lengthof(tmp)), lastof(tmp));
|
||||||
AppendPathSeparator(tmp, MAX_PATH);
|
AppendPathSeparator(tmp, MAX_PATH);
|
||||||
ttd_strlcat(tmp, PERSONAL_DIR, MAX_PATH);
|
ttd_strlcat(tmp, PERSONAL_DIR, MAX_PATH);
|
||||||
AppendPathSeparator(tmp, MAX_PATH);
|
AppendPathSeparator(tmp, MAX_PATH);
|
||||||
_searchpaths[SP_SHARED_DIR] = strdup(tmp);
|
_searchpaths[SP_SHARED_DIR] = strdup(tmp);
|
||||||
|
} else {
|
||||||
|
_searchpaths[SP_SHARED_DIR] = NULL;
|
||||||
|
}
|
||||||
#else
|
#else
|
||||||
_searchpaths[SP_PERSONAL_DIR] = NULL;
|
_searchpaths[SP_PERSONAL_DIR] = NULL;
|
||||||
_searchpaths[SP_SHARED_DIR] = NULL;
|
_searchpaths[SP_SHARED_DIR] = NULL;
|
||||||
|
@ -726,8 +733,11 @@ HRESULT OTTDSHGetFolderPath(HWND hwnd, int csidl, HANDLE hToken, DWORD dwFlags,
|
||||||
#else
|
#else
|
||||||
# define W(x) x "A"
|
# define W(x) x "A"
|
||||||
#endif
|
#endif
|
||||||
if (!LoadLibraryList((Function*)&SHGetFolderPath, "SHFolder.dll\0" W("SHGetFolderPath") "\0\0")) {
|
/* The function lives in shell32.dll for all current Windows versions, but it first started to appear in SHFolder.dll. */
|
||||||
DEBUG(misc, 0, "Unable to load " W("SHGetFolderPath") "from SHFolder.dll");
|
if (!LoadLibraryList((Function*)&SHGetFolderPath, "shell32.dll\0" W("SHGetFolderPath") "\0\0")) {
|
||||||
|
if (!LoadLibraryList((Function*)&SHGetFolderPath, "SHFolder.dll\0" W("SHGetFolderPath") "\0\0")) {
|
||||||
|
DEBUG(misc, 0, "Unable to load " W("SHGetFolderPath") "from either shell32.dll or SHFolder.dll");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
#undef W
|
#undef W
|
||||||
first_time = false;
|
first_time = false;
|
||||||
|
@ -752,6 +762,17 @@ HRESULT OTTDSHGetFolderPath(HWND hwnd, int csidl, HANDLE hToken, DWORD dwFlags,
|
||||||
|
|
||||||
return (HRESULT)0;
|
return (HRESULT)0;
|
||||||
|
|
||||||
|
case CSIDL_PERSONAL:
|
||||||
|
case CSIDL_COMMON_DOCUMENTS: {
|
||||||
|
HKEY key;
|
||||||
|
if (RegOpenKeyEx(csidl == CSIDL_PERSONAL ? HKEY_CURRENT_USER : HKEY_LOCAL_MACHINE, REGSTR_PATH_SPECIAL_FOLDERS, 0, KEY_READ, &key) != ERROR_SUCCESS) break;
|
||||||
|
DWORD len = MAX_PATH;
|
||||||
|
ret = RegQueryValueEx(key, csidl == CSIDL_PERSONAL ? _T("Personal") : _T("Common Documents"), NULL, NULL, (LPBYTE)pszPath, &len);
|
||||||
|
RegCloseKey(key);
|
||||||
|
if (ret == ERROR_SUCCESS) return (HRESULT)0;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
/* XXX - other types to go here when needed... */
|
/* XXX - other types to go here when needed... */
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -40,12 +40,6 @@ extern uint _codepage; // local code-page in the system @see win32_v.cpp:WM_INPU
|
||||||
# define WIDE_TO_MB_BUFFER(str, buffer, buflen) (str)
|
# define WIDE_TO_MB_BUFFER(str, buffer, buflen) (str)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* Override SHGetFolderPath with our custom implementation */
|
|
||||||
#if defined(SHGetFolderPath)
|
|
||||||
#undef SHGetFolderPath
|
|
||||||
#endif
|
|
||||||
#define SHGetFolderPath OTTDSHGetFolderPath
|
|
||||||
|
|
||||||
HRESULT OTTDSHGetFolderPath(HWND, int, HANDLE, DWORD, LPTSTR);
|
HRESULT OTTDSHGetFolderPath(HWND, int, HANDLE, DWORD, LPTSTR);
|
||||||
|
|
||||||
#if defined(__MINGW32__)
|
#if defined(__MINGW32__)
|
||||||
|
|
|
@ -429,17 +429,17 @@ void RoadVehicle::UpdateDeltaXY(Direction direction)
|
||||||
*/
|
*/
|
||||||
inline int RoadVehicle::GetCurrentMaxSpeed() const
|
inline int RoadVehicle::GetCurrentMaxSpeed() const
|
||||||
{
|
{
|
||||||
if (_settings_game.vehicle.roadveh_acceleration_model == AM_ORIGINAL) return min(this->vcache.cached_max_speed, this->current_order.max_speed * 2);
|
|
||||||
|
|
||||||
int max_speed = this->vcache.cached_max_speed;
|
int max_speed = this->vcache.cached_max_speed;
|
||||||
|
|
||||||
/* Limit speed to 50% while reversing, 75% in curves. */
|
/* Limit speed to 50% while reversing, 75% in curves. */
|
||||||
for (const RoadVehicle *u = this; u != NULL; u = u->Next()) {
|
for (const RoadVehicle *u = this; u != NULL; u = u->Next()) {
|
||||||
if (this->state <= RVSB_TRACKDIR_MASK && IsReversingRoadTrackdir((Trackdir)this->state)) {
|
if (_settings_game.vehicle.roadveh_acceleration_model == AM_REALISTIC) {
|
||||||
max_speed = this->vcache.cached_max_speed / 2;
|
if (this->state <= RVSB_TRACKDIR_MASK && IsReversingRoadTrackdir((Trackdir)this->state)) {
|
||||||
break;
|
max_speed = this->vcache.cached_max_speed / 2;
|
||||||
} else if ((u->direction & 1) == 0) {
|
break;
|
||||||
max_speed = this->vcache.cached_max_speed * 3 / 4;
|
} else if ((u->direction & 1) == 0) {
|
||||||
|
max_speed = this->vcache.cached_max_speed * 3 / 4;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Vehicle is on the middle part of a bridge. */
|
/* Vehicle is on the middle part of a bridge. */
|
||||||
|
|
|
@ -2770,6 +2770,14 @@ bool AfterLoadGame()
|
||||||
v->acceleration = avi->acceleration;
|
v->acceleration = avi->acceleration;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Blocked tiles could be reserved due to a bug, which causes
|
||||||
|
* other places to assert upon e.g. station reconstruction. */
|
||||||
|
for (TileIndex t = 0; t < map_size; t++) {
|
||||||
|
if (HasStationTileRail(t) && IsStationTileBlocked(t)) {
|
||||||
|
SetRailStationReservation(t, false);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Road stops is 'only' updating some caches */
|
/* Road stops is 'only' updating some caches */
|
||||||
|
|
|
@ -44,7 +44,7 @@
|
||||||
/* static */ bool ScriptBase::Chance(uint out, uint max)
|
/* static */ bool ScriptBase::Chance(uint out, uint max)
|
||||||
{
|
{
|
||||||
EnforcePrecondition(false, out <= max);
|
EnforcePrecondition(false, out <= max);
|
||||||
return (uint16)Rand() <= (uint16)((65535 * out) / max);
|
return ScriptBase::RandRange(max) < out;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* static */ bool ScriptBase::ChanceItem(int unused_param, uint out, uint max)
|
/* static */ bool ScriptBase::ChanceItem(int unused_param, uint out, uint max)
|
||||||
|
|
|
@ -70,6 +70,7 @@ public:
|
||||||
* @param unused_param This parameter is not used, but is needed to work with lists.
|
* @param unused_param This parameter is not used, but is needed to work with lists.
|
||||||
* @param out How many times it should return true.
|
* @param out How many times it should return true.
|
||||||
* @param max Out of this many times.
|
* @param max Out of this many times.
|
||||||
|
* @pre \a out is at most equal to \a max.
|
||||||
* @return True if the chance worked out.
|
* @return True if the chance worked out.
|
||||||
*/
|
*/
|
||||||
static bool ChanceItem(int unused_param, uint out, uint max);
|
static bool ChanceItem(int unused_param, uint out, uint max);
|
||||||
|
|
|
@ -371,10 +371,11 @@ int Train::GetCurveSpeedLimit() const
|
||||||
*/
|
*/
|
||||||
int Train::GetCurrentMaxSpeed() const
|
int Train::GetCurrentMaxSpeed() const
|
||||||
{
|
{
|
||||||
if (_settings_game.vehicle.train_acceleration_model == AM_ORIGINAL) return min(this->gcache.cached_max_track_speed, this->current_order.max_speed);
|
int max_speed = _settings_game.vehicle.train_acceleration_model == AM_ORIGINAL ?
|
||||||
|
this->gcache.cached_max_track_speed :
|
||||||
|
this->tcache.cached_max_curve_speed;
|
||||||
|
|
||||||
int max_speed = this->tcache.cached_max_curve_speed;
|
if (_settings_game.vehicle.train_acceleration_model == AM_REALISTIC && IsRailStationTile(this->tile)) {
|
||||||
if (IsRailStationTile(this->tile)) {
|
|
||||||
StationID sid = GetStationIndex(this->tile);
|
StationID sid = GetStationIndex(this->tile);
|
||||||
if (this->current_order.ShouldStopAtStation(this, sid)) {
|
if (this->current_order.ShouldStopAtStation(this, sid)) {
|
||||||
int station_ahead;
|
int station_ahead;
|
||||||
|
@ -400,7 +401,7 @@ int Train::GetCurrentMaxSpeed() const
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const Train *u = this; u != NULL; u = u->Next()) {
|
for (const Train *u = this; u != NULL; u = u->Next()) {
|
||||||
if (u->track == TRACK_BIT_DEPOT) {
|
if (_settings_game.vehicle.train_acceleration_model == AM_REALISTIC && u->track == TRACK_BIT_DEPOT) {
|
||||||
max_speed = min(max_speed, 61);
|
max_speed = min(max_speed, 61);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -2775,7 +2776,7 @@ int Train::UpdateSpeed()
|
||||||
switch (_settings_game.vehicle.train_acceleration_model) {
|
switch (_settings_game.vehicle.train_acceleration_model) {
|
||||||
default: NOT_REACHED();
|
default: NOT_REACHED();
|
||||||
case AM_ORIGINAL:
|
case AM_ORIGINAL:
|
||||||
return this->DoUpdateSpeed(this->acceleration * (this->GetAccelerationStatus() == AS_BRAKE ? -4 : 2), 0, min(this->gcache.cached_max_track_speed, this->current_order.max_speed));
|
return this->DoUpdateSpeed(this->acceleration * (this->GetAccelerationStatus() == AS_BRAKE ? -4 : 2), 0, this->GetCurrentMaxSpeed());
|
||||||
|
|
||||||
case AM_REALISTIC:
|
case AM_REALISTIC:
|
||||||
return this->DoUpdateSpeed(this->GetAcceleration(), this->GetAccelerationStatus() == AS_BRAKE ? 0 : 2, this->GetCurrentMaxSpeed());
|
return this->DoUpdateSpeed(this->GetAcceleration(), this->GetAccelerationStatus() == AS_BRAKE ? 0 : 2, this->GetCurrentMaxSpeed());
|
||||||
|
|
Loading…
Reference in New Issue