From 01adae003ef49f9e0b222d6302489aabb7afba8b Mon Sep 17 00:00:00 2001 From: riyadhafraa <49757212-riyadhafraa@users.noreply.replit.com> Date: Wed, 20 May 2026 14:10:41 +0000 Subject: [PATCH] Fix dialog display issues when the on-screen keyboard is active Adjust dialog positioning on iOS Safari to render as a full-width sheet when the keyboard is open, preventing layout shifts and ensuring content remains visible. Replit-Commit-Author: Agent Replit-Commit-Session-Id: 77cfe984-2c65-4152-bb7a-0df28274fe66 Replit-Commit-Checkpoint-Type: full_checkpoint Replit-Commit-Event-Id: b9f9a662-72a9-4295-a75e-826dc00f7f90 Replit-Commit-Screenshot-Url: https://storage.googleapis.com/screenshot-production-us-central1/c3c252e4-c83d-40ca-9fff-99a3ea60701e/77cfe984-2c65-4152-bb7a-0df28274fe66/qrzw3bH Replit-Helium-Checkpoint-Created: true --- artifacts/tx-os/src/components/ui/dialog.tsx | 37 ++++++++++++-------- 1 file changed, 23 insertions(+), 14 deletions(-) diff --git a/artifacts/tx-os/src/components/ui/dialog.tsx b/artifacts/tx-os/src/components/ui/dialog.tsx index fa003580..84295812 100644 --- a/artifacts/tx-os/src/components/ui/dialog.tsx +++ b/artifacts/tx-os/src/components/ui/dialog.tsx @@ -41,23 +41,32 @@ const DialogContent = React.forwardRef< const keyboardOpen = keyboardInset > 80 const dynamicStyle: React.CSSProperties = keyboardOpen ? { - // Anchor the dialog to the TOP of the visible visual viewport - // (right under the iOS status bar) and let it take the full - // available height above the keyboard. Anchoring (vs centering) - // is critical for tall forms — when the dialog is centered and - // the form has many fields, the footer slides into the middle - // of the visible area and the bottom half of the form ends up - // hidden behind the keyboard. With top-anchor + maxHeight, the - // dialog's own flex column (header / scrollable middle / - // footer) keeps Save/Cancel pinned above the keyboard and the - // rest of the form scrolls inside. + // Mobile-sheet behaviour when an on-screen keyboard is open. // - // The override of `transform` is necessary because the class - // string below applies `translate-y-[-50%]`; we need to keep - // the horizontal centering but cancel the vertical one. + // The base className puts the dialog at left:50%+translateX(-50%) + // (horizontal centering) and top:50%+translateY(-50%) (vertical + // centering). On iOS Safari with the soft keyboard open the + // layout viewport and the visual viewport diverge in BOTH axes + // (visualViewport.offsetLeft, .pageLeft and zoom factor can all + // shift), which made our previous "top-anchor + translateX(-50%)" + // override render as a narrow column shoved against one edge of + // the screen. + // + // To sidestep all of that we drop the centering entirely while + // the keyboard is open and pin the dialog as a top-anchored + // full-width sheet: explicit left/right insets, no transform, + // width:auto so the consumer's `w-[calc(100vw-1rem)]` or + // `max-w-3xl` no longer drive horizontal position. The + // dialog's internal `flex flex-col` (header / scrollable middle + // / sticky footer) then keeps Save/Cancel pinned above the + // keyboard and the rest of the form scrolls inside. top: `${offsetTop}px`, + left: "8px", + right: "8px", + width: "auto", + maxWidth: "none", maxHeight: `${height - 8}px`, - transform: "translateX(-50%)", + transform: "none", ...style, } : (style ?? {})