MenuClose

Block Banner — React Page Block

Announcement banner: a slim accent-tinted strip for one important message with an optional action. Dismissible for real — labeled button, Escape works, onDismiss persists the choice.

View source
PreviewReact
Starting live preview

Usage

import { BlockBanner } from "@/components/BlockBanner";

export function Announce() {
  return (
    <BlockBanner
      message="Orbit 2.4 is rolling out this week — release replays for every plan."
      action={{ label: "Read the changelog", href: "/changelog" }}
      onDismiss={() => localStorage.setItem("banner-dismissed", "1")}
      {...{
        message: "Orbit 2.4 is rolling out this week — release replays for every plan. (demo)",
        sticky: true,
        accent: "#d5ed9a",
        scheme: "dark"
      }}
    />
  );
}
Implementation notes & API

Purpose: announcement banner. Copy it, ship it — every string, link and color arrives through props. Runtime: pure DOM + CSS. No WebGPU, canvas, animation library or external assets; SSR-safe on first render. Theming: root custom properties (--vb-bg, --vb-fg, --vb-accent, --vb-border, --vb-radius, --vb-container) or the accent/scheme/className/style props. scheme flips the dark default to light. Guardrails: responsive via container queries down to 320px; interactive behavior degrades on touch; prefers-reduced-motion drops entrance/scroll motion while content stays complete. Sticky banners overlay the top of the viewport; set sticky={false} for an in-flow strip. Escape dismisses while focus is inside.

PropertyTypeNotes / default
messageReactNodeThe one important thing
action{ label, href? , onClick? } | nullOptional inline action
dismissible / dismissLabel / onDismissboolean / string / () => voidDismiss control; persist the choice yourself
stickybooleantrue; false keeps the strip inline in flow
regionLabelstringLandmark label, "Announcement" by default
scheme"dark" | "light"dark
accentstring (hex)Sets --vb-accent for the whole block
className / stylestring / CSSPropertiesApplied to the section root
childrenReactNodeReplaces the default content entirely
View source on GitHubFree for commercial projects · MIT