From 109b671a320cf9b864be8bc0aae3c1244ad40b47 Mon Sep 17 00:00:00 2001 From: jvsena42 Date: Mon, 19 Oct 2026 08:50:37 -0300 Subject: [PATCH 1/4] fix: keep sheet buttons above the navigation bar Co-Authored-By: Claude Opus 5.5 --- .../subscriptions/SubscriptionsScreen.kt | 2 +- .../to/bitkit/ui/sheets/ForgotPinSheet.kt | 2 + changelog.d/next/1572.fixed.md | 1 + .../security/forgot-pin-nav-bar-inset.xml | 44 +++++++++++++++++++ 4 files changed, 48 insertions(+), 1 deletion(-) create mode 100644 changelog.d/next/1572.fixed.md create mode 100644 journeys/security/forgot-pin-nav-bar-inset.xml diff --git a/app/src/main/java/to/bitkit/ui/screens/subscriptions/SubscriptionsScreen.kt b/app/src/main/java/to/bitkit/ui/screens/subscriptions/SubscriptionsScreen.kt index 52049e6860..3093c21240 100644 --- a/app/src/main/java/to/bitkit/ui/screens/subscriptions/SubscriptionsScreen.kt +++ b/app/src/main/java/to/bitkit/ui/screens/subscriptions/SubscriptionsScreen.kt @@ -683,7 +683,7 @@ fun SubscriptionSheet(appViewModel: AppViewModel, initialRoute: SubscriptionRout .gradientBackground(startColor = Colors.Gray6, endColor = Colors.Black) ) { if (subscription == null) { - Column(Modifier.fillMaxSize().padding(horizontal = 16.dp)) { + Column(Modifier.fillMaxSize().navigationBarsPadding().padding(horizontal = 16.dp)) { SheetTopBar(titleText = stringResource(R.string.subscriptions__subscription)) FillHeight() BodyM(stringResource(R.string.subscriptions__unavailable), color = Colors.White64) diff --git a/app/src/main/java/to/bitkit/ui/sheets/ForgotPinSheet.kt b/app/src/main/java/to/bitkit/ui/sheets/ForgotPinSheet.kt index bb6f60f1a2..8528c72fcf 100644 --- a/app/src/main/java/to/bitkit/ui/sheets/ForgotPinSheet.kt +++ b/app/src/main/java/to/bitkit/ui/sheets/ForgotPinSheet.kt @@ -3,6 +3,7 @@ package to.bitkit.ui.sheets import androidx.compose.foundation.Image import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.navigationBarsPadding import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.width import androidx.compose.material3.ExperimentalMaterial3Api @@ -56,6 +57,7 @@ private fun Content( .fillMaxWidth() .sheetHeight(isModal = true) .gradientBackground() + .navigationBarsPadding() .padding(horizontal = 16.dp) ) { SheetTopBar( diff --git a/changelog.d/next/1572.fixed.md b/changelog.d/next/1572.fixed.md new file mode 100644 index 0000000000..ff345eb71c --- /dev/null +++ b/changelog.d/next/1572.fixed.md @@ -0,0 +1 @@ +The Forgot PIN and unavailable subscription sheets now keep their buttons above the navigation bar. diff --git a/journeys/security/forgot-pin-nav-bar-inset.xml b/journeys/security/forgot-pin-nav-bar-inset.xml new file mode 100644 index 0000000000..1f06a7cc89 --- /dev/null +++ b/journeys/security/forgot-pin-nav-bar-inset.xml @@ -0,0 +1,44 @@ + + + The "Forgot PIN?" sheet keeps its "Reset (Requires Recovery Phrase)" button above the + navigation bar. The sheet host applies no bottom inset, so the sheet content has to; without it + the button sits under the gesture handle on devices with gesture navigation. + + Precondition: onboarded dev wallet with gesture navigation enabled on the device and the PIN + disabled (Settings ▸ Security ▸ PIN Code shows "Disabled"), no biometrics enrolled on the + device. Start on the wallet home screen. The journey enables a PIN you choose and disables it + again at the end, so remember it. Enter a wrong PIN exactly once: exhausting attempts leads to + the forgot-PIN wallet reset, and never tap the Reset button. + + Read the navigation-bar top edge from the NavigationBar window frame in + `adb shell dumpsys window windows`, or from the bottom of the screen minus the navigation-bar + inset. The Reset button carries no tag; find it in `android layout` by its text. On iOS, compare + the button frame from `snapshot-ui` against the home indicator safe area instead. + + + Tap the menu button (tag "HeaderMenu") and tap Settings (tag "DrawerSettings") + Tap the Security tab (tag "Tab-security") + Tap PIN Code (tag "PINCode") + Tap Enable PIN (tag "EnablePin") + Enter a 4-digit PIN with the number pad (tags "N0"–"N9") + Re-enter the same 4-digit PIN to confirm it + On the biometrics screen, tap Skip (tag "SkipButton") + Tap OK (tag "OK") + Run adb shell input keyevent KEYCODE_HOME and wait 3 seconds + Run adb shell am start -n to.bitkit.dev/to.bitkit.ui.MainActivity + Verify the PIN pad is visible (testTag "PinPad") + Enter one wrong 4-digit PIN + Verify the attempts text (tag "AttemptsRemaining") reads "... attempts remaining. Forgot your PIN?" + Tap the attempts text (tag "AttemptsRemaining") + Verify the "Forgot PIN?" sheet is visible (tag "ForgotPIN") + Verify the bottom bound of the "Reset (Requires Recovery Phrase)" button is above the navigation-bar top edge + Take a screenshot and verify the gesture handle does not overlap the Reset button + Press back and verify the PIN pad is visible again (testTag "PinPad") + Enter the PIN chosen above and verify the wallet home screen is visible (testTag "Send") + Tap the menu button (tag "HeaderMenu") and tap Settings (tag "DrawerSettings") + Tap the Security tab (tag "Tab-security") + Tap PIN Code (tag "PINCode") + Tap Disable PIN (tag "DisablePin") and enter the PIN chosen above on the disable sheet (tag "DisablePIN") + Verify the PIN Code row (tag "PINCode") shows "Disabled" + + From 5eb5435a992b358d94c34175ebf9136683682c0a Mon Sep 17 00:00:00 2001 From: jvsena42 Date: Mon, 19 Oct 2026 09:13:20 -0300 Subject: [PATCH 2/4] test: match forgot pin journey to on-device tags Co-Authored-By: Claude Opus 5.5 --- journeys/security/forgot-pin-nav-bar-inset.xml | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/journeys/security/forgot-pin-nav-bar-inset.xml b/journeys/security/forgot-pin-nav-bar-inset.xml index 1f06a7cc89..7c56f86daf 100644 --- a/journeys/security/forgot-pin-nav-bar-inset.xml +++ b/journeys/security/forgot-pin-nav-bar-inset.xml @@ -10,9 +10,10 @@ again at the end, so remember it. Enter a wrong PIN exactly once: exhausting attempts leads to the forgot-PIN wallet reset, and never tap the Reset button. - Read the navigation-bar top edge from the NavigationBar window frame in - `adb shell dumpsys window windows`, or from the bottom of the screen minus the navigation-bar - inset. The Reset button carries no tag; find it in `android layout` by its text. On iOS, compare + The navigation-bar top edge is the screen height (`adb shell wm size`) minus the bottom + `navigationBars` inset that `adb shell dumpsys window windows` reports. `android layout` gives + the Reset button no bounds and no tag, so read its bounds from `adb shell uiautomator dump`. With + no biometrics enrolled, the biometrics Skip button exposes only its text. On iOS, compare the button frame from `snapshot-ui` against the home indicator safe area instead. @@ -22,23 +23,23 @@ Tap Enable PIN (tag "EnablePin") Enter a 4-digit PIN with the number pad (tags "N0"–"N9") Re-enter the same 4-digit PIN to confirm it - On the biometrics screen, tap Skip (tag "SkipButton") + On the biometrics screen, tap Skip Tap OK (tag "OK") Run adb shell input keyevent KEYCODE_HOME and wait 3 seconds Run adb shell am start -n to.bitkit.dev/to.bitkit.ui.MainActivity - Verify the PIN pad is visible (testTag "PinPad") + Verify the PIN pad is visible with the text "Please enter your PIN code" and keys (tag "N1") Enter one wrong 4-digit PIN Verify the attempts text (tag "AttemptsRemaining") reads "... attempts remaining. Forgot your PIN?" Tap the attempts text (tag "AttemptsRemaining") Verify the "Forgot PIN?" sheet is visible (tag "ForgotPIN") - Verify the bottom bound of the "Reset (Requires Recovery Phrase)" button is above the navigation-bar top edge + Verify from `adb shell uiautomator dump` that the bottom bound of the "Reset (Requires Recovery Phrase)" button is above the navigation-bar top edge Take a screenshot and verify the gesture handle does not overlap the Reset button - Press back and verify the PIN pad is visible again (testTag "PinPad") + Press back and verify the PIN pad is visible again with keys (tag "N1") Enter the PIN chosen above and verify the wallet home screen is visible (testTag "Send") Tap the menu button (tag "HeaderMenu") and tap Settings (tag "DrawerSettings") Tap the Security tab (tag "Tab-security") Tap PIN Code (tag "PINCode") - Tap Disable PIN (tag "DisablePin") and enter the PIN chosen above on the disable sheet (tag "DisablePIN") + Tap Disable PIN (tag "DisablePin") and enter the PIN chosen above on the "Disable PIN" screen Verify the PIN Code row (tag "PINCode") shows "Disabled" From 965d98fb45612ffa67aac6fc8c42fe75c8bd83b0 Mon Sep 17 00:00:00 2001 From: jvsena42 Date: Mon, 19 Oct 2026 09:17:42 -0300 Subject: [PATCH 3/4] docs: mark forgot pin inset journey android-only Co-Authored-By: Claude Opus 5.5 --- journeys/README.md | 1 + journeys/security/forgot-pin-nav-bar-inset.xml | 4 ++-- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/journeys/README.md b/journeys/README.md index 78347624e5..79e69fd2aa 100644 --- a/journeys/README.md +++ b/journeys/README.md @@ -171,6 +171,7 @@ Known differences in the corpus, as of the iOS port (synonymdev/bitkit-ios#691): | `transfers/closed-channel-transfer-settles.xml` | not ported — the closed-channel and order-closure settle rules are an iOS follow-up | | `onchain-receive/*` | port pending in synonymdev/bitkit-ios#588, which wires `onchainTransactionConfirmed` into the same received-sheet flow but carries no `journeys/` files. Two adaptations when it lands: iOS suppresses replayed historical receives with a `pendingRestoreActivitySeen` flag cleared by the first post-restore on-chain sync, not the one-hour block-timestamp guard used here, so a stale-confirmation step has to drive a restore instead of a clock; and iOS has no foreground-service path, so `confirmed-only-background-notification.xml` has no counterpart | | `backup/show-mnemonic-long-words.xml` | not ported — the long-word fit is an Android-only change (synonymdev/bitkit-android#633); whether iOS wraps long words at larger text sizes is unchecked | +| `security/forgot-pin-nav-bar-inset.xml` | not ported — Android-only fix (synonymdev/bitkit-android#1572): the Android sheet host adds no navigation-bar inset, so each sheet screen pads itself. iOS sheets keep their content inside the bottom safe area | | `deeplinks/pubky-contact.xml` | ported — same contact routing and unlock behavior | | `pubky-auth/signin-cold-start.xml` | `pubky-auth/open-signin-link.xml`, adapted — iOS opens the same sign-in link on a terminated app through `bitkit://pubky-auth/signin`. Android only: the raw `pubkyauth` scheme, the "Loading Your Pubky Profile" toast while the session restores, and Authorize through to `PubkyAuthOK` | | `pubky-auth/signin-with-second-link.xml` | not ported — iOS still drops a pending sign-in link when a second link opens on the PIN screen (synonymdev/bitkit-ios#985); port it with that fix | diff --git a/journeys/security/forgot-pin-nav-bar-inset.xml b/journeys/security/forgot-pin-nav-bar-inset.xml index 7c56f86daf..2ea0c20b72 100644 --- a/journeys/security/forgot-pin-nav-bar-inset.xml +++ b/journeys/security/forgot-pin-nav-bar-inset.xml @@ -13,8 +13,8 @@ The navigation-bar top edge is the screen height (`adb shell wm size`) minus the bottom `navigationBars` inset that `adb shell dumpsys window windows` reports. `android layout` gives the Reset button no bounds and no tag, so read its bounds from `adb shell uiautomator dump`. With - no biometrics enrolled, the biometrics Skip button exposes only its text. On iOS, compare - the button frame from `snapshot-ui` against the home indicator safe area instead. + no biometrics enrolled, the biometrics Skip button exposes only its text. Android only; see the + cross-platform table in `journeys/README.md`. Tap the menu button (tag "HeaderMenu") and tap Settings (tag "DrawerSettings") From c61445b1997620bb801125d120208904a77db598 Mon Sep 17 00:00:00 2001 From: jvsena42 Date: Mon, 19 Oct 2026 09:25:08 -0300 Subject: [PATCH 4/4] test: return home before locking in forgot pin journey Co-Authored-By: Claude Opus 5.5 --- journeys/security/forgot-pin-nav-bar-inset.xml | 1 + 1 file changed, 1 insertion(+) diff --git a/journeys/security/forgot-pin-nav-bar-inset.xml b/journeys/security/forgot-pin-nav-bar-inset.xml index 2ea0c20b72..d8e3ae86c6 100644 --- a/journeys/security/forgot-pin-nav-bar-inset.xml +++ b/journeys/security/forgot-pin-nav-bar-inset.xml @@ -25,6 +25,7 @@ Re-enter the same 4-digit PIN to confirm it On the biometrics screen, tap Skip Tap OK (tag "OK") + Press back until the wallet home screen is visible (testTag "Send") Run adb shell input keyevent KEYCODE_HOME and wait 3 seconds Run adb shell am start -n to.bitkit.dev/to.bitkit.ui.MainActivity Verify the PIN pad is visible with the text "Please enter your PIN code" and keys (tag "N1")