Skip to content
Game development

Game dev guide · · 7 min read

Game economy balancing in a spreadsheet: a worked model

Balance upgrade prices with one formula and one metric, runs to afford: a worked spreadsheet, a curve that breaks, one that holds, and a sink for the pile-up.

A tank filled with gold coins under a faucet that drops coins in, with a small drain pipe at the lower right. Large text reads faucets and sinks.

What goes into a game economy spreadsheet?

Four numbers and three formulas are enough to start: a base price, a price growth, a base income and an income growth. Put them in their own cells, never inside a formula, so you can change one and watch every row move.

The model here is a small game with short runs. After each run you earn coins, and you spend them on one upgrade line with 25 levels. The upgrade price is ROUND(base_cost * cost_growth ^ level). The coins earned per run are ROUND(base_income * income_growth ^ level). The third column is the one that matters: runs to afford, which is price divided by income. It tells you how many runs a player must play to buy the next level.

I used a base cost of 300, a cost growth of 1.16, a base income of 100 and an income growth of 1.10. The animation fills the sheet column by column, then changes the single growth cell from 1.16 to 1.30 so you can see what one cell does to the whole game. The same three functions in GDScript give the same numbers: I ran them in Godot 4.5.1 and they print 300, 630, 1323, 2780, 5838 and 12262 for levels 0, 5, 10, 15, 20 and 25.

A spreadsheet with columns for level, cost, coins per run and runs, and four parameter cells on the right. The formulas are typed into the formula bar and filled down. Then the cost growth cell changes from 1.16 to 1.30 and the runs column turns red with values up to 195.5.
The whole model on one sheet. Changing one cell, the cost growth, moves the runs-to-afford column from 11.3 to 195.5 at level 25.

How do you price upgrades so each one takes similar effort?

Let the price grow by a fixed percentage per level, then check it against income. This is the standard shape for incremental games: next price equals base price times a growth rate raised to the number you already own. Anthony Pecorella's Math of Idle Games shows it with a base of 4 and a rate of 1.07 for the first generator of AdVenture Capitalist. Your growth rate comes from your game, not from his.

The mistake is to look at the price curve alone. A price that grows 16 percent per level looks scary and is fine here, because income grows 10 percent per level at the same time. What the player feels is the ratio, so plot the ratio.

Keep the formula in one place in your code and call it from the shop, the UI and your tests. That way the spreadsheet and the game cannot drift apart.

class_name Economy
extends RefCounted

const BASE_COST := 300.0
const COST_GROWTH := 1.16
const BASE_INCOME := 100.0
const INCOME_GROWTH := 1.10

static func upgrade_cost(level: int) -> int:
	return roundi(BASE_COST * pow(COST_GROWTH, level))

static func income_per_run(level: int) -> int:
	return roundi(BASE_INCOME * pow(INCOME_GROWTH, level))

static func runs_to_afford(level: int) -> float:
	return float(upgrade_cost(level)) / float(income_per_run(level))

Which price growth holds, and which one breaks?

Pick a target band for runs to afford, then test three growth rates against it. Here the band is 3 to 12 runs: the first upgrade takes 3 runs, and the last one takes about four times as long. If a run is two minutes, that is 6 minutes at the start and 24 at the end.

With a growth of 1.05 the price grows slower than income, so runs to afford fall from 3.0 to 0.9 by level 25. Every run buys a level, and the upgrade line stops being a decision. With 1.16 it rises from 3.0 to 11.3 and stays inside the band. With 1.30 it passes 16 runs at level 10 and 36.7 at level 15, and at level 25 a level costs 211,692 coins, or 195.5 runs of play.

A wall like that does not feel hard, it feels broken. Players quit at the first level where one purchase takes more than a session. For the other side of the same problem, what a run is worth when upgrades carry over, see roguelite meta progression.

A chart of runs to afford against upgrade level from 0 to 25. A shaded band marks 3 to 12 runs. A blue line for growth 1.05 falls to 0.9, a green line for 1.16 rises gently to 11.3, and a red line for 1.30 shoots past the top of the chart, marked off the chart, ending at 195.
Runs to afford for three price growth rates. Only 1.16 stays in the 3 to 12 band. The red curve is cut at 40 and ends at 195.5 runs.

How do you choose the growth number instead of guessing it?

Decide the two end points, then solve for the growth. The relation is cost_growth = income_growth * (end_runs / start_runs) ^ (1 / levels). With 3 runs at the start, 12 at the end, 25 levels and an income growth of 1.10, that is 1.10 times 4 to the power of 1/25, which is 1.1627. Rounded, that is the 1.16 used above.

This also tells you what to change when a playtest says the end is too slow. Lower the target end value from 12 to 8 and the growth becomes 1.144. You tune one decision, how long the last upgrade should take, and the formula does the rest.

This model has one upgrade line and a player who buys the next level as soon as they can afford it. Real games have several lines and players who save. Use the sheet to find numbers that are wrong by a factor of two or ten, not to settle the final value. For a mode that never ends, balancing an endless mode goes further on curves.

What are faucets and sinks, and why does the balance pile up?

A faucet is anything that puts coins into the game, a sink is anything that takes them out. If faucets stay larger than sinks, the balance grows without limit and prices lose their meaning. The terms come from MMO design, where one Game Developer article calls the idea money in, money out. A single player game has no player market, so the problem is simpler: the number on the price tag stops mattering.

I simulated 60 days at 4 runs per day with the 1.16 curve. The player buys the next level whenever possible. All 25 levels are bought on day 39, because the income keeps coming and nothing is left to buy. By day 60 the balance is 93,709 coins, which is 8.9 times the price of the last upgrade (10,571). Every future item now looks cheap.

The second tank adds a sink that starts only when every level is bought: a repeatable boost that costs 90 percent of what a run pays. The early game is identical, and at day 60 the balance is 8,884, or 0.8 times the last upgrade price. The sink is a tax, so the boost has to be something players want to buy. Prices tied to income are easy to tune, but they also take the reward out of playing harder, so use them for the late game only.

In the 1.30 version the player is stuck at level 16 after 60 days. A sink cannot fix that. It is a price problem, so go back to the sheet.

Two tanks fill with gold over 60 days. The left tank, with no sink, fills up to 93,709 coins, far above a dashed line marking the price of the top upgrade. The right tank has a drain pipe and ends at 8,884 coins, just under the line.
The same player for 60 days, with and without a late-game sink. Balance divided by the last upgrade price: 8.9 against 0.8.

What should you check with real players?

Log the number you modeled. In every build, write down how many runs it took to afford each upgrade, and compare it with the sheet. If players take twice as long as the model says, they are either playing worse than you assumed or spending coins on something you forgot to model.

Do this with a handful of testers, not with yourself. Developers play too well. The playtest guide covers how many people to watch and what to ask. And before you add a second currency or a third upgrade line, read how to scope a game you can finish: each new line multiplies the sheet.

Questions people ask

What growth rate should upgrade costs use?
There is no universal value. Choose how long the first and last upgrade should take, then solve for the growth with income growth times the ratio of end to start runs, raised to one over the number of levels.
What is the difference between a faucet and a sink?
A faucet adds currency to the game, such as rewards for finishing a run. A sink removes it, such as shop purchases, repair costs or entry fees. If faucets stay above sinks for long, the balance grows without limit.
Should I balance in a spreadsheet or in the game?
Start in a spreadsheet to find numbers that are off by a large factor, then confirm with logged data from real players. The sheet is fast to change, the game shows what players really do.

Sources and further reading