diff --git a/src/script/api/CMakeLists.txt b/src/script/api/CMakeLists.txt index 585d2d43fd..05e9a294d2 100644 --- a/src/script/api/CMakeLists.txt +++ b/src/script/api/CMakeLists.txt @@ -151,6 +151,7 @@ add_files( script_basestation.hpp script_bridge.hpp script_bridgelist.hpp + script_timemode.hpp script_cargo.hpp script_cargolist.hpp script_cargomonitor.hpp @@ -226,6 +227,7 @@ add_files( script_basestation.cpp script_bridge.cpp script_bridgelist.cpp + script_timemode.cpp script_cargo.cpp script_cargolist.cpp script_cargomonitor.cpp diff --git a/src/script/api/ai_changelog.hpp b/src/script/api/ai_changelog.hpp index 0a35d43ed4..6af41d52a4 100644 --- a/src/script/api/ai_changelog.hpp +++ b/src/script/api/ai_changelog.hpp @@ -18,6 +18,7 @@ * This version is not yet released. The following changes are not set in stone yet. * * API additions: + * \li AITimeMode * \li AITown::ROAD_LAYOUT_RANDOM * \li AIVehicle::IsPrimaryVehicle * diff --git a/src/script/api/game_changelog.hpp b/src/script/api/game_changelog.hpp index 0dfb08c2e5..570e8c589b 100644 --- a/src/script/api/game_changelog.hpp +++ b/src/script/api/game_changelog.hpp @@ -22,6 +22,7 @@ * \li GSAsyncMode * \li GSCompanyMode::IsValid * \li GSCompanyMode::IsDeity + * \li GSTimeMode * \li GSTown::ROAD_LAYOUT_RANDOM * \li GSVehicle::IsPrimaryVehicle * \li GSOrder::SetOrderJumpTo diff --git a/src/script/api/script_date.cpp b/src/script/api/script_date.cpp index 0c1a0eea0f..eda165c56e 100644 --- a/src/script/api/script_date.cpp +++ b/src/script/api/script_date.cpp @@ -9,6 +9,7 @@ #include "../../stdafx.h" #include "script_date.hpp" +#include "script_timemode.hpp" #include "../../date_func.h" #include "../../settings_type.h" @@ -25,7 +26,9 @@ /* static */ ScriptDate::Date ScriptDate::GetCurrentDate() { - return (ScriptDate::Date)::CalTime::CurDate().base(); + if (ScriptTimeMode::IsCalendarMode()) return (ScriptDate::Date)::CalTime::CurDate().base(); + + return (ScriptDate::Date)EconTime::CurDate().base(); } /* static */ SQInteger ScriptDate::GetDayLengthFactor() @@ -37,7 +40,12 @@ { if (date < 0) return DATE_INVALID; - ::CalTime::YearMonthDay ymd = ::CalTime::ConvertDateToYMD(date); + if (ScriptTimeMode::IsCalendarMode()) { + ::CalTime::YearMonthDay ymd = ::CalTime::ConvertDateToYMD(date); + return ymd.year.base(); + } + + ::EconTime::YearMonthDay ymd = ::EconTime::ConvertDateToYMD(date); return ymd.year.base(); } @@ -45,7 +53,12 @@ { if (date < 0) return DATE_INVALID; - ::CalTime::YearMonthDay ymd = ::CalTime::ConvertDateToYMD(date); + if (ScriptTimeMode::IsCalendarMode()) { + ::CalTime::YearMonthDay ymd = ::CalTime::ConvertDateToYMD(date); + return ymd.month + 1; + } + + ::EconTime::YearMonthDay ymd = ::EconTime::ConvertDateToYMD(date); return ymd.month + 1; } @@ -53,7 +66,12 @@ { if (date < 0) return DATE_INVALID; - ::CalTime::YearMonthDay ymd = ::CalTime::ConvertDateToYMD(date); + if (ScriptTimeMode::IsCalendarMode()) { + ::CalTime::YearMonthDay ymd = ::CalTime::ConvertDateToYMD(date); + return ymd.day; + } + + ::EconTime::YearMonthDay ymd = ::EconTime::ConvertDateToYMD(date); return ymd.day; } @@ -63,7 +81,9 @@ if (day_of_month < 1 || day_of_month > 31) return DATE_INVALID; if (year < 0 || year > CalTime::MAX_YEAR) return DATE_INVALID; - return (ScriptDate::Date)::CalTime::ConvertYMDToDate(year, month - 1, day_of_month).base(); + if (ScriptTimeMode::IsCalendarMode()) return (ScriptDate::Date)::CalTime::ConvertYMDToDate(year, month - 1, day_of_month).base(); + + return (ScriptDate::Date)::EconTime::ConvertYMDToDate(year, month - 1, day_of_month).base(); } /* static */ SQInteger ScriptDate::GetSystemTime() diff --git a/src/script/api/script_object.cpp b/src/script/api/script_object.cpp index 25c8a3c688..2196f4e1d5 100644 --- a/src/script/api/script_object.cpp +++ b/src/script/api/script_object.cpp @@ -277,6 +277,16 @@ ScriptObject::ActiveInstance::~ActiveInstance() return GetStorage()->allow_do_command; } +/* static */ void ScriptObject::SetTimeMode(bool calendar) +{ + GetStorage()->time_mode = calendar; +} + +/* static */ bool ScriptObject::IsCalendarTimeMode() +{ + return GetStorage()->time_mode; +} + /* static */ void ScriptObject::SetCompany(CompanyID company) { if (GetStorage()->root_company == INVALID_OWNER) GetStorage()->root_company = company; diff --git a/src/script/api/script_object.hpp b/src/script/api/script_object.hpp index 1430f613f4..70938e48d9 100644 --- a/src/script/api/script_object.hpp +++ b/src/script/api/script_object.hpp @@ -255,6 +255,20 @@ protected: */ static bool GetAllowDoCommand(); + /** + * Set if the script is running in calendar time or economy time mode. + * Calendar time is used by OpenTTD for technology like vehicle introductions and expiration, and variable snowline. It can be sped up or slowed down by the player. + * Economy time always runs at the same pace and handles things like cargo production, everything related to money, etc. + * @param Calendar Should we use calendar time mode? (Set to false for economy time mode.) + */ + static void SetTimeMode(bool calendar); + + /** + * Check if the script is operating in calendar time mode, or in economy time mode. See SetTimeMode() for more information. + * @return True if we are in calendar time mode, false if we are in economy time mode. + */ + static bool IsCalendarTimeMode(); + /** * Set the current company to execute commands for or request * information about. diff --git a/src/script/api/script_timemode.cpp b/src/script/api/script_timemode.cpp new file mode 100644 index 0000000000..f927368f8a --- /dev/null +++ b/src/script/api/script_timemode.cpp @@ -0,0 +1,29 @@ +/* + * This file is part of OpenTTD. + * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2. + * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see . + */ + +/** @file script_timemode.cpp Implementation of ScriptTimeMode. */ + +#include "../../stdafx.h" +#include "script_timemode.hpp" + +#include "../../safeguards.h" + +ScriptTimeMode::ScriptTimeMode(bool calendar) +{ + this->last_time_mode = ScriptObject::IsCalendarTimeMode(); + ScriptObject::SetTimeMode(calendar); +} + +ScriptTimeMode::~ScriptTimeMode() +{ + ScriptObject::SetTimeMode(this->last_time_mode); +} + +/* static */ bool ScriptTimeMode::IsCalendarMode() +{ + return ScriptObject::IsCalendarTimeMode(); +} diff --git a/src/script/api/script_timemode.hpp b/src/script/api/script_timemode.hpp new file mode 100644 index 0000000000..eb03b0b3f9 --- /dev/null +++ b/src/script/api/script_timemode.hpp @@ -0,0 +1,45 @@ +/* + * This file is part of OpenTTD. + * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2. + * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see . + */ + +/** @file script_timemode.hpp Switch the time mode. */ + +#ifndef SCRIPT_TIMEMODE_HPP +#define SCRIPT_TIMEMODE_HPP + +#include "script_object.hpp" + +/** + * Class to switch the current time. + * If you create an instance of this class, the mode will be switched to either calendar time or economy time mode. + * @note Destroying this object will restore the previous time mode. + * @api ai game + */ +class ScriptTimeMode : public ScriptObject { +private: + bool last_time_mode; ///< The last time mode we were using. +public: + /** + * Creating an instance of this class switches the time mode used for queries and commands. + * Calendar time is used by OpenTTD for technology like vehicle introductions and expiration, and variable snowline. It can be sped up or slowed down by the player. + * Economy time always runs at the same pace and handles things like cargo production, everything related to money, etc. + * @param Calendar Should we use calendar time mode? (Set to false for economy time mode.) + */ + ScriptTimeMode(bool calendar); + + /** + * Destroying this instance resets the time mode to the mode it was in when the instance was created. + */ + ~ScriptTimeMode(); + + /** + * Check if the script is operating in calendar time mode, or in economy time mode. See ScriptTimeMode() for more information. + * @return True if we are in calendar time mode, false if we are in economy time mode. + */ + static bool IsCalendarMode(); +}; + +#endif /* SCRIPT_TIMEMODE_HPP */ diff --git a/src/script/script_storage.hpp b/src/script/script_storage.hpp index c0802e4d22..98b7b903c8 100644 --- a/src/script/script_storage.hpp +++ b/src/script/script_storage.hpp @@ -43,6 +43,7 @@ private: class ScriptObject *mode_instance; ///< The instance belonging to the current build mode. ScriptAsyncModeProc *async_mode; ///< The current command async mode we are in. class ScriptObject *async_mode_instance; ///< The instance belonging to the current command async mode. + bool time_mode; ///< True if we in calendar time mode, or false (default) if we are in economy time mode. CompanyID root_company; ///< The root company, the company that the script really belongs to. CompanyID company; ///< The current company. @@ -84,6 +85,7 @@ public: mode_instance (nullptr), async_mode (nullptr), async_mode_instance (nullptr), + time_mode (false), root_company (INVALID_OWNER), company (INVALID_OWNER), delay (1),