Skip to content

Commit 1b1a6f3

Browse files
committed
Select input initial commit
1 parent 4005d6a commit 1b1a6f3

File tree

4 files changed

+121
-0
lines changed

4 files changed

+121
-0
lines changed
Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
import React, {useState} from 'react'
2+
import {Meta} from '@storybook/react'
3+
4+
import {BaseStyles, Box, ThemeProvider} from '..'
5+
import {SelectInput, SelectInputProps} from '.'
6+
7+
export default {
8+
title: 'Forms/Select Input',
9+
component: SelectInput,
10+
decorators: [
11+
Story => {
12+
return (
13+
<ThemeProvider>
14+
<BaseStyles>
15+
<Box paddingTop={5}>{Story()}</Box>
16+
</BaseStyles>
17+
</ThemeProvider>
18+
)
19+
}
20+
],
21+
argTypes: {
22+
disabled: {
23+
name: 'Disabled',
24+
defaultValue: false,
25+
control: {
26+
type: 'boolean'
27+
}
28+
},
29+
size: {
30+
name: 'Sizes',
31+
options: ['small', 'medium', 'large'],
32+
control: {type: 'radio'}
33+
}
34+
}
35+
} as Meta
36+
37+
export const Default = ({...args}: SelectInputProps) => {
38+
const [selectedValue, setSelected] = useState<string | undefined>(undefined)
39+
const handleChange = () => {
40+
setSelected(selectedValue)
41+
}
42+
43+
return (
44+
<>
45+
<Box as="form" p={3} sx={{display: 'flex', alignItems: 'flex-start'}}>
46+
<SelectInput selectedValue={selectedValue} onSelect={handleChange} {...args}>
47+
<SelectInput.Option value="">Choose your option</SelectInput.Option>
48+
<SelectInput.Option value="1">1</SelectInput.Option>
49+
<SelectInput.Option value="2">2</SelectInput.Option>
50+
<SelectInput.Option value="3">3</SelectInput.Option>
51+
</SelectInput>
52+
</Box>
53+
</>
54+
)
55+
}

src/SelectInput/SelectInput.tsx

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
import React, {HTMLAttributes, ComponentPropsWithRef} from 'react'
2+
import styled from 'styled-components'
3+
import TextInputWrapper from '../_TextInputWrapper'
4+
import UnstyledSelectInput from './_UnstyledSelectInput'
5+
import {SxProp} from '../sx'
6+
import {TriangleDownIcon, TriangleUpIcon} from '@primer/octicons-react'
7+
8+
const SelectCaret = styled.span`
9+
display: grid;
10+
grid-template-rows: 1fr 1fr;
11+
`
12+
13+
export type SelectInputProps = {
14+
disabled?: boolean
15+
selectedValue?: string | undefined
16+
children: React.ReactNode
17+
size?: 'small' | 'large'
18+
} & SxProp &
19+
HTMLAttributes<HTMLButtonElement> &
20+
ComponentPropsWithRef<typeof UnstyledSelectInput>
21+
22+
type OptionProps = {children: string; value: string | undefined}
23+
24+
const OptionComponent = (props: OptionProps) => {
25+
return <option>{props.children}</option>
26+
}
27+
28+
const SelectInputComponent = React.forwardRef<HTMLSelectElement, SelectInputProps>(
29+
({sx, size, selectedValue, children, ...props}: SelectInputProps, ref) => {
30+
return (
31+
<TextInputWrapper disabled={props.disabled} sx={sx} variant={size}>
32+
<UnstyledSelectInput ref={ref} value={selectedValue} {...props}>
33+
{children}
34+
</UnstyledSelectInput>
35+
<SelectCaret>
36+
<TriangleUpIcon />
37+
<TriangleDownIcon />
38+
</SelectCaret>
39+
</TextInputWrapper>
40+
)
41+
}
42+
)
43+
44+
const SelectInput = Object.assign(SelectInputComponent, {Option: OptionComponent})
45+
46+
export {SelectInput}
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
import styled from 'styled-components'
2+
import sx from '../sx'
3+
4+
const UnstyledSelectInput = styled.select`
5+
border: 0;
6+
font-size: inherit;
7+
font-family: inherit;
8+
background-color: transparent;
9+
-webkit-appearance: none;
10+
color: inherit;
11+
width: 100%;
12+
&:focus {
13+
outline: 0;
14+
}
15+
16+
${sx};
17+
`
18+
19+
export default UnstyledSelectInput

src/SelectInput/index.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
export {SelectInput, SelectInputProps} from './SelectInput'

0 commit comments

Comments
 (0)