fix(Dashboard): Add border to row when hovering HoverMenu in edit mode (#27593)

(cherry picked from commit 265390c243)
This commit is contained in:
Ross Mabbett 2024-04-04 19:31:07 -04:00 committed by Michael S. Molina
parent 899cd0eda8
commit ecc6ced4d4
4 changed files with 53 additions and 3 deletions

View File

@ -186,6 +186,11 @@ const DashboardContentWrapper = styled.div`
pointer-events: none;
}
.grid-row.grid-row--hovered:after,
.dashboard-component-tabs > .grid-row--hovered:after {
border: 2px dashed ${theme.colors.primary.base};
}
.resizable-container {
& .dashboard-component-chart-holder {
.dashboard-chart {

View File

@ -135,6 +135,7 @@ class Row extends React.PureComponent {
this.state = {
isFocused: false,
isInView: false,
hoverMenuHovered: false,
};
this.handleDeleteComponent = this.handleDeleteComponent.bind(this);
this.handleUpdateMeta = this.handleUpdateMeta.bind(this);
@ -143,6 +144,7 @@ class Row extends React.PureComponent {
'background',
);
this.handleChangeFocus = this.handleChangeFocus.bind(this);
this.handleMenuHover = this.handleMenuHover.bind(this);
this.setVerticalEmptyContainerHeight = debounce(
this.setVerticalEmptyContainerHeight.bind(this),
FAST_DEBOUNCE,
@ -235,6 +237,11 @@ class Row extends React.PureComponent {
deleteComponent(component.id, parentId);
}
handleMenuHover = hovered => {
const { isHovered } = hovered;
this.setState(() => ({ hoverMenuHovered: isHovered }));
};
render() {
const {
component: rowComponent,
@ -252,7 +259,7 @@ class Row extends React.PureComponent {
onChangeTab,
isComponentVisible,
} = this.props;
const { containerHeight } = this.state;
const { containerHeight, hoverMenuHovered } = this.state;
const rowItems = rowComponent.children || [];
@ -287,7 +294,11 @@ class Row extends React.PureComponent {
editMode={editMode}
>
{editMode && (
<HoverMenu innerRef={dragSourceRef} position="left">
<HoverMenu
onHover={this.handleMenuHover}
innerRef={dragSourceRef}
position="left"
>
<DragHandle position="left" />
<DeleteComponentButton onDelete={this.handleDeleteComponent} />
<IconButton
@ -300,6 +311,7 @@ class Row extends React.PureComponent {
className={cx(
'grid-row',
rowItems.length === 0 && 'grid-row--empty',
hoverMenuHovered && 'grid-row--hovered',
backgroundStyle.className,
)}
data-test={`grid-row-${backgroundStyle.className}`}

View File

@ -17,7 +17,8 @@
* under the License.
*/
import React from 'react';
import { render } from 'spec/helpers/testing-library';
import { render, screen } from 'spec/helpers/testing-library';
import userEvent from '@testing-library/user-event';
import HoverMenu from 'src/dashboard/components/menu/HoverMenu';
@ -25,3 +26,16 @@ test('should render a div.hover-menu', () => {
const { container } = render(<HoverMenu />);
expect(container.querySelector('.hover-menu')).toBeInTheDocument();
});
test('should call onHover when mouse enters and leaves', () => {
const onHover = jest.fn();
render(<HoverMenu onHover={onHover} />);
const hoverMenu = screen.getByTestId('hover-menu');
userEvent.hover(hoverMenu);
expect(onHover).toBeCalledWith({ isHovered: true });
userEvent.unhover(hoverMenu);
expect(onHover).toBeCalledWith({ isHovered: false });
});

View File

@ -1,3 +1,4 @@
/* eslint-disable react/no-unused-state */
/**
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
@ -24,6 +25,7 @@ interface HoverMenuProps {
position: 'left' | 'top';
innerRef: RefObject<HTMLDivElement>;
children: React.ReactNode;
onHover?: (data: { isHovered: boolean }) => void;
}
const HoverStyleOverrides = styled.div`
@ -70,6 +72,20 @@ export default class HoverMenu extends React.PureComponent<HoverMenuProps> {
children: null,
};
handleMouseEnter = () => {
const { onHover } = this.props;
if (onHover) {
onHover({ isHovered: true });
}
};
handleMouseLeave = () => {
const { onHover } = this.props;
if (onHover) {
onHover({ isHovered: false });
}
};
render() {
const { innerRef, position, children } = this.props;
return (
@ -81,6 +97,9 @@ export default class HoverMenu extends React.PureComponent<HoverMenuProps> {
position === 'left' && 'hover-menu--left',
position === 'top' && 'hover-menu--top',
)}
onMouseEnter={this.handleMouseEnter}
onMouseLeave={this.handleMouseLeave}
data-test="hover-menu"
>
{children}
</div>