
Block puzzle difficulty: how simulation bots caught a game you could never lose
If every tray of three pieces is guaranteed to fit, a player who finds each tray's solution never loses. Block Turn now keeps that guarantee for the first 10 trays only.
As first specified, the classic mode of Block Turn had no game over. We found out from bots: on October 3, 2026, under the supply rule written in the spec (v1), a bot that plans the whole tray played 80 games, and all 80 hit the 3,000-move cap. The shipped rule, v7, ends a planner's game after a median of 122 moves and a greedy bot's after 47.
Numbers come from the sugar-game repository: the supply experiment log (docs/block/lab.md, measured 2026-10-03), the spec review, and the engine code and tests. Checked on October 19, 2026.
Contents (7)
One friendly promise removed the game over
Block Turn is an 8×8 block puzzle in the Block Blast mold: you get three pieces, place them, full rows and columns clear, and then you get three more. The spec we started from (v2.0) promised this in section 7.1: "When a new set of three pieces is dealt, there is at least one order in which all three fit on the current board." It was meant to answer players who feel the piece supply is rigged. The spec even added that a player can still get stuck by placing badly.
That caveat only covers weak play. For a player who finds the solution, the promise turns into a loop:
- When a tray arrives, some order places all three pieces.
- Play that order and the tray is empty.
- The next tray gets the same guarantee. Back to step 1.
The run never ends. Nothing in that argument depends on piece weights, so dealing more awkward pieces cannot break it. The bots confirmed that too (v3 and v4 below).
A greedy bot and a planning bot on the same seeds
The engine stores the board as a single 64-bit integer, so scoring a position takes a handful of bit operations.
- Greedy bot: it scores every legal move right now with the formula below and plays the best one. A cleared line is worth 10, so it usually picks the move that clears the most lines.
- Planning bot: it searches every order and placement of the pieces left in the tray, plays the first move of the best plan, and searches again on the next move.
Both use the same board score:
score = lines cleared × 10 − 3 × holes − 0.3 × filled cells + 2 × room
holes = empty cells boxed in on all four sides
room = is there space for a 3×3 square, a 1×4 bar, a 4×1 bar (0–3)
In the final comparison each supply version got 160 greedy games and 80 planner games, and every version used the same seeds. A game stops at 3,000 moves. The bots are not models of people. We assume a person lands somewhere between them, and we use the bot numbers only to rank supply rules against each other.
The four numbers that decided it
- Planner games that hit the 3,000-move cap. Anything above zero rejects the version, because it means the game cannot be lost.
- Planner median divided by greedy median. In a high-score mode, "play better, last longer" is most of the fun, so we wanted skill to show up as run length.
- Greedy run length, so a careless player doesn't wash out in a few trays.
- Tray generation time at p95, to see whether supply cost matters on a phone.
Supply rules v1 to v7, side by side
The awkward pieces are the 3×3 square, the 2×3 rectangle in both orientations and the four-cell bar in both orientations. "Pressure" means that every N moves those pieces gain one more multiple of their base weight, up to a cap.
| Version | Supply rule | Greedy median | Planner median | Planner games at cap | Outcome |
|---|---|---|---|---|---|
| v1 | The spec: every tray fully placeable | 56 moves | 3,000 moves | 80/80 | Rejected |
| v2 | v1, plus 3× weight for pieces of 3 cells or fewer when fewer than 28 cells are empty | Not in the results table | Dropped (made the game easier) | ||
| v3 | v1 plus pressure every 30 moves, up to 5× | Not in the results table | 60/60 | Rejected | |
| v4 | v1 plus pressure every 20 moves, up to 8× | Not in the results table | 60/60 | Rejected | |
| v5 | v7 plus pressure every 30 moves, up to 5× | 44 moves | 80 moves | 0 | A/B candidate |
| v6 | v7 plus pressure every 20 moves, up to 8× | 44 moves | 82 moves | 0 | Not used |
| v7 | Full guarantee for the first 10 trays, then only "at least one piece fits" | 47 moves | 122 moves | 0 | Default |
Under v1 the planner's median game lasted 1,001 trays and scored 26,772 points. Under v7 it was 41 trays and 998 points. In the four versions with full numbers (v1, v5, v6, v7), the greedy bot never reached the cap.
We picked v7 for the skill gap: 122 moves against 47 is 2.6×. Adding pressure (v5, v6) cut that gap to 1.8 to 1.9×, mostly by cutting the strong player's runs short. Shorter runs mean more game-over screens, but they also mean a good player gets less for being good. So v7 shipped as the default, and v5 is parked as an A/B candidate.

Supply cost turned out to be a non-issue. Tray generation stayed at or under 0.2 ms at p95 for every version with timings in the table, and the spec's last-resort fallback (deal three single cells) never fired in 2,710 trays of the earlier Python simulation.
If a game spec says the player can "always" do something, run a bot that exploits that promise to the end before you build on it. Reading the sentence will not show you the problem.
The AI's first review pushed the other way
Earlier the same day, the spec review written by our AI coding agent had already simulated the supply rule in Python. It ran a random bot and a one-move greedy bot for 150 games each, with medians of 17 and 26 moves. It also tried a bot that reads the whole tray, then gave up on it: searching a single tray on an empty board took more than ten minutes in Python.
From those short runs, the review concluded that a solvable tray does not guarantee a long game, and recommended "relief" supply: deal smaller pieces when the board gets crowded. That is v2 in the table.
A promise that only matters to the strongest player had been tested with the weakest bots. Once the Kotlin engine existed, the planning bot ran in reasonable time and every v1 planner game hit the cap. v2 was dropped, and spec v2.1 rewrote the supply promise as v7. The engine, the experiment tool and the tests landed together in commit cd62087 (October 4, 2026, Korea time).
(The Python greedy bot used a different board score with no "room" term, so its 26 moves and the Kotlin greedy bot's 56 under v1 are not a like-for-like comparison.)
The v1 finding is pinned by a unit test, a planner cannot be stopped under the full guarantee: on 20 seeds, playing each tray's solution must pass 300 moves.
What we still have to check
- We don't know how long a human run is yet. The target is a median of 60 to 150 moves (roughly 4 to 10 minutes), and if real runs fall outside it we switch to v5. The end-of-run event that carries the move count,
post_score, had fired only twice in total as of our October 17 GA4 review. The same review noted that the first-run flow never showed classic mode, so commitd1f6de1(1.1.2) added a button into classic mode after the last tutorial. - Since 1.1.4 (
b2d305d, October 17) a classic run allows two revives. The supply experiment ran without revives, so run length with revives needs measuring again. - The default supply rule itself is pinned by a test (
default supply guarantees the first ten trays fully and never deals a dead tray after), so switching the default back to v1 would fail it. What no test checks is that a planner actually loses before the cap under the default supply. Today only a fresh supply experiment run shows that.
How the earlier apps came out of the same agent-driven workflow is in How we shipped four Android apps in 20 days with an AI coding agent.
FAQ
What should the game over condition be in a block puzzle?
The game ends when none of the remaining pieces fits anywhere. If the supply only ever deals trays that fully fit, a strong player never meets that condition. Block Turn guarantees full trays for the first 10 and, after that, only that at least one piece fits.
Can't you fix it by dealing more hard pieces?
No. Even with awkward pieces weighted up to 8× (v4), every planner game reached the 3,000-move cap. While the full guarantee stands, weights only change which solvable tray you get.
How many games does a balance simulation need?
In the final comparison we ran 160 greedy and 80 planner games per version, on the same seeds for every version (the earlier v3 and v4 runs used 60 planner games). That was enough to separate results like 80/80 games at the cap versus 0/80.
This note is written from values SugarMount measured itself; an AI coding agent was used to draft it.
More AX notes
- A reverse-construction generator and the gate behind 1,100 arrow-puzzle levels
- Testers said the time was "too long, so it's easy": checking that with a simulation before cutting puzzle par times by 30%
- Puzzle game day-one churn: per-device event timelines, exact board math and four walls in chapter one
- Pre-gzipping Android assets, measured: zero APK savings, and .pack.gz became .pack with a FileNotFoundException
- A market:// link opens a store chooser on SKT-sold Samsung phones: set the Play package first
- A splash that never moved on: addOnCompleteListener(this) and onStop