From 814a78ba4627b39fb7b003527f14ee31733ccd8a Mon Sep 17 00:00:00 2001 From: Ryan McKinley Date: Fri, 22 Oct 2021 09:16:32 -0700 Subject: [PATCH] Value mappings: scroll values when many items exist (#40733) --- .../grafana-ui/src/components/Modal/Modal.tsx | 17 ++- .../ValueMappingsEditorModal.test.tsx | 4 +- .../ValueMappingsEditorModal.tsx | 106 +++++++++++------- .../components/ValuePicker/ValuePicker.tsx | 32 +++--- .../PanelEditor/getFieldOverrideElements.tsx | 1 + 5 files changed, 101 insertions(+), 59 deletions(-) diff --git a/packages/grafana-ui/src/components/Modal/Modal.tsx b/packages/grafana-ui/src/components/Modal/Modal.tsx index bdc734687d1..c92377aca91 100644 --- a/packages/grafana-ui/src/components/Modal/Modal.tsx +++ b/packages/grafana-ui/src/components/Modal/Modal.tsx @@ -89,10 +89,25 @@ export function Modal(props: PropsWithChildren) { ); } -function ModalButtonRow({ children }: { children: React.ReactNode }) { +function ModalButtonRow({ leftItems, children }: { leftItems?: React.ReactNode; children: React.ReactNode }) { const theme = useTheme2(); const styles = getModalStyles(theme); + if (leftItems) { + return ( +
+ + + {leftItems} + + + {children} + + +
+ ); + } + return (
diff --git a/packages/grafana-ui/src/components/ValueMappingsEditor/ValueMappingsEditorModal.test.tsx b/packages/grafana-ui/src/components/ValueMappingsEditor/ValueMappingsEditorModal.test.tsx index da80804f835..9c961ded1ad 100644 --- a/packages/grafana-ui/src/components/ValueMappingsEditor/ValueMappingsEditorModal.test.tsx +++ b/packages/grafana-ui/src/components/ValueMappingsEditor/ValueMappingsEditorModal.test.tsx @@ -121,6 +121,7 @@ describe('When adding and updating range map', () => { it('should add new range map', async () => { const onChangeSpy = jest.fn(); setup(onChangeSpy, { value: [] }); + screen.getAllByTestId('remove-value-mapping')[0].click(); fireEvent.click(screen.getByLabelText(selectors.components.ValuePicker.button('Add a new mapping'))); const selectComponent = await screen.findByLabelText(selectors.components.ValuePicker.select('Add a new mapping')); @@ -148,10 +149,11 @@ describe('When adding and updating range map', () => { }); }); -describe('When adding and updating tegex map', () => { +describe('When adding and updating regex map', () => { it('should add new regex map', async () => { const onChangeSpy = jest.fn(); setup(onChangeSpy, { value: [] }); + screen.getAllByTestId('remove-value-mapping')[0].click(); fireEvent.click(screen.getByLabelText(selectors.components.ValuePicker.button('Add a new mapping'))); const selectComponent = await screen.findByLabelText(selectors.components.ValuePicker.select('Add a new mapping')); diff --git a/packages/grafana-ui/src/components/ValueMappingsEditor/ValueMappingsEditorModal.tsx b/packages/grafana-ui/src/components/ValueMappingsEditor/ValueMappingsEditorModal.tsx index 4feae052e3d..1951015bb67 100644 --- a/packages/grafana-ui/src/components/ValueMappingsEditor/ValueMappingsEditorModal.tsx +++ b/packages/grafana-ui/src/components/ValueMappingsEditor/ValueMappingsEditorModal.tsx @@ -81,51 +81,65 @@ export function ValueMappingsEditorModal({ value, onChange, onClose }: Props) { onClose(); }; + // Start with an empty row + useEffect(() => { + if (!value?.length) { + onAddValueMapping({ value: MappingType.ValueToText }); + } + // eslint-disable-next-line react-hooks/exhaustive-deps + }, []); + return ( <> - - - - - - - - - - - - - {(provided) => ( - - {rows.map((row, index) => ( - - ))} - {provided.placeholder} - - )} - - -
- Condition - Display textColor
- - +
+ + + + + + + + + + + + + {(provided) => ( + + {rows.map((row, index) => ( + + ))} + {provided.placeholder} + + )} + + +
+ Condition + Display textColor
+
+ + + } + > @@ -138,6 +152,12 @@ export function ValueMappingsEditorModal({ value, onChange, onClose }: Props) { } export const getStyles = (theme: GrafanaTheme2) => ({ + tableWrap: css` + max-height: calc(80vh - 170px); + min-height: 40px; + overflow: auto; + `, + editTable: css({ width: '100%', marginBottom: theme.spacing(2), diff --git a/packages/grafana-ui/src/components/ValuePicker/ValuePicker.tsx b/packages/grafana-ui/src/components/ValuePicker/ValuePicker.tsx index becb214cf7a..53c68bcb47f 100644 --- a/packages/grafana-ui/src/components/ValuePicker/ValuePicker.tsx +++ b/packages/grafana-ui/src/components/ValuePicker/ValuePicker.tsx @@ -3,9 +3,9 @@ import { IconName } from '../../types'; import { SelectableValue } from '@grafana/data'; import { Button, ButtonVariant } from '../Button'; import { Select } from '../Select/Select'; -import { FullWidthButtonContainer } from '../Button/FullWidthButtonContainer'; import { ComponentSize } from '../../types/size'; import { selectors } from '@grafana/e2e-selectors'; +import { useTheme2 } from '../../themes'; export interface ValuePickerProps { /** Label to display on the picker button */ @@ -20,6 +20,8 @@ export interface ValuePickerProps { variant?: ButtonVariant; /** Size of button */ size?: ComponentSize; + /** Min width for select in grid units */ + minWidth?: number; /** Should the picker cover the full width of its parent */ isFullWidth?: boolean; /** Control where the menu is rendered */ @@ -32,29 +34,31 @@ export function ValuePicker({ options, onChange, variant, + minWidth = 16, size = 'sm', isFullWidth = true, menuPlacement, }: ValuePickerProps) { const [isPicking, setIsPicking] = useState(false); + const theme = useTheme2(); - const buttonEl = ( - - ); return ( <> - {!isPicking && (isFullWidth ? {buttonEl} : buttonEl)} + {!isPicking && ( + + )} {isPicking && ( - +