diff --git a/src/openrct2-ui/interface/Graph.cpp b/src/openrct2-ui/interface/Graph.cpp index 85b3272264..48e5dc233b 100644 --- a/src/openrct2-ui/interface/Graph.cpp +++ b/src/openrct2-ui/interface/Graph.cpp @@ -104,7 +104,7 @@ namespace Graph struct FinancialTooltipInfo { const ScreenCoordsXY coords; - const money32 money{}; + const money64 money{}; }; static constexpr auto ChartMaxDataCount = 64; @@ -122,21 +122,22 @@ static int32_t IndexForCursorAndHistory(const int32_t historyCount, const int32_ } static const ScreenCoordsXY ScreenCoordsForHistoryIndex( - const int32_t index, const money32* history, const int32_t chartX, const int32_t chartY, const int32_t modifier, + const int32_t index, const money64* history, const int32_t chartX, const int32_t chartY, const int32_t modifier, const int32_t offset) { auto coords = ScreenCoordsXY{ chartX + ChartDataWidth * (ChartMaxIndex - index), - chartY + ChartMaxHeight - ((((history[index] >> modifier) + offset) * 170) / 256) }; + chartY + ChartMaxHeight + - (((static_cast(history[index] >> modifier) + offset) * 170) / 256) }; return coords; } static const FinancialTooltipInfo finance_tooltip_info_from_money( - const money32* history, const int32_t historyCount, const int32_t modifier, const int32_t offset, + const money64* history, const int32_t historyCount, const int32_t modifier, const int32_t offset, const ScreenRect& chartFrame, const ScreenCoordsXY& cursorPosition) { if (!chartFrame.Contains(cursorPosition)) { - return { {}, MONEY32_UNDEFINED }; + return { {}, MONEY64_UNDEFINED }; } const auto historyIndex = IndexForCursorAndHistory(historyCount, cursorPosition.x, chartFrame.GetLeft()); @@ -148,7 +149,7 @@ static const FinancialTooltipInfo finance_tooltip_info_from_money( namespace Graph { - static void DrawMonths(rct_drawpixelinfo* dpi, const money32* history, int32_t count, const ScreenCoordsXY& origCoords) + static void DrawMonths(rct_drawpixelinfo* dpi, const money64* history, int32_t count, const ScreenCoordsXY& origCoords) { int32_t i, yearOver32, currentMonth, currentDay; @@ -158,7 +159,7 @@ namespace Graph auto screenCoords = origCoords; for (i = count - 1; i >= 0; i--) { - if (history[i] != MONEY32_UNDEFINED && yearOver32 % 4 == 0) + if (history[i] != MONEY64_UNDEFINED && yearOver32 % 4 == 0) { // Draw month text int32_t monthFormat = DateGameShortMonthNames[date_get_month((yearOver32 / 4) + MONTH_COUNT)]; @@ -176,14 +177,14 @@ namespace Graph } static void DrawLineA( - rct_drawpixelinfo* dpi, const money32* history, int32_t count, const ScreenCoordsXY& origCoords, int32_t modifier, + rct_drawpixelinfo* dpi, const money64* history, int32_t count, const ScreenCoordsXY& origCoords, int32_t modifier, int32_t offset) { auto lastCoords = ScreenCoordsXY{ -1, -1 }; auto coords = origCoords; for (int32_t i = count - 1; i >= 0; i--) { - if (history[i] != MONEY32_UNDEFINED) + if (history[i] != MONEY64_UNDEFINED) { coords.y = origCoords.y + 170 - 6 - ((((history[i] >> modifier) + offset) * 170) / 256); @@ -206,14 +207,14 @@ namespace Graph } static void DrawLineB( - rct_drawpixelinfo* dpi, const money32* history, int32_t count, const ScreenCoordsXY& origCoords, int32_t modifier, + rct_drawpixelinfo* dpi, const money64* history, int32_t count, const ScreenCoordsXY& origCoords, int32_t modifier, int32_t offset) { auto lastCoords = ScreenCoordsXY{ -1, -1 }; auto coords = origCoords; for (int32_t i = count - 1; i >= 0; i--) { - if (history[i] != MONEY32_UNDEFINED) + if (history[i] != MONEY64_UNDEFINED) { coords.y = origCoords.y + 170 - 6 - ((((history[i] >> modifier) + offset) * 170) / 256); @@ -233,7 +234,7 @@ namespace Graph } static void DrawHoveredValue( - rct_drawpixelinfo* dpi, const money32* history, const int32_t historyCount, const ScreenCoordsXY& screenCoords, + rct_drawpixelinfo* dpi, const money64* history, const int32_t historyCount, const ScreenCoordsXY& screenCoords, const int32_t modifier, const int32_t offset) { const auto cursorPosition = context_get_cursor_position_scaled(); @@ -247,7 +248,7 @@ namespace Graph const auto info = finance_tooltip_info_from_money( history, ChartMaxDataCount, modifier, offset, chartFrame, cursorPosition); - if (info.money == MONEY32_UNDEFINED) + if (info.money == MONEY64_UNDEFINED) { return; } @@ -270,7 +271,7 @@ namespace Graph } void Draw( - rct_drawpixelinfo* dpi, const money32* history, const int32_t count, const ScreenCoordsXY& screenCoords, + rct_drawpixelinfo* dpi, const money64* history, const int32_t count, const ScreenCoordsXY& screenCoords, const int32_t modifier, const int32_t offset) { DrawMonths(dpi, history, count, screenCoords); diff --git a/src/openrct2-ui/interface/Graph.h b/src/openrct2-ui/interface/Graph.h index 296c41ba88..509f19a5fd 100644 --- a/src/openrct2-ui/interface/Graph.h +++ b/src/openrct2-ui/interface/Graph.h @@ -18,7 +18,7 @@ namespace Graph { void Draw(rct_drawpixelinfo* dpi, uint8_t* history, int32_t count, const ScreenCoordsXY& screenPos); void Draw( - rct_drawpixelinfo* dpi, const money32* history, const int32_t count, const ScreenCoordsXY& coords, + rct_drawpixelinfo* dpi, const money64* history, const int32_t count, const ScreenCoordsXY& coords, const int32_t modifier, const int32_t offset); } // namespace Graph diff --git a/src/openrct2-ui/windows/Cheats.cpp b/src/openrct2-ui/windows/Cheats.cpp index 03ad9bb394..1cce45704d 100644 --- a/src/openrct2-ui/windows/Cheats.cpp +++ b/src/openrct2-ui/windows/Cheats.cpp @@ -616,7 +616,7 @@ public: { auto colour = colours[1]; auto ft = Formatter(); - ft.Add(_moneySpinnerValue); + ft.Add(_moneySpinnerValue); if (IsWidgetDisabled(WIDX_MONEY_SPINNER)) { colour |= COLOUR_FLAG_INSET; diff --git a/src/openrct2-ui/windows/DemolishRidePrompt.cpp b/src/openrct2-ui/windows/DemolishRidePrompt.cpp index e79477b548..395bd145cf 100644 --- a/src/openrct2-ui/windows/DemolishRidePrompt.cpp +++ b/src/openrct2-ui/windows/DemolishRidePrompt.cpp @@ -167,7 +167,7 @@ static void window_ride_demolish_paint(rct_window* w, rct_drawpixelinfo* dpi) auto stringId = (gParkFlags & PARK_FLAGS_NO_MONEY) ? STR_DEMOLISH_RIDE_ID : STR_DEMOLISH_RIDE_ID_MONEY; auto ft = Formatter(); ride->FormatNameTo(ft); - ft.Add(_demolishRideCost); + ft.Add(_demolishRideCost); ScreenCoordsXY stringCoords(w->windowPos.x + WW / 2, w->windowPos.y + (WH / 2) - 3); DrawTextWrapped(dpi, stringCoords, WW - 4, stringId, ft, { TextAlignment::CENTRE }); @@ -184,7 +184,7 @@ static void window_ride_refurbish_paint(rct_window* w, rct_drawpixelinfo* dpi) auto stringId = (gParkFlags & PARK_FLAGS_NO_MONEY) ? STR_REFURBISH_RIDE_ID_NO_MONEY : STR_REFURBISH_RIDE_ID_MONEY; auto ft = Formatter(); ride->FormatNameTo(ft); - ft.Add(_demolishRideCost / 2); + ft.Add(_demolishRideCost / 2); ScreenCoordsXY stringCoords(w->windowPos.x + WW / 2, w->windowPos.y + (WH / 2) - 3); DrawTextWrapped(dpi, stringCoords, WW - 4, stringId, ft, { TextAlignment::CENTRE }); diff --git a/src/openrct2-ui/windows/Finances.cpp b/src/openrct2-ui/windows/Finances.cpp index 16ee1e81b9..650dfb284b 100644 --- a/src/openrct2-ui/windows/Finances.cpp +++ b/src/openrct2-ui/windows/Finances.cpp @@ -515,7 +515,7 @@ static void window_finances_summary_invalidate(rct_window* w) window_finances_set_pressed_tab(w); auto ft = Formatter::Common(); ft.Increment(6); - ft.Add(gBankLoan); + ft.Add(gBankLoan); } /** @@ -566,9 +566,9 @@ static void window_finances_summary_paint(rct_window* w, rct_drawpixelinfo* dpi) // Objective related financial information if (gScenarioObjective.Type == OBJECTIVE_MONTHLY_FOOD_INCOME) { - money32 lastMonthProfit = finance_get_last_month_shop_profit(); + auto lastMonthProfit = finance_get_last_month_shop_profit(); ft = Formatter(); - ft.Add(lastMonthProfit); + ft.Add(lastMonthProfit); DrawTextBasic( dpi, w->windowPos + ScreenCoordsXY{ 280, 279 }, STR_LAST_MONTH_PROFIT_FROM_FOOD_DRINK_MERCHANDISE_SALES_LABEL, ft); } @@ -621,17 +621,17 @@ static void window_finances_summary_scrollpaint(rct_window* w, rct_drawpixelinfo screenCoords.y += 14; // Month expenditures - money32 profit = 0; + money64 profit = 0; for (int32_t j = 0; j < static_cast(ExpenditureType::Count); j++) { - money32 expenditure = gExpenditureTable[i][j]; + auto expenditure = gExpenditureTable[i][j]; if (expenditure != 0) { profit += expenditure; const rct_string_id format = expenditure >= 0 ? STR_FINANCES_SUMMARY_INCOME_VALUE : STR_FINANCES_SUMMARY_EXPENDITURE_VALUE; ft = Formatter(); - ft.Add(expenditure); + ft.Add(expenditure); DrawTextBasic( dpi, screenCoords + ScreenCoordsXY{ EXPENDITURE_COLUMN_WIDTH, 0 }, format, ft, { TextAlignment::RIGHT }); } @@ -642,7 +642,7 @@ static void window_finances_summary_scrollpaint(rct_window* w, rct_drawpixelinfo // Month profit const rct_string_id format = profit >= 0 ? STR_FINANCES_SUMMARY_INCOME_VALUE : STR_FINANCES_SUMMARY_LOSS_VALUE; ft = Formatter(); - ft.Add(profit); + ft.Add(profit); DrawTextBasic(dpi, screenCoords + ScreenCoordsXY{ EXPENDITURE_COLUMN_WIDTH, 0 }, format, ft, { TextAlignment::RIGHT }); gfx_fill_rect( @@ -713,7 +713,7 @@ static void window_finances_financial_graph_paint(rct_window* w, rct_drawpixelin auto graphBottomRight = w->windowPos + ScreenCoordsXY{ pageWidget->right - 4, pageWidget->bottom - 4 }; // Cash (less loan) - money32 cashLessLoan = gCash - gBankLoan; + auto cashLessLoan = gCash - gBankLoan; DrawTextBasic( dpi, graphTopLeft - ScreenCoordsXY{ 0, 11 }, @@ -728,8 +728,8 @@ static void window_finances_financial_graph_paint(rct_window* w, rct_drawpixelin int32_t yAxisScale = 0; for (int32_t i = 0; i < 64; i++) { - money32 balance = gCashHistory[i]; - if (balance == MONEY32_UNDEFINED) + auto balance = gCashHistory[i]; + if (balance == MONEY64_UNDEFINED) continue; // Modifier balance then keep halving until less than 127 pixels @@ -743,12 +743,12 @@ static void window_finances_financial_graph_paint(rct_window* w, rct_drawpixelin // Y axis labels auto coords = graphTopLeft + ScreenCoordsXY{ 18, 14 }; - money32 axisBase; + money64 axisBase; for (axisBase = MONEY(12, 00); axisBase >= MONEY(-12, 00); axisBase -= MONEY(6, 00)) { - money32 axisValue = axisBase << yAxisScale; + auto axisValue = axisBase << yAxisScale; auto ft = Formatter(); - ft.Add(axisValue); + ft.Add(axisValue); DrawTextBasic( dpi, coords + ScreenCoordsXY{ 70, 0 }, STR_FINANCES_FINANCIAL_GRAPH_CASH_VALUE, ft, { FontSpriteBase::SMALL, TextAlignment::RIGHT }); @@ -821,7 +821,7 @@ static void window_finances_park_value_graph_paint(rct_window* w, rct_drawpixeli auto graphBottomRight = w->windowPos + ScreenCoordsXY{ pageWidget->right - 4, pageWidget->bottom - 4 }; // Park value - money32 parkValue = gParkValue; + auto parkValue = gParkValue; DrawTextBasic(dpi, graphTopLeft - ScreenCoordsXY{ 0, 11 }, STR_FINANCES_PARK_VALUE, &parkValue); // Graph @@ -831,8 +831,8 @@ static void window_finances_park_value_graph_paint(rct_window* w, rct_drawpixeli int32_t yAxisScale = 0; for (int32_t i = 0; i < 64; i++) { - money32 balance = gParkValueHistory[i]; - if (balance == MONEY32_UNDEFINED) + auto balance = gParkValueHistory[i]; + if (balance == MONEY64_UNDEFINED) continue; // Modifier balance then keep halving until less than 255 pixels @@ -846,12 +846,12 @@ static void window_finances_park_value_graph_paint(rct_window* w, rct_drawpixeli // Y axis labels auto coords = graphTopLeft + ScreenCoordsXY{ 18, 14 }; - money32 axisBase; + money64 axisBase; for (axisBase = MONEY(24, 00); axisBase >= MONEY(0, 00); axisBase -= MONEY(6, 00)) { - money32 axisValue = axisBase << yAxisScale; + auto axisValue = axisBase << yAxisScale; auto ft = Formatter(); - ft.Add(axisValue); + ft.Add(axisValue); DrawTextBasic( dpi, coords + ScreenCoordsXY{ 70, 0 }, STR_FINANCES_FINANCIAL_GRAPH_CASH_VALUE, ft, { FontSpriteBase::SMALL, TextAlignment::RIGHT }); @@ -923,7 +923,7 @@ static void window_finances_profit_graph_paint(rct_window* w, rct_drawpixelinfo* auto graphBottomRight = w->windowPos + ScreenCoordsXY{ pageWidget->right - 4, pageWidget->bottom - 4 }; // Weekly profit - money32 weeklyPofit = gCurrentProfit; + auto weeklyPofit = gCurrentProfit; DrawTextBasic( dpi, graphTopLeft - ScreenCoordsXY{ 0, 11 }, weeklyPofit >= 0 ? STR_FINANCES_WEEKLY_PROFIT_POSITIVE : STR_FINANCES_WEEKLY_PROFIT_LOSS, &weeklyPofit); @@ -935,8 +935,8 @@ static void window_finances_profit_graph_paint(rct_window* w, rct_drawpixelinfo* int32_t yAxisScale = 0; for (int32_t i = 0; i < 64; i++) { - money32 balance = gWeeklyProfitHistory[i]; - if (balance == MONEY32_UNDEFINED) + auto balance = gWeeklyProfitHistory[i]; + if (balance == MONEY64_UNDEFINED) continue; // Modifier balance then keep halving until less than 127 pixels @@ -950,12 +950,12 @@ static void window_finances_profit_graph_paint(rct_window* w, rct_drawpixelinfo* // Y axis labels auto screenPos = graphTopLeft + ScreenCoordsXY{ 18, 14 }; - money32 axisBase; + money64 axisBase; for (axisBase = MONEY(12, 00); axisBase >= MONEY(-12, 00); axisBase -= MONEY(6, 00)) { - money32 axisValue = axisBase << yAxisScale; + money64 axisValue = axisBase << yAxisScale; auto ft = Formatter(); - ft.Add(axisValue); + ft.Add(axisValue); DrawTextBasic( dpi, screenPos + ScreenCoordsXY{ 70, 0 }, STR_FINANCES_FINANCIAL_GRAPH_CASH_VALUE, ft, { FontSpriteBase::SMALL, TextAlignment::RIGHT }); @@ -1117,7 +1117,7 @@ static void window_finances_marketing_paint(rct_window* w, rct_drawpixelinfo* dp if (campaignButton->type != WindowWidgetType::Empty) { // Draw button text - money32 pricePerWeek = AdvertisingCampaignPricePerWeek[i]; + money64 pricePerWeek = AdvertisingCampaignPricePerWeek[i]; DrawTextBasic(dpi, screenCoords + ScreenCoordsXY{ 4, 0 }, MarketingCampaignNames[i][0]); DrawTextBasic(dpi, screenCoords + ScreenCoordsXY{ WH_SUMMARY, 0 }, STR_MARKETING_PER_WEEK, &pricePerWeek); diff --git a/src/openrct2-ui/windows/Footpath.cpp b/src/openrct2-ui/windows/Footpath.cpp index bd14160bb9..910ddf5218 100644 --- a/src/openrct2-ui/windows/Footpath.cpp +++ b/src/openrct2-ui/windows/Footpath.cpp @@ -633,7 +633,8 @@ static void window_footpath_paint(rct_window* w, rct_drawpixelinfo* dpi) { if (!(gParkFlags & PARK_FLAGS_NO_MONEY)) { - DrawTextBasic(dpi, screenCoords, STR_COST_LABEL, &_window_footpath_cost, { TextAlignment::CENTRE }); + money64 cost = _window_footpath_cost; + DrawTextBasic(dpi, screenCoords, STR_COST_LABEL, &cost, { TextAlignment::CENTRE }); } } } diff --git a/src/openrct2-ui/windows/GameBottomToolbar.cpp b/src/openrct2-ui/windows/GameBottomToolbar.cpp index 4f65f9a81b..097d5bc3c5 100644 --- a/src/openrct2-ui/windows/GameBottomToolbar.cpp +++ b/src/openrct2-ui/windows/GameBottomToolbar.cpp @@ -414,7 +414,7 @@ static void window_game_bottom_toolbar_draw_left_panel(rct_drawpixelinfo* dpi, r : NOT_TRANSLUCENT(w->colours[0])); rct_string_id stringId = gCash < 0 ? STR_BOTTOM_TOOLBAR_CASH_NEGATIVE : STR_BOTTOM_TOOLBAR_CASH; auto ft = Formatter(); - ft.Add(gCash); + ft.Add(gCash); DrawTextBasic(dpi, screenCoords, stringId, ft, { colour, TextAlignment::CENTRE }); } diff --git a/src/openrct2-ui/windows/Guest.cpp b/src/openrct2-ui/windows/Guest.cpp index 8f379285be..b201bc6fb9 100644 --- a/src/openrct2-ui/windows/Guest.cpp +++ b/src/openrct2-ui/windows/Guest.cpp @@ -1657,7 +1657,7 @@ void window_guest_finance_paint(rct_window* w, rct_drawpixelinfo* dpi) // Cash in pocket { auto ft = Formatter(); - ft.Add(peep->CashInPocket); + ft.Add(peep->CashInPocket); DrawTextBasic(dpi, screenCoords, STR_GUEST_STAT_CASH_IN_POCKET, ft); screenCoords.y += LIST_ROW_HEIGHT; } @@ -1665,7 +1665,7 @@ void window_guest_finance_paint(rct_window* w, rct_drawpixelinfo* dpi) // Cash spent { auto ft = Formatter(); - ft.Add(peep->CashSpent); + ft.Add(peep->CashSpent); DrawTextBasic(dpi, screenCoords, STR_GUEST_STAT_CASH_SPENT, ft); screenCoords.y += LIST_ROW_HEIGHT * 2; } @@ -1677,14 +1677,14 @@ void window_guest_finance_paint(rct_window* w, rct_drawpixelinfo* dpi) // Paid to enter { auto ft = Formatter(); - ft.Add(peep->PaidToEnter); + ft.Add(peep->PaidToEnter); DrawTextBasic(dpi, screenCoords, STR_GUEST_EXPENSES_ENTRANCE_FEE, ft); screenCoords.y += LIST_ROW_HEIGHT; } // Paid on rides { auto ft = Formatter(); - ft.Add(peep->PaidOnRides); + ft.Add(peep->PaidOnRides); ft.Add(peep->GuestNumRides); if (peep->GuestNumRides != 1) { @@ -1699,7 +1699,7 @@ void window_guest_finance_paint(rct_window* w, rct_drawpixelinfo* dpi) // Paid on food { auto ft = Formatter(); - ft.Add(peep->PaidOnFood); + ft.Add(peep->PaidOnFood); ft.Add(peep->AmountOfFood); if (peep->AmountOfFood != 1) { @@ -1715,7 +1715,7 @@ void window_guest_finance_paint(rct_window* w, rct_drawpixelinfo* dpi) // Paid on drinks { auto ft = Formatter(); - ft.Add(peep->PaidOnDrink); + ft.Add(peep->PaidOnDrink); ft.Add(peep->AmountOfDrinks); if (peep->AmountOfDrinks != 1) { @@ -1730,7 +1730,7 @@ void window_guest_finance_paint(rct_window* w, rct_drawpixelinfo* dpi) // Paid on souvenirs { auto ft = Formatter(); - ft.Add(peep->PaidOnSouvenirs); + ft.Add(peep->PaidOnSouvenirs); ft.Add(peep->AmountOfSouvenirs); if (peep->AmountOfSouvenirs != 1) { diff --git a/src/openrct2-ui/windows/Land.cpp b/src/openrct2-ui/windows/Land.cpp index 609e3fdfb7..ffda0b7008 100644 --- a/src/openrct2-ui/windows/Land.cpp +++ b/src/openrct2-ui/windows/Land.cpp @@ -256,7 +256,7 @@ public: { ScreenCoordsXY screenCoords; int32_t numTiles; - money32 price; + money64 price; rct_widget* previewWidget = &widgets[WIDX_PREVIEW]; DrawWidgets(dpi); @@ -284,12 +284,18 @@ public: { // Draw raise cost amount if (gLandToolRaiseCost != MONEY32_UNDEFINED && gLandToolRaiseCost != 0) - DrawTextBasic(&dpi, screenCoords, STR_RAISE_COST_AMOUNT, &gLandToolRaiseCost, { TextAlignment::CENTRE }); + { + price = gLandToolRaiseCost; + DrawTextBasic(&dpi, screenCoords, STR_RAISE_COST_AMOUNT, &price, { TextAlignment::CENTRE }); + } screenCoords.y += 10; // Draw lower cost amount if (gLandToolLowerCost != MONEY32_UNDEFINED && gLandToolLowerCost != 0) - DrawTextBasic(&dpi, screenCoords, STR_LOWER_COST_AMOUNT, &gLandToolLowerCost, { TextAlignment::CENTRE }); + { + price = gLandToolLowerCost; + DrawTextBasic(&dpi, screenCoords, STR_LOWER_COST_AMOUNT, &price, { TextAlignment::CENTRE }); + } screenCoords.y += 50; // Draw paint price @@ -302,17 +308,17 @@ public: objManager.GetLoadedObject(ObjectType::TerrainSurface, gLandToolTerrainSurface)); if (surfaceObj != nullptr) { - price += numTiles * surfaceObj->Price; + price += numTiles * static_cast(surfaceObj->Price); } } if (gLandToolTerrainEdge != OBJECT_ENTRY_INDEX_NULL) - price += numTiles * 100; + price += numTiles * 100LL; if (price != 0) { auto ft = Formatter(); - ft.Add(price); + ft.Add(price); DrawTextBasic(&dpi, screenCoords, STR_COST_AMOUNT, ft.Data(), { TextAlignment::CENTRE }); } } diff --git a/src/openrct2-ui/windows/NewCampaign.cpp b/src/openrct2-ui/windows/NewCampaign.cpp index 00940518e9..3be0a7a6ed 100644 --- a/src/openrct2-ui/windows/NewCampaign.cpp +++ b/src/openrct2-ui/windows/NewCampaign.cpp @@ -353,12 +353,12 @@ public: screenCoords = windowPos + ScreenCoordsXY{ 14, 60 }; // Price per week - money32 pricePerWeek = AdvertisingCampaignPricePerWeek[campaign.campaign_type]; + money64 pricePerWeek = AdvertisingCampaignPricePerWeek[campaign.campaign_type]; DrawTextBasic(&dpi, screenCoords, STR_MARKETING_COST_PER_WEEK, &pricePerWeek); screenCoords.y += 13; // Total price - money32 totalPrice = AdvertisingCampaignPricePerWeek[campaign.campaign_type] * campaign.no_weeks; + money64 totalPrice = AdvertisingCampaignPricePerWeek[campaign.campaign_type] * campaign.no_weeks; DrawTextBasic(&dpi, screenCoords, STR_MARKETING_TOTAL_COST, &totalPrice); } }; diff --git a/src/openrct2-ui/windows/NewRide.cpp b/src/openrct2-ui/windows/NewRide.cpp index 3dbde5e4c3..6bdcc02b25 100644 --- a/src/openrct2-ui/windows/NewRide.cpp +++ b/src/openrct2-ui/windows/NewRide.cpp @@ -942,7 +942,7 @@ static void window_new_ride_paint_ride_information( { // Get price of ride int32_t unk2 = GetRideTypeDescriptor(item.Type).StartTrackPiece; - money32 price = GetRideTypeDescriptor(item.Type).BuildCosts.TrackPrice; + money64 price = GetRideTypeDescriptor(item.Type).BuildCosts.TrackPrice; price *= TrackPricing[unk2]; price = (price >> 17) * 10 * GetRideTypeDescriptor(item.Type).BuildCosts.PriceEstimateMultiplier; @@ -952,7 +952,7 @@ static void window_new_ride_paint_ride_information( stringId = STR_NEW_RIDE_COST_FROM; ft = Formatter(); - ft.Add(price); + ft.Add(price); DrawTextBasic(dpi, screenPos + ScreenCoordsXY{ width, 51 }, stringId, ft, { TextAlignment::RIGHT }); } } diff --git a/src/openrct2-ui/windows/Park.cpp b/src/openrct2-ui/windows/Park.cpp index d8af2509a8..49afa0557a 100644 --- a/src/openrct2-ui/windows/Park.cpp +++ b/src/openrct2-ui/windows/Park.cpp @@ -1183,7 +1183,7 @@ static void window_park_price_paint(rct_window* w, rct_drawpixelinfo* dpi) + ScreenCoordsXY{ w->widgets[WIDX_PAGE_BACKGROUND].left + 4, w->widgets[WIDX_PAGE_BACKGROUND].top + 30 }; DrawTextBasic(dpi, screenCoords, STR_INCOME_FROM_ADMISSIONS, &gTotalIncomeFromAdmissions); - money32 parkEntranceFee = park_get_entrance_fee(); + money64 parkEntranceFee = park_get_entrance_fee(); auto stringId = parkEntranceFee == 0 ? STR_FREE : STR_BOTTOM_TOOLBAR_CASH; screenCoords = w->windowPos + ScreenCoordsXY{ w->widgets[WIDX_PRICE].left + 1, w->widgets[WIDX_PRICE].top + 1 }; DrawTextBasic(dpi, screenCoords, stringId, &parkEntranceFee, { w->colours[1] }); @@ -1489,14 +1489,14 @@ static void window_park_objective_paint(rct_window* w, rct_drawpixelinfo* dpi) if (gScenarioObjective.Type == OBJECTIVE_FINISH_5_ROLLERCOASTERS) ft.Add(gScenarioObjective.MinimumExcitement); else - ft.Add(gScenarioObjective.Currency); + ft.Add(gScenarioObjective.Currency); } screenCoords.y += DrawTextWrapped(dpi, screenCoords, 221, ObjectiveNames[gScenarioObjective.Type], ft); screenCoords.y += 5; // Objective outcome - if (gScenarioCompletedCompanyValue != MONEY32_UNDEFINED) + if (gScenarioCompletedCompanyValue != MONEY64_UNDEFINED) { if (gScenarioCompletedCompanyValue == COMPANY_VALUE_ON_FAILED_OBJECTIVE) { @@ -1507,7 +1507,7 @@ static void window_park_objective_paint(rct_window* w, rct_drawpixelinfo* dpi) { // Objective completed ft = Formatter(); - ft.Add(gScenarioCompletedCompanyValue); + ft.Add(gScenarioCompletedCompanyValue); DrawTextWrapped(dpi, screenCoords, 222, STR_OBJECTIVE_ACHIEVED, ft); } } diff --git a/src/openrct2-ui/windows/Research.cpp b/src/openrct2-ui/windows/Research.cpp index b3fea5afaf..446b83c243 100644 --- a/src/openrct2-ui/windows/Research.cpp +++ b/src/openrct2-ui/windows/Research.cpp @@ -561,7 +561,7 @@ void window_research_funding_page_paint(rct_window* w, rct_drawpixelinfo* dpi, r return; int32_t currentResearchLevel = gResearchFundingLevel; - money32 currentResearchCostPerWeek = research_cost_table[currentResearchLevel]; + money64 currentResearchCostPerWeek = research_cost_table[currentResearchLevel]; DrawTextBasic(dpi, w->windowPos + ScreenCoordsXY{ 10, 77 }, STR_RESEARCH_COST_PER_MONTH, ¤tResearchCostPerWeek); } diff --git a/src/openrct2-ui/windows/Ride.cpp b/src/openrct2-ui/windows/Ride.cpp index 4d6934a255..cbaef78e8f 100644 --- a/src/openrct2-ui/windows/Ride.cpp +++ b/src/openrct2-ui/windows/Ride.cpp @@ -6507,10 +6507,10 @@ static void window_ride_income_invalidate(rct_window* w) if (ride == nullptr) return; - w->widgets[WIDX_TITLE].text = STR_ARG_14_STRINGID; + w->widgets[WIDX_TITLE].text = STR_ARG_18_STRINGID; auto ft = Formatter::Common(); - ft.Increment(14); + ft.Increment(18); ride->FormatNameTo(ft); auto rideEntry = ride->GetRideEntry(); @@ -6536,11 +6536,10 @@ static void window_ride_income_invalidate(rct_window* w) window_ride_income_widgets[WIDX_SECONDARY_PRICE_LABEL].text = STR_SHOP_ITEM_PRICE_LABEL_ON_RIDE_PHOTO; window_ride_income_widgets[WIDX_PRIMARY_PRICE_SAME_THROUGHOUT_PARK].type = WindowWidgetType::Empty; - window_ride_income_widgets[WIDX_PRIMARY_PRICE].text = STR_ARG_6_CURRENCY2DP; + window_ride_income_widgets[WIDX_PRIMARY_PRICE].text = STR_BOTTOM_TOOLBAR_CASH; money16 ridePrimaryPrice = ride_get_price(ride); ft.Rewind(); - ft.Increment(6); - ft.Add(ridePrimaryPrice); + ft.Add(ridePrimaryPrice); if (ridePrimaryPrice == 0) window_ride_income_widgets[WIDX_PRIMARY_PRICE].text = STR_FREE; @@ -6591,7 +6590,9 @@ static void window_ride_income_invalidate(rct_window* w) // Set secondary item price window_ride_income_widgets[WIDX_SECONDARY_PRICE].text = STR_RIDE_SECONDARY_PRICE_VALUE; - ft.Add(ride->price[1]); + ft.Rewind(); + ft.Increment(10); + ft.Add(ride->price[1]); if (ride->price[1] == 0) window_ride_income_widgets[WIDX_SECONDARY_PRICE].text = STR_FREE; } @@ -6607,7 +6608,7 @@ static void window_ride_income_invalidate(rct_window* w) static void window_ride_income_paint(rct_window* w, rct_drawpixelinfo* dpi) { rct_string_id stringId; - money32 profit, costPerHour; + money64 profit, costPerHour; ShopItem primaryItem, secondaryItem; WindowDrawWidgets(w, dpi); @@ -6665,7 +6666,7 @@ static void window_ride_income_paint(rct_window* w, rct_drawpixelinfo* dpi) screenCoords.y += 18; // Income per hour - if (ride->income_per_hour != MONEY32_UNDEFINED) + if (ride->income_per_hour != MONEY64_UNDEFINED) { DrawTextBasic(dpi, screenCoords, STR_INCOME_PER_HOUR, &ride->income_per_hour); screenCoords.y += LIST_ROW_HEIGHT; @@ -6678,7 +6679,7 @@ static void window_ride_income_paint(rct_window* w, rct_drawpixelinfo* dpi) screenCoords.y += LIST_ROW_HEIGHT; // Profit per hour - if (ride->profit != MONEY32_UNDEFINED) + if (ride->profit != MONEY64_UNDEFINED) { DrawTextBasic(dpi, screenCoords, STR_PROFIT_PER_HOUR, &ride->profit); screenCoords.y += LIST_ROW_HEIGHT; diff --git a/src/openrct2-ui/windows/RideList.cpp b/src/openrct2-ui/windows/RideList.cpp index e61ef1db77..ec9ff7d81a 100644 --- a/src/openrct2-ui/windows/RideList.cpp +++ b/src/openrct2-ui/windows/RideList.cpp @@ -632,7 +632,7 @@ static void window_ride_list_scrollpaint(rct_window* w, rct_drawpixelinfo* dpi, break; case INFORMATION_TYPE_PROFIT: formatSecondary = 0; - if (ride->profit != MONEY32_UNDEFINED) + if (ride->profit != MONEY64_UNDEFINED) { formatSecondary = STR_PROFIT_LABEL; ft.Add(ride->profit); @@ -644,7 +644,7 @@ static void window_ride_list_scrollpaint(rct_window* w, rct_drawpixelinfo* dpi, break; case INFORMATION_TYPE_TOTAL_PROFIT: formatSecondary = 0; - if (ride->total_profit != MONEY32_UNDEFINED) + if (ride->total_profit != MONEY64_UNDEFINED) { formatSecondary = STR_RIDE_LIST_TOTAL_PROFIT_LABEL; ft.Add(ride->total_profit); @@ -674,7 +674,7 @@ static void window_ride_list_scrollpaint(rct_window* w, rct_drawpixelinfo* dpi, } case INFORMATION_TYPE_INCOME: formatSecondary = 0; - if (ride->income_per_hour != MONEY32_UNDEFINED) + if (ride->income_per_hour != MONEY64_UNDEFINED) { formatSecondary = STR_RIDE_LIST_INCOME_LABEL; ft.Add(ride->income_per_hour); diff --git a/src/openrct2-ui/windows/ScenarioSelect.cpp b/src/openrct2-ui/windows/ScenarioSelect.cpp index c29d950b22..715fc3c707 100644 --- a/src/openrct2-ui/windows/ScenarioSelect.cpp +++ b/src/openrct2-ui/windows/ScenarioSelect.cpp @@ -535,7 +535,7 @@ static void window_scenarioselect_paint(rct_window* w, rct_drawpixelinfo* dpi) if (scenario->objective_type == OBJECTIVE_FINISH_5_ROLLERCOASTERS) ft.Add(scenario->objective_arg_2); else - ft.Add(scenario->objective_arg_2); + ft.Add(scenario->objective_arg_2); } screenPos.y += DrawTextWrapped(dpi, screenPos, 170, STR_OBJECTIVE, ft) + 5; @@ -551,7 +551,7 @@ static void window_scenarioselect_paint(rct_window* w, rct_drawpixelinfo* dpi) ft = Formatter(); ft.Add(STR_STRING); ft.Add(completedByName); - ft.Add(scenario->highscore->company_value); + ft.Add(scenario->highscore->company_value); screenPos.y += DrawTextWrapped(dpi, screenPos, 170, STR_COMPLETED_BY_WITH_COMPANY_VALUE, ft); } } diff --git a/src/openrct2-ui/windows/Staff.cpp b/src/openrct2-ui/windows/Staff.cpp index 4ffd184587..e52024d075 100644 --- a/src/openrct2-ui/windows/Staff.cpp +++ b/src/openrct2-ui/windows/Staff.cpp @@ -1071,7 +1071,7 @@ void window_staff_stats_paint(rct_window* w, rct_drawpixelinfo* dpi) if (!(gParkFlags & PARK_FLAGS_NO_MONEY)) { auto ft = Formatter(); - ft.Add(GetStaffWage(peep->AssignedStaffType)); + ft.Add(GetStaffWage(peep->AssignedStaffType)); DrawTextBasic(dpi, screenCoords, STR_STAFF_STAT_WAGES, ft); screenCoords.y += LIST_ROW_HEIGHT; } diff --git a/src/openrct2-ui/windows/StaffList.cpp b/src/openrct2-ui/windows/StaffList.cpp index 52053bf080..e3458544f1 100644 --- a/src/openrct2-ui/windows/StaffList.cpp +++ b/src/openrct2-ui/windows/StaffList.cpp @@ -286,7 +286,7 @@ public: if (!(gParkFlags & PARK_FLAGS_NO_MONEY)) { auto ft = Formatter(); - ft.Add(GetStaffWage(GetSelectedStaffType())); + ft.Add(GetStaffWage(GetSelectedStaffType())); DrawTextBasic(&dpi, windowPos + ScreenCoordsXY{ width - 155, 32 }, STR_COST_PER_MONTH, ft); } diff --git a/src/openrct2/Editor.cpp b/src/openrct2/Editor.cpp index 18e3262bbf..af4a1fbe30 100644 --- a/src/openrct2/Editor.cpp +++ b/src/openrct2/Editor.cpp @@ -345,12 +345,12 @@ namespace Editor gGuestInitialCash = std::clamp( gGuestInitialCash, static_cast(MONEY(10, 00)), static_cast(MAX_ENTRANCE_FEE)); - gInitialCash = std::min(gInitialCash, 100000); + gInitialCash = std::min(gInitialCash, 100000); finance_reset_cash_to_initial(); - gBankLoan = std::clamp(gBankLoan, MONEY(0, 00), MONEY(5000000, 00)); + gBankLoan = std::clamp(gBankLoan, MONEY(0, 00), MONEY(5000000, 00)); - gMaxBankLoan = std::clamp(gMaxBankLoan, MONEY(0, 00), MONEY(5000000, 00)); + gMaxBankLoan = std::clamp(gMaxBankLoan, MONEY(0, 00), MONEY(5000000, 00)); gBankLoanInterestRate = std::clamp(gBankLoanInterestRate, 5, 80); } diff --git a/src/openrct2/actions/RideCreateAction.cpp b/src/openrct2/actions/RideCreateAction.cpp index df9fa87135..3b57344c95 100644 --- a/src/openrct2/actions/RideCreateAction.cpp +++ b/src/openrct2/actions/RideCreateAction.cpp @@ -283,8 +283,8 @@ GameActions::Result::Ptr RideCreateAction::Execute() const ride->no_primary_items_sold = 0; ride->no_secondary_items_sold = 0; ride->last_crash_type = RIDE_CRASH_TYPE_NONE; - ride->income_per_hour = MONEY32_UNDEFINED; - ride->profit = MONEY32_UNDEFINED; + ride->income_per_hour = MONEY64_UNDEFINED; + ride->profit = MONEY64_UNDEFINED; ride->connected_message_throttle = 0; ride->entrance_style = 0; ride->num_block_brakes = 0; diff --git a/src/openrct2/actions/ScenarioSetSettingAction.cpp b/src/openrct2/actions/ScenarioSetSettingAction.cpp index 6bd4291e86..9f0b58b7ee 100644 --- a/src/openrct2/actions/ScenarioSetSettingAction.cpp +++ b/src/openrct2/actions/ScenarioSetSettingAction.cpp @@ -73,18 +73,18 @@ GameActions::Result::Ptr ScenarioSetSettingAction::Execute() const } break; case ScenarioSetSetting::InitialCash: - gInitialCash = std::clamp(_value, MONEY(0, 00), MONEY(1000000, 00)); + gInitialCash = std::clamp(_value, MONEY(0, 00), MONEY(1000000, 00)); gCash = gInitialCash; window_invalidate_by_class(WC_FINANCES); window_invalidate_by_class(WC_BOTTOM_TOOLBAR); break; case ScenarioSetSetting::InitialLoan: - gBankLoan = std::clamp(_value, MONEY(0, 00), MONEY(5000000, 00)); + gBankLoan = std::clamp(_value, MONEY(0, 00), MONEY(5000000, 00)); gMaxBankLoan = std::max(gBankLoan, gMaxBankLoan); window_invalidate_by_class(WC_FINANCES); break; case ScenarioSetSetting::MaximumLoanSize: - gMaxBankLoan = std::clamp(_value, MONEY(0, 00), MONEY(5000000, 00)); + gMaxBankLoan = std::clamp(_value, MONEY(0, 00), MONEY(5000000, 00)); gBankLoan = std::min(gBankLoan, gMaxBankLoan); window_invalidate_by_class(WC_FINANCES); break; @@ -103,7 +103,7 @@ GameActions::Result::Ptr ScenarioSetSettingAction::Execute() const } break; case ScenarioSetSetting::AverageCashPerGuest: - gGuestInitialCash = std::clamp(_value, MONEY(0, 00), MONEY(1000, 00)); + gGuestInitialCash = std::clamp(_value, MONEY(0, 00), MONEY(1000, 00)); break; case ScenarioSetSetting::GuestInitialHappiness: gGuestInitialHappiness = std::clamp(_value, 40, 250); diff --git a/src/openrct2/common.h b/src/openrct2/common.h index 7b81c78ae6..7592614748 100644 --- a/src/openrct2/common.h +++ b/src/openrct2/common.h @@ -141,6 +141,12 @@ using money64 = fixed64_1dp; #define MONEY_FREE MONEY(0, 00) #define MONEY16_UNDEFINED static_cast(static_cast(0xFFFF)) #define MONEY32_UNDEFINED (static_cast(0x80000000)) +#define MONEY64_UNDEFINED (static_cast(0x8000000000000000)) + +static constexpr money64 ToMoney64(money32 value) +{ + return value == MONEY32_UNDEFINED ? MONEY64_UNDEFINED : value; +} using EMPTY_ARGS_VOID_POINTER = void(); using rct_string_id = uint16_t; diff --git a/src/openrct2/interface/InteractiveConsole.cpp b/src/openrct2/interface/InteractiveConsole.cpp index 7545d42a93..59d7231374 100644 --- a/src/openrct2/interface/InteractiveConsole.cpp +++ b/src/openrct2/interface/InteractiveConsole.cpp @@ -774,7 +774,7 @@ static int32_t cc_set(InteractiveConsole& console, const arguments_t& argv) } else if (argv[0] == "current_loan" && invalidArguments(&invalidArgs, int_valid[0])) { - gBankLoan = std::clamp(MONEY(int_val[0] - (int_val[0] % 1000), 0), MONEY(0, 0), gMaxBankLoan); + gBankLoan = std::clamp(MONEY(int_val[0] - (int_val[0] % 1000), 0), MONEY(0, 0), gMaxBankLoan); console.Execute("get current_loan"); } else if (argv[0] == "max_loan" && invalidArguments(&invalidArgs, int_valid[0])) diff --git a/src/openrct2/localisation/Formatter.h b/src/openrct2/localisation/Formatter.h index 49d03febb6..39a968603f 100644 --- a/src/openrct2/localisation/Formatter.h +++ b/src/openrct2/localisation/Formatter.h @@ -82,6 +82,7 @@ public: std::is_same_v::type, int16_t> || std::is_same_v::type, int32_t> || std::is_same_v::type, money32> || + std::is_same_v::type, money64> || std::is_same_v::type, rct_string_id> || std::is_same_v::type, uint16_t> || std::is_same_v::type, uint32_t> || diff --git a/src/openrct2/localisation/Formatting.cpp b/src/openrct2/localisation/Formatting.cpp index 6c64e6e9f6..3cb8188cf7 100644 --- a/src/openrct2/localisation/Formatting.cpp +++ b/src/openrct2/localisation/Formatting.cpp @@ -657,6 +657,10 @@ namespace OpenRCT2 { FormatArgument(ss, token, std::get(value)); } + else if (std::holds_alternative(value)) + { + FormatArgument(ss, token, std::get(value)); + } else if (std::holds_alternative(value)) { FormatArgument(ss, token, std::get(value)); @@ -755,11 +759,13 @@ namespace OpenRCT2 case FormatToken::Comma32: case FormatToken::Int32: case FormatToken::Comma2dp32: - case FormatToken::Currency2dp: - case FormatToken::Currency: case FormatToken::Sprite: anyArgs.push_back(ReadFromArgs(args)); break; + case FormatToken::Currency2dp: + case FormatToken::Currency: + anyArgs.push_back(ReadFromArgs(args)); + break; case FormatToken::UInt16: case FormatToken::MonthYear: case FormatToken::Month: diff --git a/src/openrct2/localisation/Formatting.h b/src/openrct2/localisation/Formatting.h index cf056c8160..9726a89141 100644 --- a/src/openrct2/localisation/Formatting.h +++ b/src/openrct2/localisation/Formatting.h @@ -145,7 +145,7 @@ namespace OpenRCT2 using FormatBuffer = FormatBufferBase; - using FormatArg_t = std::variant; + using FormatArg_t = std::variant; class FmtString { diff --git a/src/openrct2/management/Finance.cpp b/src/openrct2/management/Finance.cpp index 12f7858baf..dc78081c5d 100644 --- a/src/openrct2/management/Finance.cpp +++ b/src/openrct2/management/Finance.cpp @@ -35,20 +35,20 @@ static constexpr const int32_t dword_988E60[static_cast(ExpenditureType 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 0, 0, }; -money32 gInitialCash; -money32 gCash; -money32 gBankLoan; +money64 gInitialCash; +money64 gCash; +money64 gBankLoan; uint8_t gBankLoanInterestRate; -money32 gMaxBankLoan; -money32 gCurrentExpenditure; -money32 gCurrentProfit; -money32 gHistoricalProfit; -money32 gWeeklyProfitAverageDividend; +money64 gMaxBankLoan; +money64 gCurrentExpenditure; +money64 gCurrentProfit; +money64 gHistoricalProfit; +money64 gWeeklyProfitAverageDividend; uint16_t gWeeklyProfitAverageDivisor; -money32 gCashHistory[FINANCE_GRAPH_SIZE]; -money32 gWeeklyProfitHistory[FINANCE_GRAPH_SIZE]; -money32 gParkValueHistory[FINANCE_GRAPH_SIZE]; -money32 gExpenditureTable[EXPENDITURE_TABLE_MONTH_COUNT][static_cast(ExpenditureType::Count)]; +money64 gCashHistory[FINANCE_GRAPH_SIZE]; +money64 gWeeklyProfitHistory[FINANCE_GRAPH_SIZE]; +money64 gParkValueHistory[FINANCE_GRAPH_SIZE]; +money64 gExpenditureTable[EXPENDITURE_TABLE_MONTH_COUNT][static_cast(ExpenditureType::Count)]; /** * Checks the condition if the game is required to use money. @@ -186,9 +186,9 @@ void finance_reset_history() { for (int32_t i = 0; i < FINANCE_GRAPH_SIZE; i++) { - gCashHistory[i] = MONEY32_UNDEFINED; - gWeeklyProfitHistory[i] = MONEY32_UNDEFINED; - gParkValueHistory[i] = MONEY32_UNDEFINED; + gCashHistory[i] = MONEY64_UNDEFINED; + gWeeklyProfitHistory[i] = MONEY64_UNDEFINED; + gParkValueHistory[i] = MONEY64_UNDEFINED; } } @@ -221,7 +221,7 @@ void finance_init() gBankLoanInterestRate = 10; gParkValue = 0; gCompanyValue = 0; - gScenarioCompletedCompanyValue = MONEY32_UNDEFINED; + gScenarioCompletedCompanyValue = MONEY64_UNDEFINED; gTotalAdmissions = 0; gTotalIncomeFromAdmissions = 0; gScenarioCompletedBy = "?"; @@ -276,22 +276,22 @@ void finance_update_daily_profit() window_invalidate_by_class(WC_FINANCES); } -money32 finance_get_initial_cash() +money64 finance_get_initial_cash() { return gInitialCash; } -money32 finance_get_current_loan() +money64 finance_get_current_loan() { return gBankLoan; } -money32 finance_get_maximum_loan() +money64 finance_get_maximum_loan() { return gMaxBankLoan; } -money32 finance_get_current_cash() +money64 finance_get_current_cash() { return gCash; } @@ -306,7 +306,7 @@ void finance_shift_expenditure_table() // If EXPENDITURE_TABLE_MONTH_COUNT months have passed then is full, sum the oldest month if (gDateMonthsElapsed >= EXPENDITURE_TABLE_MONTH_COUNT) { - money32 sum = 0; + money64 sum = 0; for (uint32_t i = 0; i < static_cast(ExpenditureType::Count); i++) { sum += gExpenditureTable[EXPENDITURE_TABLE_MONTH_COUNT - 1][i]; @@ -344,12 +344,12 @@ void finance_reset_cash_to_initial() /** * Gets the last month's profit from food, drink and merchandise. */ -money32 finance_get_last_month_shop_profit() +money64 finance_get_last_month_shop_profit() { - money32 profit = 0; + money64 profit = 0; if (gDateMonthsElapsed != 0) { - money32* lastMonthExpenditure = gExpenditureTable[1]; + const auto* lastMonthExpenditure = gExpenditureTable[1]; profit += lastMonthExpenditure[static_cast(ExpenditureType::ShopSales)]; profit += lastMonthExpenditure[static_cast(ExpenditureType::ShopStock)]; diff --git a/src/openrct2/management/Finance.h b/src/openrct2/management/Finance.h index eea938e838..99a0a5f7b0 100644 --- a/src/openrct2/management/Finance.h +++ b/src/openrct2/management/Finance.h @@ -36,26 +36,26 @@ enum class ExpenditureType : int32_t extern const money32 research_cost_table[RESEARCH_FUNDING_COUNT]; -extern money32 gInitialCash; -extern money32 gCash; -extern money32 gBankLoan; +extern money64 gInitialCash; +extern money64 gCash; +extern money64 gBankLoan; extern uint8_t gBankLoanInterestRate; -extern money32 gMaxBankLoan; -extern money32 gCurrentExpenditure; -extern money32 gCurrentProfit; +extern money64 gMaxBankLoan; +extern money64 gCurrentExpenditure; +extern money64 gCurrentProfit; /** * The total profit for the entire scenario that precedes * the current financial table. */ -extern money32 gHistoricalProfit; +extern money64 gHistoricalProfit; -extern money32 gWeeklyProfitAverageDividend; +extern money64 gWeeklyProfitAverageDividend; extern uint16_t gWeeklyProfitAverageDivisor; -extern money32 gCashHistory[FINANCE_GRAPH_SIZE]; -extern money32 gWeeklyProfitHistory[FINANCE_GRAPH_SIZE]; -extern money32 gParkValueHistory[FINANCE_GRAPH_SIZE]; -extern money32 gExpenditureTable[EXPENDITURE_TABLE_MONTH_COUNT][static_cast(ExpenditureType::Count)]; +extern money64 gCashHistory[FINANCE_GRAPH_SIZE]; +extern money64 gWeeklyProfitHistory[FINANCE_GRAPH_SIZE]; +extern money64 gParkValueHistory[FINANCE_GRAPH_SIZE]; +extern money64 gExpenditureTable[EXPENDITURE_TABLE_MONTH_COUNT][static_cast(ExpenditureType::Count)]; bool finance_check_money_required(uint32_t flags); bool finance_check_affordability(money32 cost, uint32_t flags); @@ -70,9 +70,9 @@ void finance_update_daily_profit(); void finance_shift_expenditure_table(); void finance_reset_cash_to_initial(); -money32 finance_get_initial_cash(); -money32 finance_get_current_loan(); -money32 finance_get_maximum_loan(); -money32 finance_get_current_cash(); +money64 finance_get_initial_cash(); +money64 finance_get_current_loan(); +money64 finance_get_maximum_loan(); +money64 finance_get_current_cash(); -money32 finance_get_last_month_shop_profit(); +money64 finance_get_last_month_shop_profit(); diff --git a/src/openrct2/paint/Paint.cpp b/src/openrct2/paint/Paint.cpp index dcec3ea8b0..d39013413c 100644 --- a/src/openrct2/paint/Paint.cpp +++ b/src/openrct2/paint/Paint.cpp @@ -920,7 +920,7 @@ bool PaintAttachToPreviousPS(paint_session* session, uint32_t image_id, int16_t * @param rotation (ebp) */ void PaintFloatingMoneyEffect( - paint_session* session, money32 amount, rct_string_id string_id, int16_t y, int16_t z, int8_t y_offsets[], int16_t offset_x, + paint_session* session, money64 amount, rct_string_id string_id, int16_t y, int16_t z, int8_t y_offsets[], int16_t offset_x, uint32_t rotation) { auto* ps = session->AllocateStringPaintEntry(); @@ -938,8 +938,7 @@ void PaintFloatingMoneyEffect( ps->string_id = string_id; ps->next = nullptr; - ps->args[0] = amount; - ps->args[1] = y; + std::memcpy(ps->args, &amount, sizeof(amount)); ps->args[2] = 0; ps->args[3] = 0; ps->y_offsets = reinterpret_cast(y_offsets); diff --git a/src/openrct2/paint/Paint.h b/src/openrct2/paint/Paint.h index 6b5ff077a2..756567c0e3 100644 --- a/src/openrct2/paint/Paint.h +++ b/src/openrct2/paint/Paint.h @@ -330,7 +330,7 @@ void paint_util_push_tunnel_rotated(paint_session* session, uint8_t direction, u bool PaintAttachToPreviousAttach(paint_session* session, uint32_t image_id, int16_t x, int16_t y); bool PaintAttachToPreviousPS(paint_session* session, uint32_t image_id, int16_t x, int16_t y); void PaintFloatingMoneyEffect( - paint_session* session, money32 amount, rct_string_id string_id, int16_t y, int16_t z, int8_t y_offsets[], int16_t offset_x, + paint_session* session, money64 amount, rct_string_id string_id, int16_t y, int16_t z, int8_t y_offsets[], int16_t offset_x, uint32_t rotation); paint_session* PaintSessionAlloc(rct_drawpixelinfo* dpi, uint32_t viewFlags); diff --git a/src/openrct2/rct1/S4Importer.cpp b/src/openrct2/rct1/S4Importer.cpp index 6522fea81d..546368d65c 100644 --- a/src/openrct2/rct1/S4Importer.cpp +++ b/src/openrct2/rct1/S4Importer.cpp @@ -280,7 +280,7 @@ public: return true; } - int32_t CorrectRCT1ParkValue(money32 oldParkValue) + money32 CorrectRCT1ParkValue(money32 oldParkValue) { if (oldParkValue == MONEY32_UNDEFINED) { @@ -1327,13 +1327,13 @@ private: gInitialCash = _s4.cash; gCompanyValue = _s4.company_value; - gParkValue = CorrectRCT1ParkValue(_s4.park_value); + gParkValue = ToMoney64(CorrectRCT1ParkValue(_s4.park_value)); gCurrentProfit = _s4.profit; for (size_t i = 0; i < RCT12_FINANCE_GRAPH_SIZE; i++) { gCashHistory[i] = _s4.cash_history[i]; - gParkValueHistory[i] = CorrectRCT1ParkValue(_s4.park_value_history[i]); + gParkValueHistory[i] = ToMoney64(CorrectRCT1ParkValue(_s4.park_value_history[i])); gWeeklyProfitHistory[i] = _s4.weekly_profit_history[i]; } @@ -2300,7 +2300,7 @@ private: // This is corrected here, but since scenario_objective_currency doubles as minimum excitement rating, // we need to check the goal to avoid affecting scenarios like Volcania. if (_s4.scenario_objective_type == OBJECTIVE_PARK_VALUE_BY) - gScenarioObjective.Currency = CorrectRCT1ParkValue(_s4.scenario_objective_currency); + gScenarioObjective.Currency = ToMoney64(CorrectRCT1ParkValue(_s4.scenario_objective_currency)); else gScenarioObjective.Currency = _s4.scenario_objective_currency; diff --git a/src/openrct2/rct2/S6Importer.cpp b/src/openrct2/rct2/S6Importer.cpp index ee7525c4a5..979c0f1ec5 100644 --- a/src/openrct2/rct2/S6Importer.cpp +++ b/src/openrct2/rct2/S6Importer.cpp @@ -321,7 +321,7 @@ public: { gCashHistory[i] = _s6.balance_history[i]; gWeeklyProfitHistory[i] = _s6.weekly_profit_history[i]; - gParkValueHistory[i] = _s6.park_value_history[i]; + gParkValueHistory[i] = ToMoney64(_s6.park_value_history[i]); } gScenarioCompletedCompanyValue = _s6.completed_company_value; diff --git a/src/openrct2/ride/Ride.h b/src/openrct2/ride/Ride.h index 521192e014..fb4a202d00 100644 --- a/src/openrct2/ride/Ride.h +++ b/src/openrct2/ride/Ride.h @@ -309,7 +309,7 @@ public: // Various flags stating whether a window needs to be refreshed uint8_t window_invalidate_flags; uint32_t total_customers; - money32 total_profit; + money64 total_profit; uint8_t popularity; uint8_t popularity_time_out; // Updated every purchase and ?possibly by time? uint8_t popularity_next; // When timeout reached this will be the next popularity @@ -359,8 +359,8 @@ public: uint8_t not_fixed_timeout; uint8_t last_crash_type; uint8_t connected_message_throttle; - money32 income_per_hour; - money32 profit; + money64 income_per_hour; + money64 profit; TrackColour track_colour[NUM_COLOUR_SCHEMES]; uint8_t music; uint8_t entrance_style; diff --git a/src/openrct2/scenario/Scenario.cpp b/src/openrct2/scenario/Scenario.cpp index 657db21cdd..4f74f49195 100644 --- a/src/openrct2/scenario/Scenario.cpp +++ b/src/openrct2/scenario/Scenario.cpp @@ -75,8 +75,8 @@ Objective gScenarioObjective; bool gAllowEarlyCompletionInNetworkPlay; uint16_t gScenarioParkRatingWarningDays; -money32 gScenarioCompletedCompanyValue; -money32 gScenarioCompanyValueRecord; +money64 gScenarioCompletedCompanyValue; +money64 gScenarioCompanyValueRecord; char gScenarioFileName[MAX_PATH]; @@ -144,7 +144,7 @@ void scenario_begin() gCurrentProfit = 0; gWeeklyProfitAverageDividend = 0; gWeeklyProfitAverageDivisor = 0; - gScenarioCompletedCompanyValue = MONEY32_UNDEFINED; + gScenarioCompletedCompanyValue = MONEY64_UNDEFINED; gTotalAdmissions = 0; gTotalIncomeFromAdmissions = 0; gScenarioCompletedBy = "?"; @@ -197,7 +197,7 @@ void scenario_failure() */ void scenario_success() { - const money32 companyValue = gCompanyValue; + auto companyValue = gCompanyValue; gScenarioCompletedCompanyValue = companyValue; peep_applause(); @@ -928,8 +928,8 @@ ObjectiveStatus Objective::CheckRepayLoanAndParkValue() const ObjectiveStatus Objective::CheckMonthlyFoodIncome() const { - money32* lastMonthExpenditure = gExpenditureTable[1]; - int32_t lastMonthProfit = lastMonthExpenditure[static_cast(ExpenditureType::ShopSales)] + const auto* lastMonthExpenditure = gExpenditureTable[1]; + auto lastMonthProfit = lastMonthExpenditure[static_cast(ExpenditureType::ShopSales)] + lastMonthExpenditure[static_cast(ExpenditureType::ShopStock)] + lastMonthExpenditure[static_cast(ExpenditureType::FoodDrinkSales)] + lastMonthExpenditure[static_cast(ExpenditureType::FoodDrinkStock)]; @@ -978,7 +978,7 @@ static void scenario_objective_check() */ ObjectiveStatus Objective::Check() const { - if (gScenarioCompletedCompanyValue != MONEY32_UNDEFINED) + if (gScenarioCompletedCompanyValue != MONEY64_UNDEFINED) { return ObjectiveStatus::Undecided; } diff --git a/src/openrct2/scenario/Scenario.h b/src/openrct2/scenario/Scenario.h index cb3daaf3dd..4c9513a124 100644 --- a/src/openrct2/scenario/Scenario.h +++ b/src/openrct2/scenario/Scenario.h @@ -373,7 +373,7 @@ struct Objective }; union { - money32 Currency; + money64 Currency; uint16_t MinimumExcitement; // For the "Finish 5 coaster with a minimum excitement rating" objective. }; @@ -423,7 +423,7 @@ enum #define AUTOSAVE_PAUSE 0 #define DEFAULT_NUM_AUTOSAVES_TO_KEEP 10 -static constexpr money32 COMPANY_VALUE_ON_FAILED_OBJECTIVE = 0x80000001; +static constexpr money64 COMPANY_VALUE_ON_FAILED_OBJECTIVE = 0x8000000000000001; extern const rct_string_id ScenarioCategoryStringIds[SCENARIO_CATEGORY_COUNT]; @@ -433,8 +433,8 @@ extern random_engine_t gScenarioRand; extern Objective gScenarioObjective; extern bool gAllowEarlyCompletionInNetworkPlay; extern uint16_t gScenarioParkRatingWarningDays; -extern money32 gScenarioCompletedCompanyValue; -extern money32 gScenarioCompanyValueRecord; +extern money64 gScenarioCompletedCompanyValue; +extern money64 gScenarioCompanyValueRecord; extern rct_s6_info gS6Info; extern std::string gScenarioName; diff --git a/src/openrct2/scenario/ScenarioRepository.cpp b/src/openrct2/scenario/ScenarioRepository.cpp index 9f9aefcd48..822d884cf1 100644 --- a/src/openrct2/scenario/ScenarioRepository.cpp +++ b/src/openrct2/scenario/ScenarioRepository.cpp @@ -318,7 +318,7 @@ private: class ScenarioRepository final : public IScenarioRepository { private: - static constexpr uint32_t HighscoreFileVersion = 1; + static constexpr uint32_t HighscoreFileVersion = 2; std::shared_ptr const _env; ScenarioFileIndex const _fileIndex; @@ -416,7 +416,7 @@ public: return nullptr; } - bool TryRecordHighscore(int32_t language, const utf8* scenarioFileName, money32 companyValue, const utf8* name) override + bool TryRecordHighscore(int32_t language, const utf8* scenarioFileName, money64 companyValue, const utf8* name) override { // Scan the scenarios so we have a fresh list to query. This is to prevent the issue of scenario completions // not getting recorded, see #4951. @@ -598,7 +598,7 @@ private: { auto fs = FileStream(path, FILE_MODE_OPEN); uint32_t fileVersion = fs.ReadValue(); - if (fileVersion != 1) + if (fileVersion != 1 && fileVersion != 2) { Console::Error::WriteLine("Invalid or incompatible highscores file."); return; @@ -612,7 +612,7 @@ private: scenario_highscore_entry* highscore = InsertHighscore(); highscore->fileName = fs.ReadString(); highscore->name = fs.ReadString(); - highscore->company_value = fs.ReadValue(); + highscore->company_value = fileVersion == 1 ? fs.ReadValue() : fs.ReadValue(); highscore->timestamp = fs.ReadValue(); } } @@ -784,7 +784,7 @@ const scenario_index_entry* scenario_repository_get_by_index(size_t index) return repo->GetByIndex(index); } -bool scenario_repository_try_record_highscore(const utf8* scenarioFileName, money32 companyValue, const utf8* name) +bool scenario_repository_try_record_highscore(const utf8* scenarioFileName, money64 companyValue, const utf8* name) { IScenarioRepository* repo = GetScenarioRepository(); return repo->TryRecordHighscore(LocalisationService_GetCurrentLanguage(), scenarioFileName, companyValue, name); diff --git a/src/openrct2/scenario/ScenarioRepository.h b/src/openrct2/scenario/ScenarioRepository.h index 8a1b7b19b8..0ee807a384 100644 --- a/src/openrct2/scenario/ScenarioRepository.h +++ b/src/openrct2/scenario/ScenarioRepository.h @@ -20,7 +20,7 @@ struct scenario_highscore_entry { utf8* fileName; utf8* name; - money32 company_value; + money64 company_value; datetime64 timestamp; }; @@ -38,7 +38,7 @@ struct scenario_index_entry // Objective uint8_t objective_type; uint8_t objective_arg_1; - int32_t objective_arg_2; + int64_t objective_arg_2; int16_t objective_arg_3; scenario_highscore_entry* highscore = nullptr; @@ -71,7 +71,7 @@ struct IScenarioRepository virtual const scenario_index_entry* GetByPath(const utf8* path) const abstract; virtual bool TryRecordHighscore( - int32_t language, const utf8* scenarioFileName, money32 companyValue, const utf8* name) abstract; + int32_t language, const utf8* scenarioFileName, money64 companyValue, const utf8* name) abstract; }; std::unique_ptr CreateScenarioRepository(const std::shared_ptr& env); @@ -80,5 +80,5 @@ IScenarioRepository* GetScenarioRepository(); void scenario_repository_scan(); size_t scenario_repository_get_count(); const scenario_index_entry* scenario_repository_get_by_index(size_t index); -bool scenario_repository_try_record_highscore(const utf8* scenarioFileName, money32 companyValue, const utf8* name); +bool scenario_repository_try_record_highscore(const utf8* scenarioFileName, money64 companyValue, const utf8* name); void scenario_translate(scenario_index_entry* scenarioEntry); diff --git a/src/openrct2/scripting/Duktape.hpp b/src/openrct2/scripting/Duktape.hpp index 95de254bb3..de51173220 100644 --- a/src/openrct2/scripting/Duktape.hpp +++ b/src/openrct2/scripting/Duktape.hpp @@ -123,6 +123,13 @@ namespace OpenRCT2::Scripting duk_put_prop_string(_ctx, _idx, name); } + void Set(const char* name, int64_t value) + { + EnsureObjectPushed(); + duk_push_number(_ctx, value); + duk_put_prop_string(_ctx, _idx, name); + } + void Set(const char* name, uint64_t value) { EnsureObjectPushed(); @@ -280,6 +287,12 @@ namespace OpenRCT2::Scripting return DukValue::take_from_stack(ctx); } + template<> inline DukValue ToDuk(duk_context* ctx, const int64_t& value) + { + duk_push_number(ctx, value); + return DukValue::take_from_stack(ctx); + } + template<> inline DukValue ToDuk(duk_context* ctx, const std::string_view& value) { duk_push_lstring(ctx, value.data(), value.size()); diff --git a/src/openrct2/scripting/ScPark.hpp b/src/openrct2/scripting/ScPark.hpp index ba0b65a1e0..18be4cb1f2 100644 --- a/src/openrct2/scripting/ScPark.hpp +++ b/src/openrct2/scripting/ScPark.hpp @@ -247,11 +247,11 @@ namespace OpenRCT2::Scripting class ScPark { public: - money32 cash_get() const + money64 cash_get() const { return gCash; } - void cash_set(money32 value) + void cash_set(money64 value) { ThrowIfGameStateNotMutable(); @@ -280,11 +280,11 @@ namespace OpenRCT2::Scripting } } - money32 bankLoan_get() const + money64 bankLoan_get() const { return gBankLoan; } - void bankLoan_set(money32 value) + void bankLoan_set(money64 value) { ThrowIfGameStateNotMutable(); @@ -296,11 +296,11 @@ namespace OpenRCT2::Scripting } } - money32 maxBankLoan_get() const + money64 maxBankLoan_get() const { return gMaxBankLoan; } - void maxBankLoan_set(money32 value) + void maxBankLoan_set(money64 value) { ThrowIfGameStateNotMutable(); @@ -362,11 +362,11 @@ namespace OpenRCT2::Scripting return gGuestInitialThirst; } - money32 value_get() const + money64 value_get() const { return gParkValue; } - void value_set(money32 value) + void value_set(money64 value) { ThrowIfGameStateNotMutable(); @@ -378,11 +378,11 @@ namespace OpenRCT2::Scripting } } - money32 companyValue_get() const + money64 companyValue_get() const { return gCompanyValue; } - void companyValue_set(money32 value) + void companyValue_set(money64 value) { ThrowIfGameStateNotMutable(); @@ -414,11 +414,11 @@ namespace OpenRCT2::Scripting } } - money32 totalIncomeFromAdmissions_get() const + money64 totalIncomeFromAdmissions_get() const { return gTotalIncomeFromAdmissions; } - void totalIncomeFromAdmissions_set(money32 value) + void totalIncomeFromAdmissions_set(money64 value) { ThrowIfGameStateNotMutable(); diff --git a/src/openrct2/scripting/ScScenario.hpp b/src/openrct2/scripting/ScScenario.hpp index 5a2174a846..4d47ea3403 100644 --- a/src/openrct2/scripting/ScScenario.hpp +++ b/src/openrct2/scripting/ScScenario.hpp @@ -107,7 +107,7 @@ namespace OpenRCT2::Scripting } } - money32 excitement_get() + money64 excitement_get() { if (gScenarioObjective.Type == OBJECTIVE_FINISH_5_ROLLERCOASTERS) { @@ -116,7 +116,7 @@ namespace OpenRCT2::Scripting return 0; } - void excitement_set(money32 value) + void excitement_set(money64 value) { ThrowIfGameStateNotMutable(); if (gScenarioObjective.Type == OBJECTIVE_FINISH_5_ROLLERCOASTERS) @@ -125,7 +125,7 @@ namespace OpenRCT2::Scripting } } - money32 parkValue_get() + money64 parkValue_get() { if (gScenarioObjective.Type == OBJECTIVE_PARK_VALUE_BY || gScenarioObjective.Type == OBJECTIVE_REPAY_LOAN_AND_PARK_VALUE) @@ -135,7 +135,7 @@ namespace OpenRCT2::Scripting return 0; } - void parkValue_set(money32 value) + void parkValue_set(money64 value) { ThrowIfGameStateNotMutable(); if (gScenarioObjective.Type == OBJECTIVE_PARK_VALUE_BY @@ -145,7 +145,7 @@ namespace OpenRCT2::Scripting } } - money32 monthlyIncome_get() + money64 monthlyIncome_get() { if (gScenarioObjective.Type == OBJECTIVE_MONTHLY_RIDE_INCOME || gScenarioObjective.Type == OBJECTIVE_MONTHLY_FOOD_INCOME) @@ -155,7 +155,7 @@ namespace OpenRCT2::Scripting return 0; } - void monthlyIncome_set(money32 value) + void monthlyIncome_set(money64 value) { ThrowIfGameStateNotMutable(); if (gScenarioObjective.Type == OBJECTIVE_PARK_VALUE_BY @@ -246,7 +246,7 @@ namespace OpenRCT2::Scripting DukValue completedCompanyValue_get() const { auto ctx = GetContext()->GetScriptEngine().GetContext(); - if (gScenarioCompletedCompanyValue == MONEY32_UNDEFINED + if (gScenarioCompletedCompanyValue == MONEY64_UNDEFINED || gScenarioCompletedCompanyValue == COMPANY_VALUE_ON_FAILED_OBJECTIVE) { return ToDuk(ctx, nullptr); @@ -261,7 +261,7 @@ namespace OpenRCT2::Scripting std::string status_get() const { - if (gScenarioCompletedCompanyValue == MONEY32_UNDEFINED) + if (gScenarioCompletedCompanyValue == MONEY64_UNDEFINED) return "inProgress"; else if (gScenarioCompletedCompanyValue == COMPANY_VALUE_ON_FAILED_OBJECTIVE) return "failed"; @@ -271,18 +271,18 @@ namespace OpenRCT2::Scripting { ThrowIfGameStateNotMutable(); if (value == "inProgress") - gScenarioCompletedCompanyValue = MONEY32_UNDEFINED; + gScenarioCompletedCompanyValue = MONEY64_UNDEFINED; else if (value == "failed") gScenarioCompletedCompanyValue = COMPANY_VALUE_ON_FAILED_OBJECTIVE; else if (value == "completed") gScenarioCompletedCompanyValue = gCompanyValue; } - money32 companyValueRecord_get() const + money64 companyValueRecord_get() const { return gScenarioCompanyValueRecord; } - void companyValueRecord_set(money32 value) + void companyValueRecord_set(money64 value) { ThrowIfGameStateNotMutable(); gScenarioCompanyValueRecord = value; diff --git a/src/openrct2/util/Util.cpp b/src/openrct2/util/Util.cpp index 1cd52ab180..78225880b7 100644 --- a/src/openrct2/util/Util.cpp +++ b/src/openrct2/util/Util.cpp @@ -729,6 +729,12 @@ int32_t add_clamp_int32_t(int32_t value, int32_t value_to_add) return value; } +int64_t add_clamp_int64_t(int64_t value, int64_t value_to_add) +{ + add_clamp_body(value, value_to_add, INT64_MIN, INT64_MAX); + return value; +} + money32 add_clamp_money32(money32 value, money32 value_to_add) { // This function is intended only for clarity, as money32 @@ -737,6 +743,14 @@ money32 add_clamp_money32(money32 value, money32 value_to_add) return add_clamp_int32_t(value, value_to_add); } +money32 add_clamp_money64(money64 value, money64 value_to_add) +{ + // This function is intended only for clarity, as money64 + // is technically the same as int64_t + assert_struct_size(money64, sizeof(int64_t)); + return add_clamp_int64_t(value, value_to_add); +} + #undef add_clamp_body uint8_t lerp(uint8_t a, uint8_t b, float t) diff --git a/src/openrct2/util/Util.h b/src/openrct2/util/Util.h index 5040954e6e..766d60faa1 100644 --- a/src/openrct2/util/Util.h +++ b/src/openrct2/util/Util.h @@ -63,7 +63,9 @@ bool util_gzip_compress(FILE* source, FILE* dest); int8_t add_clamp_int8_t(int8_t value, int8_t value_to_add); int16_t add_clamp_int16_t(int16_t value, int16_t value_to_add); int32_t add_clamp_int32_t(int32_t value, int32_t value_to_add); +int64_t add_clamp_int64_t(int64_t value, int64_t value_to_add); money32 add_clamp_money32(money32 value, money32 value_to_add); +money32 add_clamp_money64(money64 value, money64 value_to_add); uint8_t lerp(uint8_t a, uint8_t b, float t); float flerp(float a, float b, float t); diff --git a/src/openrct2/world/MoneyEffect.cpp b/src/openrct2/world/MoneyEffect.cpp index 4ff854a571..85e328b805 100644 --- a/src/openrct2/world/MoneyEffect.cpp +++ b/src/openrct2/world/MoneyEffect.cpp @@ -133,12 +133,12 @@ void MoneyEffect::Update() sprite_remove(this); } -std::pair MoneyEffect::GetStringId() const +std::pair MoneyEffect::GetStringId() const { rct_string_id spentStringId = Vertical ? STR_MONEY_EFFECT_SPEND_HIGHP : STR_MONEY_EFFECT_SPEND; rct_string_id receiveStringId = Vertical ? STR_MONEY_EFFECT_RECEIVE_HIGHP : STR_MONEY_EFFECT_RECEIVE; rct_string_id stringId = receiveStringId; - money32 outValue = Value; + money64 outValue = Value; if (Value < 0) { outValue *= -1; diff --git a/src/openrct2/world/Park.cpp b/src/openrct2/world/Park.cpp index 1fb1b4db18..91c2f07206 100644 --- a/src/openrct2/world/Park.cpp +++ b/src/openrct2/world/Park.cpp @@ -246,12 +246,12 @@ uint16_t Park::GetParkRating() const return gParkRating; } -money32 Park::GetParkValue() const +money64 Park::GetParkValue() const { return gParkValue; } -money32 Park::GetCompanyValue() const +money64 Park::GetCompanyValue() const { return gCompanyValue; } @@ -482,10 +482,10 @@ int32_t Park::CalculateParkRating() const return result; } -money32 Park::CalculateParkValue() const +money64 Park::CalculateParkValue() const { // Sum ride values - money32 result = 0; + money64 result = 0; for (const auto& ride : GetRideManager()) { result += CalculateRideValue(&ride); @@ -497,23 +497,23 @@ money32 Park::CalculateParkValue() const return result; } -money32 Park::CalculateRideValue(const Ride* ride) const +money64 Park::CalculateRideValue(const Ride* ride) const { - money32 result = 0; + money64 result = 0; if (ride != nullptr && ride->value != RIDE_VALUE_UNDEFINED) { const auto& rtd = ride->GetRideTypeDescriptor(); - result = (ride->value * 10) * (ride_customers_in_last_5_minutes(ride) + rtd.BonusValue * 4); + result = (ride->value * 10LL) * (static_cast(ride_customers_in_last_5_minutes(ride)) + rtd.BonusValue * 4); } return result; } -money32 Park::CalculateCompanyValue() const +money64 Park::CalculateCompanyValue() const { - money32 result = gParkValue - gBankLoan; + auto result = gParkValue - gBankLoan; // Clamp addition to prevent overflow - result = add_clamp_money32(result, finance_get_current_cash()); + result = add_clamp_money64(result, finance_get_current_cash()); return result; } @@ -767,20 +767,20 @@ void Park::UpdateHistories() // Update park rating, guests in park and current cash history HistoryPushRecord(gParkRatingHistory, CalculateParkRating() / 4); HistoryPushRecord(gGuestsInParkHistory, std::min(gNumGuestsInPark, 5000) / 20); - HistoryPushRecord(gCashHistory, finance_get_current_cash() - gBankLoan); + HistoryPushRecord(gCashHistory, finance_get_current_cash() - gBankLoan); // Update weekly profit history - money32 currentWeeklyProfit = gWeeklyProfitAverageDividend; + auto currentWeeklyProfit = gWeeklyProfitAverageDividend; if (gWeeklyProfitAverageDivisor != 0) { currentWeeklyProfit /= gWeeklyProfitAverageDivisor; } - HistoryPushRecord(gWeeklyProfitHistory, currentWeeklyProfit); + HistoryPushRecord(gWeeklyProfitHistory, currentWeeklyProfit); gWeeklyProfitAverageDividend = 0; gWeeklyProfitAverageDivisor = 0; // Update park value history - HistoryPushRecord(gParkValueHistory, gParkValue); + HistoryPushRecord(gParkValueHistory, gParkValue); // Invalidate relevant windows auto intent = Intent(INTENT_ACTION_UPDATE_GUEST_COUNT); diff --git a/src/openrct2/world/Park.h b/src/openrct2/world/Park.h index 8340666370..e998d48104 100644 --- a/src/openrct2/world/Park.h +++ b/src/openrct2/world/Park.h @@ -59,16 +59,16 @@ namespace OpenRCT2 bool IsOpen() const; uint16_t GetParkRating() const; - money32 GetParkValue() const; - money32 GetCompanyValue() const; + money64 GetParkValue() const; + money64 GetCompanyValue() const; void Initialise(); void Update(const Date& date); int32_t CalculateParkSize() const; int32_t CalculateParkRating() const; - money32 CalculateParkValue() const; - money32 CalculateCompanyValue() const; + money64 CalculateParkValue() const; + money64 CalculateCompanyValue() const; static uint8_t CalculateGuestInitialHappiness(uint8_t percentage); Guest* GenerateGuest(); @@ -77,7 +77,7 @@ namespace OpenRCT2 void UpdateHistories(); private: - money32 CalculateRideValue(const Ride* ride) const; + money64 CalculateRideValue(const Ride* ride) const; money16 CalculateTotalRideValueForMoney() const; uint32_t CalculateSuggestedMaxGuests() const; uint32_t CalculateGuestGenerationProbability() const;