@kalink-ui/seedly 0.1.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/package.json +78 -0
- package/src/components/.DS_Store +0 -0
- package/src/components/box/box.css.ts +47 -0
- package/src/components/box/box.stories.tsx +29 -0
- package/src/components/box/box.tsx +55 -0
- package/src/components/box/index.ts +2 -0
- package/src/components/button/button.css.ts +33 -0
- package/src/components/button/button.stories.tsx +31 -0
- package/src/components/button/button.tsx +33 -0
- package/src/components/button/index.ts +2 -0
- package/src/components/center/.DS_Store +0 -0
- package/src/components/center/center.css.ts +35 -0
- package/src/components/center/center.stories.tsx +31 -0
- package/src/components/center/center.tsx +46 -0
- package/src/components/center/index.ts +2 -0
- package/src/components/cluster/.DS_Store +0 -0
- package/src/components/cluster/cluster.css.ts +60 -0
- package/src/components/cluster/cluster.stories.tsx +37 -0
- package/src/components/cluster/cluster.tsx +46 -0
- package/src/components/cluster/index.ts +2 -0
- package/src/components/cover/.DS_Store +0 -0
- package/src/components/cover/cover.css.ts +60 -0
- package/src/components/cover/cover.stories.tsx +45 -0
- package/src/components/cover/cover.tsx +55 -0
- package/src/components/cover/index.ts +2 -0
- package/src/components/frame/.DS_Store +0 -0
- package/src/components/frame/frame.css.ts +61 -0
- package/src/components/frame/frame.stories.tsx +39 -0
- package/src/components/frame/frame.tsx +28 -0
- package/src/components/frame/index.ts +2 -0
- package/src/components/grid/.DS_Store +0 -0
- package/src/components/grid/grid.css.ts +26 -0
- package/src/components/grid/grid.stories.tsx +50 -0
- package/src/components/grid/grid.tsx +48 -0
- package/src/components/grid/index.ts +2 -0
- package/src/components/layout.mdx +206 -0
- package/src/components/sidebar/.DS_Store +0 -0
- package/src/components/sidebar/index.ts +2 -0
- package/src/components/sidebar/sidebar.css.ts +68 -0
- package/src/components/sidebar/sidebar.stories.tsx +60 -0
- package/src/components/sidebar/sidebar.tsx +77 -0
- package/src/components/stack/.DS_Store +0 -0
- package/src/components/stack/index.ts +2 -0
- package/src/components/stack/stack.css.ts +36 -0
- package/src/components/stack/stack.stories.tsx +72 -0
- package/src/components/stack/stack.tsx +44 -0
- package/src/components/switcher/.DS_Store +0 -0
- package/src/components/switcher/index.ts +2 -0
- package/src/components/switcher/switcher.css.ts +93 -0
- package/src/components/switcher/switcher.stories.tsx +66 -0
- package/src/components/switcher/switcher.tsx +53 -0
- package/src/styles/index.ts +2 -0
- package/src/styles/seed/.DS_Store +0 -0
- package/src/styles/seed/index.ts +1 -0
- package/src/styles/seed/seed.stories.tsx +52 -0
- package/src/styles/seed/seed.tsx +53 -0
- package/src/styles/styles.mdx +98 -0
- package/src/styles/system-contract.css.ts +144 -0
- package/src/types/index.ts +5 -0
- package/src/types/utils.types.ts +15 -0
- package/src/utils/__tests__/extract-sprinkles-props.test.ts +101 -0
- package/src/utils/__tests__/is-object.test.ts +24 -0
- package/src/utils/__tests__/map-contract-vars.test.ts +34 -0
- package/src/utils/arg-types/.DS_Store +0 -0
- package/src/utils/arg-types/arg-types-from-recipe.ts +37 -0
- package/src/utils/arg-types/arg-types-from-sprinkles.ts +43 -0
- package/src/utils/arg-types/common/composable.ts +13 -0
- package/src/utils/arg-types/common/index.ts +4 -0
- package/src/utils/arg-types/common/polymorphic.ts +14 -0
- package/src/utils/arg-types/common/referable.ts +10 -0
- package/src/utils/arg-types/common/stylable.ts +14 -0
- package/src/utils/arg-types/common-args.ts +26 -0
- package/src/utils/arg-types/index.ts +3 -0
- package/src/utils/extract-sprinkles-props.ts +46 -0
- package/src/utils/index.ts +3 -0
- package/src/utils/is-object.ts +3 -0
- package/src/utils/map-contract-vars.ts +10 -0
package/package.json
ADDED
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@kalink-ui/seedly",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"sideEffects": false,
|
|
5
|
+
"license": "MIT",
|
|
6
|
+
"exports": {
|
|
7
|
+
"./box": "./src/components/box/index.ts",
|
|
8
|
+
"./button": "./src/components/button/index.ts",
|
|
9
|
+
"./center": "./src/components/center/index.ts",
|
|
10
|
+
"./cluster": "./src/components/cluster/index.ts",
|
|
11
|
+
"./cover": "./src/components/cover/index.ts",
|
|
12
|
+
"./frame": "./src/components/frame/index.ts",
|
|
13
|
+
"./grid": "./src/components/grid/index.ts",
|
|
14
|
+
"./sidebar": "./src/components/sidebar/index.ts",
|
|
15
|
+
"./stack": "./src/components/stack/index.ts",
|
|
16
|
+
"./switcher": "./src/components/switcher/index.ts",
|
|
17
|
+
"./styles": "./src/styles/index.ts",
|
|
18
|
+
"./types": "./src/types/index.ts",
|
|
19
|
+
"./utils": "./src/utils/index.ts"
|
|
20
|
+
},
|
|
21
|
+
"devDependencies": {
|
|
22
|
+
"@chromatic-com/storybook": "^3.2.4",
|
|
23
|
+
"@storybook/addon-docs": "^8.6.4",
|
|
24
|
+
"@storybook/addon-essentials": "^8.6.4",
|
|
25
|
+
"@storybook/addon-interactions": "^8.6.4",
|
|
26
|
+
"@storybook/addon-onboarding": "^8.6.4",
|
|
27
|
+
"@storybook/blocks": "^8.6.4",
|
|
28
|
+
"@storybook/react": "^8.6.4",
|
|
29
|
+
"@storybook/react-vite": "^8.6.4",
|
|
30
|
+
"@storybook/test": "^8.6.4",
|
|
31
|
+
"@turbo/gen": "^2.3.4",
|
|
32
|
+
"@types/node": "^22.10.10",
|
|
33
|
+
"@types/react": "19.0.8",
|
|
34
|
+
"@types/react-dom": "19.0.3",
|
|
35
|
+
"@vanilla-extract/css": "^1.17.1",
|
|
36
|
+
"@vanilla-extract/css-utils": "^0.1.4",
|
|
37
|
+
"@vanilla-extract/dynamic": "^2.1.2",
|
|
38
|
+
"@vanilla-extract/recipes": "^0.5.5",
|
|
39
|
+
"@vanilla-extract/sprinkles": "^1.6.3",
|
|
40
|
+
"@vanilla-extract/vite-plugin": "^5.0.0",
|
|
41
|
+
"@vitejs/plugin-react": "^4.3.4",
|
|
42
|
+
"react": "^19.0.0",
|
|
43
|
+
"react-dom": "^19.0.0",
|
|
44
|
+
"storybook": "^8.6.4",
|
|
45
|
+
"tsup": "^8.3.6",
|
|
46
|
+
"type-fest": "^4.33.0",
|
|
47
|
+
"typescript": "5.7.3",
|
|
48
|
+
"vite": "^6.0.11",
|
|
49
|
+
"vite-tsconfig-paths": "^5.1.4",
|
|
50
|
+
"vitest": "^3.0.4",
|
|
51
|
+
"@kalink-ui/eslint-config": "0.1.0",
|
|
52
|
+
"@kalink-ui/typescript-config": "0.0.0"
|
|
53
|
+
},
|
|
54
|
+
"peerDependencies": {
|
|
55
|
+
"@vanilla-extract/css": "^1.17.1",
|
|
56
|
+
"@vanilla-extract/css-utils": "^0.1.4",
|
|
57
|
+
"@vanilla-extract/dynamic": "^2.1.2",
|
|
58
|
+
"@vanilla-extract/recipes": "^0.5.5",
|
|
59
|
+
"@vanilla-extract/sprinkles": "^1.6.3",
|
|
60
|
+
"react": "^19.0.0",
|
|
61
|
+
"react-dom": "^19.0.0"
|
|
62
|
+
},
|
|
63
|
+
"publishConfig": {
|
|
64
|
+
"access": "public"
|
|
65
|
+
},
|
|
66
|
+
"files": [
|
|
67
|
+
"./src/**/*"
|
|
68
|
+
],
|
|
69
|
+
"dependencies": {
|
|
70
|
+
"clsx": "^2.1.1"
|
|
71
|
+
},
|
|
72
|
+
"scripts": {
|
|
73
|
+
"lint": "eslint . --max-warnings 0",
|
|
74
|
+
"build-storybook": "storybook build",
|
|
75
|
+
"dev": "storybook dev -p 6006 --no-open",
|
|
76
|
+
"tsc": "tsc --noEmit"
|
|
77
|
+
}
|
|
78
|
+
}
|
|
Binary file
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
import { createVar } from '@vanilla-extract/css';
|
|
2
|
+
import { recipe, type RecipeVariants } from '@vanilla-extract/recipes';
|
|
3
|
+
|
|
4
|
+
import { sys } from '@/styles/system-contract.css';
|
|
5
|
+
import { mapContractVars } from '@/utils/map-contract-vars';
|
|
6
|
+
|
|
7
|
+
export const colorForeground = createVar();
|
|
8
|
+
export const colorBackground = createVar();
|
|
9
|
+
|
|
10
|
+
export const boxRecipe = recipe({
|
|
11
|
+
variants: {
|
|
12
|
+
variant: {
|
|
13
|
+
solid: {
|
|
14
|
+
color: colorForeground,
|
|
15
|
+
backgroundColor: colorBackground,
|
|
16
|
+
|
|
17
|
+
vars: {
|
|
18
|
+
[colorForeground]: sys.color.foreground,
|
|
19
|
+
[colorBackground]: sys.color.background,
|
|
20
|
+
},
|
|
21
|
+
},
|
|
22
|
+
|
|
23
|
+
outline: {
|
|
24
|
+
color: colorBackground,
|
|
25
|
+
backgroundColor: 'transparent',
|
|
26
|
+
|
|
27
|
+
borderColor: colorBackground,
|
|
28
|
+
borderStyle: 'solid',
|
|
29
|
+
borderWidth: '1px',
|
|
30
|
+
},
|
|
31
|
+
},
|
|
32
|
+
|
|
33
|
+
spacing: mapContractVars(sys.spacing, (key) => ({
|
|
34
|
+
padding: sys.spacing[key],
|
|
35
|
+
})),
|
|
36
|
+
|
|
37
|
+
elevation: mapContractVars(sys.elevation, (key) => ({
|
|
38
|
+
boxShadow: sys.elevation[key],
|
|
39
|
+
})),
|
|
40
|
+
|
|
41
|
+
radius: mapContractVars(sys.shape.corner, (key) => ({
|
|
42
|
+
borderRadius: sys.shape.corner[key],
|
|
43
|
+
})),
|
|
44
|
+
},
|
|
45
|
+
});
|
|
46
|
+
|
|
47
|
+
export type BoxVariants = NonNullable<RecipeVariants<typeof boxRecipe>>;
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import { Box, boxRecipe } from '@/components/box';
|
|
2
|
+
import { argTypesFromRecipe, CommonArgs, commonArgs } from '@/utils/arg-types';
|
|
3
|
+
|
|
4
|
+
import type { Meta, StoryObj } from '@storybook/react';
|
|
5
|
+
|
|
6
|
+
const meta = {
|
|
7
|
+
title: 'Layout/Box',
|
|
8
|
+
component: Box,
|
|
9
|
+
tags: ['autodocs'],
|
|
10
|
+
args: {
|
|
11
|
+
children: 'Box content',
|
|
12
|
+
},
|
|
13
|
+
argTypes: {
|
|
14
|
+
...argTypesFromRecipe(boxRecipe),
|
|
15
|
+
|
|
16
|
+
...commonArgs([
|
|
17
|
+
CommonArgs.COMPOSABLE,
|
|
18
|
+
CommonArgs.POLYMORPHIC,
|
|
19
|
+
CommonArgs.STYLABLE,
|
|
20
|
+
CommonArgs.REFERABLE,
|
|
21
|
+
]),
|
|
22
|
+
},
|
|
23
|
+
} satisfies Meta<typeof Box>;
|
|
24
|
+
|
|
25
|
+
export default meta;
|
|
26
|
+
|
|
27
|
+
type Story = StoryObj<typeof Box>;
|
|
28
|
+
|
|
29
|
+
export const Default: Story = {};
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
import { clsx } from 'clsx';
|
|
2
|
+
|
|
3
|
+
import type { PolymorphicComponentProps } from '@/types/utils.types.js';
|
|
4
|
+
|
|
5
|
+
import { boxRecipe, type BoxVariants } from './box.css';
|
|
6
|
+
|
|
7
|
+
type BoxProps<TUse extends React.ElementType> =
|
|
8
|
+
PolymorphicComponentProps<TUse> & {
|
|
9
|
+
/**
|
|
10
|
+
* The main variation of the box
|
|
11
|
+
*/
|
|
12
|
+
variant?: BoxVariants['variant'];
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* The spacing between the box borders and its contents
|
|
16
|
+
*/
|
|
17
|
+
spacing?: BoxVariants['spacing'];
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* The elevation of the box
|
|
21
|
+
*/
|
|
22
|
+
elevation?: BoxVariants['elevation'];
|
|
23
|
+
|
|
24
|
+
/**
|
|
25
|
+
* The radius of the box
|
|
26
|
+
*/
|
|
27
|
+
radius?: BoxVariants['radius'];
|
|
28
|
+
};
|
|
29
|
+
|
|
30
|
+
/**
|
|
31
|
+
* A evenly spaced container for grouping related elements. Can
|
|
32
|
+
* be styled with colors, borders, and shadows.
|
|
33
|
+
*
|
|
34
|
+
* https://every-layout.dev/layouts/box
|
|
35
|
+
*/
|
|
36
|
+
export const Box = <TUse extends React.ElementType = 'div'>({
|
|
37
|
+
spacing,
|
|
38
|
+
radius,
|
|
39
|
+
elevation,
|
|
40
|
+
className,
|
|
41
|
+
variant,
|
|
42
|
+
...props
|
|
43
|
+
}: BoxProps<TUse>) => {
|
|
44
|
+
const { use: Comp = 'div', ...rest } = props;
|
|
45
|
+
|
|
46
|
+
return (
|
|
47
|
+
<Comp
|
|
48
|
+
className={clsx(
|
|
49
|
+
boxRecipe({ variant, spacing, radius, elevation }),
|
|
50
|
+
className,
|
|
51
|
+
)}
|
|
52
|
+
{...rest}
|
|
53
|
+
/>
|
|
54
|
+
);
|
|
55
|
+
};
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { createTheme } from '@vanilla-extract/css';
|
|
2
|
+
import { recipe, type RecipeVariants } from '@vanilla-extract/recipes';
|
|
3
|
+
|
|
4
|
+
import { sys } from '@/styles/system-contract.css';
|
|
5
|
+
|
|
6
|
+
export const [buttonTheme, buttonsys] = createTheme({
|
|
7
|
+
color: {
|
|
8
|
+
light: sys.color.foreground,
|
|
9
|
+
dark: sys.color.background,
|
|
10
|
+
},
|
|
11
|
+
});
|
|
12
|
+
|
|
13
|
+
export const buttonRecipe = recipe({
|
|
14
|
+
base: {
|
|
15
|
+
padding: '0',
|
|
16
|
+
|
|
17
|
+
backgroundColor: 'unset',
|
|
18
|
+
border: 'unset',
|
|
19
|
+
|
|
20
|
+
cursor: 'pointer',
|
|
21
|
+
},
|
|
22
|
+
variants: {
|
|
23
|
+
variant: {
|
|
24
|
+
bare: {},
|
|
25
|
+
plain: {},
|
|
26
|
+
outline: {},
|
|
27
|
+
ghost: {},
|
|
28
|
+
link: {},
|
|
29
|
+
},
|
|
30
|
+
},
|
|
31
|
+
});
|
|
32
|
+
|
|
33
|
+
export type ButtonVariants = NonNullable<RecipeVariants<typeof buttonRecipe>>;
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import { CommonArgs, commonArgs, argTypesFromRecipe } from '@/utils/arg-types';
|
|
2
|
+
|
|
3
|
+
import { Button } from './button';
|
|
4
|
+
import { buttonRecipe } from './button.css';
|
|
5
|
+
|
|
6
|
+
import type { Meta, StoryObj } from '@storybook/react';
|
|
7
|
+
|
|
8
|
+
const meta = {
|
|
9
|
+
title: 'Component/Button',
|
|
10
|
+
component: Button,
|
|
11
|
+
tags: ['autodocs'],
|
|
12
|
+
args: {
|
|
13
|
+
children: 'Button label',
|
|
14
|
+
},
|
|
15
|
+
argTypes: {
|
|
16
|
+
...argTypesFromRecipe(buttonRecipe),
|
|
17
|
+
|
|
18
|
+
...commonArgs([
|
|
19
|
+
CommonArgs.COMPOSABLE,
|
|
20
|
+
CommonArgs.POLYMORPHIC,
|
|
21
|
+
CommonArgs.STYLABLE,
|
|
22
|
+
CommonArgs.REFERABLE,
|
|
23
|
+
]),
|
|
24
|
+
},
|
|
25
|
+
} satisfies Meta<typeof Button>;
|
|
26
|
+
|
|
27
|
+
export default meta;
|
|
28
|
+
|
|
29
|
+
type Story = StoryObj<typeof Button>;
|
|
30
|
+
|
|
31
|
+
export const Default: Story = {};
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { clsx } from 'clsx';
|
|
2
|
+
|
|
3
|
+
import { Box } from '@/components/box';
|
|
4
|
+
import type { PolymorphicComponentProps } from '@/types/utils.types';
|
|
5
|
+
|
|
6
|
+
import { buttonRecipe, type ButtonVariants } from './button.css';
|
|
7
|
+
|
|
8
|
+
type ButtonProps<TUse extends React.ElementType> =
|
|
9
|
+
PolymorphicComponentProps<TUse> & {
|
|
10
|
+
/**
|
|
11
|
+
* The main variation of the button
|
|
12
|
+
*/
|
|
13
|
+
variant?: ButtonVariants['variant'];
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
export const Button = <TUse extends React.ElementType = 'button'>({
|
|
17
|
+
children,
|
|
18
|
+
className,
|
|
19
|
+
variant,
|
|
20
|
+
...props
|
|
21
|
+
}: ButtonProps<TUse>) => {
|
|
22
|
+
const { use: Comp = 'button', ...rest } = props;
|
|
23
|
+
|
|
24
|
+
return (
|
|
25
|
+
<Comp
|
|
26
|
+
use={Box}
|
|
27
|
+
className={clsx(buttonRecipe({ variant }), className)}
|
|
28
|
+
{...rest}
|
|
29
|
+
>
|
|
30
|
+
{children}
|
|
31
|
+
</Comp>
|
|
32
|
+
);
|
|
33
|
+
};
|
|
Binary file
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
import { recipe, type RecipeVariants } from '@vanilla-extract/recipes';
|
|
2
|
+
|
|
3
|
+
import { sys } from '@/styles/system-contract.css';
|
|
4
|
+
import { mapContractVars } from '@/utils/map-contract-vars';
|
|
5
|
+
|
|
6
|
+
export const centerRecipe = recipe({
|
|
7
|
+
base: {
|
|
8
|
+
display: 'block',
|
|
9
|
+
boxSizing: 'content-box',
|
|
10
|
+
marginInline: 'auto',
|
|
11
|
+
maxInlineSize: sys.layout.measure,
|
|
12
|
+
},
|
|
13
|
+
|
|
14
|
+
variants: {
|
|
15
|
+
andText: {
|
|
16
|
+
true: {
|
|
17
|
+
textAlign: 'center',
|
|
18
|
+
},
|
|
19
|
+
},
|
|
20
|
+
|
|
21
|
+
intrinsic: {
|
|
22
|
+
true: {
|
|
23
|
+
display: 'flex',
|
|
24
|
+
flexDirection: 'column',
|
|
25
|
+
alignItems: 'center',
|
|
26
|
+
},
|
|
27
|
+
},
|
|
28
|
+
|
|
29
|
+
gutters: mapContractVars(sys.spacing, (key) => ({
|
|
30
|
+
paddingInline: sys.spacing[key],
|
|
31
|
+
})),
|
|
32
|
+
},
|
|
33
|
+
});
|
|
34
|
+
|
|
35
|
+
export type CenterVariants = NonNullable<RecipeVariants<typeof centerRecipe>>;
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import { argTypesFromRecipe, CommonArgs, commonArgs } from '@/utils/arg-types';
|
|
2
|
+
|
|
3
|
+
import { Center } from './center';
|
|
4
|
+
import { centerRecipe } from './center.css';
|
|
5
|
+
|
|
6
|
+
import type { Meta, StoryObj } from '@storybook/react';
|
|
7
|
+
|
|
8
|
+
const meta = {
|
|
9
|
+
title: 'Layout/Center',
|
|
10
|
+
component: Center,
|
|
11
|
+
tags: ['autodocs'],
|
|
12
|
+
args: {
|
|
13
|
+
children: 'Centered content',
|
|
14
|
+
},
|
|
15
|
+
argTypes: {
|
|
16
|
+
...argTypesFromRecipe(centerRecipe),
|
|
17
|
+
|
|
18
|
+
...commonArgs([
|
|
19
|
+
CommonArgs.COMPOSABLE,
|
|
20
|
+
CommonArgs.POLYMORPHIC,
|
|
21
|
+
CommonArgs.STYLABLE,
|
|
22
|
+
CommonArgs.REFERABLE,
|
|
23
|
+
]),
|
|
24
|
+
},
|
|
25
|
+
} satisfies Meta<typeof Center>;
|
|
26
|
+
|
|
27
|
+
export default meta;
|
|
28
|
+
|
|
29
|
+
type Story = StoryObj<typeof Center>;
|
|
30
|
+
|
|
31
|
+
export const Default: Story = {};
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import { clsx } from 'clsx';
|
|
2
|
+
import { ElementType } from 'react';
|
|
3
|
+
|
|
4
|
+
import { PolymorphicComponentProps } from '@/types/utils.types';
|
|
5
|
+
|
|
6
|
+
import { centerRecipe, CenterVariants } from './center.css';
|
|
7
|
+
|
|
8
|
+
type CenterProps<TUse extends ElementType> = PolymorphicComponentProps<TUse> & {
|
|
9
|
+
/**
|
|
10
|
+
* Center align the text too with `text-align: center`
|
|
11
|
+
*/
|
|
12
|
+
andText?: CenterVariants['andText'];
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* Center child elements based on their content width
|
|
16
|
+
*/
|
|
17
|
+
intrinsic?: CenterVariants['intrinsic'];
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* The minimum space on either side of the content
|
|
21
|
+
*/
|
|
22
|
+
gutters?: CenterVariants['gutters'];
|
|
23
|
+
};
|
|
24
|
+
|
|
25
|
+
/**
|
|
26
|
+
* A custom element for centering a block-level element horizontally,
|
|
27
|
+
* with a max-width value representing the typographic measure.
|
|
28
|
+
*
|
|
29
|
+
* https://every-layout.dev/layouts/center
|
|
30
|
+
*/
|
|
31
|
+
export const Center = <TUse extends ElementType>({
|
|
32
|
+
andText,
|
|
33
|
+
gutters,
|
|
34
|
+
intrinsic,
|
|
35
|
+
className,
|
|
36
|
+
...props
|
|
37
|
+
}: CenterProps<TUse>) => {
|
|
38
|
+
const { use: Comp = 'div', ...rest } = props;
|
|
39
|
+
|
|
40
|
+
return (
|
|
41
|
+
<Comp
|
|
42
|
+
className={clsx(centerRecipe({ andText, gutters, intrinsic }), className)}
|
|
43
|
+
{...rest}
|
|
44
|
+
/>
|
|
45
|
+
);
|
|
46
|
+
};
|
|
Binary file
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
import { recipe, type RecipeVariants } from '@vanilla-extract/recipes';
|
|
2
|
+
|
|
3
|
+
import { sys } from '@/styles/system-contract.css';
|
|
4
|
+
import { mapContractVars } from '@/utils/map-contract-vars';
|
|
5
|
+
|
|
6
|
+
export const clusterRecipe = recipe({
|
|
7
|
+
base: {
|
|
8
|
+
display: 'flex',
|
|
9
|
+
flexWrap: 'wrap',
|
|
10
|
+
justifyContent: 'flex-start',
|
|
11
|
+
alignItems: 'flex-start',
|
|
12
|
+
},
|
|
13
|
+
|
|
14
|
+
variants: {
|
|
15
|
+
spacing: mapContractVars(sys.spacing, (key) => ({
|
|
16
|
+
gap: sys.spacing[key],
|
|
17
|
+
})),
|
|
18
|
+
|
|
19
|
+
justify: {
|
|
20
|
+
start: {
|
|
21
|
+
justifyContent: 'flex-start',
|
|
22
|
+
},
|
|
23
|
+
end: {
|
|
24
|
+
justifyContent: 'flex-end',
|
|
25
|
+
},
|
|
26
|
+
center: {
|
|
27
|
+
justifyContent: 'center',
|
|
28
|
+
},
|
|
29
|
+
spaceBetween: {
|
|
30
|
+
justifyContent: 'space-between',
|
|
31
|
+
},
|
|
32
|
+
spaceAround: {
|
|
33
|
+
justifyContent: 'space-around',
|
|
34
|
+
},
|
|
35
|
+
spaceEvenly: {
|
|
36
|
+
justifyContent: 'space-evenly',
|
|
37
|
+
},
|
|
38
|
+
},
|
|
39
|
+
|
|
40
|
+
align: {
|
|
41
|
+
start: {
|
|
42
|
+
alignItems: 'flex-start',
|
|
43
|
+
},
|
|
44
|
+
end: {
|
|
45
|
+
alignItems: 'flex-end',
|
|
46
|
+
},
|
|
47
|
+
center: {
|
|
48
|
+
alignItems: 'center',
|
|
49
|
+
},
|
|
50
|
+
stretch: {
|
|
51
|
+
alignItems: 'stretch',
|
|
52
|
+
},
|
|
53
|
+
baseline: {
|
|
54
|
+
alignItems: 'baseline',
|
|
55
|
+
},
|
|
56
|
+
},
|
|
57
|
+
},
|
|
58
|
+
});
|
|
59
|
+
|
|
60
|
+
export type ClusterVariants = NonNullable<RecipeVariants<typeof clusterRecipe>>;
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
import { argTypesFromRecipe, CommonArgs, commonArgs } from '@/utils/arg-types';
|
|
2
|
+
|
|
3
|
+
import { Cluster } from './cluster';
|
|
4
|
+
import { clusterRecipe } from './cluster.css';
|
|
5
|
+
|
|
6
|
+
import type { Meta, StoryObj } from '@storybook/react';
|
|
7
|
+
|
|
8
|
+
const meta = {
|
|
9
|
+
title: 'Layout/Cluster',
|
|
10
|
+
component: Cluster,
|
|
11
|
+
tags: ['autodocs'],
|
|
12
|
+
args: {
|
|
13
|
+
children: (
|
|
14
|
+
<>
|
|
15
|
+
<div>Cluster element one</div>
|
|
16
|
+
<div>Cluster element two</div>
|
|
17
|
+
<div>Cluster element three</div>
|
|
18
|
+
</>
|
|
19
|
+
),
|
|
20
|
+
},
|
|
21
|
+
argTypes: {
|
|
22
|
+
...argTypesFromRecipe(clusterRecipe),
|
|
23
|
+
|
|
24
|
+
...commonArgs([
|
|
25
|
+
CommonArgs.COMPOSABLE,
|
|
26
|
+
CommonArgs.POLYMORPHIC,
|
|
27
|
+
CommonArgs.STYLABLE,
|
|
28
|
+
CommonArgs.REFERABLE,
|
|
29
|
+
]),
|
|
30
|
+
},
|
|
31
|
+
} satisfies Meta<typeof Cluster>;
|
|
32
|
+
|
|
33
|
+
export default meta;
|
|
34
|
+
|
|
35
|
+
type Story = StoryObj<typeof Cluster>;
|
|
36
|
+
|
|
37
|
+
export const Default: Story = {};
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import { clsx } from 'clsx';
|
|
2
|
+
import { ElementType } from 'react';
|
|
3
|
+
|
|
4
|
+
import { PolymorphicComponentProps } from '@/types/utils.types';
|
|
5
|
+
|
|
6
|
+
import { clusterRecipe, ClusterVariants } from './cluster.css';
|
|
7
|
+
|
|
8
|
+
type ClusterProps<TUse extends ElementType> =
|
|
9
|
+
PolymorphicComponentProps<TUse> & {
|
|
10
|
+
/**
|
|
11
|
+
* The spacing between items
|
|
12
|
+
*/
|
|
13
|
+
spacing?: ClusterVariants['spacing'];
|
|
14
|
+
|
|
15
|
+
/**
|
|
16
|
+
* The alignment of items along the main axis
|
|
17
|
+
*/
|
|
18
|
+
justify?: ClusterVariants['justify'];
|
|
19
|
+
|
|
20
|
+
/**
|
|
21
|
+
* The alignment of items along the cross axis
|
|
22
|
+
*/
|
|
23
|
+
align?: ClusterVariants['align'];
|
|
24
|
+
};
|
|
25
|
+
|
|
26
|
+
/**
|
|
27
|
+
* A custom element for grouping items, with control over the margin between them
|
|
28
|
+
*
|
|
29
|
+
* https://every-layout.dev/layouts/cluster
|
|
30
|
+
*/
|
|
31
|
+
export const Cluster = <TUse extends ElementType>({
|
|
32
|
+
spacing,
|
|
33
|
+
justify,
|
|
34
|
+
align,
|
|
35
|
+
className,
|
|
36
|
+
...props
|
|
37
|
+
}: ClusterProps<TUse>) => {
|
|
38
|
+
const { use: Comp = 'div', ...rest } = props;
|
|
39
|
+
|
|
40
|
+
return (
|
|
41
|
+
<Comp
|
|
42
|
+
className={clsx(clusterRecipe({ spacing, align, justify }), className)}
|
|
43
|
+
{...rest}
|
|
44
|
+
/>
|
|
45
|
+
);
|
|
46
|
+
};
|
|
Binary file
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
import { createVar, globalStyle } from '@vanilla-extract/css';
|
|
2
|
+
import { recipe, type RecipeVariants } from '@vanilla-extract/recipes';
|
|
3
|
+
|
|
4
|
+
import { sys } from '@/styles/system-contract.css';
|
|
5
|
+
import { mapContractVars } from '@/utils/map-contract-vars';
|
|
6
|
+
|
|
7
|
+
const spaceVar = createVar();
|
|
8
|
+
export const minSizeVar = createVar();
|
|
9
|
+
|
|
10
|
+
export const coverRecipe = recipe({
|
|
11
|
+
base: {
|
|
12
|
+
display: 'flex',
|
|
13
|
+
flexDirection: 'column',
|
|
14
|
+
|
|
15
|
+
minBlockSize: minSizeVar,
|
|
16
|
+
padding: spaceVar,
|
|
17
|
+
|
|
18
|
+
vars: {
|
|
19
|
+
[minSizeVar]: '100vh',
|
|
20
|
+
},
|
|
21
|
+
},
|
|
22
|
+
|
|
23
|
+
variants: {
|
|
24
|
+
spacing: mapContractVars(sys.spacing, (key) => ({
|
|
25
|
+
sys: {
|
|
26
|
+
[spaceVar]: sys.spacing[key],
|
|
27
|
+
},
|
|
28
|
+
})),
|
|
29
|
+
|
|
30
|
+
noPad: {
|
|
31
|
+
true: {
|
|
32
|
+
padding: 0,
|
|
33
|
+
},
|
|
34
|
+
},
|
|
35
|
+
},
|
|
36
|
+
});
|
|
37
|
+
|
|
38
|
+
globalStyle(`${coverRecipe.classNames.base} > *`, {
|
|
39
|
+
marginBlock: spaceVar,
|
|
40
|
+
});
|
|
41
|
+
|
|
42
|
+
globalStyle(
|
|
43
|
+
`${coverRecipe.classNames.base} > :first-child:not([data-cover-center])`,
|
|
44
|
+
{
|
|
45
|
+
marginBlockStart: 0,
|
|
46
|
+
},
|
|
47
|
+
);
|
|
48
|
+
|
|
49
|
+
globalStyle(
|
|
50
|
+
`${coverRecipe.classNames.base} > :last-child:not([data-cover-center])`,
|
|
51
|
+
{
|
|
52
|
+
marginBlockEnd: 0,
|
|
53
|
+
},
|
|
54
|
+
);
|
|
55
|
+
|
|
56
|
+
globalStyle(`${coverRecipe.classNames.base} > [data-cover-center]`, {
|
|
57
|
+
marginBlock: 'auto',
|
|
58
|
+
});
|
|
59
|
+
|
|
60
|
+
export type CoverVariants = NonNullable<RecipeVariants<typeof coverRecipe>>;
|