Warm ledger verification
Scope: the W10 acceptance record, amended with the shipped W11/W12/W13 dispositions and the W14 manual/device evidence for the Warm ledger UI review (#369, #392/#393). It records the pinned executable and later evidence heads, automated and manual evidence, the qualitative Material 3 audit, and every remaining limitation. It does not claim a signed Play release; #41 still owns that gate.
The code contract is ADR-0079; the screen/component descriptions are in ui.md; the contribution workflow is design-contribution.md.
Pinned candidate
| Item | Value |
|---|---|
| Source commit | 49153ee1bbe0a44a5d557664bf21525e74b287c2 (main after W09 18fa308 and #400 8b08a15, release 0.22.1) |
| Branch reviewed | ui-review/w10-final-evidence |
| Executable | debug APK from that commit, sha256 19224996bb769f063cda7cf5e7b20019ea14aec983d3ebadee189a0f32126c81 |
| Screenshot build | same debug APK installed on the pinned docs-shots AVD |
| Manual/device build | same debug APK on docs-shots (API 36); release behaviour is covered separately by the release smoke below |
The documentation and screenshot commits that followed the W10 executable were
docs-only at that point; the later W11 and W12 code commits are recorded in the
amendment below, not folded into this historical candidate.
Screenshots are debug-build captures with the deterministic DEBUG_SEED
fixture, not release screenshots. Release builds never include the fixture
receiver or the component gallery.
W14 acceptance candidate
W14 re-ran the remaining manual/device cases after the W13/#407 merge. It uses one executable and two device profiles; the automated gate logs are the W13 run at the same code tree.
| Item | Value |
|---|---|
| Source commit | 40120ace6110a78aff72bf80c62aff76c2ec9fb0 (W13 #407 merged via #410) |
| Debug APK | aa4cb8e66c56b08852dc268c7c06cad98724be5259d1637704cf8592fb7b7109 from ./gradlew assembleDebug (exit 0) |
| Phone device | docs-shots, pixel_7, API 36, 1080×2400 @ 420 dpi (411×914 dp); TalkBack 16.0.0.738667889; debug.force_rtl=1 retained from W11 |
| Foldable device | w14-fold, Pixel 9 Pro Fold profile, API 36 google_apis x86_64; inner 2076×2152 @ 390 dpi, cover 1080×2424 @ 390 dpi; posture list CLOSED/HALF_OPENED/OPENED |
| Evidence | /tmp/opencode/w14-evidence/ (run-local; not committed binaries) |
w14-fold was created from the installed SDK for this run:
avdmanager create avd -n w14-fold -k "system-images;android-36;google_apis;x86_64" -d pixel_9_pro_fold.
git diff b0cf303 40120ac is CHANGELOG.md only, so the retained W13 gate
logs exercise the same code and tests as the merged commit. All manual UI
actions used the T3 device_open agent-device command; adb was used only
for installs, logs, settings, display dumps and the TalkBack reboot.
W11/W12/W13/W14 amendment
The candidate table and gate log below are the historical W10 record at
49153ee. Later merged/shipped work changed Kotlin, tests and docs after it:
| Wave | Head | Scope | Evidence |
|---|---|---|---|
| W11 | 2917624 |
#405 signed-money direction (LTR money role in rows, day headers, Home statistics) | RtlMoneyPolicyTest, RtlSignedMoneyOrderTest; ADR-0079 amendment |
| W12 | cb5dcd2 (code/test/evidence head; a docs-only evidence commit follows on the PR branch) |
#406 measured whole-token Home statistics, measured section action and FAB-column clearance, plus the CI 320x640 viewport harness fix | HomeStatLayoutTest, HomeHeroCardTest, HomeLargeTextRegressionTest, SectionHeaderTest, ShellChromeTest; ADR-0088 |
| W13 | 40120ac (PR #410, merged 2026-11-03; branch head b0cf303) |
#407 measured 320x640 reset click delivery and repaired the three viewport assumptions in the existing editor/reset tests (test-only; production reset and picker code unchanged) | TransactionsContentTest#filteredEmptyOffersResetThatClearsQueryAndFiltersTogether, TransactionDetailScreenTest#dateFieldAnnouncesTheValueOnceAndNamesTheChangeAction, TransactionDetailScreenTest#datePickerOpensOnTheLoadedTransactionDate |
| W14 | evidence head 40120ac (no code change) |
#393 manual/device matrix: actual foldable postures, measured cutout geometry including the lock screen, TalkBack re-bind and speech attempt | docs/quality/warm-ledger-verification.md manual matrix; /tmp/opencode/w14-evidence/ |
The W12 local gate log is retained in /tmp/opencode/w12-evidence for this run
(run-local review artifacts, not committed binaries): the JVM/coverage/lint/
ktlint rerun and first-run flake note, docs/ui/supply-chain/QA-driver guard logs,
the native API 36 XML (938 cases, 0 failures), the forced 320x640 API 36 XML
(935 pass; only the three documented W08/W09/#407 editor-baseline cases fail),
the API 26 smoke XML (15 cases, 0 failures), the release smoke log/PNG/crash log
and the API 36 E2E journey/extras logs and captures.
CI at 9df87b0 failed 10 viewport-coordinate cases at 320x640/mdpi (8 Home
shell-containment, 2 SectionHeader clearance). The fix keeps the logical
411x914/320x568/411x500 viewports but scales the simulation density so they fit
the real physical px window, asserts the simulated viewport maps inside the
physical px bounds and that the root keeps its requested logical size, and
derives SectionHeader end/start expectations from the measured header root.
Focused red/green at 320x640 and native 411 is 14/14; the native 411 full suite
is 938/0. The forced local 320x640 full run leaves exactly the pre-existing
editor-baseline cases (#407: date field, date picker, filtered reset); those are
outside this change and are not among the 10 targeted failures. CI remains the
authoritative 320 lane.
W13 (#407) classified the three pre-existing editor-baseline failures with measured evidence instead of asserting they were harmless:
- Two different 320x640 configurations exist. CI creates AVD
testwith no hardware profile (320x640 px at 160 dpi; status bar 24 px + navigation bar 24 px). The local reproduction usedwm size 320x640 && wm density 160on the Pixel 9 Pro AVD, which keeps that profile's 52 px status bar and 24 px navigation bar — 28 dp less content height. The original three tests pass 3/3 on a locally created bare 320x640 profile (matching CI's 938/0 artifact) and fail 3/3 under the stricter Pixel override, so the override is a stress viewport rather than a CI clone. Both were made green. filteredEmptyOffersResetThatClearsQueryAndFiltersTogetherrenders the realTransactionsContentat a 320x640 dp root. AfterperformTextInput("xyz")the recovery column is taller than its result area, so Reset filters measured y 642..682 in a 640 dp root: clipped to zero bounds. The test'sperformClick()injected at that off-window point, the event was dropped, and the callbacks stayedquery="xyz",direction=null,category=1. Invoking the button'sSemanticsActions.OnClickfrom a fresh state, or dismissing the keyboard and scrolling first, cleared all three together, so the production reset was correct and the failure was the test's unstated "the action is on screen" assumption.- The two date tests place the editor in a 411 dp-wide box that the 320 dp
parent coerces to the window width, and assumed the Date & time row was
visible. At 320x640 the row measured y 573..637 below the editor body's scroll
viewport (the Save footer is a sibling, not an overlay), so
assertIsDisplayedfailed and the tap never reached the field (the date-picker test then looked for a dialog that never opened). Scrolling the real editor to the row (y 488..552) restores both the announcement assertion and the picker OK path (OK at x 276..334, partially clipped but clickable). - The fix is test-only: dismiss the search keyboard where it is up, scroll the existing scrollable owner before acting, and keep every behavioural assertion, including "query AND filters clear together" plus newly asserted chip visibility before and after the tap; no production state, control or layout changed.
The current tree declares 1395 JVM test declarations and 760 instrumented
test declarations at the time of this amendment. The first local JVM run at
5bc4d65 hit one unrelated flake in
TransactionDetailDraftRecoveryTest.delete_cleansNewlyStagedFilesAndReleasesReservations;
it passed alone and the full JVM/coverage/lint/ktlint rerun was green with no
source change. The W10 table's 1388/899 counts describe that historical candidate
only. Local API 37 remains under the standing before-app-assertion
infrastructure exception; CI API 37 is mandatory.
Automated evidence
All commands below were run locally at the pinned candidate unless noted.
Logs, JUnit XML and captures are retained in /tmp/opencode/w10-evidence/.
| Gate | Command | Result |
|---|---|---|
| JVM + coverage + lint + ktlint | cd android-app && ./gradlew test jacocoTestDebugUnitTestReport jacocoTestDebugUnitTestCoverage lint ktlintCheck |
1388 tests, 0 failures, 0 errors, 0 skipped; line coverage 45.83 % (4204/9174); BUILD SUCCESSFUL |
| UI guard | bash scripts/ui-guard.sh |
passes all rules and self-tests |
| Architecture guard | bash scripts/arch-guard.sh |
passes |
| Docs guard | bash scripts/docs-guard.sh |
passes links, paths, budgets, ADR parity, index/nav parity (124 Markdown files), version claims and count parity (62 production rules, 1388 JVM tests, 744 instrumented tests) |
| CI contract guards | test-ci-hygiene.sh, test-ci-smoke-matrix.sh, test-workflow-paths.sh, test-lint-config.sh |
pass |
| Site build | uvx zensical build (0.0.74) |
Build finished, no issues |
| Full instrumented, API 36 | ANDROID_SERIAL=emulator-5554 ./gradlew connectedDebugAndroidTest |
899 tests, 0 failures, 0 errors, 0 skipped; BUILD SUCCESSFUL in 18m29s |
| Minimum API smoke, API 26 | the four CI-critical classes from android-tests.yml |
15 tests, 0 failures, 0 errors, 0 skipped (emulator-5556, Android 8.0) |
| Release smoke | ANDROID_SERIAL=emulator-5558 bash scripts/release-smoke.sh |
assembleReleaseLocal R8 APK installed, launched, topResumedActivity and no FATAL EXCEPTION (debug-key signed); evidence release-smoke.png, release-crash.log |
| End-to-end QA journeys | python3 scripts/android_ui_qa.py onboarding/seed/journey/extras on API 36 |
pass; onboarding/seed/journey/extras reached journey-complete, extras-complete, capture dedupe and the PIN lifecycle; 66 settled captures retained |
| Focused W08/W09 editor baseline | 3 original editor tests at native size and forced 320x640/160 dpi | native 3/3 pass; forced 3/3 fail (date row/OK viewport assumptions; filtered reset tracked as #407) — see below; all three are green at both sizes after the W13 test-only repair |
Local API 37 is governed by the standing policy: it may be skipped only when
the pinned image fails before app assertions, with the exact head, image and
logs. No API 37 attempt was made at the W12 code head 5bc4d65 or final head
18085df; there is no exact-head attempt to claim. W13 did attempt the smoke
subset on its branch working tree (based on e04f575, before this evidence
commit) and the failure is again before any app assertion: the first install
attempt failed and a retry succeeded; two instrumentation runs then produced
testRunFailed with INSTRUMENTATION_ABORTED: System has crashed /
Instrumentation run failed due to Process crashed and zero executed
tests. The emulator exited during the run, and the retained boot log shows
cmd: Failure calling service activity: Broken pipe (32) while the system was
still starting. The exception rests on the inherited image/host diagnosis:
- Image
system-images;android-37.0;google_apis_playstore;x86_64(Pixel_9_Pro_API_37, API 37.0), emulator37.2.13.0build16740729. - W10 attempt/retry logs:
/tmp/opencode/w10-evidence/api37-smoke.log,api37-smoke-retry.log,api37-emulator.log; W11 logs:/tmp/opencode/w11-evidence/api37-smoke-final.log,api37-emulator-final.log. - Failure before any app assertion:
adb installreturnedcmd: Can't find service: package/activity; the W11 device then failed to listadditional_test_outputwithTransport endpoint is not connected. - The host, SDK image path/version, AVD definition and emulator binary are
unchanged from those attempts (
Linux alienware 7.3.1-pikaos, image revision 7, API 37.0, emulator37.2.13.0build16740729); W13 installed no new image or toolchain. CI API 37 remains mandatory and validates the exact PR head.
Material 3 audit (qualitative scores)
Scores are a qualitative reading of the shipped code and evidence; they are not pass/fail acceptance and do not replace the manual matrix below. Intentional Warm ledger choices count in the score; the score does not ask the app to adopt stock M3 fonts, radii or a spring-only motion system.
| Category | Score | Status | Evidence |
|---|---|---|---|
| Color tokens | 9/10 | pass | Semantic ColorScheme roles, one Warm palette owner in Color.kt, dynamic roles in Roles.kt; measured hero/dynamic pairs in HeroAccentContrastTest, HiddenRowContrastTest, BudgetContrastTest. Raw black/white remain only on the photographic viewer/cropper scrim (allowlisted). |
| Typography | 9/10 | pass | DM Sans + Newsreader roles in Type.kt, tabular money features, no money truncation; WarmLedgerContractTest and DesignSystemMatrixTest read laid-out text. Deliberate local sizes are documented exceptions. |
| Shape | 9/10 | pass | Named AppShape meanings over the 4/8/16/20/28 dp scale; fields, amount fields, grouping cards and chips compose one owner. |
| Elevation | 8/10 | pass | Tonal surfaceContainerLow grouping, one strong hero surface, no decorative shadows. Material dialogs keep their standard tonal elevation. |
| Components | 8/10 | pass | Material 3 composables plus shared ui/components/ owners; gallery inventory covers every shared control. One documented duplication remains: Activity builds an inline delete dialog instead of reusing TransactionDeleteConfirmDialog. |
| Layout | 8/10 | pass | Window-size-driven bar/rail, adaptive 1200/600 dp content width, 320 dp and short-height coverage. The 200 % Home hero now measures its labels/amounts into three, two or one whole-token columns and keeps View all clear of the FAB (W12 #406). |
| Navigation | 9/10 | pass | One NavHost, route table in ui.md, bounded scrolling compact bar and short-height rail with selection reveal, deep-link and back contracts tested. |
| Motion | 9/10 | pass | One Motion owner, one easing curve, animator-scale-aware transitions, no infinite decorative motion; reduced motion settles at scale 0. Material MotionScheme/Expressive spring APIs are not required by the pinned BOM. |
| Accessibility | 8/10 | pass | Named merged rows, 48 dp action targets, switch roles, live-region errors and measured contrast. Manual TalkBack focus rendering passed; W14 passed the foldable-posture case on an emulator AVD, while full explore-by-touch traversal and a visibly rendered cutout are still unavailable (recorded below). RTL money ordering is fixed by #405 (W11) and re-asserted in the W12 Home regression. |
| Theming | 9/10 | pass | Warm static light/dark, opt-in dynamic colour on Android 12+, system/light/dark modes, and a dynamic fallback for every role; verified in both themes and a wallpaper-derived scheme. |
Overall qualitative score: 86/100 (sum of the ten rows). The score is intentionally separate from the acceptance disposition: a high score cannot hide a failed or unrun mandatory manual case.
Priority finding dispositions
All twenty-two child findings (#370–#391) have a shipped disposition. The PR column is the merged wave that carried the fix; issue state is GitHub metadata, not evidence of a remaining code gap.
| Issue | Wave / PR | Disposition |
|---|---|---|
| #370 | W01 / #394 | Fixed: password semantics, masked PIN, digit-count state. Closed. |
| #371 | W01 / #394 | Fixed: remaining-attempt feedback. Closed. |
| #372 | W02 / #395 | Fixed: Save grows with large text. Closed. |
| #373 | W03 / #396 | Fixed: hidden rows keep readable roles and a Hidden pill. Closed. |
| #374 | W05 / #398 | Fixed: Reports selection survives tooltip/month changes. Closed. |
| #375 | W04 / #397 | Fixed: review-card money is detected metadata only. Closed. |
| #376 | W04 / #397 | Fixed: debug copy/export hidden in release builds. Closed. |
| #377 | W03 / #396 | Fixed: one named switch row per immediate setting. Closed. |
| #378 | W06 / #399 | Fixed: invalid remove-limit swipe suppressed. Closed. |
| #379 | W05 / #398 | Fixed: no budget marker without a configured limit. Closed. |
| #380 | W02 / #395 | Fixed: unified money/status presentation. Closed. |
| #381 | W05 / #398 | Fixed: quiet Home supporting surfaces and hierarchy. Closed. |
| #382 | W06 / #399 | Fixed: one named budget-card edit/set-limit action. Closed. |
| #383 | W07 / #401 | Fixed: read-only attachment opening and failure feedback. Closed. |
| #384 | W07 / #401 | Fixed: named viewer controls and typed coordinates. Closed. |
| #385 | W08 / #402 | Fixed: month grid, short-height rail and RTL reveal. Closed. |
| #386 | W03 / #396 | Fixed: Activity filters, row actions and locale dates. Closed. |
| #387 | W02 / #395 | Fixed: editor field shapes and responsive form. Closed. |
| #388 | W08 / #402 | Shipped in the merged wave (settings/category width, onboarding viewport, lock insets, hero contrast). The issue stayed open because its closing link did not fire; no code gap found. Recommend closing. |
| #389 | W08 / #402 | Shipped in the merged wave (Motion.NAV_REVEAL_MILLIS, density-independent shake). The issue stayed open because its closing link did not fire; no code gap found. Recommend closing. |
| #390 | W09 / #403 | Fixed: cross-screen regression matrix. Closed. |
| #391 | W09 / #403 | Shipped in the merged wave (existing unfiltered API 36 suite plus summarize-instrumented-results.sh). The issue stayed open because its closing link did not fire; no code gap found. Recommend closing. |
New findings raised by this final matrix (not silently absorbed into a closed issue):
| Finding | Severity | Disposition |
|---|---|---|
RTL money sign moves to the logical end (RM 500.00+) in rows, day headers and the hero. |
Medium (correctness/readability) | Fixed — W11 / #405 (merged 2917624): signed money roles pin the authored left-to-right order; RtlMoneyPolicyTest, RtlSignedMoneyOrderTest and the W12 Home regression assert glyph order/structure. |
| At 200 % text the Home hero stat labels wrap mid-word and the FAB can cover part of View all. | Low–Medium (visual) | Fixed — W12 / #406: measured whole-token 3/2/1-column reflow, a measured section action that stacks or keeps the shell FAB column clear, and HomeLargeTextRegressionTest bounds/touch/navigation coverage. #393's tracker state must not be read as acceptance: W14 closes the foldable-posture case, but the full TalkBack traversal and rendered-cutout cases remain outstanding. |
| Original W08/W09 filtered-empty reset fails under forced 320×640. | Medium (verification) | Fixed — W13 / #407, merged as #410 at 40120ac: measured the recovery action at y 642..682 in a 640 dp root, showed the un-scrolled click is dropped, and repaired the tests (reset: dismiss the keyboard then performScrollTo; date rows: performScrollTo); production reset verified on device. #393 remains unaccepted for full TalkBack traversal and a rendered cutout; W14 adds the foldable-posture pass. |
Manual and device acceptance
Device: pinned docs-shots AVD (pixel_7, API 36, build
google/sdk_gphone64_x86_64/emu64xa:16/BE2A.250530.026.F3/13894323:userdebug/dev-keys),
1080×2400 px, density 420 (411×914 dp), font scale 1.0, locale en-US, light
theme, gesture navigation, TalkBack 16.0.0.738667889 when enabled. Manual
actions used the T3 device tools; keyboard injection (where the device command
has no key-event primitive) is labelled. W14 added w14-fold (Pixel 9 Pro
Fold profile, API 36) for posture and cutout checks; its device metadata,
captured frames and a TalkBack log excerpt are in /tmp/opencode/w14-evidence/.
Automated tests are listed separately above.
| Case | Result | Evidence and exact limitation |
|---|---|---|
| TalkBack focus, speech and traversal | Partial (W14 re-check) | After a device reboot TalkBack bound (Service[label=TalkBack, feedbackType[FEEDBACK_SPOKEN, FEEDBACK_HAPTIC, FEEDBACK_AUDIBLE]…]) with touchExplorationEnabled=true and serviceHandlesDoubleTap=true; tb-bound-baseline.png shows the green focus ring on launch. A slow injected pan (gesture pan 300 500 0 500 2000) produced two GoogleTTSServiceImpl: Synthesis request for locale eng-USA TTS synthesis requests (talkback-log-excerpt.txt); the log proves synthesis/audio-focus activity, not audible output or the spoken text. A raw coordinate tap at the hero card left the ring on the banner (tb-tap-hero.png is byte-identical to the pre-tap tb-baseline.png), and a small pan over Review activated Review instead of exploring it (tb-pan-review.png). The device tools have no accessibility-focus injection and do not expose the spoken text, so full explore-by-touch/focus/action traversal is still unrun; no full pass is claimed. |
| Hardware keyboard + IME Next | Pass | D-pad/Tab focus reached the Budgets tab and Enter opened Budgets; the lock PIN was typed on the hardware keyboard (six dots rendered) and unlocked; the editor's IME Next moved focus from Amount to Merchant. |
| IME-open editor | Pass | Keyboard visible (Gboard, number input); Save transaction stayed fully visible above the keyboard and the form scrolled. Capture: ime-open-editor.png. |
| Display cutout | Partial (W14 re-check) | The foldable AVD exposes real framework cutouts: inner insets=Rect(0, 136 - 0, 0) with bounding top-right 1940..2076 × 0..136, cover insets=Rect(0, 152 - 0, 0) punch hole 484..596 × 20..152 (/tmp/opencode/w14-evidence/cutout-geometry.txt). App-lock content starts at y=386 (inner) / y=539 (cover), clear of both cutouts (07-open-lock.png, 08-closed-lock.png, JSON snapshots). The emulator framebuffer still does not paint the cutout black, so a rendered-cutout visual remains unverified; the lock still consumes system bars only and does not claim cutout avoidance (ADR-0087/0088). |
| Short landscape / short-height rail | Pass | 1280×320 dp (density 160): the rail scrolled to reveal Settings on selection; capture short-landscape-rail-scrolled.png and short-landscape-settings-rail.png. |
| Large text (200 %) | Pass (W12 re-check) | 411/320 dp: statistic labels and full amounts stay whole (two columns at 411, one at 320), and View all remains a 48 dp target clear of the FAB. fulltext-home-200.png is the W10 before capture; W12 manual captures and exact-viewport bounds are in the W12 evidence archive and HomeLargeTextRegressionTest. |
| Dynamic colour | Pass (dark captured) | Appearance > Dynamic color on, Dark selected: a wallpaper-derived blue scheme rendered on Home (dynamic-dark-home.png); static Warm light was restored afterwards. A dynamic-light capture was not retained; the role/contrast tests cover both dynamic schemes. |
| RTL | Pass (W11 #405) | debug.force_rtl=1 originally moved money signs to the logical end; the merged W11 money-direction role keeps +RM 500.00 authored. W12 re-asserts the role and labels/amounts in HomeLargeTextRegressionTest.rtlAtDoubleText...; the API 26 manual device kept an en-US runtime locale, so no new W12 RTL screenshot is claimed. |
| Reduced motion | Pass | settings animations off set all three scales to 0; the Activity tab settled immediately; the contract tests pin scale-0 behaviour. |
| Back / unsaved guard | Pass | System Back from an edited draft opened the shared Save / Discard / Keep editing dialog (back-unsaved-guard.png); Back from detail returns to the origin route. |
| Applicable foldable | Pass (W14, emulator) | w14-fold (Pixel 9 Pro Fold profile, API 36) accepted fold closed, fold half-open and fold open with hinge 0°/90°/180° and device states CLOSED/HALF_OPENED/OPENED (posture.log). Open (2076×2152) uses the rail and wide column; half-open keeps Home/Activity/Settings usable across the hinge plane (one blank frame during the window relaunch, no crash); closed (1080×2424) uses the bottom bar. 03-halfopen-home.png is the blank relaunch frame and 03-halfopen-home-retry.png is the settled capture described above. Captures 01-open-home.png…05-halfopen-settings.png; 06-open-settings.png is byte-identical to 05 because OPEN and HALF_OPENED use the same 2076×2152 window on this AVD, so it is not independent posture evidence. posture.log is a replay of the same pose sequence recorded after the captures (the 1080×2424 vs 2076×2152 frame sizes corroborate it). Limitation: emulator posture only; the app has no FoldingFeature/WindowLayoutInfo use, so hinge avoidance is not claimed. |
| External viewer opens | Pass | A saved text attachment opened in the system HTMLViewerActivity with the exact read-only content (external-viewer-html.png); Chrome's first-run setup was not a valid viewer path and was not counted. |
| External viewer return lock | Pass | Back from the viewer landed on the PIN lock screen (return-lock-from-htmlviewer.png); the PIN was then entered with the hardware keyboard. |
| Four-direction pan clamps | Pass | In-app receipt viewer at 225 %: right, left, up and down each reached its bound and disabled that control while the opposite direction stayed enabled. Captures viewer-pan-{right,left,up,down}-clamp.png. |
W08/W09 320 dp editor baseline
W09 recorded three temporary transaction-editor failures under a forced 320×640 / 160 dpi display override. This pass reproduces the original three methods, not an unrelated sibling test:
- Tests:
TransactionDetailScreenTest#dateFieldAnnouncesTheValueOnceAndNamesTheChangeAction,TransactionDetailScreenTest#datePickerOpensOnTheLoadedTransactionDate,TransactionsContentTest#filteredEmptyOffersResetThatClearsQueryAndFiltersTogether. - Native baseline on API 36: 3 tests, 0 failures (all three pass; retained XML editor-320-original-native.xml).
- Forced 320×640 / 160 dpi: 3 tests, 3 failures, 0 skipped (retained XML
editor-320-original-override.xml). The date row failed
assertIsDisplayed; the date picker failed to find its OK node; the original filtered-reset case failed withexpected:<[]> but was:<[xyz]>— the query remained after Reset filters. - Manual check at the same 320×640 viewport: the Date & time row is reachable after one scroll, the date picker opens, and OK is visible at the bottom (date-picker-320.png). That supports a test-viewport explanation for the two date cases only.
W13 disposition (#407). The filtered-reset case was measured, not assumed:
under the Pixel-profile 320×640 override the recovery action row measured
y 642..682 in a 640 dp root, so the test's un-scrolled click was injected
outside the window and dropped; the callbacks stayed query="xyz",
direction=null, category=1. Invoking the button's semantics action from a
fresh state, or dismissing the keyboard and scrolling first, cleared query
and both filters. The same original tests pass 3/3 on a bare 320×640/160 dpi
AVD profile (status bar 24 + navigation bar 24), which is what CI boots; the
Pixel override is 28 dp shorter and is the stricter reproduction. A manual
320×640 journey on a seeded API 36 device reproduced the filtered-empty screen
(query xyz, Expenses + Food chips) and its small scrollable recovery
viewport, scrolled to Reset filters, and the tap restored the 14-row month with the query and
both chips gone. The date row likewise sits below the editor body's scroll
viewport until scrolled. W13 repairs the three tests only (the reset test
dismisses the search keyboard and scrolls; the date tests scroll the editor
body; every behavioural assertion is kept);
production reset/picker code, layout, routes and money are unchanged. W13 gate
results on the branch based on e04f575: JVM 1395/0 with lint/ktlint/coverage
green, full API 36 938/0 at native 411x914, 938/0 on a bare CI-profile
320x640 AVD, and 938/0 at forced Pixel-profile 320x640, API 26 smoke 15/0,
release smoke pass, and E2E seed/journey/extras pass. The repair is merged as
410 at 40120ac; the retained W13 logs are in /tmp/opencode/w13-evidence/.
W14 is the evidence-only follow-up and leaves #393 open for the two remaining manual cases.
Screenshots and fixture metadata
Regenerated with the repository tooling:
bash scripts/generate_screenshots.sh
It built assembleDebug, booted the pinned docs-shots AVD (pixel_7, API 36,
1080×2400, 420 dpi → 411×914 dp, font 1.0, en-US, light, gesture navigation),
cleared only the debug package, launched the app, broadcast DEBUG_SEED,
entered SysUI demo mode and captured the 11 routes. The run finished with
done: 11 PNGs; each capture waited for a rendered, settled frame.
| File | sha256 |
|---|---|
budgets.png |
22787ade5834f506283644ec1bebdc5a7c64d918b492b27eed5e745893eed406 |
home.png |
a58b7cfc6b5bda2630ce2500641fe173a291b03f458b52742530574032a9cd89 |
onboarding.png |
56917afc97a9470d60dfa225988b4298bc1959142f757710f750ef8ba2d21977 |
reports.png |
af8a239eafd0dbba8f2af40e4f8c4749cd30636b913334d37cc0a6b78802193b |
review-queue.png |
3401f71d49827d80c68804c9ff4e46549fc7855564104c0ddcc0265046e6b8d0 |
security.png |
8b7ccd6d3369e39a7dde39da40e5bc207709e482b2df27ad679d9ce7c95ec1c8 |
settings.png |
d8f82fbbed90916e40c1b7d1ca65830ab8f287e65539fd6a0ac18042b66fffb9 |
transaction-detail.png |
5a01d7ff91a612034f1d8121b493c7158a61f7ff82a39cc22487395d09f5695f |
transactions.png |
9032c33a85be607439851e26e0a795d8f10cf0569c50d27513180d1128093538 |
troubleshooting.png |
3eebc1e5b6e9439ca8c6918f0f9532cb0eaa5292706040add7c75531e5645de4 |
unsaved-changes.png |
330df79c1dc5feb3aef4512163e90010ebdcf888a01ff45872169054304e6de1 |
The images are debug, seeded captures: home, transactions, budgets and
reports use the demo month; review-queue is the fixed two-row sample.
unsaved-changes and transaction-detail contain a focused text field, so
their pixels are not byte-stable between runs. Recordings were not regenerated;
the tour clips remain historical until the recording workflow runs on a host
with ffmpeg and the pinned AVD.
Remaining limitations and #41 handoff
- #393 is not accepted by this pass. W14 closed the foldable-posture gap on an actual foldable AVD, measured the real cutout geometry (including the lock screen) and re-bound TalkBack with observed TTS synthesis requests; the remaining mandatory gaps are a full TalkBack explore-by-touch/focus/action traversal and a visually rendered cutout. #393 therefore stays open for those two items and the #41 handoff must not treat it as accepted.
- RTL money signs were fixed by W11 (
2917624, #405); the W12 Home regression re-asserts the money role. - 200 % Home was fixed by W12 (#406): whole-token statistic columns and a FAB-safe View all action. The full TalkBack traversal and rendered-cutout cases still block #393 acceptance.
- 320 dp filtered reset (#407) was fixed by W13 as a test-harness defect
and merged as #410 at
40120ac: the three affected tests now scroll their existing scrollable owner before acting at 320×640, with every behaviour assertion retained. Production reset, date-picker and editor code did not change. - TalkBack: W14 rebound the service after a reboot and observed
touchExplorationEnabled=true, a launch focus ring and real en-US TTS synthesis from a slow injected pan; injected taps still did not drive a reproducible explore-by-touch focus sequence and the spoken text is not exposed by the device tools. A human/physical-device traversal remains the gate. - Cutout / foldable: W14 passed the foldable posture cases on
w14-fold(CLOSED/HALF_OPENED/OPENED; rail vs bottom bar; lock captured). The cutout remains partial: the foldable's framework cutout is real and the lock content clears it, but the emulator framebuffer does not paint the notch, so a rendered-cutout visual needs a physical device. - Release: the release smoke proves the minified APK installs, launches, resumes and does not crash; it does not prove signed-Play, 16 KB, pre-launch, soak or production gates. Those remain #41's scope.