Skip to content

Commit

Permalink
checkpoint
Browse files Browse the repository at this point in the history
  • Loading branch information
marco committed Mar 10, 2021
1 parent 96e3d83 commit 022ac21
Show file tree
Hide file tree
Showing 3 changed files with 96 additions and 22 deletions.
26 changes: 26 additions & 0 deletions src/Input/DownshiftSelect/Select.stories.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -379,3 +379,29 @@ ConfigurableWidth.parameters = {
},
},
};

const SmallContainer = styled(Select.Components.Container)`
max-width: 200px;
font-size: 11px;
`;

export const Small = Template.bind({});
Small.args = {
label: "I'm so small!",
placeholder: 'Try typing here :-P',
components: { Container: SmallContainer },
helperText: 'Why would you do this to me?',
};
Small.parameters = {
docs: {
description: {
story:
"<p>By default, the Select dictates a font-size of 16px that cascades through (almost) all sub-components. Appropriate spaces are defined using <code>em</code>, so if you want to resize the Select, just change the container's font-size.</p><p>The exception to the 16px default is the helper text, which also just uses an <code>em</code> relative value.</p>",
},
},
};

export const EmptyListText = Template.bind({});
EmptyListText.args = {
emptyListText: '¯\\_(ツ)_/¯',
};
49 changes: 44 additions & 5 deletions src/Input/DownshiftSelect/Select.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,9 @@ export const defaultTransformFunction = (items: Item[], inputValue: string) =>

export const defaultItemToString = (item: Item) => item.label;

export const defaultEmptyListText =
'No results found. Try another keyword to search for.';

export interface Components {
Container: typeof internalComponents.Container;
Label: typeof internalComponents.Label;
Expand All @@ -24,6 +27,7 @@ export interface Components {
ToggleButton: typeof internalComponents.ToggleButton;
Menu: typeof internalComponents.Menu;
Item: typeof internalComponents.Item;
EmptyList: typeof internalComponents.EmptyList;
HelperText: typeof internalComponents.HelperText;
}

Expand All @@ -46,6 +50,7 @@ export type MenuProps = HTMLAttributes<HTMLElement>;
export interface ItemProps extends HTMLAttributes<HTMLElement> {
item: Item;
}
export type EmptyListProps = HTMLAttributes<HTMLElement>;
export type HelperTextProps = HTMLAttributes<HTMLInputElement>;

export interface Props extends ComboboxProps {
Expand Down Expand Up @@ -95,6 +100,8 @@ export interface Props extends ComboboxProps {
// onInputValueChange?: (inputValue: string) => void;

onClear?: () => void;

emptyListText?: string;
}

export const Select: React.FC<Props> & { Components: Components } = ({
Expand All @@ -117,6 +124,9 @@ export const Select: React.FC<Props> & { Components: Components } = ({
// inputValue: inputValueExternal,
// onInputValueChange: onInputValueChangeExternal,
onClear,
onFocus: onFocusExternal,
onBlur: onBlurExternal,
emptyListText = defaultEmptyListText,
...props
}) => {
const mergedComponents = {
Expand All @@ -135,6 +145,7 @@ export const Select: React.FC<Props> & { Components: Components } = ({
ToggleButton,
Menu,
Item,
EmptyList,
HelperText,
} = mergedComponents;

Expand All @@ -149,6 +160,7 @@ export const Select: React.FC<Props> & { Components: Components } = ({
getMenuProps,
getItemProps,
reset,
openMenu,
} = useCombobox<Item>({
items: displayItems,
onInputValueChange: ({ inputValue }) => {
Expand Down Expand Up @@ -191,12 +203,31 @@ export const Select: React.FC<Props> & { Components: Components } = ({
reset();
};

const [isFocused, setIsFocused] = useState<boolean>(false);
const onFocusInternal = () => {
setIsFocused(true);
openMenu();
};
const onBlurInternal = () => setIsFocused(false);
const onFocus = () => {
if (isFunction(onFocusExternal)) {
onFocusExternal();
}
onFocusInternal();
};
const onBlur = () => {
if (isFunction(onBlurExternal)) {
onBlurExternal();
}
onBlurInternal();
};

return (
<Container>
{label && (
<Label
{...getLabelProps()}
data-active={isOpen}
data-active={isFocused}
data-disabled={disabled}
data-invalid={invalid}
>
Expand All @@ -206,11 +237,16 @@ export const Select: React.FC<Props> & { Components: Components } = ({
<Combobox
{...getComboboxProps()}
data-disabled={disabled}
data-status={status}
data-invalid={invalid}
data-active={isFocused}
>
<Input
{...getInputProps({ disabled: disabled || disableTyping, ...props })}
{...getInputProps({
disabled: disabled || disableTyping,
onFocus,
onBlur,
...props,
})}
placeholder={placeholder}
aria-invalid={invalid}
{...(helperText && { 'aria-describedBy': helperId })}
Expand All @@ -237,7 +273,7 @@ export const Select: React.FC<Props> & { Components: Components } = ({
</IndicatorsContainer>
</Combobox>
<Menu {...getMenuProps()}>
{isOpen &&
{isOpen && displayItems.length > 0 ? (
displayItems.map((item, index) => (
<Item
{...getItemProps({
Expand All @@ -251,7 +287,10 @@ export const Select: React.FC<Props> & { Components: Components } = ({
>
{defaultItemToString(item)}
</Item>
))}
))
) : (
<EmptyList>{emptyListText}</EmptyList>
)}
</Menu>
{helperText && (
<HelperText id={helperId} data-invalid={invalid}>
Expand Down
43 changes: 26 additions & 17 deletions src/Input/DownshiftSelect/SelectStyle.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import {
IndicatorsContainerProps,
InputProps,
ItemProps,
EmptyListProps,
LabelProps,
LoadingIndicatorProps,
MenuProps,
Expand All @@ -17,13 +18,13 @@ import {

export const Container = styled.div<ContainerProps>`
position: relative;
font-size: 16px;
`;

export const Label = styled.label<LabelProps>`
display: block;
margin-bottom: 8px;
color: ${Greyscale.devilsgrey};
font-size: 16px;
font-weight: 500;
&[data-active='true'] {
Expand All @@ -42,17 +43,17 @@ export const Label = styled.label<LabelProps>`
export const Combobox = styled.div<ComboboxProps>`
display: grid;
grid-template-columns: 1fr auto;
grid-column-gap: 12px;
padding: 12px 16px 12px 16px;
border-radius: 8px;
grid-column-gap: 0.75em;
padding: 0.75em 1em 0.75em 1em;
border-radius: 0.5em;
background-color: #ebf5fa;
font-size: 16px;
:hover {
background-color: #d6eaf2;
}
&[aria-expanded='true'] {
&[aria-expanded='true'],
&[data-active='true'] {
background-color: #c2e0ed;
}
Expand All @@ -68,9 +69,9 @@ export const Combobox = styled.div<ComboboxProps>`
export const Input = styled.input<InputProps>`
border: none;
background-color: transparent;
outline: none; // TODO
outline: none; // Okay, because the background-color changes on focus
color: ${Greyscale.devilsgrey};
font-size: 16px;
font-size: inherit;
text-overflow: ellipsis;
&:not([value='']) {
Expand All @@ -86,17 +87,16 @@ export const IndicatorsContainer = styled.div<IndicatorsContainerProps>`
display: flex;
flex-direction: row;
> :not(:last-child) {
margin-right: 12px;
margin-right: 0.75em;
}
font-size: 16px;
`;

export const _IndicatorButton = styled.button`
padding: 0;
border: none;
background: none;
color: ${Greyscale.devilsgrey};
font-size: 16px;
font-size: inherit;
`;

export const ClearButton = styled(_IndicatorButton)<LoadingIndicatorProps>``;
Expand All @@ -105,16 +105,16 @@ export const ToggleButton = styled(_IndicatorButton)<ToggleButtonProps>``;

export const LoadingIndicator = styled(Loading)<LoadingIndicatorProps>`
align-items: center;
font-size: 9px;
font-size: 0.5625em;
`;

export const Menu = styled.ul<MenuProps>`
margin-top: 4px;
position: absolute;
width: 100%;
padding: 8px 0 8px 0;
padding: 0.5em 0 0.5em 0;
border: 1px solid #eeeeee;
border-radius: 8px;
border-radius: 0.5em;
box-shadow: ${Shadow.down3};
background-color: white;
Expand All @@ -124,9 +124,8 @@ export const Menu = styled.ul<MenuProps>`
`;

export const Item = styled.li<ItemProps>`
padding: 8px 16px;
padding: 0.5em 1em;
list-style-type: none;
font-size: 16px;
cursor: pointer;
white-space: nowrap;
overflow: hidden;
Expand All @@ -144,10 +143,20 @@ export const Item = styled.li<ItemProps>`
}
`;

export const EmptyList = styled.li<EmptyListProps>`
padding: 0.5em 1em;
list-style-type: none;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
color: ${Greyscale.lightgrey};
cursor: not-allowed;
`;

export const HelperText = styled.span<HelperTextProps>`
margin-top: 4px;
color: ${Greyscale.devilsgrey};
font-size: 14px;
font-size: 0.875em;
&[data-invalid='true'] {
color: ${PrimaryColor.glintsred};
Expand Down

0 comments on commit 022ac21

Please sign in to comment.