@openwarelabs/blocks 0.0.0-stage → 0.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +45 -2
- package/dist/heroes/Hero01/Hero01.d.cts +3 -0
- package/dist/heroes/Hero01/Hero01.d.ts +3 -0
- package/dist/heroes/Hero01/Hero01.types.d.cts +18 -0
- package/dist/heroes/Hero01/Hero01.types.d.ts +18 -0
- package/dist/heroes/Hero02/Hero02.d.cts +3 -0
- package/dist/heroes/Hero02/Hero02.d.ts +3 -0
- package/dist/heroes/Hero02/Hero02.types.d.cts +18 -0
- package/dist/heroes/Hero02/Hero02.types.d.ts +18 -0
- package/dist/heroes/Hero03/Hero03.d.cts +3 -0
- package/dist/heroes/Hero03/Hero03.d.ts +3 -0
- package/dist/heroes/Hero03/Hero03.types.d.cts +40 -0
- package/dist/heroes/Hero03/Hero03.types.d.ts +40 -0
- package/dist/heroes/Hero04/Hero04.d.cts +3 -0
- package/dist/heroes/Hero04/Hero04.d.ts +3 -0
- package/dist/heroes/Hero04/Hero04.types.d.cts +21 -0
- package/dist/heroes/Hero04/Hero04.types.d.ts +21 -0
- package/dist/heroes/Hero05/Hero05.d.cts +3 -0
- package/dist/heroes/Hero05/Hero05.d.ts +3 -0
- package/dist/heroes/Hero05/Hero05.types.d.cts +24 -0
- package/dist/heroes/Hero05/Hero05.types.d.ts +24 -0
- package/dist/heroes/Hero06/Hero06.d.cts +3 -0
- package/dist/heroes/Hero06/Hero06.d.ts +3 -0
- package/dist/heroes/Hero06/Hero06.types.d.cts +37 -0
- package/dist/heroes/Hero06/Hero06.types.d.ts +37 -0
- package/dist/index.cjs +370 -0
- package/dist/index.cjs.map +7 -0
- package/dist/index.d.cts +13 -0
- package/dist/index.d.ts +13 -0
- package/dist/index.js +347 -0
- package/dist/index.js.map +7 -0
- package/dist/shared/BlockActions.d.cts +5 -0
- package/dist/shared/BlockActions.d.ts +5 -0
- package/dist/shared/icons.d.cts +4 -0
- package/dist/shared/icons.d.ts +4 -0
- package/dist/shared/shared.types.d.cts +38 -0
- package/dist/shared/shared.types.d.ts +38 -0
- package/dist/styles.css +569 -0
- package/package.json +55 -4
package/README.md
CHANGED
|
@@ -1,3 +1,46 @@
|
|
|
1
|
-
#
|
|
1
|
+
# Openware UI blocks
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
Whole page sections built from [Openware UI](https://github.com/openwarelabs/ui) (`@openwarelabs/ui`), as React components that take their content as props. Drop one in, pass your words, actions and screenshots, and it follows the theme, the brand colour and every screen width.
|
|
4
|
+
|
|
5
|
+
```sh
|
|
6
|
+
npm install @openwarelabs/ui @openwarelabs/blocks
|
|
7
|
+
```
|
|
8
|
+
|
|
9
|
+
```tsx
|
|
10
|
+
import "@openwarelabs/ui/fonts.css";
|
|
11
|
+
import "@openwarelabs/ui/styles.css";
|
|
12
|
+
import "@openwarelabs/blocks/styles.css"; // after the library's
|
|
13
|
+
|
|
14
|
+
import { Hero01 } from "@openwarelabs/blocks";
|
|
15
|
+
|
|
16
|
+
<Hero01
|
|
17
|
+
eyebrow="New: agents that open their own pull requests"
|
|
18
|
+
title="The workspace for shipping software"
|
|
19
|
+
description="Plan the work, hand the routine parts to agents, review every change and ship it."
|
|
20
|
+
primaryAction={{ label: "Start for free", href: "/signup" }}
|
|
21
|
+
secondaryAction={{ label: "Book a demo", href: "/demo" }}
|
|
22
|
+
note="Free for teams of up to five. No card needed."
|
|
23
|
+
visual={<img src="/screenshot.png" alt="The overview page" />}
|
|
24
|
+
/>;
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
The page needs `data-theme` on `<html>` and `class="ow-app"` on `<body>`, as for the library.
|
|
28
|
+
|
|
29
|
+
## Blocks
|
|
30
|
+
|
|
31
|
+
| Component | What it is | Content |
|
|
32
|
+
| --------- | -------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------ |
|
|
33
|
+
| `Hero01` | Centred, with a screenshot below that runs on into the page | `title`, `description`, `primaryAction`, `secondaryAction`, `eyebrow`, `note`, `visual` |
|
|
34
|
+
| `Hero02` | Split: words on the left, the product on the right | the same, plus `points` (ticked reasons to believe) |
|
|
35
|
+
| `Hero03` | With an email field, for a waitlist or a trial | `submitLabel`, `onSubmit(email)`, `successTitle`, `successDescription`, `labels` for the field's words |
|
|
36
|
+
| `Hero04` | On Openware's dot grid, with room either side | `start`, `end`, `interactive` |
|
|
37
|
+
| `Hero05` | With customers' logos below | `logosTitle`, `logos: { name, logo }[]` |
|
|
38
|
+
| `Hero06` | Download buttons for a desktop app, the visitor's system first | `platforms: { id, name, requirement, href \| onDownload }[]`, `version`, `otherDownloads` |
|
|
39
|
+
|
|
40
|
+
Actions are `{ label, href?, onClick?, startIcon?, endIcon? }`: with `href` they're links styled as buttons, so they work with any router. Every block also takes the attributes of its `<section>` (`className`, `id` and so on). The docs show each one live, with its props: `npm run dev` in the repository, then Blocks → Heroes.
|
|
41
|
+
|
|
42
|
+
More blocks become components release by release; until then, the others in the docs are code to copy.
|
|
43
|
+
|
|
44
|
+
## With AI tools
|
|
45
|
+
|
|
46
|
+
The Openware MCP server (`npx -y @openwarelabs/ui-mcp`) knows every block's props and examples, so Claude Code, Codex or Cursor use the components rather than rewriting them.
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { Hero01Props } from "./Hero01.types.cjs";
|
|
2
|
+
/** A centred hero: an eyebrow, the headline, a lead, two actions and a note, with the product below, running on into the page. */
|
|
3
|
+
export declare function Hero01({ eyebrow, title, description, primaryAction, secondaryAction, note, visual, className, ...props }: Hero01Props): import("react").JSX.Element;
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { Hero01Props } from "./Hero01.types.js";
|
|
2
|
+
/** A centred hero: an eyebrow, the headline, a lead, two actions and a note, with the product below, running on into the page. */
|
|
3
|
+
export declare function Hero01({ eyebrow, title, description, primaryAction, secondaryAction, note, visual, className, ...props }: Hero01Props): import("react").JSX.Element;
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import type { HTMLAttributes, ReactNode } from "react";
|
|
2
|
+
import type { BlockAction } from "../../shared/shared.types.cjs";
|
|
3
|
+
export interface Hero01Props extends Omit<HTMLAttributes<HTMLElement>, "title" | "children"> {
|
|
4
|
+
/** A short line in a Chip above the title: news, a launch or the product's name. */
|
|
5
|
+
eyebrow?: ReactNode;
|
|
6
|
+
/** The headline, in the hero style: what the product does, in a few words. */
|
|
7
|
+
title: ReactNode;
|
|
8
|
+
/** A sentence or two under the title: who it's for and what it changes. */
|
|
9
|
+
description: ReactNode;
|
|
10
|
+
/** The one main action, as a primary pill button. */
|
|
11
|
+
primaryAction: BlockAction;
|
|
12
|
+
/** A second, lower-stakes action beside it. */
|
|
13
|
+
secondaryAction?: BlockAction;
|
|
14
|
+
/** A small line under the buttons, such as "Free for teams of up to five. No card needed." */
|
|
15
|
+
note?: ReactNode;
|
|
16
|
+
/** The product under the text, usually a screenshot (`<img src alt>`). It's centred, up to 1080px wide, and fades out at the bottom. */
|
|
17
|
+
visual?: ReactNode;
|
|
18
|
+
}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import type { HTMLAttributes, ReactNode } from "react";
|
|
2
|
+
import type { BlockAction } from "../../shared/shared.types.js";
|
|
3
|
+
export interface Hero01Props extends Omit<HTMLAttributes<HTMLElement>, "title" | "children"> {
|
|
4
|
+
/** A short line in a Chip above the title: news, a launch or the product's name. */
|
|
5
|
+
eyebrow?: ReactNode;
|
|
6
|
+
/** The headline, in the hero style: what the product does, in a few words. */
|
|
7
|
+
title: ReactNode;
|
|
8
|
+
/** A sentence or two under the title: who it's for and what it changes. */
|
|
9
|
+
description: ReactNode;
|
|
10
|
+
/** The one main action, as a primary pill button. */
|
|
11
|
+
primaryAction: BlockAction;
|
|
12
|
+
/** A second, lower-stakes action beside it. */
|
|
13
|
+
secondaryAction?: BlockAction;
|
|
14
|
+
/** A small line under the buttons, such as "Free for teams of up to five. No card needed." */
|
|
15
|
+
note?: ReactNode;
|
|
16
|
+
/** The product under the text, usually a screenshot (`<img src alt>`). It's centred, up to 1080px wide, and fades out at the bottom. */
|
|
17
|
+
visual?: ReactNode;
|
|
18
|
+
}
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { Hero02Props } from "./Hero02.types.cjs";
|
|
2
|
+
/** A split hero: the words on the left and the product on the right. They stack on phones. */
|
|
3
|
+
export declare function Hero02({ eyebrow, title, description, primaryAction, secondaryAction, points, visual, className, ...props }: Hero02Props): import("react").JSX.Element;
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { Hero02Props } from "./Hero02.types.js";
|
|
2
|
+
/** A split hero: the words on the left and the product on the right. They stack on phones. */
|
|
3
|
+
export declare function Hero02({ eyebrow, title, description, primaryAction, secondaryAction, points, visual, className, ...props }: Hero02Props): import("react").JSX.Element;
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import type { HTMLAttributes, ReactNode } from "react";
|
|
2
|
+
import type { BlockAction } from "../../shared/shared.types.cjs";
|
|
3
|
+
export interface Hero02Props extends Omit<HTMLAttributes<HTMLElement>, "title" | "children"> {
|
|
4
|
+
/** A short line in a Chip above the title. */
|
|
5
|
+
eyebrow?: ReactNode;
|
|
6
|
+
/** The headline. In half the width it takes the page-title size, so a few words fit on a line. */
|
|
7
|
+
title: ReactNode;
|
|
8
|
+
/** A sentence or two under the title. */
|
|
9
|
+
description: ReactNode;
|
|
10
|
+
/** The one main action, as a primary pill button. */
|
|
11
|
+
primaryAction: BlockAction;
|
|
12
|
+
/** A second action beside it, such as a demo. */
|
|
13
|
+
secondaryAction?: BlockAction;
|
|
14
|
+
/** Short reasons to believe it, each with a tick: "Runs in your own CI". */
|
|
15
|
+
points?: ReactNode[];
|
|
16
|
+
/** The product on the right (under the text on phones), usually a screenshot. */
|
|
17
|
+
visual?: ReactNode;
|
|
18
|
+
}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import type { HTMLAttributes, ReactNode } from "react";
|
|
2
|
+
import type { BlockAction } from "../../shared/shared.types.js";
|
|
3
|
+
export interface Hero02Props extends Omit<HTMLAttributes<HTMLElement>, "title" | "children"> {
|
|
4
|
+
/** A short line in a Chip above the title. */
|
|
5
|
+
eyebrow?: ReactNode;
|
|
6
|
+
/** The headline. In half the width it takes the page-title size, so a few words fit on a line. */
|
|
7
|
+
title: ReactNode;
|
|
8
|
+
/** A sentence or two under the title. */
|
|
9
|
+
description: ReactNode;
|
|
10
|
+
/** The one main action, as a primary pill button. */
|
|
11
|
+
primaryAction: BlockAction;
|
|
12
|
+
/** A second action beside it, such as a demo. */
|
|
13
|
+
secondaryAction?: BlockAction;
|
|
14
|
+
/** Short reasons to believe it, each with a tick: "Runs in your own CI". */
|
|
15
|
+
points?: ReactNode[];
|
|
16
|
+
/** The product on the right (under the text on phones), usually a screenshot. */
|
|
17
|
+
visual?: ReactNode;
|
|
18
|
+
}
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { Hero03Props } from "./Hero03.types.cjs";
|
|
2
|
+
/** A hero with an email field: join a waitlist or start a trial in one step, with a confirmation in place of the form. */
|
|
3
|
+
export declare function Hero03({ eyebrow, title, description, submitLabel, onSubmit, note, successTitle, successDescription, visual, labels, className, ...props }: Hero03Props): import("react").JSX.Element;
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { Hero03Props } from "./Hero03.types.js";
|
|
2
|
+
/** A hero with an email field: join a waitlist or start a trial in one step, with a confirmation in place of the form. */
|
|
3
|
+
export declare function Hero03({ eyebrow, title, description, submitLabel, onSubmit, note, successTitle, successDescription, visual, labels, className, ...props }: Hero03Props): import("react").JSX.Element;
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import type { HTMLAttributes, ReactNode } from "react";
|
|
2
|
+
/** The words around the form that aren't content, in English unless you pass your own. */
|
|
3
|
+
export interface Hero03Labels {
|
|
4
|
+
/** The field's accessible name. @default "Work email" */
|
|
5
|
+
email?: string;
|
|
6
|
+
/** @default "you@company.com" */
|
|
7
|
+
placeholder?: string;
|
|
8
|
+
/** The button that brings the form back after joining. @default "Change email" */
|
|
9
|
+
change?: string;
|
|
10
|
+
/** @default "Enter your work email to join the waitlist." */
|
|
11
|
+
empty?: string;
|
|
12
|
+
/** @default "That doesn't look like an email address. Try one like maya@example.com." */
|
|
13
|
+
invalid?: string;
|
|
14
|
+
/** Shown when `onSubmit` fails without a message of its own. @default "That didn't go through. Try again in a moment." */
|
|
15
|
+
failed?: string;
|
|
16
|
+
}
|
|
17
|
+
export interface Hero03Props extends Omit<HTMLAttributes<HTMLElement>, "title" | "children" | "onSubmit"> {
|
|
18
|
+
/** A short line in a Chip above the title, such as "Early access". */
|
|
19
|
+
eyebrow?: ReactNode;
|
|
20
|
+
/** The headline, in the hero style. */
|
|
21
|
+
title: ReactNode;
|
|
22
|
+
/** A sentence or two under the title. */
|
|
23
|
+
description: ReactNode;
|
|
24
|
+
/** The button's words: "Join the waitlist", "Start your trial". */
|
|
25
|
+
submitLabel: ReactNode;
|
|
26
|
+
/**
|
|
27
|
+
* Sends the address to your waitlist. While its promise is pending the button shows a spinner; if it throws,
|
|
28
|
+
* the error's message shows under the field, and once it resolves the form gives way to `successTitle`.
|
|
29
|
+
*/
|
|
30
|
+
onSubmit(email: string): void | Promise<void>;
|
|
31
|
+
/** A small line under the field, such as "One email when your place is ready. Nothing else." */
|
|
32
|
+
note?: ReactNode;
|
|
33
|
+
/** What replaces the form once someone has joined: "You're on the list". */
|
|
34
|
+
successTitle: ReactNode;
|
|
35
|
+
/** A line under it, given the address they joined with. */
|
|
36
|
+
successDescription?(email: string): ReactNode;
|
|
37
|
+
/** Something under the form: a screenshot, or what they'll get. */
|
|
38
|
+
visual?: ReactNode;
|
|
39
|
+
labels?: Hero03Labels;
|
|
40
|
+
}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import type { HTMLAttributes, ReactNode } from "react";
|
|
2
|
+
/** The words around the form that aren't content, in English unless you pass your own. */
|
|
3
|
+
export interface Hero03Labels {
|
|
4
|
+
/** The field's accessible name. @default "Work email" */
|
|
5
|
+
email?: string;
|
|
6
|
+
/** @default "you@company.com" */
|
|
7
|
+
placeholder?: string;
|
|
8
|
+
/** The button that brings the form back after joining. @default "Change email" */
|
|
9
|
+
change?: string;
|
|
10
|
+
/** @default "Enter your work email to join the waitlist." */
|
|
11
|
+
empty?: string;
|
|
12
|
+
/** @default "That doesn't look like an email address. Try one like maya@example.com." */
|
|
13
|
+
invalid?: string;
|
|
14
|
+
/** Shown when `onSubmit` fails without a message of its own. @default "That didn't go through. Try again in a moment." */
|
|
15
|
+
failed?: string;
|
|
16
|
+
}
|
|
17
|
+
export interface Hero03Props extends Omit<HTMLAttributes<HTMLElement>, "title" | "children" | "onSubmit"> {
|
|
18
|
+
/** A short line in a Chip above the title, such as "Early access". */
|
|
19
|
+
eyebrow?: ReactNode;
|
|
20
|
+
/** The headline, in the hero style. */
|
|
21
|
+
title: ReactNode;
|
|
22
|
+
/** A sentence or two under the title. */
|
|
23
|
+
description: ReactNode;
|
|
24
|
+
/** The button's words: "Join the waitlist", "Start your trial". */
|
|
25
|
+
submitLabel: ReactNode;
|
|
26
|
+
/**
|
|
27
|
+
* Sends the address to your waitlist. While its promise is pending the button shows a spinner; if it throws,
|
|
28
|
+
* the error's message shows under the field, and once it resolves the form gives way to `successTitle`.
|
|
29
|
+
*/
|
|
30
|
+
onSubmit(email: string): void | Promise<void>;
|
|
31
|
+
/** A small line under the field, such as "One email when your place is ready. Nothing else." */
|
|
32
|
+
note?: ReactNode;
|
|
33
|
+
/** What replaces the form once someone has joined: "You're on the list". */
|
|
34
|
+
successTitle: ReactNode;
|
|
35
|
+
/** A line under it, given the address they joined with. */
|
|
36
|
+
successDescription?(email: string): ReactNode;
|
|
37
|
+
/** Something under the form: a screenshot, or what they'll get. */
|
|
38
|
+
visual?: ReactNode;
|
|
39
|
+
labels?: Hero03Labels;
|
|
40
|
+
}
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { Hero04Props } from "./Hero04.types.cjs";
|
|
2
|
+
/** A hero on Openware's dot grid, with the dots turning brass under the pointer and room for something either side. */
|
|
3
|
+
export declare function Hero04({ eyebrow, title, description, primaryAction, secondaryAction, start, end, interactive, className, ...props }: Hero04Props): import("react").JSX.Element;
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { Hero04Props } from "./Hero04.types.js";
|
|
2
|
+
/** A hero on Openware's dot grid, with the dots turning brass under the pointer and room for something either side. */
|
|
3
|
+
export declare function Hero04({ eyebrow, title, description, primaryAction, secondaryAction, start, end, interactive, className, ...props }: Hero04Props): import("react").JSX.Element;
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import type { HTMLAttributes, ReactNode } from "react";
|
|
2
|
+
import type { BlockAction } from "../../shared/shared.types.cjs";
|
|
3
|
+
export interface Hero04Props extends Omit<HTMLAttributes<HTMLElement>, "title" | "children"> {
|
|
4
|
+
/** A short line in a Chip above the title. */
|
|
5
|
+
eyebrow?: ReactNode;
|
|
6
|
+
/** The headline, in the hero style. */
|
|
7
|
+
title: ReactNode;
|
|
8
|
+
/** A sentence or two under the title. */
|
|
9
|
+
description: ReactNode;
|
|
10
|
+
/** The one main action, as a primary pill button. */
|
|
11
|
+
primaryAction: BlockAction;
|
|
12
|
+
/** A second action beside it. */
|
|
13
|
+
secondaryAction?: BlockAction;
|
|
14
|
+
/** Something beside the text on the left, such as a few cards. Hidden below 1180px wide, where there's no room. */
|
|
15
|
+
start?: ReactNode;
|
|
16
|
+
/** The same on the right. */
|
|
17
|
+
end?: ReactNode;
|
|
18
|
+
/** The dots turn brass under the pointer.
|
|
19
|
+
* @default true */
|
|
20
|
+
interactive?: boolean;
|
|
21
|
+
}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import type { HTMLAttributes, ReactNode } from "react";
|
|
2
|
+
import type { BlockAction } from "../../shared/shared.types.js";
|
|
3
|
+
export interface Hero04Props extends Omit<HTMLAttributes<HTMLElement>, "title" | "children"> {
|
|
4
|
+
/** A short line in a Chip above the title. */
|
|
5
|
+
eyebrow?: ReactNode;
|
|
6
|
+
/** The headline, in the hero style. */
|
|
7
|
+
title: ReactNode;
|
|
8
|
+
/** A sentence or two under the title. */
|
|
9
|
+
description: ReactNode;
|
|
10
|
+
/** The one main action, as a primary pill button. */
|
|
11
|
+
primaryAction: BlockAction;
|
|
12
|
+
/** A second action beside it. */
|
|
13
|
+
secondaryAction?: BlockAction;
|
|
14
|
+
/** Something beside the text on the left, such as a few cards. Hidden below 1180px wide, where there's no room. */
|
|
15
|
+
start?: ReactNode;
|
|
16
|
+
/** The same on the right. */
|
|
17
|
+
end?: ReactNode;
|
|
18
|
+
/** The dots turn brass under the pointer.
|
|
19
|
+
* @default true */
|
|
20
|
+
interactive?: boolean;
|
|
21
|
+
}
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { Hero05Props } from "./Hero05.types.cjs";
|
|
2
|
+
/** The usual hero, with the headline beside the lead, then a row of customers' logos as the first proof. */
|
|
3
|
+
export declare function Hero05({ eyebrow, title, description, primaryAction, secondaryAction, logosTitle, logos, className, ...props }: Hero05Props): import("react").JSX.Element;
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { Hero05Props } from "./Hero05.types.js";
|
|
2
|
+
/** The usual hero, with the headline beside the lead, then a row of customers' logos as the first proof. */
|
|
3
|
+
export declare function Hero05({ eyebrow, title, description, primaryAction, secondaryAction, logosTitle, logos, className, ...props }: Hero05Props): import("react").JSX.Element;
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import type { HTMLAttributes, ReactNode } from "react";
|
|
2
|
+
import type { BlockAction } from "../../shared/shared.types.cjs";
|
|
3
|
+
export interface Hero05Logo {
|
|
4
|
+
/** The company, for the list's key. Put it in the logo too: as the <img>'s alt, or as text beside an SVG. */
|
|
5
|
+
name: string;
|
|
6
|
+
/** The logo: an `<img src alt>` or an inline SVG, in one colour (currentColor), about 22px tall. */
|
|
7
|
+
logo: ReactNode;
|
|
8
|
+
}
|
|
9
|
+
export interface Hero05Props extends Omit<HTMLAttributes<HTMLElement>, "title" | "children"> {
|
|
10
|
+
/** A short line in a Chip above the title. */
|
|
11
|
+
eyebrow?: ReactNode;
|
|
12
|
+
/** The headline, in the hero style, on the left. */
|
|
13
|
+
title: ReactNode;
|
|
14
|
+
/** A sentence or two, on the right beside the title. */
|
|
15
|
+
description: ReactNode;
|
|
16
|
+
/** The one main action, as a primary pill button. */
|
|
17
|
+
primaryAction: BlockAction;
|
|
18
|
+
/** A second action beside it. */
|
|
19
|
+
secondaryAction?: BlockAction;
|
|
20
|
+
/** A line above the logos: "These teams ship with Acme every day". */
|
|
21
|
+
logosTitle: ReactNode;
|
|
22
|
+
/** Customers' logos, in a row that wraps to a grid on smaller screens. Six to eight look best. */
|
|
23
|
+
logos: Hero05Logo[];
|
|
24
|
+
}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import type { HTMLAttributes, ReactNode } from "react";
|
|
2
|
+
import type { BlockAction } from "../../shared/shared.types.js";
|
|
3
|
+
export interface Hero05Logo {
|
|
4
|
+
/** The company, for the list's key. Put it in the logo too: as the <img>'s alt, or as text beside an SVG. */
|
|
5
|
+
name: string;
|
|
6
|
+
/** The logo: an `<img src alt>` or an inline SVG, in one colour (currentColor), about 22px tall. */
|
|
7
|
+
logo: ReactNode;
|
|
8
|
+
}
|
|
9
|
+
export interface Hero05Props extends Omit<HTMLAttributes<HTMLElement>, "title" | "children"> {
|
|
10
|
+
/** A short line in a Chip above the title. */
|
|
11
|
+
eyebrow?: ReactNode;
|
|
12
|
+
/** The headline, in the hero style, on the left. */
|
|
13
|
+
title: ReactNode;
|
|
14
|
+
/** A sentence or two, on the right beside the title. */
|
|
15
|
+
description: ReactNode;
|
|
16
|
+
/** The one main action, as a primary pill button. */
|
|
17
|
+
primaryAction: BlockAction;
|
|
18
|
+
/** A second action beside it. */
|
|
19
|
+
secondaryAction?: BlockAction;
|
|
20
|
+
/** A line above the logos: "These teams ship with Acme every day". */
|
|
21
|
+
logosTitle: ReactNode;
|
|
22
|
+
/** Customers' logos, in a row that wraps to a grid on smaller screens. Six to eight look best. */
|
|
23
|
+
logos: Hero05Logo[];
|
|
24
|
+
}
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { Hero06Props } from "./Hero06.types.cjs";
|
|
2
|
+
/** A hero for a desktop app: a download button for each system, with the visitor's own first, and the app beside it. */
|
|
3
|
+
export declare function Hero06({ eyebrow, title, description, platforms, version, otherDownloads, downloadLabel, visual, className, ...props }: Hero06Props): import("react").JSX.Element;
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { Hero06Props } from "./Hero06.types.js";
|
|
2
|
+
/** A hero for a desktop app: a download button for each system, with the visitor's own first, and the app beside it. */
|
|
3
|
+
export declare function Hero06({ eyebrow, title, description, platforms, version, otherDownloads, downloadLabel, visual, className, ...props }: Hero06Props): import("react").JSX.Element;
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
import type { HTMLAttributes, ReactNode } from "react";
|
|
2
|
+
import type { BlockLink } from "../../shared/shared.types.cjs";
|
|
3
|
+
/** The systems Hero06 can recognise, to put the visitor's own first. */
|
|
4
|
+
export type Hero06PlatformId = "mac" | "windows" | "linux";
|
|
5
|
+
export interface Hero06Platform {
|
|
6
|
+
id: Hero06PlatformId;
|
|
7
|
+
/** "macOS", "Windows", "Linux". */
|
|
8
|
+
name: string;
|
|
9
|
+
/** What it needs, shown for the visitor's system: "macOS 13 or later". */
|
|
10
|
+
requirement?: ReactNode;
|
|
11
|
+
/** The download's address. Makes the button a link. */
|
|
12
|
+
href?: string;
|
|
13
|
+
/** Runs when its button is pressed, for a download you start yourself. */
|
|
14
|
+
onDownload?(): void;
|
|
15
|
+
}
|
|
16
|
+
export interface Hero06Props extends Omit<HTMLAttributes<HTMLElement>, "title" | "children"> {
|
|
17
|
+
/** A short line in a Chip above the title, such as "Acme for desktop". */
|
|
18
|
+
eyebrow?: ReactNode;
|
|
19
|
+
/** The headline. In half the width it takes the page-title size. */
|
|
20
|
+
title: ReactNode;
|
|
21
|
+
/** A sentence or two under the title. */
|
|
22
|
+
description: ReactNode;
|
|
23
|
+
/**
|
|
24
|
+
* A button for each system. The visitor's own (or the first, on phones and anything unknown) leads as the primary
|
|
25
|
+
* "Download for …" button; the rest follow as smaller ones with just their names.
|
|
26
|
+
*/
|
|
27
|
+
platforms: Hero06Platform[];
|
|
28
|
+
/** Shown under the buttons, before the requirement: "Version 3.2.0". */
|
|
29
|
+
version?: ReactNode;
|
|
30
|
+
/** A link at the end of that line, to every download. */
|
|
31
|
+
otherDownloads?: BlockLink;
|
|
32
|
+
/** The primary button's words.
|
|
33
|
+
* @default (name) => `Download for ${name}` */
|
|
34
|
+
downloadLabel?(name: string): string;
|
|
35
|
+
/** The app on the right (under the text on phones), usually a screenshot. */
|
|
36
|
+
visual?: ReactNode;
|
|
37
|
+
}
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
import type { HTMLAttributes, ReactNode } from "react";
|
|
2
|
+
import type { BlockLink } from "../../shared/shared.types.js";
|
|
3
|
+
/** The systems Hero06 can recognise, to put the visitor's own first. */
|
|
4
|
+
export type Hero06PlatformId = "mac" | "windows" | "linux";
|
|
5
|
+
export interface Hero06Platform {
|
|
6
|
+
id: Hero06PlatformId;
|
|
7
|
+
/** "macOS", "Windows", "Linux". */
|
|
8
|
+
name: string;
|
|
9
|
+
/** What it needs, shown for the visitor's system: "macOS 13 or later". */
|
|
10
|
+
requirement?: ReactNode;
|
|
11
|
+
/** The download's address. Makes the button a link. */
|
|
12
|
+
href?: string;
|
|
13
|
+
/** Runs when its button is pressed, for a download you start yourself. */
|
|
14
|
+
onDownload?(): void;
|
|
15
|
+
}
|
|
16
|
+
export interface Hero06Props extends Omit<HTMLAttributes<HTMLElement>, "title" | "children"> {
|
|
17
|
+
/** A short line in a Chip above the title, such as "Acme for desktop". */
|
|
18
|
+
eyebrow?: ReactNode;
|
|
19
|
+
/** The headline. In half the width it takes the page-title size. */
|
|
20
|
+
title: ReactNode;
|
|
21
|
+
/** A sentence or two under the title. */
|
|
22
|
+
description: ReactNode;
|
|
23
|
+
/**
|
|
24
|
+
* A button for each system. The visitor's own (or the first, on phones and anything unknown) leads as the primary
|
|
25
|
+
* "Download for …" button; the rest follow as smaller ones with just their names.
|
|
26
|
+
*/
|
|
27
|
+
platforms: Hero06Platform[];
|
|
28
|
+
/** Shown under the buttons, before the requirement: "Version 3.2.0". */
|
|
29
|
+
version?: ReactNode;
|
|
30
|
+
/** A link at the end of that line, to every download. */
|
|
31
|
+
otherDownloads?: BlockLink;
|
|
32
|
+
/** The primary button's words.
|
|
33
|
+
* @default (name) => `Download for ${name}` */
|
|
34
|
+
downloadLabel?(name: string): string;
|
|
35
|
+
/** The app on the right (under the text on phones), usually a screenshot. */
|
|
36
|
+
visual?: ReactNode;
|
|
37
|
+
}
|