Changeset - r28628:5977866b9ea5
[Not reviewed]
master
0 4 0
merni-ns - 9 months ago 2024-01-31 19:11:48
66267867+merni-ns@users.noreply.github.com
Fix #11938: Check infinite money setting in cases where it was missed (#11939)
4 files changed with 11 insertions and 7 deletions:
0 comments (0 inline, 0 general)
src/economy.cpp
Show inline comments
 
@@ -833,23 +833,27 @@ static void CompaniesPayInterest()
 
	for (const Company *c : Company::Iterate()) {
 
		cur_company.Change(c->index);
 

	
 
		/* Over a year the paid interest should be "loan * interest percentage",
 
		 * but... as that number is likely not dividable by 12 (pay each month),
 
		 * one needs to account for that in the monthly fee calculations.
 
		 *
 
		 * To easily calculate what one should pay "this" month, you calculate
 
		 * what (total) should have been paid up to this month and you subtract
 
		 * whatever has been paid in the previous months. This will mean one month
 
		 * it'll be a bit more and the other it'll be a bit less than the average
 
		 * monthly fee, but on average it will be exact.
 
		 *
 
		 * In order to prevent cheating or abuse (just not paying interest by not
 
		 * taking a loan we make companies pay interest on negative cash as well
 
		 * taking a loan) we make companies pay interest on negative cash as well,
 
		 * except if infinite money is enabled.
 
		 */
 
		Money yearly_fee = c->current_loan * _economy.interest_rate / 100;
 
		if (c->money < 0) {
 
			yearly_fee += -c->money *_economy.interest_rate / 100;
 
		Money available_money = GetAvailableMoney(c->index);
 
		if (available_money < 0) {
 
			yearly_fee += -available_money * _economy.interest_rate / 100;
 
		}
 
		Money up_to_previous_month = yearly_fee * TimerGameEconomy::month / 12;
 
		Money up_to_this_month = yearly_fee * (TimerGameEconomy::month + 1) / 12;
 

	
 
		SubtractMoneyFromCompany(CommandCost(EXPENSES_LOAN_INTEREST, up_to_this_month - up_to_previous_month));
 

	
src/misc_cmd.cpp
Show inline comments
 
@@ -93,22 +93,22 @@ CommandCost CmdDecreaseLoan(DoCommandFla
 
	switch (cmd) {
 
		default: return CMD_ERROR; // Invalid method
 
		case LoanCommand::Interval: // Pay back one step
 
			loan = std::min(c->current_loan, (Money)LOAN_INTERVAL);
 
			break;
 
		case LoanCommand::Max: // Pay back as much as possible
 
			loan = std::max(std::min(c->current_loan, c->money), (Money)LOAN_INTERVAL);
 
			loan = std::max(std::min(c->current_loan, GetAvailableMoneyForCommand()), (Money)LOAN_INTERVAL);
 
			loan -= loan % LOAN_INTERVAL;
 
			break;
 
		case LoanCommand::Amount: // Repay the given amount of loan
 
			loan = amount;
 
			if (loan % LOAN_INTERVAL != 0 || loan < LOAN_INTERVAL || loan > c->current_loan) return CMD_ERROR; // Invalid amount to loan
 
			break;
 
	}
 

	
 
	if (c->money < loan) {
 
	if (GetAvailableMoneyForCommand() < loan) {
 
		SetDParam(0, loan);
 
		return_cmd_error(STR_ERROR_CURRENCY_REQUIRED);
 
	}
 

	
 
	if (flags & DC_EXEC) {
 
		c->money        -= loan;
src/town_cmd.cpp
Show inline comments
 
@@ -3432,13 +3432,13 @@ TownActions GetMaskOfTownActions(Company
 
	TownActions buttons = TACT_NONE;
 

	
 
	/* Spectators and unwanted have no options */
 
	if (cid != COMPANY_SPECTATOR && !(_settings_game.economy.bribe && t->unwanted[cid])) {
 

	
 
		/* Actions worth more than this are not able to be performed */
 
		Money avail = Company::Get(cid)->money;
 
		Money avail = GetAvailableMoney(cid);
 

	
 
		/* Check the action bits for validity and
 
		 * if they are valid add them */
 
		for (uint i = 0; i != lengthof(_town_action_costs); i++) {
 
			const TownActions cur = (TownActions)(1 << i);
 

	
src/town_gui.cpp
Show inline comments
 
@@ -242,13 +242,13 @@ public:
 
	void DrawWidget(const Rect &r, WidgetID widget) const override
 
	{
 
		switch (widget) {
 
			case WID_TA_ACTION_INFO:
 
				if (this->sel_index != -1) {
 
					Money action_cost = _price[PR_TOWN_ACTION] * _town_action_costs[this->sel_index] >> 8;
 
					bool affordable = Company::IsValidID(_local_company) && action_cost < Company::Get(_local_company)->money;
 
					bool affordable = Company::IsValidID(_local_company) && action_cost < GetAvailableMoney(_local_company);
 

	
 
					SetDParam(0, action_cost);
 
					DrawStringMultiLine(r.Shrink(WidgetDimensions::scaled.framerect),
 
						this->action_tooltips[this->sel_index],
 
						affordable ? TC_YELLOW : TC_RED);
 
				}
0 comments (0 inline, 0 general)