diff --git a/src/economy.cpp b/src/economy.cpp index 0efa7981e9..4376a92bbd 100644 --- a/src/economy.cpp +++ b/src/economy.cpp @@ -109,6 +109,10 @@ Prices _price; Money _additional_cash_required; static PriceMultipliers _price_base_multiplier; +CargoScaler _town_cargo_scaler; +CargoScaler _industry_cargo_scaler; +CargoScaler _industry_inverse_cargo_scaler; + extern int GetAmountOwnedBy(const Company *c, Owner owner); /** @@ -2689,3 +2693,15 @@ uint ScaleQuantity(uint amount, int cf, int fine, bool allow_trunc) return amount; } + +uint CargoScaler::ScaleAllowTrunc(uint num) +{ + return this->ScaleWithBias(num, Random() & 0xFFFF); +} + +void UpdateCargoScalers() +{ + _town_cargo_scaler.SetScale((_settings_game.economy.town_cargo_scale << 16) / 100); + _industry_cargo_scaler.SetScale((_settings_game.economy.industry_cargo_scale << 16) / 100); + _industry_inverse_cargo_scaler.SetScale((100 << 16) / std::max(1, _settings_game.economy.industry_cargo_scale)); +} diff --git a/src/economy_func.h b/src/economy_func.h index 0c35d078a9..33a53b87e5 100644 --- a/src/economy_func.h +++ b/src/economy_func.h @@ -25,6 +25,10 @@ extern Economy _economy; /* Prices and also the fractional part. */ extern Prices _price; +extern CargoScaler _town_cargo_scaler; +extern CargoScaler _industry_cargo_scaler; +extern CargoScaler _industry_inverse_cargo_scaler; + int UpdateCompanyRatingAndValue(Company *c, bool update); void StartupIndustryDailyChanges(bool init_counter); @@ -52,4 +56,6 @@ inline bool EconomyIsInRecession() uint ScaleQuantity(uint amount, int scale_factor, bool allow_trunc = false); uint ScaleQuantity(uint amount, int cf, int fine, bool allow_trunc = false); +void UpdateCargoScalers(); + #endif /* ECONOMY_FUNC_H */ diff --git a/src/economy_type.h b/src/economy_type.h index e8918f82b7..4f11f42976 100644 --- a/src/economy_type.h +++ b/src/economy_type.h @@ -253,4 +253,33 @@ enum TickRateMode : byte { TRM_END, ///< Used for iterations and limit testing }; +struct CargoScaler { +private: + uint32_t scale16 = 1 << 16; + + inline uint ScaleWithBias(uint num, uint32_t bias) + { + return (uint)((((uint64_t)num * (uint64_t)this->scale16) + bias) >> 16); + } + +public: + inline bool HasScaling() const + { + return this->scale16 != (1 << 16); + } + + inline void SetScale(uint32_t scale16) + { + this->scale16 = scale16; + } + + inline uint Scale(uint num) + { + if (num == 0) return 0; + return std::max(1, this->ScaleWithBias(num, 0x8000)); + } + + uint ScaleAllowTrunc(uint num); +}; + #endif /* ECONOMY_TYPE_H */ diff --git a/src/industry_cmd.cpp b/src/industry_cmd.cpp index e8868dd415..b33a3f0d30 100644 --- a/src/industry_cmd.cpp +++ b/src/industry_cmd.cpp @@ -524,8 +524,9 @@ static bool TransportIndustryGoods(TileIndex tile) const IndustrySpec *indspec = GetIndustrySpec(i->type); bool moved_cargo = false; + const uint step_limit = _industry_cargo_scaler.Scale(255); for (uint j = 0; j < lengthof(i->produced_cargo_waiting); j++) { - uint cw = std::min(i->produced_cargo_waiting[j], ScaleQuantity(255u, _settings_game.economy.industry_cargo_scale_factor)); + uint cw = std::min(i->produced_cargo_waiting[j], step_limit); if (cw > indspec->minimal_cargo && i->produced_cargo[j] != INVALID_CARGO) { i->produced_cargo_waiting[j] -= cw; @@ -1187,7 +1188,7 @@ static void ProduceIndustryGoodsFromRate(Industry *i, bool scale) if (i->produced_cargo[j] == INVALID_CARGO) continue; uint amount = i->production_rate[j]; if (amount != 0 && scale) { - amount = ScaleQuantity(amount, _settings_game.economy.industry_cargo_scale_factor); + amount = _industry_cargo_scaler.Scale(amount); } i->produced_cargo_waiting[j] = ClampTo(i->produced_cargo_waiting[j] + amount); } @@ -1217,7 +1218,7 @@ static void ProduceIndustryGoods(Industry *i) i->counter--; - const bool scale_ticks = (_settings_game.economy.industry_cargo_scale_factor != 0) && HasBit(indsp->callback_mask, CBM_IND_PRODUCTION_256_TICKS); + const bool scale_ticks = _industry_cargo_scaler.HasScaling() && HasBit(indsp->callback_mask, CBM_IND_PRODUCTION_256_TICKS); if (scale_ticks) { if ((i->counter % _scaled_production_ticks) == 0) { if (HasBit(indsp->callback_mask, CBM_IND_PRODUCTION_256_TICKS)) IndustryProductionCallback(i, 1); @@ -1284,7 +1285,7 @@ void OnTick_Industry() if (_game_mode == GM_EDITOR) return; - _scaled_production_ticks = ScaleQuantity(INDUSTRY_PRODUCE_TICKS, -_settings_game.economy.industry_cargo_scale_factor); + _scaled_production_ticks = _industry_inverse_cargo_scaler.Scale(INDUSTRY_PRODUCE_TICKS); for (Industry *i : Industry::Iterate()) { ProduceIndustryGoods(i); } diff --git a/src/industry_gui.cpp b/src/industry_gui.cpp index 7441e38b75..0f352c0d46 100644 --- a/src/industry_gui.cpp +++ b/src/industry_gui.cpp @@ -1164,7 +1164,7 @@ static void UpdateIndustryProduction(Industry *i) for (byte j = 0; j < lengthof(i->produced_cargo); j++) { if (i->produced_cargo[j] != INVALID_CARGO) { - i->last_month_production[j] = ScaleQuantity(8 * i->production_rate[j], _settings_game.economy.industry_cargo_scale_factor); + i->last_month_production[j] = _industry_cargo_scaler.Scale(8 * i->production_rate[j]); } } } diff --git a/src/lang/extra/czech.txt b/src/lang/extra/czech.txt index 85787068da..9b78e3b48f 100644 --- a/src/lang/extra/czech.txt +++ b/src/lang/extra/czech.txt @@ -481,12 +481,6 @@ STR_CONFIG_SETTING_TOWN_MAX_ROAD_SLOPE_ZERO :bez omezení STR_CONFIG_SETTING_ALLOW_TOWN_BRIDGES :Města mohou stavět mosty: {STRING} STR_CONFIG_SETTING_ALLOW_TOWN_BRIDGES_HELPTEXT :Povolí městům výstavbu mostů -STR_CONFIG_SETTING_TOWN_CARGO_FACTOR :Faktor produkce nákladu městy (méně < 0 < více): {STRING} -STR_CONFIG_SETTING_TOWN_CARGO_FACTOR_HELPTEXT :Cestující, pošta a ostatní produkce nákladu městy zhruba odpovídá hodnotě 2^faktor (je závislá exponenciálně) - -STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR :Faktor produkce nákladu průmyslem (méně < 0 < více): {STRING} -STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR_HELPTEXT :Produkce nákladu průmyslem zhruba odpovídá hodnotě 2^faktor (je závislá exponenciálně). Nezahrnuje průmysl založený na kácení lesů.{}Není zaručena úplná kompatibilita se všemi průmyslovými řetězci z NewGRF. - STR_CONFIG_SETTING_TOWN_ABOVE_HEIGHT :Žádná města nad výškovou úroveň: {STRING} STR_CONFIG_SETTING_TOWN_ABOVE_HEIGHT_HELPTEXT :Nad stanovenou výškovou úrovní se nebudou při tvorbě mapy generovat žádná města. diff --git a/src/lang/extra/english.txt b/src/lang/extra/english.txt index 49bacdc86b..231da1f33f 100644 --- a/src/lang/extra/english.txt +++ b/src/lang/extra/english.txt @@ -559,11 +559,14 @@ STR_CONFIG_SETTING_TOWN_MAX_ROAD_SLOPE_ZERO :No limit STR_CONFIG_SETTING_ALLOW_TOWN_BRIDGES :Towns are allowed to build bridges: {STRING2} STR_CONFIG_SETTING_ALLOW_TOWN_BRIDGES_HELPTEXT :Enabling this setting allows towns to build bridges -STR_CONFIG_SETTING_TOWN_CARGO_FACTOR :Town cargo generation factor (less < 0 < more): {STRING2} -STR_CONFIG_SETTING_TOWN_CARGO_FACTOR_HELPTEXT :Passenger, mail, and other town cargo production is scaled by approximately 2^factor (exponential) +STR_CONFIG_SETTING_TOWN_CARGO_SCALE :Scale town cargo production: {STRING2} +STR_CONFIG_SETTING_TOWN_CARGO_SCALE_HELPTEXT :Scale the cargo production of towns by this percentage. -STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR :Industry cargo generation factor (less < 0 < more): {STRING2} -STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR_HELPTEXT :Primary industry cargo production is scaled by approximately 2^factor (exponential). This excludes tree-cutting industries.{}This is not guaranteed to be fully compatible with all industry NewGRFs. +STR_CONFIG_SETTING_INDUSTRY_CARGO_SCALE :Scale industry cargo production: {STRING2} +STR_CONFIG_SETTING_INDUSTRY_CARGO_SCALE_HELPTEXT :Scale the cargo production of industries by this percentage. +STR_CONFIG_SETTING_INDUSTRY_CARGO_SCALE_HELPTEXT_EXTRA :{STRING}{}This excludes tree-cutting industries.{}This is not guaranteed to be fully compatible with all industry NewGRFs. + +STR_CONFIG_SETTING_CARGO_SCALE_VALUE :{NUM}% STR_CONFIG_SETTING_TOWN_ABOVE_HEIGHT :No towns above height level: {STRING2} STR_CONFIG_SETTING_TOWN_ABOVE_HEIGHT_HELPTEXT :No towns above the specified height level are built during map creation. diff --git a/src/lang/extra/galician.txt b/src/lang/extra/galician.txt index f4c1bfa6b5..2c6eaba8f0 100644 --- a/src/lang/extra/galician.txt +++ b/src/lang/extra/galician.txt @@ -499,12 +499,6 @@ STR_CONFIG_SETTING_TOWN_MAX_ROAD_SLOPE_ZERO :Sen límite STR_CONFIG_SETTING_ALLOW_TOWN_BRIDGES :As vilas poden construír pontes: {STRING} STR_CONFIG_SETTING_ALLOW_TOWN_BRIDGES_HELPTEXT :Habilitar isto permite as vilas construír pontes -STR_CONFIG_SETTING_TOWN_CARGO_FACTOR :Factor de xeración de carga das vilas (menos < 0 < máis): {STRING} -STR_CONFIG_SETTING_TOWN_CARGO_FACTOR_HELPTEXT :Os pasaxeiros, correo e outras cargas de produción nas vilas escálanse aproximadamente por 2^factor (exponencial) - -STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR :Factor de xeración de carga das industrias (menos < 0 < máis): {STRING} -STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR_HELPTEXT :A produción de carga das industrias primarias escálanse aproximadamente por 2^factor (exponencial). Isto exclúe as industrias de tala de árbores.{}Isto non garantiza ser completamente compatible con todos os NewGRFs de industria. - STR_CONFIG_SETTING_TOWN_ABOVE_HEIGHT :Sen vilas por enriba da altitude: {STRING} STR_CONFIG_SETTING_TOWN_ABOVE_HEIGHT_HELPTEXT :Non se constrúen vilas por enriba da altitude especificada durante a creación do mapa. diff --git a/src/lang/extra/german.txt b/src/lang/extra/german.txt index 71717562d5..6365354cd9 100644 --- a/src/lang/extra/german.txt +++ b/src/lang/extra/german.txt @@ -418,12 +418,6 @@ STR_CONFIG_SETTING_SIMULATE_SIGNALS_VALUE :{COMMA} Kachel{ STR_CONFIG_SETTING_DAY_LENGTH_FACTOR :Faktor für Tageslänge: {STRING} STR_CONFIG_SETTING_DAY_LENGTH_FACTOR_HELPTEXT :Die Spielgeschwindigkeit wird um diesen Faktor reduziert. -STR_CONFIG_SETTING_TOWN_CARGO_FACTOR :Faktor für die Erzeugung von städtischer Fracht (weniger < 0 < mehr): {STRING} -STR_CONFIG_SETTING_TOWN_CARGO_FACTOR_HELPTEXT :Passagiere, Post und andere städtische Frachtproduktion wird um ungefähr 2^Faktor (exponentiell) skaliert. - -STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR :Faktor für die Erzeugung von Fracht durch Industrien (weniger < 0 < mehr): {STRING} -STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR_HELPTEXT :Die Frachterzeugung von Rohstoff-Industrien wird etwa um 2^Faktor skaliert (exponentiell). Ausgenommen sind Holz-erntende Industrien.{}Es wird keine Kompatibilität mit allen Industrie-NewGRFs garantiert. - STR_CONFIG_SETTING_TOWN_ABOVE_HEIGHT :Keine Städte in einer Höhe über: {STRING} STR_CONFIG_SETTING_TOWN_ABOVE_HEIGHT_HELPTEXT :Während der Spielfelderstellung werden keine Städte oberhalb der angegebenen Höhe platziert. diff --git a/src/lang/extra/korean.txt b/src/lang/extra/korean.txt index c6b02e9355..c2413563db 100644 --- a/src/lang/extra/korean.txt +++ b/src/lang/extra/korean.txt @@ -499,12 +499,6 @@ STR_CONFIG_SETTING_TOWN_MAX_ROAD_SLOPE_ZERO :제한 없음 STR_CONFIG_SETTING_ALLOW_TOWN_BRIDGES :도시가 다리를 만드는 것을 허용: {STRING} STR_CONFIG_SETTING_ALLOW_TOWN_BRIDGES_HELPTEXT :도시가 다리를 만드는 허용하려면 이 설정을 켜세요 -STR_CONFIG_SETTING_TOWN_CARGO_FACTOR :도시 화물 생성 계수 (적음 < 0 < 많음): {STRING} -STR_CONFIG_SETTING_TOWN_CARGO_FACTOR_HELPTEXT :도시가 생산하는 화물의 양을 2^(생성 계수)에 근접하게 조절합니다. - -STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR :산업시설 화물 생성 계수 (적음 < 0 < 많음): {STRING} -STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR_HELPTEXT :1차 산업시설이 생산하는 화물의 양을 2^(생성 계수)에 근접하게 조절합니다. 나무를 베는 산업시설에는 적용되지 않습니다.{}모든 산업시설 관련 NewGRF와 모두 호환되지는 않을 수 있습니다. - STR_CONFIG_SETTING_TOWN_ABOVE_HEIGHT :이 고도 위에는 도시를 생성하지 않음: {STRING} STR_CONFIG_SETTING_TOWN_ABOVE_HEIGHT_HELPTEXT :지도를 생성할 때 특정 고도 위에는 도시를 만들지 않도록 만듭니다. diff --git a/src/lang/extra/simplified_chinese.txt b/src/lang/extra/simplified_chinese.txt index 5fb97bfafc..dd862a7b09 100644 --- a/src/lang/extra/simplified_chinese.txt +++ b/src/lang/extra/simplified_chinese.txt @@ -493,12 +493,6 @@ STR_CONFIG_SETTING_TOWN_MAX_ROAD_SLOPE_ZERO :无限制 STR_CONFIG_SETTING_ALLOW_TOWN_BRIDGES :城镇被允许建造桥梁: {STRING} STR_CONFIG_SETTING_ALLOW_TOWN_BRIDGES_HELPTEXT :决定城镇是否可以建造桥梁 -STR_CONFIG_SETTING_TOWN_CARGO_FACTOR :城镇货物生成因子 (更少 < 0 < 更多): {STRING} -STR_CONFIG_SETTING_TOWN_CARGO_FACTOR_HELPTEXT :旅客、邮件和其他城镇货物的生成倍数为2^因子 (实验性) - -STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR :工业货物生成因子 (更少 < 0 < 更多): {STRING} -STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR_HELPTEXT :原料工业货物的生成倍数为2^因子 (实验性){}这包括伐木工业{}可能与NewGRF工业冲突 - STR_CONFIG_SETTING_TOWN_ABOVE_HEIGHT :城镇最高海拔: {STRING} STR_CONFIG_SETTING_TOWN_ABOVE_HEIGHT_HELPTEXT :在此高度之上将没有城镇生成 diff --git a/src/misc.cpp b/src/misc.cpp index 8f7abbd4be..17e3e539f7 100644 --- a/src/misc.cpp +++ b/src/misc.cpp @@ -153,6 +153,7 @@ void InitializeGame(uint size_x, uint size_y, bool reset_date, bool reset_settin SetScaledTickVariables(); } SetupTileLoopCounts(); + UpdateCargoScalers(); UpdateCachedSnowLine(); UpdateCachedSnowLineBounds(); diff --git a/src/saveload/afterload.cpp b/src/saveload/afterload.cpp index 4d924d0020..fdf182f507 100644 --- a/src/saveload/afterload.cpp +++ b/src/saveload/afterload.cpp @@ -3948,15 +3948,24 @@ bool AfterLoadGame() } } - if (SlXvIsFeatureMissing(XSLFI_TOWN_CARGO_ADJ)) { - _settings_game.economy.town_cargo_scale_factor = 0; - } else if (SlXvIsFeaturePresent(XSLFI_TOWN_CARGO_ADJ, 1, 1)) { - /* Set 0.1 increment town cargo scale factor setting from old 1 increment setting */ - _settings_game.economy.town_cargo_scale_factor = _settings_game.economy.old_town_cargo_factor * 10; - } + if (_file_to_saveload.abstract_ftype == FT_SCENARIO) { + /* Apply the new-game cargo scale values for scenarios */ + _settings_game.economy.town_cargo_scale = _settings_newgame.economy.town_cargo_scale; + _settings_game.economy.industry_cargo_scale = _settings_newgame.economy.industry_cargo_scale; + } else { + if (SlXvIsFeatureMissing(XSLFI_TOWN_CARGO_ADJ)) { + _settings_game.economy.town_cargo_scale = 100; + } else if (SlXvIsFeaturePresent(XSLFI_TOWN_CARGO_ADJ, 1, 1)) { + _settings_game.economy.town_cargo_scale = ScaleQuantity(100, _settings_game.old_economy.town_cargo_factor * 10); + } else if (SlXvIsFeaturePresent(XSLFI_TOWN_CARGO_ADJ, 2, 2)) { + _settings_game.economy.town_cargo_scale = ScaleQuantity(100, _settings_game.old_economy.town_cargo_scale_factor); + } - if (SlXvIsFeatureMissing(XSLFI_INDUSTRY_CARGO_ADJ)) { - _settings_game.economy.industry_cargo_scale_factor = 0; + if (SlXvIsFeatureMissing(XSLFI_INDUSTRY_CARGO_ADJ)) { + _settings_game.economy.industry_cargo_scale = 100; + } else if (SlXvIsFeaturePresent(XSLFI_INDUSTRY_CARGO_ADJ, 1, 1)) { + _settings_game.economy.industry_cargo_scale = ScaleQuantity(100, _settings_game.old_economy.industry_cargo_scale_factor); + } } if (SlXvIsFeatureMissing(XSLFI_SAFER_CROSSINGS)) { @@ -4362,6 +4371,8 @@ bool AfterLoadGame() bool update_always_reserve_through = SlXvIsFeaturePresent(XSLFI_REALISTIC_TRAIN_BRAKING, 8, 10); UpdateExtraAspectsVariable(update_always_reserve_through); + UpdateCargoScalers(); + if (_networking && !_network_server) { SlProcessVENC(); diff --git a/src/settings.cpp b/src/settings.cpp index d1efd4ba3d..dc76c87761 100644 --- a/src/settings.cpp +++ b/src/settings.cpp @@ -1854,6 +1854,7 @@ static void DayLengthChanged(int32_t new_value) RebaseScaledDateTicksBase(); SetupTileLoopCounts(); + UpdateCargoScalers(); MarkWholeScreenDirty(); } @@ -2078,6 +2079,19 @@ static bool TrainPathfinderSettingGUI(SettingOnGuiCtrlData &data) } } +static bool IndustryCargoScaleGUI(SettingOnGuiCtrlData &data) +{ + switch (data.type) { + case SOGCT_DESCRIPTION_TEXT: + SetDParam(0, data.text); + data.text = STR_CONFIG_SETTING_INDUSTRY_CARGO_SCALE_HELPTEXT_EXTRA; + return true; + + default: + return false; + } +} + /* End - GUI callbacks */ /** diff --git a/src/settings_gui.cpp b/src/settings_gui.cpp index 9e188b047c..005688c0d3 100644 --- a/src/settings_gui.cpp +++ b/src/settings_gui.cpp @@ -2457,6 +2457,7 @@ static SettingsContainer &GetSettingsTree() town_zone->Add(new SettingEntry("economy.city_zone_3_mult")); town_zone->Add(new SettingEntry("economy.city_zone_4_mult")); } + towns->Add(new SettingEntry("economy.town_cargo_scale")); towns->Add(new SettingEntry("economy.town_growth_rate")); towns->Add(new SettingEntry("economy.town_growth_cargo_transported")); towns->Add(new SettingEntry("economy.town_zone_calc_mode")); @@ -2474,12 +2475,12 @@ static SettingsContainer &GetSettingsTree() towns->Add(new SettingEntry("economy.min_town_land_area")); towns->Add(new SettingEntry("economy.min_city_land_area")); towns->Add(new SettingEntry("economy.town_cargogen_mode")); - towns->Add(new SettingEntry("economy.town_cargo_scale_factor")); towns->Add(new SettingEntry("economy.random_road_reconstruction")); } SettingsPage *industries = environment->Add(new SettingsPage(STR_CONFIG_SETTING_ENVIRONMENT_INDUSTRIES)); { + industries->Add(new SettingEntry("economy.industry_cargo_scale")); industries->Add(new SettingEntry("difficulty.industry_density")); industries->Add(new SettingEntry("construction.raw_industry_construction")); industries->Add(new SettingEntry("construction.industry_platform")); @@ -2487,7 +2488,6 @@ static SettingsContainer &GetSettingsTree() industries->Add(new SettingEntry("game_creation.oil_refinery_limit")); industries->Add(new SettingEntry("economy.type")); industries->Add(new SettingEntry("station.serve_neutral_industries")); - industries->Add(new SettingEntry("economy.industry_cargo_scale_factor")); industries->Add(new SettingEntry("station.station_delivery_mode")); } diff --git a/src/settings_type.h b/src/settings_type.h index 8189ad8418..0deeeeda13 100644 --- a/src/settings_type.h +++ b/src/settings_type.h @@ -762,10 +762,9 @@ struct EconomySettings { TownTunnelMode town_build_tunnels; ///< if/when towns are allowed to build road tunnels uint8_t town_max_road_slope; ///< maximum number of consecutive sloped road tiles which towns are allowed to build bool allow_town_bridges; ///< towns are allowed to build bridges - int8_t old_town_cargo_factor; ///< old power-of-two multiplier for town (passenger, mail) generation. May be negative. - int16_t town_cargo_scale_factor; ///< scaled power-of-two multiplier for town (passenger, mail) generation. May be negative. - int16_t industry_cargo_scale_factor; ///< scaled power-of-two multiplier for primary industry generation. May be negative. bool infrastructure_maintenance; ///< enable monthly maintenance fee for owner infrastructure + uint16_t town_cargo_scale; ///< scale cargo production of towns by this percentage. + uint16_t industry_cargo_scale; ///< scale cargo production of industries by this percentage. uint8_t day_length_factor; ///< factor which the length of day is multiplied uint16_t random_road_reconstruction; ///< chance out of 1000 per tile loop for towns to start random road re-construction bool disable_inflation_newgrf_flag; ///< Disable NewGRF inflation flag @@ -773,6 +772,12 @@ struct EconomySettings { TickRateMode tick_rate; ///< Tick rate mode }; +struct OldEconomySettings { + int8_t town_cargo_factor; ///< old power-of-two multiplier for town (passenger, mail) generation. May be negative. + int16_t town_cargo_scale_factor; ///< scaled power-of-two multiplier for town (passenger, mail) generation. May be negative. + int16_t industry_cargo_scale_factor; ///< scaled power-of-two multiplier for primary industry generation. May be negative. +}; + struct LinkGraphSettings { uint16_t recalc_time; ///< time (in days) for recalculating each link graph component. uint16_t recalc_interval; ///< time (in days) between subsequent checks for link graphs to be calculated. @@ -878,6 +883,8 @@ struct GameSettings { LocaleSettings locale; ///< settings related to used currency/unit system in the current game DebugSettings debug; ///< debug settings TimeSettings game_time; ///< time display settings. + + OldEconomySettings old_economy; }; /** All settings that are only important for the local client. */ diff --git a/src/sl/extended_ver_sl.cpp b/src/sl/extended_ver_sl.cpp index 04d01a1f8b..4c832992d1 100644 --- a/src/sl/extended_ver_sl.cpp +++ b/src/sl/extended_ver_sl.cpp @@ -94,7 +94,7 @@ const SlxiSubChunkInfo _sl_xv_sub_chunk_infos[] = { { XSLFI_SAFER_CROSSINGS, XSCF_NULL, 1, 1, "safer_crossings", nullptr, nullptr, nullptr }, { XSLFI_DEPARTURE_BOARDS, XSCF_IGNORABLE_UNKNOWN, 1, 1, "departure_boards", nullptr, nullptr, nullptr }, { XSLFI_TIMETABLES_START_TICKS, XSCF_NULL, 3, 3, "timetable_start_ticks", nullptr, nullptr, nullptr }, - { XSLFI_TOWN_CARGO_ADJ, XSCF_IGNORABLE_UNKNOWN, 2, 2, "town_cargo_adj", nullptr, nullptr, nullptr }, + { XSLFI_TOWN_CARGO_ADJ, XSCF_IGNORABLE_UNKNOWN, 3, 3, "town_cargo_adj", nullptr, nullptr, nullptr }, { XSLFI_SIG_TUNNEL_BRIDGE, XSCF_NULL, 10, 10, "signal_tunnel_bridge", nullptr, nullptr, "XBSS" }, { XSLFI_IMPROVED_BREAKDOWNS, XSCF_NULL, 8, 8, "improved_breakdowns", nullptr, nullptr, nullptr }, { XSLFI_CONSIST_BREAKDOWN_FLAG, XSCF_NULL, 1, 1, "consist_breakdown_flag", nullptr, nullptr, nullptr }, @@ -156,7 +156,7 @@ const SlxiSubChunkInfo _sl_xv_sub_chunk_infos[] = { { XSLFI_VENC_CHUNK, XSCF_IGNORABLE_ALL, 0, 1, "venc_chunk", nullptr, nullptr, "VENC" }, { XSLFI_ANIMATED_TILE_EXTRA, XSCF_NULL, 1, 1, "animated_tile_extra", nullptr, nullptr, nullptr }, { XSLFI_NEWGRF_INFO_EXTRA, XSCF_NULL, 1, 1, "newgrf_info_extra", nullptr, nullptr, nullptr }, - { XSLFI_INDUSTRY_CARGO_ADJ, XSCF_IGNORABLE_UNKNOWN, 1, 1, "industry_cargo_adj", nullptr, nullptr, nullptr }, + { XSLFI_INDUSTRY_CARGO_ADJ, XSCF_IGNORABLE_UNKNOWN, 2, 2, "industry_cargo_adj", nullptr, nullptr, nullptr }, { XSLFI_REALISTIC_TRAIN_BRAKING, XSCF_NULL, 11, 11, "realistic_train_braking", nullptr, nullptr, "VLKA" }, { XSLFI_INFLATION_FIXED_DATES, XSCF_IGNORABLE_ALL, 1, 1, "inflation_fixed_dates", nullptr, nullptr, nullptr }, { XSLFI_WATER_FLOODING, XSCF_NULL, 2, 2, "water_flooding", nullptr, nullptr, nullptr }, diff --git a/src/table/newgrf_debug_data.h b/src/table/newgrf_debug_data.h index 73cc657dc9..845ee0e811 100644 --- a/src/table/newgrf_debug_data.h +++ b/src/table/newgrf_debug_data.h @@ -1229,8 +1229,8 @@ class NIHIndustry : public NIHelper { output.print(buffer); seprintf(buffer, lastof(buffer), " CBM_IND_PRODUCTION_256_TICKS: %s", HasBit(indsp->callback_mask, CBM_IND_PRODUCTION_256_TICKS) ? "yes" : "no"); output.print(buffer); - if ((_settings_game.economy.industry_cargo_scale_factor != 0) && HasBit(indsp->callback_mask, CBM_IND_PRODUCTION_256_TICKS)) { - seprintf(buffer, lastof(buffer), " Counter production interval: %u", ScaleQuantity(INDUSTRY_PRODUCE_TICKS, -_settings_game.economy.industry_cargo_scale_factor)); + if (_industry_cargo_scaler.HasScaling() && HasBit(indsp->callback_mask, CBM_IND_PRODUCTION_256_TICKS)) { + seprintf(buffer, lastof(buffer), " Counter production interval: %u", _industry_inverse_cargo_scaler.Scale(INDUSTRY_PRODUCE_TICKS)); output.print(buffer); } seprintf(buffer, lastof(buffer), " Number of layouts: %u", (uint)indsp->layouts.size()); diff --git a/src/table/settings.h.preamble b/src/table/settings.h.preamble index 573c041cbd..95a69df057 100644 --- a/src/table/settings.h.preamble +++ b/src/table/settings.h.preamble @@ -93,6 +93,9 @@ static bool CheckTTDPatchSettingFlag(uint flag); #define SDT_VAR(base, var, type, flags, def, min, max, interval, str, strhelp, strval, pre_check, post_callback, from, to, extver, cat, guiproc, startup, patxname)\ NSD(Int, SLE_GENERAL_X(SL_VAR, base, var, type, 1, from, to, extver), #var, flags, guiproc, startup, patxname, def, min, max, interval, str, strhelp, strval, cat, pre_check, post_callback, nullptr) +#define SDT_VAR2(base, name, var, type, flags, def, min, max, interval, str, strhelp, strval, pre_check, post_callback, from, to, extver, cat, guiproc, startup, patxname)\ + NSD(Int, SLE_GENERAL_X(SL_VAR, base, var, type, 1, from, to, extver), name, flags, guiproc, startup, patxname, def, min, max, interval, str, strhelp, strval, cat, pre_check, post_callback, nullptr) + #define SDT_ENUM(base, var, type, flags, def, str, strhelp, pre_check, post_callback, from, to, extver, cat, guiproc, startup, patxname, enumlist)\ NSD(Int, SLE_GENERAL_X(SL_VAR, base, var, type, 1, from, to, extver), #var, flags | SF_ENUM, guiproc, startup, patxname, def, 0, 0, 0, str, strhelp, STR_NULL, cat, pre_check, post_callback, enumlist) diff --git a/src/table/settings/economy_settings.ini b/src/table/settings/economy_settings.ini index bfe1d0efe1..4d2fa29162 100644 --- a/src/table/settings/economy_settings.ini +++ b/src/table/settings/economy_settings.ini @@ -21,6 +21,7 @@ static void TownZoneModeChanged(int32_t new_value); static void TownZoneCustomValueChanged(int32_t new_value); static bool OrderTownGrowthRate(SettingOnGuiCtrlData &data); +static bool IndustryCargoScaleGUI(SettingOnGuiCtrlData &data); static const SettingTable _economy_settings{ [post-amble] @@ -28,6 +29,7 @@ static const SettingTable _economy_settings{ [templates] SDT_BOOL = SDT_BOOL(GameSettings, $var, $flags, $def, $str, $strhelp, $strval, $pre_cb, $post_cb, $from, $to, $extver, $cat, $guiproc, $startup, $patxname), SDT_VAR = SDT_VAR(GameSettings, $var, $type, $flags, $def, $min, $max, $interval, $str, $strhelp, $strval, $pre_cb, $post_cb, $from, $to, $extver, $cat, $guiproc, $startup, $patxname), +SDT_VAR2 = SDT_VAR2(GameSettings, $name, $var, $type, $flags, $def, $min, $max, $interval, $str, $strhelp, $strval, $pre_cb, $post_cb, $from, $to, $extver, $cat, $guiproc, $startup, $patxname), [validation] SDT_VAR = static_assert($max <= MAX_$type, "Maximum value for GameSettings.$var exceeds storage size"); @@ -146,45 +148,6 @@ strhelp = STR_CONFIG_SETTING_TOWN_CARGOGENMODE_HELPTEXT strval = STR_CONFIG_SETTING_TOWN_CARGOGENMODE_ORIGINAL cat = SC_ADVANCED -[SDT_VAR] -var = economy.old_town_cargo_factor -type = SLE_INT8 -flags = SF_PATCH -def = 0 -min = -16 -max = +8 -interval = 1 -str = STR_CONFIG_SETTING_TOWN_CARGO_FACTOR -strval = STR_JUST_INT -extver = SlXvFeatureTest(XSLFTO_AND, XSLFI_TOWN_CARGO_ADJ, 1, 1) -patxname = ""town_cargo_adj.economy.town_cargo_factor"" - -[SDT_VAR] -var = economy.town_cargo_scale_factor -type = SLE_INT16 -flags = SF_DECIMAL1 | SF_DEC1SCALE | SF_PATCH -def = 0 -min = -160 -max = +80 -interval = 1 -str = STR_CONFIG_SETTING_TOWN_CARGO_FACTOR -strval = STR_DECIMAL1_WITH_SCALE -strhelp = STR_CONFIG_SETTING_TOWN_CARGO_FACTOR_HELPTEXT -patxname = ""town_cargo_adj.economy.town_cargo_scale_factor"" - -[SDT_VAR] -var = economy.industry_cargo_scale_factor -type = SLE_INT16 -flags = SF_DECIMAL1 | SF_DEC1SCALE | SF_PATCH -def = 0 -min = -50 -max = +50 -interval = 1 -str = STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR -strval = STR_DECIMAL1_WITH_SCALE -strhelp = STR_CONFIG_SETTING_INDUSTRY_CARGO_FACTOR_HELPTEXT -patxname = ""industry_cargo_adj.economy.industry_cargo_scale_factor"" - [SDT_VAR] var = economy.max_town_heightlevel type = SLE_UINT8 @@ -739,6 +702,35 @@ strhelp = STR_CONFIG_SETTING_INFRASTRUCTURE_MAINTENANCE_HELPTEXT post_cb = [](auto) { InvalidateWindowClassesData(WC_COMPANY_INFRASTRUCTURE); } cat = SC_BASIC +[SDT_VAR] +var = economy.town_cargo_scale +type = SLE_UINT16 +flags = SF_PATCH +def = 100 +min = 1 +max = 5000 +interval = 10 +str = STR_CONFIG_SETTING_TOWN_CARGO_SCALE +strhelp = STR_CONFIG_SETTING_TOWN_CARGO_SCALE_HELPTEXT +strval = STR_CONFIG_SETTING_CARGO_SCALE_VALUE +cat = SC_BASIC +post_cb = [](auto) { UpdateCargoScalers(); } + +[SDT_VAR] +var = economy.industry_cargo_scale +type = SLE_UINT16 +flags = SF_PATCH +def = 100 +min = 5 +max = 3000 +interval = 10 +str = STR_CONFIG_SETTING_INDUSTRY_CARGO_SCALE +strhelp = STR_CONFIG_SETTING_INDUSTRY_CARGO_SCALE_HELPTEXT +strval = STR_CONFIG_SETTING_CARGO_SCALE_VALUE +cat = SC_BASIC +post_cb = [](auto) { UpdateCargoScalers(); } +guiproc = IndustryCargoScaleGUI + [SDT_VAR] var = economy.random_road_reconstruction type = SLE_UINT16 @@ -787,3 +779,44 @@ strval = STR_CONFIG_SETTING_TICK_RATE_TRADITIONAL cat = SC_EXPERT post_cb = [](auto) { SetupTickRate(); } patxname = ""economy.tick_rate"" + +## Old settings + +[SDT_VAR2] +name = ""economy.old_town_cargo_factor"" +var = old_economy.town_cargo_factor +type = SLE_INT8 +flags = SF_PATCH +def = 0 +min = -16 +max = +8 +interval = 1 +strval = STR_JUST_INT +extver = SlXvFeatureTest(XSLFTO_AND, XSLFI_TOWN_CARGO_ADJ, 1, 1) +patxname = ""town_cargo_adj.economy.town_cargo_factor"" + +[SDT_VAR2] +name = ""economy.town_cargo_scale_factor"" +var = old_economy.town_cargo_scale_factor +type = SLE_INT16 +flags = SF_DECIMAL1 | SF_DEC1SCALE | SF_PATCH +def = 0 +min = -160 +max = +80 +interval = 1 +strval = STR_DECIMAL1_WITH_SCALE +extver = SlXvFeatureTest(XSLFTO_AND, XSLFI_TOWN_CARGO_ADJ, 2, 2) +patxname = ""town_cargo_adj.economy.town_cargo_scale_factor"" + +[SDT_VAR2] +name = ""economy.industry_cargo_scale_factor"" +var = old_economy.industry_cargo_scale_factor +type = SLE_INT16 +flags = SF_DECIMAL1 | SF_DEC1SCALE | SF_PATCH +def = 0 +min = -50 +max = +50 +interval = 1 +strval = STR_DECIMAL1_WITH_SCALE +extver = SlXvFeatureTest(XSLFTO_AND, XSLFI_INDUSTRY_CARGO_ADJ, 1, 1) +patxname = ""industry_cargo_adj.economy.industry_cargo_scale_factor"" diff --git a/src/town_cmd.cpp b/src/town_cmd.cpp index 86b4882c59..e70691028d 100644 --- a/src/town_cmd.cpp +++ b/src/town_cmd.cpp @@ -668,7 +668,7 @@ static void TownGenerateCargo(Town *t, CargoID ct, uint amount, StationFinder &s amount = (amount + 1) >> 1; } - amount = ScaleQuantity(amount, _settings_game.economy.town_cargo_scale_factor, true); + amount = _town_cargo_scaler.ScaleAllowTrunc(amount); if (amount == 0) return;