diff --git a/packages/views/onboarding/components/step-shell.test.tsx b/packages/views/onboarding/components/step-shell.test.tsx index c991182026..f42f7db4ca 100644 --- a/packages/views/onboarding/components/step-shell.test.tsx +++ b/packages/views/onboarding/components/step-shell.test.tsx @@ -8,6 +8,7 @@ import { STEP_COLUMN, STEP_FRAME, STEP_GUTTER, + STEP_MEASURE, StepShellHeader, } from "./step-shell"; @@ -56,6 +57,15 @@ describe("onboarding step shell", () => { expect(STEP_BLOCK_PADDING).toMatch(/^py-/); }); + // STEP_MEASURE caps prose and form fields inside a step that sits on the + // frame. It must NOT centre: centring it would pull the content off the + // frame's left edge, which is the alignment the frame exists to provide. + it("keeps the in-frame reading measure left-aligned and padding-free", () => { + expect(STEP_MEASURE).toMatch(/max-w-\[\d+px\]/); + expect(STEP_MEASURE).not.toContain("mx-auto"); + expect(STEP_MEASURE).not.toMatch(/\bp[xlr]?-/); + }); + it("renders Back only when the step can go back", () => { const { unmount } = renderHeader({ currentStep: "workspace" }); expect(screen.queryByRole("button", { name: /back/i })).toBeNull(); diff --git a/packages/views/onboarding/components/step-shell.tsx b/packages/views/onboarding/components/step-shell.tsx index 37c59bfb95..f48f4a461f 100644 --- a/packages/views/onboarding/components/step-shell.tsx +++ b/packages/views/onboarding/components/step-shell.tsx @@ -22,15 +22,24 @@ import type { OnboardingStep } from "@multica/core/onboarding"; * - STEP_FRAME is the persistent chrome measure. Back and the step * indicator sit on it, identically, on every step, so the one element * that survives every transition never moves. - * - STEP_COLUMN is the reading measure for prose and forms. A step may use - * the frame instead when its content genuinely needs the width (the - * questionnaire's option grid does); both are centred, so the content - * stays on the frame's centreline either way. + * - STEP_COLUMN is the reading measure for prose and forms, centred. A step + * may use the frame instead when its content needs the width (the + * questionnaire's option grid, the runtime list) and cap its own prose + * with STEP_MEASURE; both are centred, so content stays on the frame's + * centreline either way. */ export const STEP_GUTTER = "px-6 sm:px-10 md:px-14 lg:px-16"; export const STEP_FRAME = "mx-auto w-full max-w-[920px]"; export const STEP_COLUMN = "mx-auto w-full max-w-[620px]"; +/** + * Reading measure applied INSIDE the frame, left-aligned rather than centred. + * Use it for prose and form fields on a step that sits on STEP_FRAME: the + * page margins then match every other step, while a workspace name still gets + * an input someone would want to type into instead of an 800px one. + */ +export const STEP_MEASURE = "max-w-[620px]"; + /** Vertical rhythm shared by every step's scrolling region. */ export const STEP_BLOCK_PADDING = "py-10"; diff --git a/packages/views/onboarding/steps/step-workspace.tsx b/packages/views/onboarding/steps/step-workspace.tsx index cb11b6173f..ce4da9366a 100644 --- a/packages/views/onboarding/steps/step-workspace.tsx +++ b/packages/views/onboarding/steps/step-workspace.tsx @@ -18,7 +18,8 @@ import { DragStrip } from "@multica/views/platform"; import { useLogout } from "../../auth"; import { STEP_BLOCK_PADDING, - STEP_COLUMN, + STEP_FRAME, + STEP_MEASURE, STEP_GUTTER, StepShellHeader, } from "../components/step-shell"; @@ -309,7 +310,7 @@ export function StepWorkspace({ style={fadeStyle} className={cn("min-h-0 flex-1 overflow-y-auto", STEP_GUTTER)} > -
+
{reusing ? workspaceCreationAllowed @@ -328,7 +329,7 @@ export function StepWorkspace({ ? t(($) => $.step_workspace.headline_first) : t(($) => $.step_workspace.creation_disabled_headline)} -

+

{reusing ? workspaceCreationAllowed ? t(($) => $.step_workspace.lede_resume) @@ -338,7 +339,7 @@ export function StepWorkspace({ : t(($) => $.step_workspace.creation_disabled_lede)}

-
+
{reusing ? (