@marigold/components 0.0.1 → 0.2.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/dist/ActionGroup/ActionGroup.d.ts +9 -0
- package/dist/ActionGroup/index.d.ts +1 -0
- package/dist/Alert/Alert.d.ts +20 -2
- package/dist/Badge/Badge.d.ts +8 -0
- package/dist/Badge/index.d.ts +1 -0
- package/dist/Box/Box.d.ts +47 -0
- package/dist/Box/index.d.ts +1 -0
- package/dist/Button/Button.d.ts +4 -3
- package/dist/Card/Card.d.ts +9 -0
- package/dist/Card/index.d.ts +1 -0
- package/dist/Checkbox/Checkbox.d.ts +14 -2
- package/dist/Checkbox/CheckboxIcons.d.ts +9 -0
- package/dist/Column/Column.d.ts +8 -0
- package/dist/Column/index.d.ts +1 -0
- package/dist/Columns/Columns.d.ts +10 -0
- package/dist/Columns/index.d.ts +1 -0
- package/dist/Container/Container.d.ts +6 -0
- package/dist/Container/index.d.ts +1 -0
- package/dist/Dialog/Dialog.d.ts +14 -0
- package/dist/Dialog/ModalDialog.d.ts +5 -0
- package/dist/Dialog/index.d.ts +1 -0
- package/dist/Divider/Divider.d.ts +7 -0
- package/dist/Divider/index.d.ts +1 -0
- package/dist/Field/Field.d.ts +11 -0
- package/dist/Field/index.d.ts +1 -0
- package/dist/Heading/Heading.d.ts +7 -5
- package/dist/Hidden/Hidden.d.ts +5 -0
- package/dist/Hidden/index.d.ts +1 -0
- package/dist/Image/Image.d.ts +7 -0
- package/dist/Image/index.d.ts +1 -0
- package/dist/Input/Input.d.ts +6 -0
- package/dist/Input/index.d.ts +1 -0
- package/dist/Label/Label.d.ts +8 -5
- package/dist/Link/Link.d.ts +7 -3
- package/dist/Menu/Menu.d.ts +12 -0
- package/dist/Menu/index.d.ts +1 -0
- package/dist/MenuItem/MenuItem.d.ts +7 -0
- package/dist/MenuItem/index.d.ts +1 -0
- package/dist/Message/Message.d.ts +7 -0
- package/dist/Message/index.d.ts +1 -0
- package/dist/Provider/MarigoldProvider.d.ts +3 -0
- package/dist/Provider/index.d.ts +3 -0
- package/dist/Radio/Radio.d.ts +14 -2
- package/dist/Radio/RadioIcons.d.ts +9 -0
- package/dist/Select/ListBox.d.ts +8 -0
- package/dist/Select/ListBoxSection.d.ts +8 -0
- package/dist/Select/Option.d.ts +8 -0
- package/dist/Select/Popover.d.ts +9 -0
- package/dist/Select/Select.d.ts +13 -3
- package/dist/Slider/Slider.d.ts +6 -3
- package/dist/Stack/Stack.d.ts +7 -0
- package/dist/Stack/index.d.ts +1 -0
- package/dist/Text/Text.d.ts +12 -3
- package/dist/Textarea/Textarea.d.ts +11 -3
- package/dist/ValidationMessage/ValidationMessage.d.ts +6 -0
- package/dist/ValidationMessage/index.d.ts +1 -0
- package/dist/components.cjs.development.js +1308 -195
- package/dist/components.cjs.development.js.map +1 -1
- package/dist/components.cjs.production.min.js +1 -1
- package/dist/components.cjs.production.min.js.map +1 -1
- package/dist/components.esm.js +1267 -185
- package/dist/components.esm.js.map +1 -1
- package/dist/index.d.ts +21 -4
- package/dist/theme.d.ts +24 -4
- package/package.json +24 -4
- package/src/ActionGroup/ActionGroup.stories.mdx +62 -0
- package/src/ActionGroup/ActionGroup.test.tsx +83 -0
- package/src/ActionGroup/ActionGroup.tsx +43 -0
- package/src/ActionGroup/index.ts +1 -0
- package/src/Alert/Alert.stories.mdx +30 -42
- package/src/Alert/Alert.test.tsx +37 -22
- package/src/Alert/Alert.tsx +31 -21
- package/src/Badge/Badge.stories.mdx +57 -0
- package/src/Badge/Badge.test.tsx +61 -0
- package/src/Badge/Badge.tsx +25 -0
- package/src/Badge/index.ts +1 -0
- package/src/Box/Box.stories.mdx +334 -0
- package/src/Box/Box.test.tsx +133 -0
- package/src/Box/Box.tsx +165 -0
- package/src/Box/index.ts +1 -0
- package/src/Button/Button.stories.mdx +58 -134
- package/src/Button/Button.test.tsx +65 -23
- package/src/Button/Button.tsx +48 -14
- package/src/Card/Card.stories.mdx +49 -0
- package/src/Card/Card.test.tsx +66 -0
- package/src/Card/Card.tsx +36 -0
- package/src/Card/index.ts +1 -0
- package/src/Checkbox/Checkbox.stories.mdx +79 -101
- package/src/Checkbox/Checkbox.test.tsx +73 -32
- package/src/Checkbox/Checkbox.tsx +114 -35
- package/src/Checkbox/CheckboxIcons.tsx +49 -0
- package/src/Column/Column.stories.mdx +49 -0
- package/src/Column/Column.test.tsx +32 -0
- package/src/Column/Column.tsx +27 -0
- package/src/Column/index.ts +1 -0
- package/src/Columns/Columns.stories.mdx +65 -0
- package/src/Columns/Columns.test.tsx +102 -0
- package/src/Columns/Columns.tsx +69 -0
- package/src/Columns/index.ts +1 -0
- package/src/Container/Container.stories.mdx +19 -0
- package/src/Container/Container.test.tsx +26 -0
- package/src/Container/Container.tsx +13 -0
- package/src/Container/index.ts +1 -0
- package/src/Dialog/Dialog.stories.mdx +73 -0
- package/src/Dialog/Dialog.test.tsx +87 -0
- package/src/Dialog/Dialog.tsx +84 -0
- package/src/Dialog/ModalDialog.tsx +47 -0
- package/src/Dialog/index.ts +1 -0
- package/src/Divider/Divider.stories.mdx +37 -0
- package/src/Divider/Divider.test.tsx +63 -0
- package/src/Divider/Divider.tsx +13 -0
- package/src/Divider/index.ts +1 -0
- package/src/Field/Field.stories.mdx +97 -0
- package/src/Field/Field.test.tsx +80 -0
- package/src/Field/Field.tsx +54 -0
- package/src/Field/index.ts +1 -0
- package/src/Heading/Heading.stories.mdx +36 -76
- package/src/Heading/Heading.test.tsx +31 -17
- package/src/Heading/Heading.tsx +15 -12
- package/src/Hidden/Hidden.stories.mdx +39 -0
- package/src/Hidden/Hidden.test.tsx +24 -0
- package/src/Hidden/Hidden.tsx +16 -0
- package/src/Hidden/index.ts +1 -0
- package/src/Image/Image.stories.mdx +36 -0
- package/src/Image/Image.test.tsx +70 -0
- package/src/Image/Image.tsx +13 -0
- package/src/Image/index.ts +1 -0
- package/src/Input/Input.stories.mdx +61 -0
- package/src/Input/Input.test.tsx +70 -0
- package/src/Input/Input.tsx +13 -0
- package/src/Input/index.ts +1 -0
- package/src/Label/Label.stories.mdx +50 -34
- package/src/Label/Label.test.tsx +45 -16
- package/src/Label/Label.tsx +26 -17
- package/src/Link/Link.stories.mdx +40 -31
- package/src/Link/Link.test.tsx +53 -28
- package/src/Link/Link.tsx +32 -14
- package/src/Menu/Menu.stories.mdx +81 -0
- package/src/Menu/Menu.test.tsx +79 -0
- package/src/Menu/Menu.tsx +41 -0
- package/src/Menu/index.ts +1 -0
- package/src/MenuItem/MenuItem.stories.mdx +37 -0
- package/src/MenuItem/MenuItem.test.tsx +63 -0
- package/src/MenuItem/MenuItem.tsx +23 -0
- package/src/MenuItem/index.ts +1 -0
- package/src/Message/Message.stories.mdx +44 -0
- package/src/Message/Message.test.tsx +87 -0
- package/src/Message/Message.tsx +43 -0
- package/src/Message/index.ts +1 -0
- package/src/Provider/MarigoldProvider.test.tsx +126 -0
- package/src/Provider/MarigoldProvider.tsx +29 -0
- package/src/Provider/index.ts +3 -0
- package/src/Radio/Radio.stories.mdx +80 -83
- package/src/Radio/Radio.test.tsx +63 -22
- package/src/Radio/Radio.tsx +110 -35
- package/src/Radio/RadioIcons.tsx +39 -0
- package/src/Select/ListBox.tsx +39 -0
- package/src/Select/ListBoxSection.tsx +40 -0
- package/src/Select/Option.tsx +48 -0
- package/src/Select/Popover.tsx +50 -0
- package/src/Select/Select.stories.mdx +72 -37
- package/src/Select/Select.test.tsx +271 -28
- package/src/Select/Select.tsx +158 -23
- package/src/Slider/Slider.stories.mdx +26 -54
- package/src/Slider/Slider.test.tsx +13 -13
- package/src/Slider/Slider.tsx +20 -18
- package/src/Stack/Stack.stories.mdx +51 -0
- package/src/Stack/Stack.test.tsx +129 -0
- package/src/Stack/Stack.tsx +39 -0
- package/src/Stack/index.ts +1 -0
- package/src/Text/Text.stories.mdx +53 -47
- package/src/Text/Text.test.tsx +55 -15
- package/src/Text/Text.tsx +44 -10
- package/src/Textarea/Textarea.stories.mdx +68 -21
- package/src/Textarea/Textarea.test.tsx +47 -16
- package/src/Textarea/Textarea.tsx +46 -14
- package/src/ValidationMessage/ValidationMessage.stories.mdx +36 -0
- package/src/ValidationMessage/ValidationMessage.test.tsx +63 -0
- package/src/ValidationMessage/ValidationMessage.tsx +28 -0
- package/src/ValidationMessage/index.ts +1 -0
- package/src/index.ts +22 -4
- package/src/theme.ts +24 -4
- package/dist/Svg/Svg.d.ts +0 -5
- package/dist/Svg/index.d.ts +0 -1
- package/dist/TextInput/TextInput.d.ts +0 -3
- package/dist/TextInput/index.d.ts +0 -1
- package/src/Svg/Svg.stories.mdx +0 -47
- package/src/Svg/Svg.test.tsx +0 -58
- package/src/Svg/Svg.tsx +0 -25
- package/src/Svg/index.ts +0 -1
- package/src/TextInput/TextInput.stories.mdx +0 -37
- package/src/TextInput/TextInput.test.tsx +0 -71
- package/src/TextInput/TextInput.tsx +0 -21
- package/src/TextInput/index.ts +0 -1
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { SVG } from '@marigold/icons';
|
|
3
|
+
|
|
4
|
+
import { Box } from '../Box';
|
|
5
|
+
|
|
6
|
+
export const CheckboxChecked = ({ disabled = false, ...props }) => (
|
|
7
|
+
<SVG width="16" height="32" viewBox="0 0 16 32" fill="none" {...props}>
|
|
8
|
+
<Box
|
|
9
|
+
as="rect"
|
|
10
|
+
x="0.5"
|
|
11
|
+
y="8.5"
|
|
12
|
+
width="15px"
|
|
13
|
+
height="15px"
|
|
14
|
+
rx="1.5"
|
|
15
|
+
variant={disabled ? 'checkbox.checked.disabled' : 'checkbox.checked'}
|
|
16
|
+
/>
|
|
17
|
+
<Box
|
|
18
|
+
as="path"
|
|
19
|
+
fillRule="evenodd"
|
|
20
|
+
clipRule="evenodd"
|
|
21
|
+
d="M13.9571 12.8338L12.4085 11.2852L6.08699 17.6007L3.59887 15.1126L2.04163 16.6588L6.08682 20.704L13.9571 12.8338Z"
|
|
22
|
+
variant="checkbox.checked.icon"
|
|
23
|
+
/>
|
|
24
|
+
</SVG>
|
|
25
|
+
);
|
|
26
|
+
|
|
27
|
+
export const CheckboxUnchecked = ({
|
|
28
|
+
disabled = false,
|
|
29
|
+
error = false,
|
|
30
|
+
...props
|
|
31
|
+
}) => (
|
|
32
|
+
<SVG width="16" height="32" viewBox="0 0 16 32" fill="none" {...props}>
|
|
33
|
+
<Box
|
|
34
|
+
as="rect"
|
|
35
|
+
x="0.5"
|
|
36
|
+
y="8.5"
|
|
37
|
+
width="15px"
|
|
38
|
+
height="15px"
|
|
39
|
+
rx="1.5"
|
|
40
|
+
variant={
|
|
41
|
+
disabled
|
|
42
|
+
? 'checkbox.unchecked.disabled'
|
|
43
|
+
: error
|
|
44
|
+
? 'checkbox.unchecked.error'
|
|
45
|
+
: 'checkbox.unchecked'
|
|
46
|
+
}
|
|
47
|
+
/>
|
|
48
|
+
</SVG>
|
|
49
|
+
);
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import { ArgsTable, Canvas, Meta, Story } from '@storybook/addon-docs';
|
|
2
|
+
import { Column } from './Column';
|
|
3
|
+
import { Text } from '../Text';
|
|
4
|
+
import { useStyles } from '@marigold/system';
|
|
5
|
+
|
|
6
|
+
<Meta
|
|
7
|
+
title="Components/Column"
|
|
8
|
+
argTypes={{
|
|
9
|
+
width: {
|
|
10
|
+
control: {
|
|
11
|
+
type: 'range',
|
|
12
|
+
min: 0,
|
|
13
|
+
max: 12,
|
|
14
|
+
step: 1,
|
|
15
|
+
},
|
|
16
|
+
description: 'Absolute width in 12 grid',
|
|
17
|
+
table: {
|
|
18
|
+
defaultValue: {
|
|
19
|
+
summary: 12,
|
|
20
|
+
},
|
|
21
|
+
},
|
|
22
|
+
},
|
|
23
|
+
}}
|
|
24
|
+
/>
|
|
25
|
+
|
|
26
|
+
# Column
|
|
27
|
+
|
|
28
|
+
export const Template = args => (
|
|
29
|
+
<Column
|
|
30
|
+
className={useStyles({
|
|
31
|
+
css: {
|
|
32
|
+
textAlign: 'center',
|
|
33
|
+
border: '1px solid red',
|
|
34
|
+
padding: 2,
|
|
35
|
+
margin: 2,
|
|
36
|
+
},
|
|
37
|
+
})}
|
|
38
|
+
width={12}
|
|
39
|
+
{...args}
|
|
40
|
+
>
|
|
41
|
+
<Text>full width</Text>
|
|
42
|
+
</Column>
|
|
43
|
+
);
|
|
44
|
+
|
|
45
|
+
<Canvas>
|
|
46
|
+
<Story name="Default">{Template.bind({})}</Story>
|
|
47
|
+
</Canvas>
|
|
48
|
+
|
|
49
|
+
<ArgsTable story="Default" />
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
|
+
import { Column } from './Column';
|
|
4
|
+
|
|
5
|
+
test('supports width prop', () => {
|
|
6
|
+
render(<Column width={6}>column</Column>);
|
|
7
|
+
const column = screen.getByText('column');
|
|
8
|
+
|
|
9
|
+
expect(column).toHaveStyle(`width: 50%`);
|
|
10
|
+
});
|
|
11
|
+
|
|
12
|
+
test('renders correct HTML element', () => {
|
|
13
|
+
render(<Column>column</Column>);
|
|
14
|
+
const column = screen.getByText('column');
|
|
15
|
+
|
|
16
|
+
expect(column instanceof HTMLDivElement).toBeTruthy();
|
|
17
|
+
});
|
|
18
|
+
|
|
19
|
+
test('accepts custom styles prop className', () => {
|
|
20
|
+
render(<Column className="custom-class-name">column</Column>);
|
|
21
|
+
const column = screen.getByText('column');
|
|
22
|
+
|
|
23
|
+
expect(column.className).toMatch('custom-class-name');
|
|
24
|
+
});
|
|
25
|
+
|
|
26
|
+
test('accepts responsive values', () => {
|
|
27
|
+
render(<Column width={[12, 6]}>column</Column>);
|
|
28
|
+
const column = screen.getByText('column');
|
|
29
|
+
|
|
30
|
+
// Note: as of November 2021 jest-dom does not support media queries...
|
|
31
|
+
expect(column).toHaveStyle('width: 100%');
|
|
32
|
+
});
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { Box } from '../Box';
|
|
3
|
+
|
|
4
|
+
type WidthValues = 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12;
|
|
5
|
+
|
|
6
|
+
export type ColumnProps = {
|
|
7
|
+
className?: string;
|
|
8
|
+
width?: WidthValues | WidthValues[];
|
|
9
|
+
};
|
|
10
|
+
|
|
11
|
+
const transform = (width: WidthValues | WidthValues[]) => {
|
|
12
|
+
if (Array.isArray(width)) {
|
|
13
|
+
return width.map(v => `${(v / 12) * 100}%`);
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
return `${(width / 12) * 100}%`;
|
|
17
|
+
};
|
|
18
|
+
|
|
19
|
+
export const Column: React.FC<ColumnProps> = ({
|
|
20
|
+
width = 12,
|
|
21
|
+
children,
|
|
22
|
+
...props
|
|
23
|
+
}) => (
|
|
24
|
+
<Box {...props} width={transform(width)}>
|
|
25
|
+
{children}
|
|
26
|
+
</Box>
|
|
27
|
+
);
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from './Column';
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
import { ArgsTable, Canvas, Meta, Story } from '@storybook/addon-docs';
|
|
2
|
+
import { Column, Columns, Text } from '@marigold/components';
|
|
3
|
+
|
|
4
|
+
<Meta
|
|
5
|
+
title="Components/Columns"
|
|
6
|
+
argTypes={{
|
|
7
|
+
space: {
|
|
8
|
+
control: {
|
|
9
|
+
type: 'range',
|
|
10
|
+
min: 0,
|
|
11
|
+
max: 96,
|
|
12
|
+
step: 2,
|
|
13
|
+
},
|
|
14
|
+
description: 'Absolute space value',
|
|
15
|
+
table: {
|
|
16
|
+
defaultValue: {
|
|
17
|
+
summary: 0,
|
|
18
|
+
},
|
|
19
|
+
},
|
|
20
|
+
},
|
|
21
|
+
horizontalAlign: {
|
|
22
|
+
control: {
|
|
23
|
+
type: 'select',
|
|
24
|
+
},
|
|
25
|
+
options: ['left', 'right', 'center'],
|
|
26
|
+
description: 'where to place',
|
|
27
|
+
table: {
|
|
28
|
+
defaultValue: {
|
|
29
|
+
summary: 'left',
|
|
30
|
+
},
|
|
31
|
+
},
|
|
32
|
+
},
|
|
33
|
+
verticalAlign: {
|
|
34
|
+
control: {
|
|
35
|
+
type: 'select',
|
|
36
|
+
},
|
|
37
|
+
options: ['top', 'bottom', 'center'],
|
|
38
|
+
description: 'where to place',
|
|
39
|
+
table: {
|
|
40
|
+
defaultValue: {
|
|
41
|
+
summary: 'top',
|
|
42
|
+
},
|
|
43
|
+
},
|
|
44
|
+
},
|
|
45
|
+
}}
|
|
46
|
+
/>
|
|
47
|
+
|
|
48
|
+
# Columns
|
|
49
|
+
|
|
50
|
+
export const Template = args => (
|
|
51
|
+
<Columns {...args}>
|
|
52
|
+
<Column width={6}>
|
|
53
|
+
<Text>First column</Text>
|
|
54
|
+
</Column>
|
|
55
|
+
<Column width={6}>
|
|
56
|
+
<Text>Second column</Text>
|
|
57
|
+
</Column>
|
|
58
|
+
</Columns>
|
|
59
|
+
);
|
|
60
|
+
|
|
61
|
+
<Canvas>
|
|
62
|
+
<Story name="Default">{Template.bind({})}</Story>
|
|
63
|
+
</Canvas>
|
|
64
|
+
|
|
65
|
+
<ArgsTable story="Default" />
|
|
@@ -0,0 +1,102 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
|
+
import { Column, Columns } from '@marigold/components';
|
|
4
|
+
|
|
5
|
+
test('supports default space prop', () => {
|
|
6
|
+
render(
|
|
7
|
+
<Columns title="column">
|
|
8
|
+
<Column>column</Column>
|
|
9
|
+
</Columns>
|
|
10
|
+
);
|
|
11
|
+
const column = screen.getByTitle(/column/);
|
|
12
|
+
|
|
13
|
+
expect(column).toHaveStyle(`margin: 0px`);
|
|
14
|
+
});
|
|
15
|
+
|
|
16
|
+
test('supports custom space prop', () => {
|
|
17
|
+
render(
|
|
18
|
+
<Columns space={24} title="column">
|
|
19
|
+
<Column>column</Column>
|
|
20
|
+
</Columns>
|
|
21
|
+
);
|
|
22
|
+
const column = screen.getByTitle(/column/);
|
|
23
|
+
|
|
24
|
+
expect(column).toHaveStyle(`margin: -12px`);
|
|
25
|
+
});
|
|
26
|
+
|
|
27
|
+
test('supports default horizontalAlign prop: left', () => {
|
|
28
|
+
render(
|
|
29
|
+
<Columns title="column">
|
|
30
|
+
<Column>column</Column>
|
|
31
|
+
</Columns>
|
|
32
|
+
);
|
|
33
|
+
const column = screen.getByTitle(/column/);
|
|
34
|
+
|
|
35
|
+
expect(column).toHaveStyle(`justify-content: flex-start`);
|
|
36
|
+
});
|
|
37
|
+
|
|
38
|
+
test('supports custom horizontalAlign prop: center', () => {
|
|
39
|
+
render(
|
|
40
|
+
<Columns horizontalAlign="center" title="column">
|
|
41
|
+
<Column>column</Column>
|
|
42
|
+
</Columns>
|
|
43
|
+
);
|
|
44
|
+
const column = screen.getByTitle(/column/);
|
|
45
|
+
|
|
46
|
+
expect(column).toHaveStyle(`justify-content: center`);
|
|
47
|
+
});
|
|
48
|
+
|
|
49
|
+
test('supports custom horizontalAlign prop: right', () => {
|
|
50
|
+
render(
|
|
51
|
+
<Columns horizontalAlign="right" title="column">
|
|
52
|
+
<Column>column</Column>
|
|
53
|
+
</Columns>
|
|
54
|
+
);
|
|
55
|
+
const column = screen.getByTitle(/column/);
|
|
56
|
+
|
|
57
|
+
expect(column).toHaveStyle(`justify-content: flex-end`);
|
|
58
|
+
});
|
|
59
|
+
|
|
60
|
+
test('supports default verticalAlign prop: top', () => {
|
|
61
|
+
render(
|
|
62
|
+
<Columns title="column">
|
|
63
|
+
<Column>column</Column>
|
|
64
|
+
</Columns>
|
|
65
|
+
);
|
|
66
|
+
const column = screen.getByTitle(/column/);
|
|
67
|
+
|
|
68
|
+
expect(column).toHaveStyle(`align-items: flex-start`);
|
|
69
|
+
});
|
|
70
|
+
|
|
71
|
+
test('supports custom verticalAlign prop: center', () => {
|
|
72
|
+
render(
|
|
73
|
+
<Columns verticalAlign="center" title="column">
|
|
74
|
+
<Column>column</Column>
|
|
75
|
+
</Columns>
|
|
76
|
+
);
|
|
77
|
+
const column = screen.getByTitle(/column/);
|
|
78
|
+
|
|
79
|
+
expect(column).toHaveStyle(`align-items: center`);
|
|
80
|
+
});
|
|
81
|
+
|
|
82
|
+
test('supports custom verticalAlign prop: bottom', () => {
|
|
83
|
+
render(
|
|
84
|
+
<Columns verticalAlign="bottom" title="column">
|
|
85
|
+
<Column>column</Column>
|
|
86
|
+
</Columns>
|
|
87
|
+
);
|
|
88
|
+
const column = screen.getByTitle(/column/);
|
|
89
|
+
|
|
90
|
+
expect(column).toHaveStyle(`align-items: flex-end`);
|
|
91
|
+
});
|
|
92
|
+
|
|
93
|
+
test('renders correct HTML element', () => {
|
|
94
|
+
render(
|
|
95
|
+
<Columns title="column">
|
|
96
|
+
<Column>column</Column>
|
|
97
|
+
</Columns>
|
|
98
|
+
);
|
|
99
|
+
const column = screen.getByTitle(/column/);
|
|
100
|
+
|
|
101
|
+
expect(column instanceof HTMLDivElement).toBeTruthy();
|
|
102
|
+
});
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
import React, { Children } from 'react';
|
|
2
|
+
import { useStyles } from '@marigold/system';
|
|
3
|
+
import { Box } from '../Box';
|
|
4
|
+
import flattenChildren from 'react-keyed-flatten-children';
|
|
5
|
+
|
|
6
|
+
type ColumnsProps = {
|
|
7
|
+
className?: string;
|
|
8
|
+
space?: number;
|
|
9
|
+
horizontalAlign?: 'left' | 'right' | 'center';
|
|
10
|
+
verticalAlign?: 'top' | 'bottom' | 'center';
|
|
11
|
+
title?: string; // Should only be used for testing.
|
|
12
|
+
};
|
|
13
|
+
|
|
14
|
+
export const Columns: React.FC<ColumnsProps> = ({
|
|
15
|
+
space = 0,
|
|
16
|
+
horizontalAlign = 'left',
|
|
17
|
+
verticalAlign = 'top',
|
|
18
|
+
className,
|
|
19
|
+
children,
|
|
20
|
+
...props
|
|
21
|
+
}) => {
|
|
22
|
+
let columnItems = flattenChildren(children);
|
|
23
|
+
let childClassNames = useStyles({ css: { p: `${space / 2}px` } });
|
|
24
|
+
|
|
25
|
+
// horizontal Alignment
|
|
26
|
+
let justify = 'flex-start';
|
|
27
|
+
if (horizontalAlign === 'right') {
|
|
28
|
+
justify = 'flex-end';
|
|
29
|
+
} else if (horizontalAlign === 'center') {
|
|
30
|
+
justify = 'center';
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
// vertical Alignment
|
|
34
|
+
let alignItems = 'flex-start';
|
|
35
|
+
if (verticalAlign === 'bottom') {
|
|
36
|
+
alignItems = 'flex-end';
|
|
37
|
+
} else if (verticalAlign === 'center') {
|
|
38
|
+
alignItems = 'center';
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
return (
|
|
42
|
+
<Box p={`${space}px`} display="flex" className={className}>
|
|
43
|
+
<Box
|
|
44
|
+
width={`calc(100% + ${space}px)`}
|
|
45
|
+
m={`${-space / 2}px`}
|
|
46
|
+
display="flex"
|
|
47
|
+
flexWrap="wrap"
|
|
48
|
+
alignItems={alignItems}
|
|
49
|
+
justifyContent={justify}
|
|
50
|
+
{...props}
|
|
51
|
+
>
|
|
52
|
+
{Children.map(
|
|
53
|
+
columnItems as unknown as React.ReactElement,
|
|
54
|
+
(child: React.ReactElement) => {
|
|
55
|
+
return React.cloneElement(
|
|
56
|
+
child,
|
|
57
|
+
{
|
|
58
|
+
className: childClassNames,
|
|
59
|
+
},
|
|
60
|
+
<Box className={child && child.props.className}>
|
|
61
|
+
{child.props.children}
|
|
62
|
+
</Box>
|
|
63
|
+
);
|
|
64
|
+
}
|
|
65
|
+
)}
|
|
66
|
+
</Box>
|
|
67
|
+
</Box>
|
|
68
|
+
);
|
|
69
|
+
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from './Columns';
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { ArgsTable, Canvas, Meta, Story } from '@storybook/addon-docs';
|
|
2
|
+
import { Container } from './Container';
|
|
3
|
+
import { Text } from '../Text';
|
|
4
|
+
|
|
5
|
+
<Meta title="Components/Container" />
|
|
6
|
+
|
|
7
|
+
# Container
|
|
8
|
+
|
|
9
|
+
export const Template = args => (
|
|
10
|
+
<Container {...args}>
|
|
11
|
+
<Text>Container with width=100%</Text>
|
|
12
|
+
</Container>
|
|
13
|
+
);
|
|
14
|
+
|
|
15
|
+
<Canvas>
|
|
16
|
+
<Story name="Default">{Template.bind({})}</Story>
|
|
17
|
+
</Canvas>
|
|
18
|
+
|
|
19
|
+
<ArgsTable story="Default" />
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
|
+
import { Container } from './Container';
|
|
4
|
+
import { Text } from '../Text';
|
|
5
|
+
|
|
6
|
+
test('renders correct HTML element', () => {
|
|
7
|
+
render(
|
|
8
|
+
<Container title="container">
|
|
9
|
+
<Text>sdf</Text>
|
|
10
|
+
</Container>
|
|
11
|
+
);
|
|
12
|
+
const container = screen.getByTitle(/container/);
|
|
13
|
+
|
|
14
|
+
expect(container instanceof HTMLDivElement).toBeTruthy();
|
|
15
|
+
});
|
|
16
|
+
|
|
17
|
+
test('accepts custom styles prop className', () => {
|
|
18
|
+
render(
|
|
19
|
+
<Container className="custom-class-name" title="container">
|
|
20
|
+
<Text>text</Text>
|
|
21
|
+
</Container>
|
|
22
|
+
);
|
|
23
|
+
const container = screen.getByTitle(/container/);
|
|
24
|
+
|
|
25
|
+
expect(container.className).toMatch('custom-class-name');
|
|
26
|
+
});
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { Box } from '../Box';
|
|
3
|
+
|
|
4
|
+
export type ContainerProps = {
|
|
5
|
+
className?: string;
|
|
6
|
+
title?: string; // Used for testing.
|
|
7
|
+
};
|
|
8
|
+
|
|
9
|
+
export const Container: React.FC<ContainerProps> = ({ children, ...props }) => (
|
|
10
|
+
<Box {...props} width="100%">
|
|
11
|
+
{children}
|
|
12
|
+
</Box>
|
|
13
|
+
);
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from './Container';
|
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
import { ArgsTable, Canvas, Meta, Story } from '@storybook/addon-docs';
|
|
2
|
+
import { Dialog, useDialogButtonProps } from './Dialog';
|
|
3
|
+
import { Button } from '../Button';
|
|
4
|
+
import { Text } from '../Text';
|
|
5
|
+
|
|
6
|
+
<Meta
|
|
7
|
+
title="Components/Dialog"
|
|
8
|
+
parameters={{
|
|
9
|
+
actions: {
|
|
10
|
+
handles: ['click'],
|
|
11
|
+
},
|
|
12
|
+
}}
|
|
13
|
+
argTypes={{
|
|
14
|
+
isOpen: {
|
|
15
|
+
control: {
|
|
16
|
+
type: 'boolean',
|
|
17
|
+
},
|
|
18
|
+
description: 'handled by state from useDialogButtonProps',
|
|
19
|
+
options: [true, false],
|
|
20
|
+
table: {
|
|
21
|
+
defaultValue: {
|
|
22
|
+
summary: false,
|
|
23
|
+
},
|
|
24
|
+
},
|
|
25
|
+
},
|
|
26
|
+
title: {
|
|
27
|
+
control: {
|
|
28
|
+
type: 'text',
|
|
29
|
+
},
|
|
30
|
+
description: 'set dialog title',
|
|
31
|
+
},
|
|
32
|
+
close: {
|
|
33
|
+
control: {
|
|
34
|
+
type: 'text',
|
|
35
|
+
},
|
|
36
|
+
description: 'handled by state from useDialogButtonProps',
|
|
37
|
+
},
|
|
38
|
+
}}
|
|
39
|
+
/>
|
|
40
|
+
|
|
41
|
+
# Dialog
|
|
42
|
+
|
|
43
|
+
export const Template = ({ ...args }) => {
|
|
44
|
+
const { state, openButtonProps, openButtonRef } = useDialogButtonProps();
|
|
45
|
+
return (
|
|
46
|
+
<>
|
|
47
|
+
<Button
|
|
48
|
+
variant="secondary"
|
|
49
|
+
size="small"
|
|
50
|
+
{...openButtonProps}
|
|
51
|
+
ref={openButtonRef}
|
|
52
|
+
>
|
|
53
|
+
Open Dialog
|
|
54
|
+
</Button>
|
|
55
|
+
{state.isOpen && (
|
|
56
|
+
<Dialog
|
|
57
|
+
title="Dialog Title"
|
|
58
|
+
isOpen={state.isOpen}
|
|
59
|
+
close={state.close}
|
|
60
|
+
{...args}
|
|
61
|
+
>
|
|
62
|
+
<Text>Dialog content</Text>
|
|
63
|
+
</Dialog>
|
|
64
|
+
)}
|
|
65
|
+
</>
|
|
66
|
+
);
|
|
67
|
+
};
|
|
68
|
+
|
|
69
|
+
<Canvas>
|
|
70
|
+
<Story name="Default">{Template.bind({})}</Story>
|
|
71
|
+
</Canvas>
|
|
72
|
+
|
|
73
|
+
<ArgsTable story="Default" />
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { fireEvent, render, screen } from '@testing-library/react';
|
|
3
|
+
import userEvent from '@testing-library/user-event';
|
|
4
|
+
import { ThemeProvider } from '@marigold/system';
|
|
5
|
+
import { Dialog, useDialogButtonProps } from './Dialog';
|
|
6
|
+
import { Button } from '../Button';
|
|
7
|
+
|
|
8
|
+
const theme = {
|
|
9
|
+
dialog: {
|
|
10
|
+
wrapper: {
|
|
11
|
+
p: '8px',
|
|
12
|
+
},
|
|
13
|
+
body: {
|
|
14
|
+
p: '4px',
|
|
15
|
+
},
|
|
16
|
+
onClose: {
|
|
17
|
+
p: '0px',
|
|
18
|
+
},
|
|
19
|
+
},
|
|
20
|
+
};
|
|
21
|
+
|
|
22
|
+
const DialogComponent: React.FC = props => {
|
|
23
|
+
const { state, openButtonProps, openButtonRef } = useDialogButtonProps();
|
|
24
|
+
return (
|
|
25
|
+
<>
|
|
26
|
+
<Button {...openButtonProps} ref={openButtonRef}>
|
|
27
|
+
Open
|
|
28
|
+
</Button>
|
|
29
|
+
{state.isOpen && (
|
|
30
|
+
<Dialog
|
|
31
|
+
title="Title"
|
|
32
|
+
isOpen={state.isOpen}
|
|
33
|
+
close={state.close}
|
|
34
|
+
{...props}
|
|
35
|
+
>
|
|
36
|
+
Content
|
|
37
|
+
</Dialog>
|
|
38
|
+
)}
|
|
39
|
+
</>
|
|
40
|
+
);
|
|
41
|
+
};
|
|
42
|
+
|
|
43
|
+
test('dialog can be opened by button', () => {
|
|
44
|
+
render(<DialogComponent />);
|
|
45
|
+
const button = screen.getByText(/Open/);
|
|
46
|
+
fireEvent.click(button);
|
|
47
|
+
const dialog = screen.getByText(/Content/);
|
|
48
|
+
expect(dialog).toBeDefined();
|
|
49
|
+
});
|
|
50
|
+
|
|
51
|
+
test('supports theme variants', () => {
|
|
52
|
+
render(
|
|
53
|
+
<ThemeProvider theme={theme}>
|
|
54
|
+
<DialogComponent data-testid="Dialog" />
|
|
55
|
+
</ThemeProvider>
|
|
56
|
+
);
|
|
57
|
+
const button = screen.getByText(/Open/);
|
|
58
|
+
fireEvent.click(button);
|
|
59
|
+
|
|
60
|
+
const dialogBody = screen.getByTestId(/Dialog/);
|
|
61
|
+
expect(dialogBody).toHaveStyle(`padding: 8px`);
|
|
62
|
+
const dialogTitle = screen.getByText(/Title/);
|
|
63
|
+
expect(dialogTitle.parentElement).toHaveStyle(`padding: 4px`);
|
|
64
|
+
});
|
|
65
|
+
|
|
66
|
+
test('close Dialog by escape key', () => {
|
|
67
|
+
render(<DialogComponent />);
|
|
68
|
+
const button = screen.getByText(/Open/);
|
|
69
|
+
fireEvent.click(button);
|
|
70
|
+
|
|
71
|
+
const dialog = screen.getByText(/Content/);
|
|
72
|
+
userEvent.type(dialog, '{esc}');
|
|
73
|
+
expect(dialog).not.toBeVisible();
|
|
74
|
+
});
|
|
75
|
+
|
|
76
|
+
test('close Dialog by close button', () => {
|
|
77
|
+
render(<DialogComponent data-testid="Dialog" />);
|
|
78
|
+
const button = screen.getByText(/Open/);
|
|
79
|
+
fireEvent.click(button);
|
|
80
|
+
|
|
81
|
+
const dialog = screen.getByTestId(/Dialog/);
|
|
82
|
+
expect(dialog).toBeVisible();
|
|
83
|
+
const buttonDiv = dialog.lastChild;
|
|
84
|
+
const onClose = buttonDiv && buttonDiv.firstChild;
|
|
85
|
+
onClose && fireEvent.click(onClose);
|
|
86
|
+
expect(dialog).not.toBeVisible();
|
|
87
|
+
});
|