@khanacademy/wonder-blocks-form 2.4.5 → 2.4.6
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/CHANGELOG.md +7 -0
- package/dist/index.js +150 -0
- package/package.json +3 -3
- package/src/components/__docs__/checkbox-group.stories.js +266 -0
- package/src/components/__docs__/checkbox.stories.js +1 -1
- package/src/components/__docs__/choice.stories.js +86 -0
- package/src/components/__docs__/labeled-text-field.argtypes.js +248 -0
- package/src/components/{labeled-text-field.stories.js → __docs__/labeled-text-field.stories.js} +274 -35
- package/src/components/__docs__/radio-group.stories.js +182 -0
- package/src/components/__docs__/radio.stories.js +160 -0
- package/src/components/__docs__/text-field.argtypes.js +206 -0
- package/src/components/{text-field.stories.js → __docs__/text-field.stories.js} +268 -28
- package/src/components/checkbox-group.js +27 -0
- package/src/components/choice.js +59 -1
- package/src/components/labeled-text-field.js +20 -0
- package/src/components/radio-group.js +27 -0
- package/src/components/text-field.js +17 -0
package/CHANGELOG.md
CHANGED
package/dist/index.js
CHANGED
|
@@ -464,6 +464,24 @@ const styles = aphrodite__WEBPACK_IMPORTED_MODULE_1__["StyleSheet"].create({
|
|
|
464
464
|
boxShadow: `0px 0px 0px 1px ${_khanacademy_wonder_blocks_color__WEBPACK_IMPORTED_MODULE_2___default.a.red}, 0px 0px 0px 2px ${_khanacademy_wonder_blocks_color__WEBPACK_IMPORTED_MODULE_2___default.a.white}`
|
|
465
465
|
}
|
|
466
466
|
});
|
|
467
|
+
|
|
468
|
+
/**
|
|
469
|
+
* A TextField is an element used to accept a single line of text from the user.
|
|
470
|
+
*
|
|
471
|
+
* ### Usage
|
|
472
|
+
*
|
|
473
|
+
* ```jsx
|
|
474
|
+
* import {TextField} from "@khanacademy/wonder-blocks-form";
|
|
475
|
+
*
|
|
476
|
+
* const [value, setValue] = React.useState("");
|
|
477
|
+
*
|
|
478
|
+
* <TextField
|
|
479
|
+
* id="some-unique-text-field-id"
|
|
480
|
+
* value={value}
|
|
481
|
+
* onChange={setValue}
|
|
482
|
+
* />
|
|
483
|
+
* ```
|
|
484
|
+
*/
|
|
467
485
|
const TextField = /*#__PURE__*/react__WEBPACK_IMPORTED_MODULE_0__["forwardRef"]((props, ref) => /*#__PURE__*/react__WEBPACK_IMPORTED_MODULE_0__["createElement"](TextFieldInternal, _extends({}, props, {
|
|
468
486
|
forwardedRef: ref
|
|
469
487
|
})));
|
|
@@ -666,6 +684,63 @@ const styles = aphrodite__WEBPACK_IMPORTED_MODULE_1__["StyleSheet"].create({
|
|
|
666
684
|
*
|
|
667
685
|
* If you wish to use just a single field, use Checkbox or Radio with the
|
|
668
686
|
* optional label and description props.
|
|
687
|
+
*
|
|
688
|
+
* ### Checkbox Usage
|
|
689
|
+
*
|
|
690
|
+
* ```jsx
|
|
691
|
+
* import {Choice, CheckboxGroup} from "@khanacademy/wonder-blocks-form";
|
|
692
|
+
*
|
|
693
|
+
* const [selectedValues, setSelectedValues] = React.useState([]);
|
|
694
|
+
*
|
|
695
|
+
* // Checkbox usage
|
|
696
|
+
* <CheckboxGroup
|
|
697
|
+
* label="some-label"
|
|
698
|
+
* description="some-description"
|
|
699
|
+
* groupName="some-group-name"
|
|
700
|
+
* onChange={setSelectedValues}
|
|
701
|
+
* selectedValues={selectedValues}
|
|
702
|
+
* />
|
|
703
|
+
* // Add as many choices as necessary
|
|
704
|
+
* <Choice
|
|
705
|
+
* label="Choice 1"
|
|
706
|
+
* value="some-choice-value"
|
|
707
|
+
* description="Some choice description."
|
|
708
|
+
* />
|
|
709
|
+
* <Choice
|
|
710
|
+
* label="Choice 2"
|
|
711
|
+
* value="some-choice-value-2"
|
|
712
|
+
* description="Some choice description."
|
|
713
|
+
* />
|
|
714
|
+
* </CheckboxGroup>
|
|
715
|
+
* ```
|
|
716
|
+
*
|
|
717
|
+
* ### Radio Usage
|
|
718
|
+
*
|
|
719
|
+
* ```jsx
|
|
720
|
+
* import {Choice, RadioGroup} from "@khanacademy/wonder-blocks-form";
|
|
721
|
+
*
|
|
722
|
+
* const [selectedValue, setSelectedValue] = React.useState("");
|
|
723
|
+
*
|
|
724
|
+
* <RadioGroup
|
|
725
|
+
* label="some-label"
|
|
726
|
+
* description="some-description"
|
|
727
|
+
* groupName="some-group-name"
|
|
728
|
+
* onChange={setSelectedValue}>
|
|
729
|
+
* selectedValues={selectedValue}
|
|
730
|
+
* />
|
|
731
|
+
* // Add as many choices as necessary
|
|
732
|
+
* <Choice
|
|
733
|
+
* label="Choice 1"
|
|
734
|
+
* value="some-choice-value"
|
|
735
|
+
* description="Some choice description."
|
|
736
|
+
* />
|
|
737
|
+
* <Choice
|
|
738
|
+
* label="Choice 2"
|
|
739
|
+
* value="some-choice-value-2"
|
|
740
|
+
* description="Some choice description."
|
|
741
|
+
* />
|
|
742
|
+
* </RadioGroup>
|
|
743
|
+
* ```
|
|
669
744
|
*/
|
|
670
745
|
class Choice extends react__WEBPACK_IMPORTED_MODULE_0__["Component"] {
|
|
671
746
|
getChoiceComponent(variant) {
|
|
@@ -725,6 +800,33 @@ const StyledLegend = Object(_khanacademy_wonder_blocks_core__WEBPACK_IMPORTED_MO
|
|
|
725
800
|
* many props for its children Choice components. The Choice component is
|
|
726
801
|
* exposed for the user to apply custom styles or to indicate which choices are
|
|
727
802
|
* disabled.
|
|
803
|
+
*
|
|
804
|
+
* ### Usage
|
|
805
|
+
*
|
|
806
|
+
* ```jsx
|
|
807
|
+
* import {Choice, CheckboxGroup} from "@khanacademy/wonder-blocks-form";
|
|
808
|
+
*
|
|
809
|
+
* const [selectedValues, setSelectedValues] = React.useState([]);
|
|
810
|
+
*
|
|
811
|
+
* <CheckboxGroup
|
|
812
|
+
* label="some-label"
|
|
813
|
+
* description="some-description"
|
|
814
|
+
* groupName="some-group-name"
|
|
815
|
+
* onChange={setSelectedValues}
|
|
816
|
+
* selectedValues={selectedValues}
|
|
817
|
+
* />
|
|
818
|
+
* // Add as many choices as necessary
|
|
819
|
+
* <Choice
|
|
820
|
+
* label="Choice 1"
|
|
821
|
+
* value="some-choice-value"
|
|
822
|
+
* />
|
|
823
|
+
* <Choice
|
|
824
|
+
* label="Choice 2"
|
|
825
|
+
* value="some-choice-value-2"
|
|
826
|
+
* description="Some choice description."
|
|
827
|
+
* />
|
|
828
|
+
* </CheckboxGroup>
|
|
829
|
+
* ```
|
|
728
830
|
*/
|
|
729
831
|
|
|
730
832
|
class CheckboxGroup extends react__WEBPACK_IMPORTED_MODULE_0__["Component"] {
|
|
@@ -820,6 +922,33 @@ const StyledLegend = Object(_khanacademy_wonder_blocks_core__WEBPACK_IMPORTED_MO
|
|
|
820
922
|
* indicate which choices are disabled. The use of the groupName prop is
|
|
821
923
|
* important to maintain expected keyboard navigation behavior for
|
|
822
924
|
* accessibility.
|
|
925
|
+
*
|
|
926
|
+
* ### Usage
|
|
927
|
+
*
|
|
928
|
+
* ```jsx
|
|
929
|
+
* import {Choice, RadioGroup} from "@khanacademy/wonder-blocks-form";
|
|
930
|
+
*
|
|
931
|
+
* const [selectedValue, setSelectedValue] = React.useState([]);
|
|
932
|
+
*
|
|
933
|
+
* <RadioGroup
|
|
934
|
+
* label="some-label"
|
|
935
|
+
* description="some-description"
|
|
936
|
+
* groupName="some-group-name"
|
|
937
|
+
* onChange={setSelectedValue}
|
|
938
|
+
* selectedValue={selectedValue}
|
|
939
|
+
* />
|
|
940
|
+
* // Add as many choices as necessary
|
|
941
|
+
* <Choice
|
|
942
|
+
* label="Choice 1"
|
|
943
|
+
* value="some-choice-value"
|
|
944
|
+
* />
|
|
945
|
+
* <Choice
|
|
946
|
+
* label="Choice 2"
|
|
947
|
+
* value="some-choice-value-2"
|
|
948
|
+
* description="Some choice description."
|
|
949
|
+
* />
|
|
950
|
+
* </RadioGroup>
|
|
951
|
+
* ```
|
|
823
952
|
*/
|
|
824
953
|
|
|
825
954
|
class RadioGroup extends react__WEBPACK_IMPORTED_MODULE_0__["Component"] {
|
|
@@ -1009,6 +1138,27 @@ LabeledTextFieldInternal.defaultProps = {
|
|
|
1009
1138
|
disabled: false,
|
|
1010
1139
|
light: false
|
|
1011
1140
|
};
|
|
1141
|
+
|
|
1142
|
+
/**
|
|
1143
|
+
* A LabeledTextField is an element used to accept a single line of text
|
|
1144
|
+
* from the user paired with a label, description, and error field elements.
|
|
1145
|
+
*
|
|
1146
|
+
* ### Usage
|
|
1147
|
+
*
|
|
1148
|
+
* ```jsx
|
|
1149
|
+
* import {LabeledTextField} from "@khanacademy/wonder-blocks-form";
|
|
1150
|
+
*
|
|
1151
|
+
* const [value, setValue] = React.useState("");
|
|
1152
|
+
*
|
|
1153
|
+
* <LabeledTextField
|
|
1154
|
+
* label="Label"
|
|
1155
|
+
* description="Hello, this is the description for this field"
|
|
1156
|
+
* placeholder="Placeholder"
|
|
1157
|
+
* value={value}
|
|
1158
|
+
* onChange={setValue}
|
|
1159
|
+
* />
|
|
1160
|
+
* ```
|
|
1161
|
+
*/
|
|
1012
1162
|
const LabeledTextField = /*#__PURE__*/react__WEBPACK_IMPORTED_MODULE_0__["forwardRef"]((props, ref) => /*#__PURE__*/react__WEBPACK_IMPORTED_MODULE_0__["createElement"](LabeledTextFieldInternal, _extends({}, props, {
|
|
1013
1163
|
forwardedRef: ref
|
|
1014
1164
|
})));
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@khanacademy/wonder-blocks-form",
|
|
3
|
-
"version": "2.4.
|
|
3
|
+
"version": "2.4.6",
|
|
4
4
|
"design": "v1",
|
|
5
5
|
"description": "Form components for Wonder Blocks.",
|
|
6
6
|
"main": "dist/index.js",
|
|
@@ -15,8 +15,8 @@
|
|
|
15
15
|
"access": "public"
|
|
16
16
|
},
|
|
17
17
|
"dependencies": {
|
|
18
|
-
"@babel/runtime": "^7.
|
|
19
|
-
"@khanacademy/wonder-blocks-clickable": "^2.
|
|
18
|
+
"@babel/runtime": "^7.18.6",
|
|
19
|
+
"@khanacademy/wonder-blocks-clickable": "^2.3.0",
|
|
20
20
|
"@khanacademy/wonder-blocks-color": "^1.1.20",
|
|
21
21
|
"@khanacademy/wonder-blocks-core": "^4.3.2",
|
|
22
22
|
"@khanacademy/wonder-blocks-icon": "^1.2.29",
|
|
@@ -0,0 +1,266 @@
|
|
|
1
|
+
// @flow
|
|
2
|
+
import * as React from "react";
|
|
3
|
+
import {StyleSheet} from "aphrodite";
|
|
4
|
+
|
|
5
|
+
import {View} from "@khanacademy/wonder-blocks-core";
|
|
6
|
+
import Color from "@khanacademy/wonder-blocks-color";
|
|
7
|
+
import {Choice, CheckboxGroup} from "@khanacademy/wonder-blocks-form";
|
|
8
|
+
import Spacing from "@khanacademy/wonder-blocks-spacing";
|
|
9
|
+
import {LabelLarge, LabelXSmall} from "@khanacademy/wonder-blocks-typography";
|
|
10
|
+
|
|
11
|
+
import type {StoryComponentType} from "@storybook/react";
|
|
12
|
+
|
|
13
|
+
import ComponentInfo from "../../../../../.storybook/components/component-info.js";
|
|
14
|
+
import {name, version} from "../../../package.json";
|
|
15
|
+
|
|
16
|
+
export default {
|
|
17
|
+
title: "Form / CheckboxGroup",
|
|
18
|
+
component: CheckboxGroup,
|
|
19
|
+
parameters: {
|
|
20
|
+
componentSubtitle: ((
|
|
21
|
+
<ComponentInfo name={name} version={version} />
|
|
22
|
+
): any),
|
|
23
|
+
},
|
|
24
|
+
};
|
|
25
|
+
|
|
26
|
+
export const Default: StoryComponentType = (args) => {
|
|
27
|
+
return (
|
|
28
|
+
<CheckboxGroup {...args}>
|
|
29
|
+
<Choice label="Pepperoni" value="pepperoni" />
|
|
30
|
+
<Choice
|
|
31
|
+
label="Sausage"
|
|
32
|
+
value="sausage"
|
|
33
|
+
description="Imported from Italy"
|
|
34
|
+
/>
|
|
35
|
+
<Choice label="Extra cheese" value="cheese" />
|
|
36
|
+
<Choice label="Green pepper" value="pepper" />
|
|
37
|
+
<Choice label="Mushroom" value="mushroom" />
|
|
38
|
+
</CheckboxGroup>
|
|
39
|
+
);
|
|
40
|
+
};
|
|
41
|
+
|
|
42
|
+
Default.args = {
|
|
43
|
+
// Required
|
|
44
|
+
groupName: "toppings",
|
|
45
|
+
selectedValues: ["pepperoni", "sausage"],
|
|
46
|
+
onChange: () => {},
|
|
47
|
+
// Optional
|
|
48
|
+
label: "Pizza toppings",
|
|
49
|
+
description: "Choose as many toppings as you would like.",
|
|
50
|
+
};
|
|
51
|
+
|
|
52
|
+
export const Basic: StoryComponentType = () => {
|
|
53
|
+
const [selectedValues, setSelectedValues] = React.useState([]);
|
|
54
|
+
|
|
55
|
+
return (
|
|
56
|
+
<CheckboxGroup
|
|
57
|
+
groupName="toppings"
|
|
58
|
+
onChange={setSelectedValues}
|
|
59
|
+
selectedValues={selectedValues}
|
|
60
|
+
>
|
|
61
|
+
<Choice label="Pepperoni" value="pepperoni" />
|
|
62
|
+
<Choice
|
|
63
|
+
label="Sausage"
|
|
64
|
+
value="sausage"
|
|
65
|
+
description="Imported from Italy"
|
|
66
|
+
/>
|
|
67
|
+
<Choice label="Extra cheese" value="cheese" />
|
|
68
|
+
<Choice label="Green pepper" value="pepper" />
|
|
69
|
+
<Choice label="Mushroom" value="mushroom" />
|
|
70
|
+
</CheckboxGroup>
|
|
71
|
+
);
|
|
72
|
+
};
|
|
73
|
+
|
|
74
|
+
Basic.parameters = {
|
|
75
|
+
docs: {
|
|
76
|
+
storyDescription: `This is a basic example of a checkbox group.
|
|
77
|
+
The Wonder Blocks \`CheckboxGroup\` component takes \`Choice\`
|
|
78
|
+
components as children. One of the \`Choice\` components here
|
|
79
|
+
includes a description.`,
|
|
80
|
+
},
|
|
81
|
+
};
|
|
82
|
+
|
|
83
|
+
export const Error: StoryComponentType = () => {
|
|
84
|
+
const toppingsError = "You have selected too many toppings";
|
|
85
|
+
const [selectedValues, setSelectedValues] = React.useState([
|
|
86
|
+
"pepperoni",
|
|
87
|
+
"sausage",
|
|
88
|
+
"cheese",
|
|
89
|
+
"pepper",
|
|
90
|
+
]);
|
|
91
|
+
const [error, setError] = React.useState(toppingsError);
|
|
92
|
+
|
|
93
|
+
// Returns an error message if more than 3 items are selected,
|
|
94
|
+
// and it returns undefined otherwise. We use undefined instead of
|
|
95
|
+
// null here because null would result in a flow error, whereas
|
|
96
|
+
// undefined would be the same as not passing in anything to the
|
|
97
|
+
// checkbox group's `errorMessage` prop.
|
|
98
|
+
const checkForError = (input) => {
|
|
99
|
+
if (input.length > 3) {
|
|
100
|
+
return toppingsError;
|
|
101
|
+
}
|
|
102
|
+
};
|
|
103
|
+
|
|
104
|
+
const handleChange = (input) => {
|
|
105
|
+
const errorMessage = checkForError(input);
|
|
106
|
+
setSelectedValues(input);
|
|
107
|
+
setError(errorMessage);
|
|
108
|
+
};
|
|
109
|
+
|
|
110
|
+
return (
|
|
111
|
+
<CheckboxGroup
|
|
112
|
+
label="Pizza order"
|
|
113
|
+
groupName="toppings"
|
|
114
|
+
description="You may choose at most three toppings"
|
|
115
|
+
onChange={handleChange}
|
|
116
|
+
errorMessage={error}
|
|
117
|
+
selectedValues={selectedValues}
|
|
118
|
+
>
|
|
119
|
+
<Choice label="Pepperoni" value="pepperoni" />
|
|
120
|
+
<Choice
|
|
121
|
+
label="Sausage"
|
|
122
|
+
value="sausage"
|
|
123
|
+
description="Imported from Italy"
|
|
124
|
+
/>
|
|
125
|
+
<Choice label="Extra cheese" value="cheese" />
|
|
126
|
+
<Choice label="Green pepper" value="pepper" />
|
|
127
|
+
<Choice label="Mushroom" value="mushroom" />
|
|
128
|
+
</CheckboxGroup>
|
|
129
|
+
);
|
|
130
|
+
};
|
|
131
|
+
|
|
132
|
+
Error.parameters = {
|
|
133
|
+
docs: {
|
|
134
|
+
storyDescription: `This is what a checkbox group looks like
|
|
135
|
+
if it has an error. It displays the error that is passed into the
|
|
136
|
+
\`errorMessage\` prop, provided the error is not null. It also
|
|
137
|
+
uses the error styling for all the checkboxes. Here, the error
|
|
138
|
+
message is saved as a state, updated in the change handler, and then
|
|
139
|
+
passed in as the \`errorMessage\` prop.`,
|
|
140
|
+
},
|
|
141
|
+
};
|
|
142
|
+
|
|
143
|
+
export const RowStyling: StoryComponentType = () => {
|
|
144
|
+
const [selectedValues, setSelectedValues] = React.useState([]);
|
|
145
|
+
|
|
146
|
+
return (
|
|
147
|
+
<View style={styles.wrapper}>
|
|
148
|
+
<LabelLarge style={styles.title}>Science</LabelLarge>
|
|
149
|
+
<CheckboxGroup
|
|
150
|
+
groupName="science-classes"
|
|
151
|
+
onChange={setSelectedValues}
|
|
152
|
+
selectedValues={selectedValues}
|
|
153
|
+
style={styles.group}
|
|
154
|
+
>
|
|
155
|
+
<Choice label="Biology" value="1" style={styles.choice} />
|
|
156
|
+
<Choice label="AP®︎ Biology" value="2" style={styles.choice} />
|
|
157
|
+
<Choice
|
|
158
|
+
label="High school biology"
|
|
159
|
+
value="3"
|
|
160
|
+
style={styles.choice}
|
|
161
|
+
/>
|
|
162
|
+
<Choice
|
|
163
|
+
label="Cosmology and astronomy"
|
|
164
|
+
value="4"
|
|
165
|
+
style={styles.choice}
|
|
166
|
+
/>
|
|
167
|
+
<Choice
|
|
168
|
+
label="Electrical engineering"
|
|
169
|
+
value="5"
|
|
170
|
+
style={styles.choice}
|
|
171
|
+
/>
|
|
172
|
+
<Choice
|
|
173
|
+
label="Health and medicine"
|
|
174
|
+
value="6"
|
|
175
|
+
style={styles.choice}
|
|
176
|
+
/>
|
|
177
|
+
</CheckboxGroup>
|
|
178
|
+
</View>
|
|
179
|
+
);
|
|
180
|
+
};
|
|
181
|
+
|
|
182
|
+
RowStyling.parameters = {
|
|
183
|
+
docs: {
|
|
184
|
+
storyDescription: `This example shows how one can add custom styles
|
|
185
|
+
to the checkbox group and to each component to achieve desired custom
|
|
186
|
+
layouts. The context in this example is inspired by the class selector
|
|
187
|
+
modal. The label is created separately because we are reflowing all
|
|
188
|
+
the elements in the group to row. The checkboxes render
|
|
189
|
+
horizontally when the style on the \`CheckboxGroup\` is set to
|
|
190
|
+
\`{flexDirection: "row"}\`. Here, \`{flexWrap: "wrap"}\` is also
|
|
191
|
+
used so the options continue on the next line.`,
|
|
192
|
+
},
|
|
193
|
+
};
|
|
194
|
+
|
|
195
|
+
export const MultipleChoiceStyling: StoryComponentType = () => {
|
|
196
|
+
const [selectedValues, setSelectedValues] = React.useState([]);
|
|
197
|
+
|
|
198
|
+
return (
|
|
199
|
+
<CheckboxGroup
|
|
200
|
+
label={<LabelLarge>Select all prime numbers</LabelLarge>}
|
|
201
|
+
description={
|
|
202
|
+
<LabelXSmall style={styles.description}>
|
|
203
|
+
Hint: There is at least one prime number
|
|
204
|
+
</LabelXSmall>
|
|
205
|
+
}
|
|
206
|
+
groupName="science-classes"
|
|
207
|
+
onChange={setSelectedValues}
|
|
208
|
+
selectedValues={selectedValues}
|
|
209
|
+
>
|
|
210
|
+
<Choice label="1" value="1" style={styles.multipleChoice} />
|
|
211
|
+
<Choice label="2" value="2" style={styles.multipleChoice} />
|
|
212
|
+
<Choice label="3" value="3" style={styles.multipleChoice} />
|
|
213
|
+
<Choice label="4" value="4" style={styles.multipleChoice} />
|
|
214
|
+
<Choice
|
|
215
|
+
label="5"
|
|
216
|
+
value="5"
|
|
217
|
+
style={[styles.multipleChoice, styles.last]}
|
|
218
|
+
/>
|
|
219
|
+
</CheckboxGroup>
|
|
220
|
+
);
|
|
221
|
+
};
|
|
222
|
+
|
|
223
|
+
MultipleChoiceStyling.parameters = {
|
|
224
|
+
docs: {
|
|
225
|
+
storyDescription: `This example shows how to use custom styling
|
|
226
|
+
to change the appearance of the checkbox group to look more like
|
|
227
|
+
a multiple choice question. You may also provide custom typography
|
|
228
|
+
to the label and description. Here, there is a line in
|
|
229
|
+
between each question, which is achieved using the
|
|
230
|
+
\`{borderTop: "solid 1px #CCC"}\` style on each \`Choice\`
|
|
231
|
+
component.`,
|
|
232
|
+
},
|
|
233
|
+
};
|
|
234
|
+
|
|
235
|
+
const styles = StyleSheet.create({
|
|
236
|
+
// Row styling
|
|
237
|
+
wrapper: {
|
|
238
|
+
width: 650,
|
|
239
|
+
},
|
|
240
|
+
group: {
|
|
241
|
+
flexDirection: "row",
|
|
242
|
+
flexWrap: "wrap",
|
|
243
|
+
},
|
|
244
|
+
choice: {
|
|
245
|
+
marginTop: Spacing.xSmall_8,
|
|
246
|
+
width: 200,
|
|
247
|
+
},
|
|
248
|
+
title: {
|
|
249
|
+
paddingBottom: Spacing.xSmall_8,
|
|
250
|
+
borderBottom: `1px solid ${Color.offBlack64}`,
|
|
251
|
+
},
|
|
252
|
+
// Multiple choice styling
|
|
253
|
+
multipleChoice: {
|
|
254
|
+
margin: 0,
|
|
255
|
+
height: 48,
|
|
256
|
+
borderTop: "solid 1px #CCC",
|
|
257
|
+
justifyContent: "center",
|
|
258
|
+
},
|
|
259
|
+
description: {
|
|
260
|
+
marginTop: 5,
|
|
261
|
+
color: Color.offBlack64,
|
|
262
|
+
},
|
|
263
|
+
last: {
|
|
264
|
+
borderBottom: "solid 1px #CCC",
|
|
265
|
+
},
|
|
266
|
+
});
|
|
@@ -117,7 +117,7 @@ export const WithLabel: StoryComponentType = () => {
|
|
|
117
117
|
WithLabel.parameters = {
|
|
118
118
|
docs: {
|
|
119
119
|
storyDescription:
|
|
120
|
-
"The checkbox can have
|
|
120
|
+
"The checkbox can have an optional label and description. This allows it to be used as a settings-like item. The user of this component is responsible for keeping track of checked state and providing an onChange callback.",
|
|
121
121
|
},
|
|
122
122
|
};
|
|
123
123
|
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
// @flow
|
|
2
|
+
import * as React from "react";
|
|
3
|
+
import {StyleSheet} from "aphrodite";
|
|
4
|
+
|
|
5
|
+
import {View} from "@khanacademy/wonder-blocks-core";
|
|
6
|
+
import {
|
|
7
|
+
Choice,
|
|
8
|
+
CheckboxGroup,
|
|
9
|
+
RadioGroup,
|
|
10
|
+
} from "@khanacademy/wonder-blocks-form";
|
|
11
|
+
import {Strut} from "@khanacademy/wonder-blocks-layout";
|
|
12
|
+
import Spacing from "@khanacademy/wonder-blocks-spacing";
|
|
13
|
+
|
|
14
|
+
import type {StoryComponentType} from "@storybook/react";
|
|
15
|
+
|
|
16
|
+
import ComponentInfo from "../../../../../.storybook/components/component-info.js";
|
|
17
|
+
import {name, version} from "../../../package.json";
|
|
18
|
+
|
|
19
|
+
export default {
|
|
20
|
+
title: "Form / Choice",
|
|
21
|
+
component: Choice,
|
|
22
|
+
parameters: {
|
|
23
|
+
componentSubtitle: ((
|
|
24
|
+
<ComponentInfo name={name} version={version} />
|
|
25
|
+
): any),
|
|
26
|
+
},
|
|
27
|
+
};
|
|
28
|
+
|
|
29
|
+
export const Default: StoryComponentType = (args) => {
|
|
30
|
+
const [selectedValues, setSelectedValues] = React.useState([]);
|
|
31
|
+
const [selectedValue, setSelectedValue] = React.useState("");
|
|
32
|
+
|
|
33
|
+
return (
|
|
34
|
+
<View style={styles.row}>
|
|
35
|
+
<CheckboxGroup
|
|
36
|
+
label="Pizza order"
|
|
37
|
+
description="Choose as many toppings as you would like."
|
|
38
|
+
groupName="Toppings"
|
|
39
|
+
onChange={setSelectedValues}
|
|
40
|
+
selectedValues={selectedValues}
|
|
41
|
+
>
|
|
42
|
+
<Choice label="Pepperoni" value="pepperoni" />
|
|
43
|
+
<Choice
|
|
44
|
+
label="Sausage"
|
|
45
|
+
value="sausage"
|
|
46
|
+
description="Imported from Italy"
|
|
47
|
+
/>
|
|
48
|
+
<Choice label="Extra cheese" value="cheese" />
|
|
49
|
+
<Choice label="Green pepper" value="pepper" />
|
|
50
|
+
<Choice label="Mushroom" value="mushroom" />
|
|
51
|
+
<Choice {...args} />
|
|
52
|
+
</CheckboxGroup>
|
|
53
|
+
<Strut size={Spacing.xLarge_32} />
|
|
54
|
+
<RadioGroup
|
|
55
|
+
label="Pizza order"
|
|
56
|
+
description="Choose only one topping."
|
|
57
|
+
groupName="Toppings"
|
|
58
|
+
onChange={setSelectedValue}
|
|
59
|
+
selectedValue={selectedValue}
|
|
60
|
+
>
|
|
61
|
+
<Choice label="Pepperoni" value="pepperoni" />
|
|
62
|
+
<Choice
|
|
63
|
+
label="Sausage"
|
|
64
|
+
value="sausage"
|
|
65
|
+
description="Imported from Italy"
|
|
66
|
+
/>
|
|
67
|
+
<Choice label="Extra cheese" value="cheese" />
|
|
68
|
+
<Choice label="Green pepper" value="pepper" />
|
|
69
|
+
<Choice label="Mushroom" value="mushroom" />
|
|
70
|
+
<Choice {...args} />
|
|
71
|
+
</RadioGroup>
|
|
72
|
+
</View>
|
|
73
|
+
);
|
|
74
|
+
};
|
|
75
|
+
|
|
76
|
+
Default.args = {
|
|
77
|
+
label: "Pineapple (Control)",
|
|
78
|
+
value: "pineapple",
|
|
79
|
+
description: "Does in fact belong on pizzas",
|
|
80
|
+
};
|
|
81
|
+
|
|
82
|
+
const styles = StyleSheet.create({
|
|
83
|
+
row: {
|
|
84
|
+
flexDirection: "row",
|
|
85
|
+
},
|
|
86
|
+
});
|