Created DropdownMenuInnerSelect and implemented it for filter dropdowns (#12626)
This PR introduces a new generic UI component DropdownMenuInnerSelect, that improves the UI by allowing to have both a dropdown menu header and a select in the header. In this PR we implement it just for filter dropdown components. Fixes https://github.com/twentyhq/core-team-issues/issues/1001
This commit is contained in:
@ -22,6 +22,8 @@ const StyledHeader = styled.li`
|
||||
background: ${({ theme, onClick }) =>
|
||||
onClick ? theme.background.transparent.light : 'none'};
|
||||
}
|
||||
|
||||
flex-shrink: 0;
|
||||
`;
|
||||
|
||||
const StyledChildrenWrapper = styled.span`
|
||||
|
||||
@ -0,0 +1,88 @@
|
||||
import { Dropdown } from '@/ui/layout/dropdown/components/Dropdown';
|
||||
import { DropdownContent } from '@/ui/layout/dropdown/components/DropdownContent';
|
||||
import { DropdownMenuItemsContainer } from '@/ui/layout/dropdown/components/DropdownMenuItemsContainer';
|
||||
import { DropdownMenuHotkeyScope } from '@/ui/layout/dropdown/constants/DropdownMenuHotkeyScope';
|
||||
import { useDropdown } from '@/ui/layout/dropdown/hooks/useDropdown';
|
||||
import { useTheme } from '@emotion/react';
|
||||
|
||||
import styled from '@emotion/styled';
|
||||
import { IconChevronDown } from 'twenty-ui/display';
|
||||
import { SelectOption } from 'twenty-ui/input';
|
||||
import { MenuItemSelect } from 'twenty-ui/navigation';
|
||||
|
||||
const StyledDropdownMenuInnerSelectDropdownButton = styled.div`
|
||||
align-items: center;
|
||||
color: ${({ theme }) => theme.font.color.secondary};
|
||||
display: flex;
|
||||
font-size: ${({ theme }) => theme.font.size.sm};
|
||||
|
||||
font-weight: ${({ theme }) => theme.font.weight.medium};
|
||||
height: ${({ theme }) => theme.spacing(7)};
|
||||
|
||||
justify-content: space-between;
|
||||
|
||||
padding-left: ${({ theme }) => theme.spacing(2)};
|
||||
padding-right: ${({ theme }) => theme.spacing(2)};
|
||||
width: 100%;
|
||||
|
||||
box-sizing: border-box;
|
||||
cursor: pointer;
|
||||
`;
|
||||
|
||||
export type DropdownMenuInnerSelectProps = {
|
||||
selectedOption: SelectOption;
|
||||
onChange: (value: SelectOption) => void;
|
||||
options: SelectOption[];
|
||||
dropdownId: string;
|
||||
};
|
||||
|
||||
export const DropdownMenuInnerSelect = ({
|
||||
selectedOption,
|
||||
onChange,
|
||||
options,
|
||||
dropdownId,
|
||||
}: DropdownMenuInnerSelectProps) => {
|
||||
const theme = useTheme();
|
||||
|
||||
const { closeDropdown } = useDropdown(dropdownId);
|
||||
|
||||
return (
|
||||
<Dropdown
|
||||
clickableComponent={
|
||||
<StyledDropdownMenuInnerSelectDropdownButton>
|
||||
<span>{selectedOption.label}</span>
|
||||
<IconChevronDown size={theme.icon.size.sm} />
|
||||
</StyledDropdownMenuInnerSelectDropdownButton>
|
||||
}
|
||||
dropdownComponents={
|
||||
<DropdownContent>
|
||||
<DropdownMenuItemsContainer>
|
||||
{options.map((selectOption) => (
|
||||
<MenuItemSelect
|
||||
key={`dropdown-menu-inner-select-item-${selectOption.value}`}
|
||||
onClick={() => {
|
||||
onChange(selectOption);
|
||||
closeDropdown();
|
||||
}}
|
||||
text={selectOption.label}
|
||||
disabled={selectOption.disabled}
|
||||
selected={selectOption.value === selectedOption.value}
|
||||
/>
|
||||
))}
|
||||
</DropdownMenuItemsContainer>
|
||||
</DropdownContent>
|
||||
}
|
||||
dropdownHotkeyScope={{
|
||||
scope: DropdownMenuHotkeyScope.InnerSelect,
|
||||
customScopes: {
|
||||
commandMenu: false,
|
||||
commandMenuOpen: false,
|
||||
},
|
||||
}}
|
||||
dropdownId={dropdownId}
|
||||
dropdownOffset={{
|
||||
x: 8,
|
||||
}}
|
||||
/>
|
||||
);
|
||||
};
|
||||
@ -0,0 +1,3 @@
|
||||
export enum DropdownMenuHotkeyScope {
|
||||
InnerSelect = 'dropdown-menu-inner-select',
|
||||
}
|
||||
Reference in New Issue
Block a user