Refactored and simplified DropdownMenuItemsContainer height management (#12547)
This PR refactors the `DropdownMenuItemsContainer` component and simplifies its inner parts, which have been modified over months for different needs without taking the time to have a global approach. It should however be noted that due to the recent refactor of the `DropdownContent`, it is now much easier to refactor `DropdownMenuItemsContainer`, mainly because of the width management being nicely handled by `DropdownContent` now. Fixes https://github.com/twentyhq/twenty/issues/11766 # Changes The `width` props of `DropdownMenuItemsContainer` and its usage in calling components have been removed. The multiple ternaries inside `DropdownMenuItemsContainer` have been reduced to one ternary on `scrollable` props. The `ScrollWrapper` usage has been removed from `DropdownMenuItemsContainer`, because the only thing we need is to have a simple `overflow-y: scroll;` CSS property. Why ? Because it was previously relevant to have a `ScrollWrapper`, when we were using an external library, but now that `ScrollWrapper` is a simple `div` with overflowing, which only benefit is to expose a hook to imperatively toggle this overflowing behavior from outside (mainly useful for table fixed row and column), and that we don’t need this for `DropdownMenuItemsContainer`, then it follows that we just need a simple overflowing `div` container, which simplifies everything and boils down our `DropdownMenuItemsContainer` to a straightforward and standard CSS stack. We remove the temporary `scrollWrapperHeightAuto` props that was used to fix a bug in a previous PR, we also rollback `ScrollWrapper` to its previous state with `width: 100%` and `height: 100%` and removed `heightAuto` props. The `hasMaxHeight` props is kept, but the `168` pixels value is extracted in a constant. # QA Component | Comment -- | -- CommandMenuActionDropdown | Reported bug https://github.com/twentyhq/twenty/issues/12541 RecordIndexActionMenuDropdown | AttachmentDropdown | Cannot test because cannot add a file (currently broken, maybe because of permissions ?) CommandMenuContextChipGroups | FavoriteFolderNavigationDrawerItemDropdown | FavoriteFolderPicker | FavoriteFolderPickerFooter | AdvancedFilterAddFilterRuleSelect | AdvancedFilterFieldSelectMenu | AdvancedFilterRecordFilterGroupOptionsDropdown | AdvancedFilterRecordFilterOperandSelect | AdvancedFilterRecordFilterOptionsDropdown | AdvancedFilterSubFieldSelectMenu | ObjectFilterDropdownBooleanSelect | ObjectFilterDropdownCountrySelect | ObjectFilterDropdownCurrencySelect | ObjectFilterDropdownNumberInput | ObjectFilterDropdownOptionSelect | Fixed “No result” case ObjectFilterDropdownRecordRemoveFilterMenuItem | Removed because unused ObjectFilterDropdownTextInput | ObjectOptionsDropdownFieldsContent | Spotted bug with icon eye https://github.com/twentyhq/twenty/issues/12545 ObjectOptionsDropdownHiddenFieldsContent | Spotted bug with icon eye https://github.com/twentyhq/twenty/issues/12545 ObjectOptionsDropdownLayoutContent | Refactored DropdownMenuItemsContainer usage with DropdownMenuSeparator, spotted bug switch view type https://github.com/twentyhq/twenty/issues/12546 ObjectOptionsDropdownMenuContent | Refactored DropdownMenuItemsContainer usage with DropdownMenuSeparator ObjectOptionsDropdownLayoutOpenInContent | ObjectOptionsDropdownMenuViewName | ObjectOptionsDropdownRecordGroupFieldsContent | ObjectOptionsDropdownRecordGroupSortContent | ObjectSortDropdownButton | RecordBoardColumnDropdownMenu | RecordBoardColumnDropdownMenu | RecordBoardColumnHeaderAggregateDropdownFieldsContent | RecordBoardColumnHeaderAggregateDropdownMenuContent | RecordBoardColumnHeaderAggregateDropdownOptionsContent | MultiItemFieldInput | Added hasMaxHeight on list of items MultiItemFieldMenuItem | RecordGroupsVisibilityDropdownSection | MultipleRecordPicker | MultipleRecordPickerMenuItems | SingleRecordPickerMenuItems | SingleRecordPickerMenuItemsWithSearch | RecordDetailRelationRecordsListItem | RecordTableColumnAggregateFooterDropdownSubmenuContent | RecordTableColumnAggregateFooterMenuContent | RecordTableHeaderPlusButtonContent | RecordTableHeaderPlusButtonContent | MultipleSelectDropdown | SettingsAccountsRowDropdownMenu | ConfigVariableDatabaseInput | ConfigVariableOptionsDropdownContent | SettingsDataModelNewFieldBreadcrumbDropDown | SettingsDataModelFieldSelectFormOptionRow | SettingsObjectFieldActiveActionDropdown | SettingsObjectFieldInactiveActionDropdown | SettingsObjectInactiveMenuDropDown | SettingsIntegrationDatabaseConnectionSummaryCard | SettingsRoleAssignmentWorkspaceMemberPickerDropdown | SettingsRolePermissionsObjectLevelObjectPickerDropdownContent | Cannot test SettingsSecurityApprovedAccessDomainRowDropdownMenu | Cannot test SettingsSecuritySSORowDropdownMenu | Cannot test SettingsServerlessFunctionTabEnvironmentVariableTableRow | Cannot test MatchColumnSelectFieldSelectDropdownContent | MatchColumnSelectSubFieldSelectDropdownContent | SubMatchingSelectInput | SupportDropdown | IconPicker | Select | SelectInput | CurrencyPickerDropdownSelect | PhoneCountryPickerDropdownSelect | CustomSlashMenu | TabListDropdown | Cannot test MultiWorkspaceDropdownDefaultComponents | Removed unnecessary StyledDropdownMenuItemsContainer MultiWorkspaceDropdownThemesComponents | MultiWorkspaceDropdownWorkspacesListComponents | UpdateViewButtonGroup | ViewBarFilterDropdownFieldSelectMenu | ViewFieldsVisibilityDropdownSection | ViewPickerContentCreateMode | ViewPickerContentEditMode | ViewPickerListContent | Add hasMaxHeight to limit the height of view list ViewPickerOptionDropdown | WorkflowEditTriggerDatabaseEventForm | WorkflowVariablesDropdownFieldItems | WorkflowVariablesDropdownObjectItems | WorkflowVariablesDropdownWorkflowStepItems | <!-- notionvc: a3a87101-9944-4b03-a29d-b2974d5ffa9d --> --------- Co-authored-by: Charles Bochet <charles@twenty.com>
This commit is contained in:
@ -150,7 +150,7 @@ export const AdvancedFilterFieldSelectMenu = ({
|
|||||||
{shouldShowVisibleFields && (
|
{shouldShowVisibleFields && (
|
||||||
<>
|
<>
|
||||||
<DropdownMenuSectionLabel label={t`Visible fields`} />
|
<DropdownMenuSectionLabel label={t`Visible fields`} />
|
||||||
<DropdownMenuItemsContainer scrollWrapperHeightAuto>
|
<DropdownMenuItemsContainer>
|
||||||
{visibleColumnsFieldMetadataItems.map(
|
{visibleColumnsFieldMetadataItems.map(
|
||||||
(visibleFieldMetadataItem, index) => (
|
(visibleFieldMetadataItem, index) => (
|
||||||
<SelectableListItem
|
<SelectableListItem
|
||||||
@ -174,7 +174,7 @@ export const AdvancedFilterFieldSelectMenu = ({
|
|||||||
{shouldShowHiddenFields && (
|
{shouldShowHiddenFields && (
|
||||||
<>
|
<>
|
||||||
<DropdownMenuSectionLabel label={t`Hidden fields`} />
|
<DropdownMenuSectionLabel label={t`Hidden fields`} />
|
||||||
<DropdownMenuItemsContainer scrollWrapperHeightAuto>
|
<DropdownMenuItemsContainer>
|
||||||
{hiddenColumnsFieldMetadataItems.map(
|
{hiddenColumnsFieldMetadataItems.map(
|
||||||
(hiddenFieldMetadataItem, index) => (
|
(hiddenFieldMetadataItem, index) => (
|
||||||
<SelectableListItem
|
<SelectableListItem
|
||||||
|
|||||||
@ -58,7 +58,7 @@ export const ObjectFilterDropdownBooleanSelect = () => {
|
|||||||
selectableItemIdArray={options.map((option) => option.toString())}
|
selectableItemIdArray={options.map((option) => option.toString())}
|
||||||
hotkeyScope={SingleRecordPickerHotkeyScope.SingleRecordPicker}
|
hotkeyScope={SingleRecordPickerHotkeyScope.SingleRecordPicker}
|
||||||
>
|
>
|
||||||
<DropdownMenuItemsContainer hasMaxHeight width="auto">
|
<DropdownMenuItemsContainer hasMaxHeight>
|
||||||
{options.map((option) => (
|
{options.map((option) => (
|
||||||
<StyledBooleanSelectContainer
|
<StyledBooleanSelectContainer
|
||||||
key={String(option)}
|
key={String(option)}
|
||||||
|
|||||||
@ -107,7 +107,7 @@ export const ObjectFilterDropdownCurrencySelect = () => {
|
|||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
<DropdownMenuSeparator />
|
<DropdownMenuSeparator />
|
||||||
<DropdownMenuItemsContainer hasMaxHeight width="auto">
|
<DropdownMenuItemsContainer hasMaxHeight>
|
||||||
{filteredSelectedItems?.map((item) => {
|
{filteredSelectedItems?.map((item) => {
|
||||||
return (
|
return (
|
||||||
<MenuItemMultiSelectAvatar
|
<MenuItemMultiSelectAvatar
|
||||||
|
|||||||
@ -38,7 +38,7 @@ export const ObjectFilterDropdownNumberInput = () => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<DropdownMenuItemsContainer width="auto">
|
<DropdownMenuItemsContainer>
|
||||||
<DropdownMenuInput
|
<DropdownMenuInput
|
||||||
ref={handleInputRef}
|
ref={handleInputRef}
|
||||||
value={objectFilterDropdownFilterValue}
|
value={objectFilterDropdownFilterValue}
|
||||||
|
|||||||
@ -151,21 +151,24 @@ export const ObjectFilterDropdownOptionSelect = () => {
|
|||||||
hotkeyScope={SingleRecordPickerHotkeyScope.SingleRecordPicker}
|
hotkeyScope={SingleRecordPickerHotkeyScope.SingleRecordPicker}
|
||||||
>
|
>
|
||||||
<DropdownMenuItemsContainer hasMaxHeight>
|
<DropdownMenuItemsContainer hasMaxHeight>
|
||||||
{optionsInDropdown?.map((option) => (
|
{showNoResult ? (
|
||||||
<MenuItemMultiSelect
|
<MenuItem text="No results" />
|
||||||
key={option.id}
|
) : (
|
||||||
selected={option.isSelected}
|
optionsInDropdown?.map((option) => (
|
||||||
isKeySelected={option.id === selectedItemId}
|
<MenuItemMultiSelect
|
||||||
onSelectChange={(selected) =>
|
key={option.id}
|
||||||
handleMultipleOptionSelectChange(option, selected)
|
selected={option.isSelected}
|
||||||
}
|
isKeySelected={option.id === selectedItemId}
|
||||||
text={option.label}
|
onSelectChange={(selected) =>
|
||||||
color={option.color}
|
handleMultipleOptionSelectChange(option, selected)
|
||||||
className=""
|
}
|
||||||
/>
|
text={option.label}
|
||||||
))}
|
color={option.color}
|
||||||
|
className=""
|
||||||
|
/>
|
||||||
|
))
|
||||||
|
)}
|
||||||
</DropdownMenuItemsContainer>
|
</DropdownMenuItemsContainer>
|
||||||
{showNoResult && <MenuItem text="No results" />}
|
|
||||||
</SelectableList>
|
</SelectableList>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@ -1,26 +0,0 @@
|
|||||||
import { useEmptyRecordFilter } from '@/object-record/object-filter-dropdown/hooks/useEmptyRecordFilter';
|
|
||||||
import { DropdownMenuItemsContainer } from '@/ui/layout/dropdown/components/DropdownMenuItemsContainer';
|
|
||||||
import { useDropdown } from '@/ui/layout/dropdown/hooks/useDropdown';
|
|
||||||
import { IconFilterOff } from 'twenty-ui/display';
|
|
||||||
import { MenuItem } from 'twenty-ui/navigation';
|
|
||||||
|
|
||||||
export const ObjectFilterDropdownRecordRemoveFilterMenuItem = () => {
|
|
||||||
const { emptyRecordFilter } = useEmptyRecordFilter();
|
|
||||||
|
|
||||||
const { closeDropdown } = useDropdown();
|
|
||||||
|
|
||||||
const handleRemoveFilter = () => {
|
|
||||||
emptyRecordFilter();
|
|
||||||
closeDropdown();
|
|
||||||
};
|
|
||||||
|
|
||||||
return (
|
|
||||||
<DropdownMenuItemsContainer>
|
|
||||||
<MenuItem
|
|
||||||
onClick={handleRemoveFilter}
|
|
||||||
LeftIcon={IconFilterOff}
|
|
||||||
text={'Remove filter'}
|
|
||||||
/>
|
|
||||||
</DropdownMenuItemsContainer>
|
|
||||||
);
|
|
||||||
};
|
|
||||||
@ -38,7 +38,7 @@ export const ObjectFilterDropdownTextInput = () => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<DropdownMenuItemsContainer width="auto">
|
<DropdownMenuItemsContainer>
|
||||||
<DropdownMenuInput
|
<DropdownMenuInput
|
||||||
ref={handleInputRef}
|
ref={handleInputRef}
|
||||||
value={objectFilterDropdownFilterValue}
|
value={objectFilterDropdownFilterValue}
|
||||||
|
|||||||
@ -106,12 +106,12 @@ export const ObjectOptionsDropdownLayoutContent = () => {
|
|||||||
</DropdownMenuHeader>
|
</DropdownMenuHeader>
|
||||||
|
|
||||||
{!!currentView && (
|
{!!currentView && (
|
||||||
<DropdownMenuItemsContainer>
|
<SelectableList
|
||||||
<SelectableList
|
selectableListInstanceId={OBJECT_OPTIONS_DROPDOWN_ID}
|
||||||
selectableListInstanceId={OBJECT_OPTIONS_DROPDOWN_ID}
|
hotkeyScope={TableOptionsHotkeyScope.Dropdown}
|
||||||
hotkeyScope={TableOptionsHotkeyScope.Dropdown}
|
selectableItemIdArray={selectableItemIdArray}
|
||||||
selectableItemIdArray={selectableItemIdArray}
|
>
|
||||||
>
|
<DropdownMenuItemsContainer scrollable={false}>
|
||||||
<SelectableListItem
|
<SelectableListItem
|
||||||
itemId={ViewType.Table}
|
itemId={ViewType.Table}
|
||||||
onEnter={() => {
|
onEnter={() => {
|
||||||
@ -157,7 +157,9 @@ export const ObjectOptionsDropdownLayoutContent = () => {
|
|||||||
onClick={handleSelectKanbanViewType}
|
onClick={handleSelectKanbanViewType}
|
||||||
/>
|
/>
|
||||||
</SelectableListItem>
|
</SelectableListItem>
|
||||||
<DropdownMenuSeparator />
|
</DropdownMenuItemsContainer>
|
||||||
|
<DropdownMenuSeparator />
|
||||||
|
<DropdownMenuItemsContainer scrollable={false}>
|
||||||
<SelectableListItem
|
<SelectableListItem
|
||||||
itemId={ViewOpenRecordInType.SIDE_PANEL}
|
itemId={ViewOpenRecordInType.SIDE_PANEL}
|
||||||
onEnter={() => {
|
onEnter={() => {
|
||||||
@ -232,8 +234,8 @@ export const ObjectOptionsDropdownLayoutContent = () => {
|
|||||||
</SelectableListItem>
|
</SelectableListItem>
|
||||||
</>
|
</>
|
||||||
)}
|
)}
|
||||||
</SelectableList>
|
</DropdownMenuItemsContainer>
|
||||||
</DropdownMenuItemsContainer>
|
</SelectableList>
|
||||||
)}
|
)}
|
||||||
</DropdownContent>
|
</DropdownContent>
|
||||||
);
|
);
|
||||||
|
|||||||
@ -173,7 +173,9 @@ export const ObjectOptionsDropdownMenuContent = () => {
|
|||||||
width="100%"
|
width="100%"
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
<DropdownMenuSeparator />
|
</DropdownMenuItemsContainer>
|
||||||
|
<DropdownMenuSeparator />
|
||||||
|
<DropdownMenuItemsContainer scrollable={false}>
|
||||||
<SelectableListItem
|
<SelectableListItem
|
||||||
itemId="Copy link to view"
|
itemId="Copy link to view"
|
||||||
onEnter={() => {
|
onEnter={() => {
|
||||||
|
|||||||
@ -286,7 +286,7 @@ export const ObjectSortDropdownButton = ({
|
|||||||
{shouldShowVisibleFields && (
|
{shouldShowVisibleFields && (
|
||||||
<>
|
<>
|
||||||
<DropdownMenuSectionLabel label={t`Visible fields`} />
|
<DropdownMenuSectionLabel label={t`Visible fields`} />
|
||||||
<DropdownMenuItemsContainer scrollWrapperHeightAuto>
|
<DropdownMenuItemsContainer>
|
||||||
{visibleFieldMetadataItems.map(
|
{visibleFieldMetadataItems.map(
|
||||||
(visibleFieldMetadataItem, index) => (
|
(visibleFieldMetadataItem, index) => (
|
||||||
<SelectableListItem
|
<SelectableListItem
|
||||||
@ -315,7 +315,7 @@ export const ObjectSortDropdownButton = ({
|
|||||||
{shouldShowHiddenFields && (
|
{shouldShowHiddenFields && (
|
||||||
<>
|
<>
|
||||||
<DropdownMenuSectionLabel label={t`Hidden fields`} />
|
<DropdownMenuSectionLabel label={t`Hidden fields`} />
|
||||||
<DropdownMenuItemsContainer scrollWrapperHeightAuto>
|
<DropdownMenuItemsContainer>
|
||||||
{hiddenFieldMetadataItems.map(
|
{hiddenFieldMetadataItems.map(
|
||||||
(hiddenFieldMetadataItem, index) => (
|
(hiddenFieldMetadataItem, index) => (
|
||||||
<SelectableListItem
|
<SelectableListItem
|
||||||
|
|||||||
@ -184,7 +184,7 @@ export const MultiItemFieldInput = <T,>({
|
|||||||
<DropdownContent ref={containerRef}>
|
<DropdownContent ref={containerRef}>
|
||||||
{!!items.length && (
|
{!!items.length && (
|
||||||
<>
|
<>
|
||||||
<DropdownMenuItemsContainer>
|
<DropdownMenuItemsContainer hasMaxHeight>
|
||||||
{items.map((item, index) =>
|
{items.map((item, index) =>
|
||||||
renderItem({
|
renderItem({
|
||||||
value: item,
|
value: item,
|
||||||
|
|||||||
@ -87,7 +87,7 @@ export const MultipleSelectDropdown = ({
|
|||||||
selectableItemIdArray={selectableItemIds}
|
selectableItemIdArray={selectableItemIds}
|
||||||
hotkeyScope={hotkeyScope}
|
hotkeyScope={hotkeyScope}
|
||||||
>
|
>
|
||||||
<DropdownMenuItemsContainer hasMaxHeight width="auto">
|
<DropdownMenuItemsContainer hasMaxHeight>
|
||||||
{itemsInDropdown?.map((item) => {
|
{itemsInDropdown?.map((item) => {
|
||||||
return (
|
return (
|
||||||
<SelectableListItem
|
<SelectableListItem
|
||||||
|
|||||||
@ -1,12 +1,8 @@
|
|||||||
import { ScrollWrapper } from '@/ui/utilities/scroll/components/ScrollWrapper';
|
import { DROPDOWN_MENU_ITEMS_CONTAINER_MAX_HEIGHT } from '@/ui/layout/dropdown/constants/DropdownMenuItemsContainerMaxHeight';
|
||||||
import { css } from '@emotion/react';
|
|
||||||
import styled from '@emotion/styled';
|
import styled from '@emotion/styled';
|
||||||
import { useId } from 'react';
|
|
||||||
import { isDefined } from 'twenty-shared/utils';
|
|
||||||
|
|
||||||
const StyledDropdownMenuItemsExternalContainer = styled.div<{
|
const StyledExternalContainer = styled.div<{
|
||||||
hasMaxHeight?: boolean;
|
maxHeight?: number;
|
||||||
width: number | 'auto' | '100%';
|
|
||||||
}>`
|
}>`
|
||||||
--padding: ${({ theme }) => theme.spacing(1)};
|
--padding: ${({ theme }) => theme.spacing(1)};
|
||||||
|
|
||||||
@ -14,22 +10,27 @@ const StyledDropdownMenuItemsExternalContainer = styled.div<{
|
|||||||
display: flex;
|
display: flex;
|
||||||
|
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
max-height: ${({ hasMaxHeight }) => (hasMaxHeight ? '168px' : 'none')};
|
max-height: ${({ maxHeight }) => (maxHeight ? `${maxHeight}px` : 'none')};
|
||||||
|
|
||||||
|
width: 100%;
|
||||||
|
|
||||||
|
height: fit-content;
|
||||||
|
|
||||||
padding: var(--padding);
|
padding: var(--padding);
|
||||||
|
box-sizing: border-box;
|
||||||
${({ width }) =>
|
|
||||||
isDefined(width) && width === '100%'
|
|
||||||
? css`
|
|
||||||
width: 100%;
|
|
||||||
`
|
|
||||||
: css`
|
|
||||||
width: ${width}px;
|
|
||||||
`}
|
|
||||||
`;
|
`;
|
||||||
|
|
||||||
const StyledDropdownMenuItemsInternalContainer = styled.div`
|
const StyledScrollableContainer = styled.div<{ maxHeight?: number }>`
|
||||||
align-items: stretch;
|
box-sizing: border-box;
|
||||||
|
|
||||||
|
display: flex;
|
||||||
|
max-height: ${({ maxHeight }) => (maxHeight ? `${maxHeight}px` : 'none')};
|
||||||
|
width: 100%;
|
||||||
|
|
||||||
|
overflow-y: scroll;
|
||||||
|
`;
|
||||||
|
|
||||||
|
const StyledInternalContainer = styled.div`
|
||||||
display: flex;
|
display: flex;
|
||||||
|
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
@ -39,64 +40,28 @@ const StyledDropdownMenuItemsInternalContainer = styled.div`
|
|||||||
width: 100%;
|
width: 100%;
|
||||||
`;
|
`;
|
||||||
|
|
||||||
const StyledScrollWrapper = styled(ScrollWrapper)`
|
|
||||||
width: 100%;
|
|
||||||
`;
|
|
||||||
|
|
||||||
export const DropdownMenuItemsContainer = ({
|
export const DropdownMenuItemsContainer = ({
|
||||||
children,
|
children,
|
||||||
hasMaxHeight,
|
hasMaxHeight,
|
||||||
className,
|
|
||||||
scrollable = true,
|
scrollable = true,
|
||||||
width = 'auto',
|
|
||||||
scrollWrapperHeightAuto,
|
|
||||||
}: {
|
}: {
|
||||||
children: React.ReactNode;
|
children: React.ReactNode;
|
||||||
hasMaxHeight?: boolean;
|
hasMaxHeight?: boolean;
|
||||||
className?: string;
|
|
||||||
scrollable?: boolean;
|
scrollable?: boolean;
|
||||||
width?: number | 'auto' | '100%';
|
|
||||||
scrollWrapperHeightAuto?: boolean;
|
|
||||||
}) => {
|
}) => {
|
||||||
const id = useId();
|
return scrollable === true ? (
|
||||||
|
<StyledScrollableContainer
|
||||||
return scrollable !== true ? (
|
maxHeight={
|
||||||
<StyledDropdownMenuItemsExternalContainer
|
hasMaxHeight ? DROPDOWN_MENU_ITEMS_CONTAINER_MAX_HEIGHT : undefined
|
||||||
hasMaxHeight={hasMaxHeight}
|
}
|
||||||
className={className}
|
|
||||||
role="listbox"
|
|
||||||
width={width}
|
|
||||||
>
|
>
|
||||||
{hasMaxHeight ? (
|
<StyledExternalContainer role="listbox">
|
||||||
<StyledScrollWrapper
|
<StyledInternalContainer>{children}</StyledInternalContainer>
|
||||||
componentInstanceId={`scroll-wrapper-dropdown-menu-${id}`}
|
</StyledExternalContainer>
|
||||||
heightAuto={scrollWrapperHeightAuto}
|
</StyledScrollableContainer>
|
||||||
>
|
|
||||||
<StyledDropdownMenuItemsInternalContainer>
|
|
||||||
{children}
|
|
||||||
</StyledDropdownMenuItemsInternalContainer>
|
|
||||||
</StyledScrollWrapper>
|
|
||||||
) : (
|
|
||||||
<StyledDropdownMenuItemsInternalContainer>
|
|
||||||
{children}
|
|
||||||
</StyledDropdownMenuItemsInternalContainer>
|
|
||||||
)}
|
|
||||||
</StyledDropdownMenuItemsExternalContainer>
|
|
||||||
) : (
|
) : (
|
||||||
<ScrollWrapper
|
<StyledExternalContainer role="listbox">
|
||||||
componentInstanceId={`scroll-wrapper-dropdown-menu-${id}`}
|
<StyledInternalContainer>{children}</StyledInternalContainer>
|
||||||
heightAuto={scrollWrapperHeightAuto}
|
</StyledExternalContainer>
|
||||||
>
|
|
||||||
<StyledDropdownMenuItemsExternalContainer
|
|
||||||
hasMaxHeight={hasMaxHeight}
|
|
||||||
className={className}
|
|
||||||
role="listbox"
|
|
||||||
width={width}
|
|
||||||
>
|
|
||||||
<StyledDropdownMenuItemsInternalContainer>
|
|
||||||
{children}
|
|
||||||
</StyledDropdownMenuItemsInternalContainer>
|
|
||||||
</StyledDropdownMenuItemsExternalContainer>
|
|
||||||
</ScrollWrapper>
|
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@ -0,0 +1 @@
|
|||||||
|
export const DROPDOWN_MENU_ITEMS_CONTAINER_MAX_HEIGHT = 168;
|
||||||
@ -46,11 +46,6 @@ const StyledDescription = styled.div`
|
|||||||
padding-left: ${({ theme }) => theme.spacing(1)};
|
padding-left: ${({ theme }) => theme.spacing(1)};
|
||||||
`;
|
`;
|
||||||
|
|
||||||
const StyledDropdownMenuItemsContainer = styled.div`
|
|
||||||
margin: ${({ theme }) => theme.spacing(1)} 0;
|
|
||||||
padding: 0 ${({ theme }) => theme.spacing(1)};
|
|
||||||
`;
|
|
||||||
|
|
||||||
export const MultiWorkspaceDropdownDefaultComponents = () => {
|
export const MultiWorkspaceDropdownDefaultComponents = () => {
|
||||||
const currentWorkspace = useRecoilValue(currentWorkspaceState);
|
const currentWorkspace = useRecoilValue(currentWorkspaceState);
|
||||||
const { t } = useLingui();
|
const { t } = useLingui();
|
||||||
@ -134,7 +129,7 @@ export const MultiWorkspaceDropdownDefaultComponents = () => {
|
|||||||
</DropdownMenuHeader>
|
</DropdownMenuHeader>
|
||||||
{workspaces.length > 1 && (
|
{workspaces.length > 1 && (
|
||||||
<>
|
<>
|
||||||
<StyledDropdownMenuItemsContainer>
|
<DropdownMenuItemsContainer>
|
||||||
{workspaces
|
{workspaces
|
||||||
.filter(({ id }) => id !== currentWorkspace?.id)
|
.filter(({ id }) => id !== currentWorkspace?.id)
|
||||||
.slice(0, 3)
|
.slice(0, 3)
|
||||||
@ -171,7 +166,7 @@ export const MultiWorkspaceDropdownDefaultComponents = () => {
|
|||||||
hasSubMenu={true}
|
hasSubMenu={true}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
</StyledDropdownMenuItemsContainer>
|
</DropdownMenuItemsContainer>
|
||||||
<DropdownMenuSeparator />
|
<DropdownMenuSeparator />
|
||||||
</>
|
</>
|
||||||
)}
|
)}
|
||||||
|
|||||||
@ -7,7 +7,7 @@ import { scrollWrapperScrollLeftComponentState } from '@/ui/utilities/scroll/sta
|
|||||||
import { scrollWrapperScrollTopComponentState } from '@/ui/utilities/scroll/states/scrollWrapperScrollTopComponentState';
|
import { scrollWrapperScrollTopComponentState } from '@/ui/utilities/scroll/states/scrollWrapperScrollTopComponentState';
|
||||||
import { useSetRecoilComponentStateV2 } from '@/ui/utilities/state/component-state/hooks/useSetRecoilComponentStateV2';
|
import { useSetRecoilComponentStateV2 } from '@/ui/utilities/state/component-state/hooks/useSetRecoilComponentStateV2';
|
||||||
|
|
||||||
const StyledScrollWrapper = styled.div<{ height: string }>`
|
const StyledScrollWrapper = styled.div`
|
||||||
&.scroll-wrapper-x-enabled {
|
&.scroll-wrapper-x-enabled {
|
||||||
overflow-x: overlay;
|
overflow-x: overlay;
|
||||||
}
|
}
|
||||||
@ -17,7 +17,7 @@ const StyledScrollWrapper = styled.div<{ height: string }>`
|
|||||||
overflow-x: hidden;
|
overflow-x: hidden;
|
||||||
overflow-y: hidden;
|
overflow-y: hidden;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
height: ${({ height }) => height};
|
height: 100%;
|
||||||
`;
|
`;
|
||||||
|
|
||||||
export type ScrollWrapperProps = {
|
export type ScrollWrapperProps = {
|
||||||
@ -26,7 +26,6 @@ export type ScrollWrapperProps = {
|
|||||||
defaultEnableXScroll?: boolean;
|
defaultEnableXScroll?: boolean;
|
||||||
defaultEnableYScroll?: boolean;
|
defaultEnableYScroll?: boolean;
|
||||||
componentInstanceId: string;
|
componentInstanceId: string;
|
||||||
heightAuto?: boolean;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
export const ScrollWrapper = ({
|
export const ScrollWrapper = ({
|
||||||
@ -35,7 +34,6 @@ export const ScrollWrapper = ({
|
|||||||
className,
|
className,
|
||||||
defaultEnableXScroll = true,
|
defaultEnableXScroll = true,
|
||||||
defaultEnableYScroll = true,
|
defaultEnableYScroll = true,
|
||||||
heightAuto = false,
|
|
||||||
}: ScrollWrapperProps) => {
|
}: ScrollWrapperProps) => {
|
||||||
const setScrollTop = useSetRecoilComponentStateV2(
|
const setScrollTop = useSetRecoilComponentStateV2(
|
||||||
scrollWrapperScrollTopComponentState,
|
scrollWrapperScrollTopComponentState,
|
||||||
@ -73,7 +71,6 @@ export const ScrollWrapper = ({
|
|||||||
id={`scroll-wrapper-${componentInstanceId}`}
|
id={`scroll-wrapper-${componentInstanceId}`}
|
||||||
className={className}
|
className={className}
|
||||||
onScroll={handleScroll}
|
onScroll={handleScroll}
|
||||||
height={heightAuto ? 'auto' : '100%'}
|
|
||||||
>
|
>
|
||||||
{children}
|
{children}
|
||||||
</StyledScrollWrapper>
|
</StyledScrollWrapper>
|
||||||
|
|||||||
@ -98,8 +98,7 @@ export const ViewBarFilterDropdownFieldSelectMenu = () => {
|
|||||||
{shouldShowVisibleFields && (
|
{shouldShowVisibleFields && (
|
||||||
<>
|
<>
|
||||||
<DropdownMenuSectionLabel label={t`Visible fields`} />
|
<DropdownMenuSectionLabel label={t`Visible fields`} />
|
||||||
|
<DropdownMenuItemsContainer>
|
||||||
<DropdownMenuItemsContainer scrollWrapperHeightAuto>
|
|
||||||
{selectableVisibleFieldMetadataItems.map(
|
{selectableVisibleFieldMetadataItems.map(
|
||||||
(visibleFieldMetadataItem) => (
|
(visibleFieldMetadataItem) => (
|
||||||
<ViewBarFilterDropdownFieldSelectMenuItem
|
<ViewBarFilterDropdownFieldSelectMenuItem
|
||||||
@ -115,7 +114,7 @@ export const ViewBarFilterDropdownFieldSelectMenu = () => {
|
|||||||
{shouldShowHiddenFields && (
|
{shouldShowHiddenFields && (
|
||||||
<>
|
<>
|
||||||
<DropdownMenuSectionLabel label={t`Hidden fields`} />
|
<DropdownMenuSectionLabel label={t`Hidden fields`} />
|
||||||
<DropdownMenuItemsContainer scrollWrapperHeightAuto>
|
<DropdownMenuItemsContainer>
|
||||||
{selectableHiddenFieldMetadataItems.map(
|
{selectableHiddenFieldMetadataItems.map(
|
||||||
(hiddenFieldMetadataItem) => (
|
(hiddenFieldMetadataItem) => (
|
||||||
<ViewBarFilterDropdownFieldSelectMenuItem
|
<ViewBarFilterDropdownFieldSelectMenuItem
|
||||||
|
|||||||
@ -96,7 +96,7 @@ export const ViewPickerListContent = () => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<DropdownContent>
|
<DropdownContent>
|
||||||
<DropdownMenuItemsContainer>
|
<DropdownMenuItemsContainer hasMaxHeight>
|
||||||
<DraggableList
|
<DraggableList
|
||||||
onDragEnd={handleDragEnd}
|
onDragEnd={handleDragEnd}
|
||||||
draggableItems={viewsOnCurrentObject.map((view, index) => {
|
draggableItems={viewsOnCurrentObject.map((view, index) => {
|
||||||
|
|||||||
Reference in New Issue
Block a user