Skip to content

Releases: WebDevBar/AdbAutoPlayer

WDB 12.12.1-36 - two days of Savannah Cup

Choose a tag to compare

@todor-wdb todor-wdb released this 09 Sep 13:26

Upstream 12.12.1 plus the fixes found by actually running the bot.

Fixed

  • The winner headline could name the wrong side. A match printed BLUE WINS directly above red won - MISS. The headline used which panel won, and panel position is not side colour. Stored data was always correct; only the printed line was wrong.
  • The CLI printed HTML. Log messages carry <span class="sc-*"> markers for the GUI; in a terminal they wrapped the words that mattered. They render as colour now, and --output text strips them.
  • DEBUG no longer floods the console. It defaulted to on. The detail still goes to ~/.local/state/adb-auto-player/debug.log, which stays empty unless something fails and then holds the failure plus what led to it.
  • A red ERROR on every run, from a helper comparing local main against origin - a fork checkout has no main.

Added

  • c1, c2, c3 as aliases for the three custom routines.
  • Savannah Cup theme windows through Top Defender, so matches file against the right theme instead of being dropped from the odds model.

Upstream 12.12.1 brings Qwen2-VL OCR fixes and dependency updates.

WDB 12.12.0-35 - Savannah Cup

Choose a tag to compare

@todor-wdb todor-wdb released this 06 Sep 18:04

Savannah Cup replaced Solstice Clash on 2026-09-03. This build spectates it.

Added

  • Savannah Cup support. Only two of fourteen screen templates were event-specific; the host dialog, Fortune Picks, the draft and prematch anchors and both result screens survived the reskin unchanged.
  • Per-event geometry. Savannah draws a 5x3 draft grid where Solstice drew 5x4, with the locked-pick row higher and under a chat ticker. Both events' coordinates coexist, so old captures still read correctly.
  • All 125 playable heroes, icons refreshed from the game. Rolan, Voracia, Eryndor and both Digimon duos were released after the previous dump and were unidentifiable before this.

Fixed

  • The theme was read wrong and stored anyway - Current Theme Fortress O instead of Forsaken Fortress. Nothing failed, so it mis-filed data silently.
  • The events list scrolls, so the card was missed when it started below the fold. Running out of list now means the event ended, and the run stops cleanly.
  • Three hero names corrected: Isabella, Smokey & Meerky, Sylphira. Old spellings still load, so saved exclusions survive.

Verified on device: four consecutive matches recorded under savannah-cup/forsaken-fortress, theme resolved by date window. Tests: 1070 client, 170 server.

WDB 12.9.25-32 - the side-orientation rework

Choose a tag to compare

@WebDevBarCoder WebDevBarCoder released this 01 Aug 11:40

The side-orientation rework. Match 1476 was recorded backwards - it stored a winner
that contradicted its own heroes - and this makes that defect unrepresentable rather
than fixed.

What changed

A match is now two canonically-sorted trios plus pointers, in both databases.
1476 happened because there were two independent side labels, match.outcome and
match_hero.side, and nothing forced them to agree. There is now one composition,
with winning_trio and blue_trio pointing into it. Which trio is "1" is a pure
function of the heroes, so two spectators who watched the same match with the panels
the other way round store it under the same numbers.

Orientation is resolved from the trios at record time - never from a banner, a tint,
a player name or a panel position - and resolved BEFORE anything is announced or
recorded. On refusal the trios and the winner are still stored, because those need no
orientation; only the draft-relative values are declined, and declined rather than
guessed.

Fixed

  • The stale carryover: after a draw or a timeout, the previous match's prediction
    and ratings were recorded against the next one.
  • 53 duplicate rows were counted twice in the model fit. 1547 decisive rows become
    1494.
  • The HIT/MISS line compared a draft-relative probability against a summary panel,
    so a mirrored match announced the inverted verdict.
  • Every odds sample was silently lost to a swallowed TypeError.

Migration

The local reshape runs automatically on launch and does the repair and the shape
change in one step - they cannot be sequenced by asking. Verified against a copy of
the operator's database: 1547 canonical, 3 unrepresentable, 0 unclassified, a snapshot
row for every match, and a second run byte-identical to the first.

342 local rows keep blue_trio NULL because the audit never covered them. 8% of
audited rows were mirrored, so guessing would be wrong about one row in twelve,
silently.

The server must be deployed and migrated before this build is used, and that
migration is irreversible. See docs/superpowers/plans/2026-08-01-side-orientation.md.

Full detail in CHANGELOG.md.

wdb-12.9.25-31

Choose a tag to compare

@WebDevBarCoder WebDevBarCoder released this 01 Aug 03:15

WebDevBar fork release 31, built from the webdevbar branch.

For the BlueStacks contributor

Everything from release 30 plus the fixes below. The two aimed at your log:

  • The overlay install no longer touches a package-manager property on your emulator.
    setprop pm.dexopt.install skip was a workaround for a measured Waydroid bug and was
    being issued on every platform. Your install died with Failure calling service package: Broken pipe (32) and BlueStacks froze. Detection is getprop ro.hardware, failing
    closed - an unrecognised device gets the ordinary Android install path. Verified on
    Waydroid: uninstall and reinstall both clean.
  • A sync rejection now names the field it rejected. [SC-33] sync server error 422
    logged only the status code and discarded the body. If your pushes are still failing,
    the next log says why in one line.

A [SC-82] device ro.hardware= line appears in the debug log, so the next report says
what the detection actually saw.

The live log now reads like a match

Six picks in draft order, the call, the bet, and the result:

BLUE 1: Aurora
RED 2: Thador
RED 3: Galahad
BLUE 4: Nara
BLUE 5: Lorsan
RED 6: Indris
BLUE 60% | RED 40%
BETTING BLUE
BLUE WINS
called blue 60% - blue won - HIT
  • The sixth pick is announced. It cannot be read from the draft screen - the game
    leaves it the instant that pick is made - so the log used to show five and jump to the
    odds.
  • The result appears at all. [SC-75] was on the hidden list under a comment about
    "the prediction, which the bubble is already showing", written before it carried the
    winner and the HIT/MISS line.
  • Screen transitions, the locked-picks summary, the hero count and the [SC-nn] codes
    move to the file. Everything is still in the session log.

Match identity

One match could occupy two rows: identity was outcome | sides | 10-minute bucket, so
mirroring a match changed every field, and a bucket splits at its boundaries. Identity is
now the two hero trios sorted, scoped by event, with the outcome out of it entirely.

Measured across 1,185 matches: 1,179 distinct identities, every repeat the same match
captured 1-16 seconds apart. Verified against production - a mirrored re-push of an
existing match returns duplicate and writes nothing.

Our own left/right labels were wrong 8% of the time

The summary screen's panel-to-side mapping flips; names and ratings do not. 73 of 909 rows
mirrored. Accuracy was understated as a result: corrected, the model reads 57.85% rather
than 55.97%.

Prevent Friendly Fire (off by default)

Skips opponents marked Friend or Guild Member in Arena and Supreme Arena, using two
independent signals - badge shape and OCR - either of which flags a card. Live-confirmed
on a real guild member and a real friend, with both signals agreeing independently.

wdb-12.9.25-30

Choose a tag to compare

@WebDevBarCoder WebDevBarCoder released this 01 Aug 02:35

WebDevBar fork release 30, built from the webdevbar branch.

For the BlueStacks contributor

Two fixes aimed directly at the problems in the debug log:

  • The overlay install no longer touches a package-manager property on your emulator.
    setprop pm.dexopt.install skip was a workaround for a measured Waydroid bug and was
    being issued on every platform. Your install died with Failure calling service package: Broken pipe (32) and BlueStacks froze. The log does not prove the property caused that,
    but there was no reason to be setting it on an emulator that never needed it. Detection
    is getprop ro.hardware, failing closed - an unrecognised device gets the ordinary
    Android install path. Nothing replaces it, because nothing else needs it.
  • A sync rejection now says which field it rejected. [SC-33] sync server error 422
    logged only the status code and threw away the body that names the failing field. If
    your pushes are still failing, the next log will say why in one line.

A [SC-82] device ro.hardware= line now appears in the debug log, so the next report says
what the detection actually saw.

Match identity

One match could occupy two rows. Identity was outcome | sides | 10-minute bucket, which
broke twice over: mirror a match and every field changes, and a bucket splits at its
boundaries - two captures nine seconds apart landed either side of a wall.

Identity is now the two hero trios, each sorted internally then against each other, scoped
by event. The outcome is not in it at all. Measured across 1,185 matches: 1,179 distinct
identities, and every repeat is the same match captured 1 to 16 seconds apart.

Existing databases are backfilled on first run. Without that the dedupe backstop would
recognise nothing and re-record matches it already had.

Our own left/right labels were wrong 8% of the time

The summary screen's panel-to-side mapping flips; player names and ratings do not. An
audit of every saved draft frame found 73 of 909 rows mirrored. That also means accuracy
was understated - corrected, the model reads 57.85% rather than 55.97%.

Prevent Friendly Fire (off by default)

Skips opponents marked Friend or Guild Member in Arena and Supreme Arena, using two
independent signals - badge shape and OCR - either of which flags a card. First live
session confirmed both agreeing on a real guild member and a real friend.

Release 30 fixes a packaged-build path bug that left the Refresh/X control unclassifiable,
and stops scanning card 3, which Arena never takes.

Also

  • Minimize to tray, off by default.
  • The live log reads as a summary; the trace stays in the debug log.

WDB 12.9.25-26 - the model survives the rotation

Choose a tag to compare

@WebDevBarCoder WebDevBarCoder released this 30 Jul 17:22

The model survives the theme rotation, and the log finally says whether it was right

Install this before 1 August if you are collecting. Flourishing Wilds closes and
Tactical Grounds opens with the same modifiers, and this build is what stops the model
throwing away everything it has learned at that boundary.

Themes that share modifiers are one population

Until now every rotation reset the hero model to nothing. That is correct when a theme
changes the roster and the battlefield - carrying strengths across the last rotation
measured 47% directional, worse than a coin. It is pure loss when the modifiers are
identical, which is the case here.

Tactical Grounds now opens with this theme's matches and heroes already behind it,
instead of sitting gated until it has collected 40 of its own.

The pooling happens when the model is fitted, not in the database. Every match stays
filed under the theme it was actually played in, one row each, so this is a switch rather
than a fusion - if the modifiers turn out to differ after all, the grouping comes out and
nothing has been lost. Converging Paths is deliberately excluded.

The live log now says whether the call was right

[SC-75] reads called blue 67% (r+h) - blue won - HIT, with the side in its own colour
and the verdict in green or grey. Before this the log named the winner of every match and
never said what had been predicted, so it reported the outcome of everything and the
accuracy of nothing.

The odds panel colours the favoured side, and only that side. A gated line is never
coloured - a gate is the model saying it does not know, and dressing that up as a call is
the one thing the gate exists to prevent.

A dead-even prediction is recorded as "no call" rather than graded, because 50/50 is the
model declining to choose.

Auto-bet

BETTING BLUE / BETTING RED is logged in colour once the handle has actually been
dragged, so the line means the tokens are committed rather than about to be. There is no
separate won/lost line: the stake always goes on the side the model called, so the HIT on
[SC-75] already is the bet result.

The slider offset cap is raised from 200px to 400px. The old cap had no recorded reason
and was never a physical limit. Note that the bar spans x=151..948 around a handle at 540,
so a 400px drag toward BLUE runs about 11px past the end of the bar and the game's
behaviour there is untested - and the token-per-pixel rate scales with your balance, so
the cap is a fixed distance, not a fixed stake.

Fixed

The coloured log shipped broken in 23 and printed raw <span class="sc-red"> tags on
screen. Every log message is escaped before it reaches the renderer, which is correct -
log lines carry device output and exception text - so an allowlist now re-permits exactly
four class names and nothing else. Verified against ten injection attempts.

Where the model actually stands

Unchanged, and honestly reported: it is selective rather than accurate. Below 56%
confidence it is worse than a coin. Above 58% it is right about two thirds of the time,
which is where the auto-bet default sits. Five rounds of measurement have now closed
calibration, band-evidence damping, the rating challenger, identification quality and the
fitted-intercept question - nothing has beaten regularised Bradley-Terry on hero identity.
Full detail in docs/solstice-clash/model-findings-ledger.md.

wdb-12.9.25-21

Choose a tag to compare

@WebDevBarCoder WebDevBarCoder released this 29 Jul 19:03

Fixes a defect that silently lost every match on an upgraded install

If your matches were failing with no such column: predicted_left, this is the fix -
and your collected data is preserved.

A shipped build never ran migrate.py, and the app hands back an existing database
untouched, so a database kept whatever schema first created it - permanently. Anyone who
installed before match.predicted_left existed had every match fail at the moment of
writing, and updating the app did not help, because nothing ever added the column. One
log showed 27 matches lost before anyone noticed.

The client now brings its own database up to date on startup, in place. Nothing to delete,
nothing to re-collect.

Also in this build

  • Hero-vs-hero records are queryable via a new hero_matchup view: one row per hero
    pair per theme, with wins, losses, tally and how many times the pair has actually met.
    Derived from the matches already stored, so it cannot drift out of step with them.
  • The log export tells you where it saved. There is no file picker - it writes to your
    Downloads folder - and previously nothing said so, while the app tried to reveal the
    file and prompted "open with..." instead. It now logs log exported to <path> and the
    log panel makes that clickable.

Notes

Three further defects were found and fixed while building the migration: a failed
migration leaking a locked database, migrating on every startup deadlocking against open
connections, and a version check that would have missed the affected databases entirely
(they carry a current-looking version and still lack the columns - it checks by column).

861 tests pass.

WDB 12.9.25-20 - a quieter log

Choose a tag to compare

@WebDevBarCoder WebDevBarCoder released this 29 Jul 03:33

Fork build on upstream 12.9.25.

A quieter log, and a full one on disk

The live view and the file want opposite things. The live view is read over a shoulder
while a draft runs, where every line that is merely true competes with the two or three
that are useful. The file is read afterwards, working out why a run went wrong, where the
line that explains it is usually one nobody would choose to watch.

Fifteen message types now go to the file only - crowd splits, spectator counts, ratings,
market and prediction records, read timings, the odds block's interval and rules - each
either already visible on the game screen or a measurement that only matters on the way
back through a log. Two are inverted rather than hidden: the device stream and the
row-count lines are worth seeing only when something is wrong.

The session file is truncated at startup, so it is always exactly one run - which is
what makes it worth attaching to a bug report unedited. A wdb log button beside export
saves it.

Theme windows are pooled

Themes rotate on a schedule the server is told about and a client is not. At the first
rotation every match - local and pushed - was filed under the event default, which is not
cosmetic: the model conditions on theme and now discards other themes' matches outright,
so a match filed under "unknown" is one no model will ever use.

GET /v1/themes serves the boundaries, every collection mode adopts them before recording
anything, and a self-heal pass re-files what had already gone wrong.

Four claims the code did not honour

Found by auditing for exactly that class, after two turned up in one evening:

  • [SC-58] locked picks screen was logged on both exits from the draft watch - including
    the timeout that had just reported the locked screen never appeared - and then read six
    cells off a draft frame as though they were locked.
  • {n}/6 picks locked was the count of heroes IDENTIFIED. On the locked screen all six
    are locked by definition, so one unreadable cell could gate a complete draft with
    "3/6 picks locked, need 4".
  • [SC-72] printed four numbers with four different scopes side by side.
  • Fit.matches counted rows the fit discards, and the display gate reads it to decide
    whether anything has been collected - so it claimed evidence the model never saw.

Also

  • The log now opens with both versions: App Version: 12.9.25 WDB Version: 12.9.25-20.
  • The odds bubble hides when the locked screen goes away rather than when the wait begins,
    so it stays up through the last-chance betting countdown.
  • A collection run no longer installs the overlay: absence is a decision, and the install
    and uninstall commands are how you make it.

WDB 12.9.25-19 - the odds appear in the game

Choose a tag to compare

@WebDevBarCoder WebDevBarCoder released this 29 Jul 02:26

Fork build on upstream 12.9.25.

The odds appear inside the game

A small rounded plate at the bottom of the screen shows the favoured side's probability
during a draft, so it can be read without looking at another window. Blue or red for which
side, one number, and nothing at all when neither side is favoured - inside the middle
band the model is right 50.2% of the time across 705 predictions, so "no favourite" and
"nothing worth showing" are the same condition. The plate appearing is itself the first
half of the signal.

Two new commands install and remove it. A collection run never installs it on its own:
absence is a decision, and a run that quietly restored something you deleted would be the
tool overriding you.

It sits below every band the automation reads and every point it taps, and it is detached
rather than blanked whenever it has nothing to say - the only state provably identical to
not having the overlay at all.

The odds themselves

  • The rating gap is now a measured step rather than a stated table. Nothing under 100
    points, then a flat edge beyond it. Over 95 rated matches that scored 7.6x its own
    standard error and won 23 of 25 splits, against the old nine-band table's 2.9x and
    18/25. Two findings: gaps under 100 are worth nothing, and past 100, more gap is not
    more edge.
  • Another theme's matches are discarded rather than discounted. Themes change the
    roster and the battlefield - a hero banned in one theme has no strength to carry into
    the next - so after a rotation the model starts from nothing and the display says so.
  • The crowd's betting split stays out, and the hero model stays at full strength.

Also

  • The log prints the fork's own version: App Version: 12.9.25 WDB Version: 12.9.25-19.
  • Draft screenshots can be kept, off by default, under a new WDB Modes setting - so a new
    idea about reading something off the draft can be tested against matches already
    collected instead of waiting weeks.

Notes for anyone else running this

The overlay APK is 9KB of plain Java and ships inside the app. On Waydroid the install
sets pm.dexopt.install=skip first, because its ahead-of-time compiler hangs for 570
seconds on a 4KB dex and wedges the package installer; with that set it installs in 25
seconds. Nothing needs configuring outside AdbAutoPlayer.

WDB 12.9.25-2 - the crowd is out

Choose a tag to compare

@WebDevBarCoder WebDevBarCoder released this 28 Jul 23:23

Fork build on upstream 12.9.25.

Solstice Clash odds: the crowd is out

The displayed number was reporting high confidence and getting it wrong. 54 scored
predictions made that measurable: it was right 27 times in 54, and scored worse than
always guessing the base rate.

The cause was not subtle. The crowd's betting split is flat across its own confidence,
scores 0.83 logloss standalone against a 0.69 constant, and is a noisy echo of the ladder
rating - the same pick 40 times in 51, and on the 11 disagreements the rating is right 8
and the crowd 3. At weight 0.70 it outvoted every signal that works and supplied nearly
all of the displayed spread.

  • W_CROWD 0.70 to 0.0. Zero, not negative: the fitted slope is indistinguishable from
    zero, so this is "stop paying for it", not "bet against it". Pools and spectator counts
    are still read and recorded, so it stays a weight to revisit.
  • W_HEROES 0.50 to 1.0. The hero model measured no edge at 245 matches and clears its
    bar at 340, in two rounds, on shuffle splits and walk-forward validation, in three
    independent implementations.
  • SIGMA_THETA 0.15 to 0.20, as the optimum drifts up with the corpus.

The block now labels itself ODDS from rating + heroes, naming only what actually moved
the number.

Also

  • Matches pool across themes within an event. The old cross-theme weighting would have
    dropped every collected match to a third of its weight at a theme rotation - starving
    the model at the moment it had the most data.
  • The theme is decided by its dated window alone; a screen read is a hint for backfilling
    and never decides.
  • Fixed a display gate that reported "0 matches for this theme" against hundreds
    collected, whenever a match's ratings OCR failed.

Everything measured, including the ~58 model configurations that lost, is recorded in
docs/solstice-clash/model-findings-ledger.md with its sample size and what would re-open
it.