# Component Contracts Every component below is implemented once for all locales, directions, and themes. Props are semantic; components do not fetch translations internally unless the architecture establishes a single typed content boundary. ## SiteHeader **Purpose:** Primary navigation, brand, locale/theme controls, login, demo CTA **States:** `default,scrolled` **Typed data:** `HeaderModel` **Copy namespace:** `header.*` **Responsive:** Desktop at >=1120; drawer trigger below **RTL:** Nav order reverses naturally; logo unchanged; directional icons selective **Accessibility:** Sticky; 44px targets; skip-link precedes it **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## MobileDrawer **Purpose:** Compact/medium navigation overlay **States:** `closed,open` **Typed data:** `DrawerModel` **Copy namespace:** `header.*` **Responsive:** Inline-start fixed drawer <=384px or 88vw **RTL:** Opens right in RTL **Accessibility:** Trap focus; inert background; Escape; focus return **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## LocaleSelector **Purpose:** Switch locale by stable route ID **States:** `closed,open,disabled` **Typed data:** `LocaleSelectorProps` **Copy namespace:** `language names` **Responsive:** Native select baseline **RTL:** Order EN/FR/AR; control follows document direction **Accessibility:** Labelled; current locale selected; preserves route/hash **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## ThemeSelector **Purpose:** Set Light/Dark/System preference **States:** `light,dark,system` **Typed data:** `ThemeSelectorProps` **Copy namespace:** `header.light/dark/system` **Responsive:** Native select or accessible segmented control **RTL:** No mirroring needed **Accessibility:** Cookie+storage; immediate; live system updates **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## HeroSection **Purpose:** Communicate category, promise, primary and secondary actions **States:** `default` **Typed data:** `HeroModel` **Copy namespace:** `hero.*` **Responsive:** 1 column <1120; 7/5 split wide **RTL:** Text aligns start; preview uses actual RTL rendering **Accessibility:** One h1; CTA order follows document direction **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## ProductPreview **Purpose:** Illustrative/evidence-governed product visual **States:** `illustrative,approved-capture` **Typed data:** `ProductPreviewModel` **Copy namespace:** `preview.*` **Responsive:** Simplify data table on compact **RTL:** Do not mirror screenshots; coded preview renders RTL **Accessibility:** Accessible caption; no false product claim **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## LifecycleProof **Purpose:** Show operational coverage without customer logos **States:** `default` **Typed data:** `LifecycleItem[]` **Copy namespace:** `trust.*` **Responsive:** 1/2/4 columns by available width **RTL:** Sequence follows reading direction **Accessibility:** List semantics; icons decorative **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## ComparisonSection **Purpose:** Fragmented versus connected workflow **States:** `default` **Typed data:** `ComparisonModel` **Copy namespace:** `comparison.*` **Responsive:** Stack compact; two columns medium+ **RTL:** Order follows locale reading direction **Accessibility:** Headings identify both columns; do not rely on color **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## WorkflowSteps **Purpose:** Four-step rental flow and tour source **States:** `default` **Typed data:** `WorkflowStep[]` **Copy namespace:** `workflow.*` **Responsive:** 1 column compact; 4 columns >=768 **RTL:** Step order follows reading direction **Accessibility:** Ordered list; numerals isolated if needed **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## RoleCards **Purpose:** Explain value by operating role **States:** `default` **Typed data:** `RoleCard[]` **Copy namespace:** `roles.*` **Responsive:** 1/2/4 columns content-driven **RTL:** Same tree; start alignment **Accessibility:** Heading hierarchy and readable card order **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## ModuleGrid **Purpose:** Describe approved product modules **States:** `default` **Typed data:** `ModuleCard[]` **Copy namespace:** `modules.*` **Responsive:** 1/2/3 columns **RTL:** Same tree; directional icons selective **Accessibility:** No capability beyond approved copy **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## MeasurementPlan **Purpose:** Show KPI definitions without invented outcomes **States:** `default` **Typed data:** `MetricDefinition[]` **Copy namespace:** `results.*` **Responsive:** Cards plus methodology block **RTL:** Same tree **Accessibility:** No unapproved numbers; ordered methodology **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## IntegrationCategories **Purpose:** Neutral category list **States:** `default` **Typed data:** `IntegrationCategory[]` **Copy namespace:** `integrations.*` **Responsive:** Cloud/list adapts without clipping **RTL:** Same tree **Accessibility:** No partner logos until verified **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## SecurityChecklist **Purpose:** Evidence-request checklist **States:** `default` **Typed data:** `SecurityCheck[]` **Copy namespace:** `security.*` **Responsive:** 1/2 columns **RTL:** Same tree **Accessibility:** No badges/certifications without approval **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## PricingPreview **Purpose:** Explain pricing factors and demo route **States:** `quote-only,approved-pricing` **Typed data:** `PricingModel` **Copy namespace:** `pricing.*` **Responsive:** Stack compact; 2 columns >=768 **RTL:** Same tree **Accessibility:** Never imply public price when absent **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## FAQAccordion **Purpose:** Localized questions and answers **States:** `closed,open` **Typed data:** `FaqItem[]` **Copy namespace:** `faq.*` **Responsive:** Single column **RTL:** Chevron mirrors only if it conveys expansion direction **Accessibility:** Native details baseline; keyboard and SR tested **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## FinalCTA **Purpose:** Final conversion block and approved secondary contact **States:** `default` **Typed data:** `FinalCtaModel` **Copy namespace:** `finalCta.*` **Responsive:** Stack compact; 2 columns >=768 **RTL:** CTA order follows document direction **Accessibility:** Secondary link suppressed until real destination approved **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## SiteFooter **Purpose:** Localized navigation, legal, evidence status internal only **States:** `default` **Typed data:** `FooterModel` **Copy namespace:** `footer.*` **Responsive:** Stack then grouped columns **RTL:** Same tree **Accessibility:** No public internal proof-status label **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## DemoDialog **Purpose:** Qualification form and submission states **States:** `idle,invalid,submitting,success,recoverable-error,terminal-error` **Typed data:** `DemoFormProps` **Copy namespace:** `form.*` **Responsive:** Modal max width; full-screen-safe compact **RTL:** Field order follows reading direction; emails isolated **Accessibility:** Focus trap, summary, inline errors, return focus **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant. ## ProductTourDialog **Purpose:** Four-step guided overview **States:** `step-1,step-2,step-3,step-4,complete` **Typed data:** `TourProps` **Copy namespace:** `tour.*` **Responsive:** Modal max width; compact-safe **RTL:** Back/next positions follow reading direction but meaning stays explicit **Accessibility:** Progress announced; focus moves to step heading **Content rule:** Block size is content-driven. Unsupported evidence suppresses the component or uses the explicitly approved neutral variant.