mirror of
https://github.com/elastic/kibana.git
synced 2025-04-23 17:28:26 -04:00
[8.x] [Dashboard][Collapsable Panels] Add auto-scroll for dragging + resizing events (#201867) (#202059)
# Backport This will backport the following commits from `main` to `8.x`: - [[Dashboard][Collapsable Panels] Add auto-scroll for dragging + resizing events (#201867)](https://github.com/elastic/kibana/pull/201867) <!--- Backport version: 9.4.3 --> ### Questions ? Please refer to the [Backport tool documentation](https://github.com/sqren/backport) <!--BACKPORT [{"author":{"name":"Hannah Mudge","email":"Heenawter@users.noreply.github.com"},"sourceCommit":{"committedDate":"2024-11-27T19:39:30Z","message":"[Dashboard][Collapsable Panels] Add auto-scroll for dragging + resizing events (#201867)\n\nCloses https://github.com/elastic/kibana/issues/201626\r\n\r\n## Summary\r\n\r\nThis PR makes it so that the grid layout will auto-scroll with the\r\nfollowing behaviour:\r\n\r\n- Auto-scroll up when....\r\n- the panel is dragged to the top 5% of the window **or above**\r\n(including outside of the window)\r\n- Auto-scroll down when....\r\n- the panel is dragged to the bottom 5% of the window **or below**\r\n(including outside of the window)\r\n- the panel is being dragged and the resize handle is dragged to the\r\nbottom 5% of the window **or below** (including outside of the window)\r\n\r\n\r\n\r\n\r\nhttps://github.com/user-attachments/assets/6880fd14-e492-4cd9-81c6-3dfb30b80960\r\n\r\n\r\n\r\n### Checklist\r\n\r\n- [x] The PR description includes the appropriate Release Notes section,\r\nand the correct `release_note:*` label is applied per the\r\n[guidelines](https://www.elastic.co/guide/en/kibana/master/contributing.html#kibana-release-notes-process)\r\n\r\n### Identify risks\r\n\r\nThere are no risks to this PR, since all work is contained in the\r\n`examples` plugin.","sha":"d81128413dd3f8096e10f85f50b5080edcf088f5","branchLabelMapping":{"^v9.0.0$":"main","^v8.18.0$":"8.x","^v(\\d+).(\\d+).\\d+$":"$1.$2"}},"sourcePullRequest":{"labels":["Feature:Dashboard","Team:Presentation","loe:small","release_note:skip","impact:high","v9.0.0","backport:prev-minor","Project:Collapsable Panels"],"title":"[Dashboard][Collapsable Panels] Add auto-scroll for dragging + resizing events","number":201867,"url":"https://github.com/elastic/kibana/pull/201867","mergeCommit":{"message":"[Dashboard][Collapsable Panels] Add auto-scroll for dragging + resizing events (#201867)\n\nCloses https://github.com/elastic/kibana/issues/201626\r\n\r\n## Summary\r\n\r\nThis PR makes it so that the grid layout will auto-scroll with the\r\nfollowing behaviour:\r\n\r\n- Auto-scroll up when....\r\n- the panel is dragged to the top 5% of the window **or above**\r\n(including outside of the window)\r\n- Auto-scroll down when....\r\n- the panel is dragged to the bottom 5% of the window **or below**\r\n(including outside of the window)\r\n- the panel is being dragged and the resize handle is dragged to the\r\nbottom 5% of the window **or below** (including outside of the window)\r\n\r\n\r\n\r\n\r\nhttps://github.com/user-attachments/assets/6880fd14-e492-4cd9-81c6-3dfb30b80960\r\n\r\n\r\n\r\n### Checklist\r\n\r\n- [x] The PR description includes the appropriate Release Notes section,\r\nand the correct `release_note:*` label is applied per the\r\n[guidelines](https://www.elastic.co/guide/en/kibana/master/contributing.html#kibana-release-notes-process)\r\n\r\n### Identify risks\r\n\r\nThere are no risks to this PR, since all work is contained in the\r\n`examples` plugin.","sha":"d81128413dd3f8096e10f85f50b5080edcf088f5"}},"sourceBranch":"main","suggestedTargetBranches":[],"targetPullRequestStates":[{"branch":"main","label":"v9.0.0","branchLabelMappingKey":"^v9.0.0$","isSourceBranch":true,"state":"MERGED","url":"https://github.com/elastic/kibana/pull/201867","number":201867,"mergeCommit":{"message":"[Dashboard][Collapsable Panels] Add auto-scroll for dragging + resizing events (#201867)\n\nCloses https://github.com/elastic/kibana/issues/201626\r\n\r\n## Summary\r\n\r\nThis PR makes it so that the grid layout will auto-scroll with the\r\nfollowing behaviour:\r\n\r\n- Auto-scroll up when....\r\n- the panel is dragged to the top 5% of the window **or above**\r\n(including outside of the window)\r\n- Auto-scroll down when....\r\n- the panel is dragged to the bottom 5% of the window **or below**\r\n(including outside of the window)\r\n- the panel is being dragged and the resize handle is dragged to the\r\nbottom 5% of the window **or below** (including outside of the window)\r\n\r\n\r\n\r\n\r\nhttps://github.com/user-attachments/assets/6880fd14-e492-4cd9-81c6-3dfb30b80960\r\n\r\n\r\n\r\n### Checklist\r\n\r\n- [x] The PR description includes the appropriate Release Notes section,\r\nand the correct `release_note:*` label is applied per the\r\n[guidelines](https://www.elastic.co/guide/en/kibana/master/contributing.html#kibana-release-notes-process)\r\n\r\n### Identify risks\r\n\r\nThere are no risks to this PR, since all work is contained in the\r\n`examples` plugin.","sha":"d81128413dd3f8096e10f85f50b5080edcf088f5"}}]}] BACKPORT--> Co-authored-by: Hannah Mudge <Heenawter@users.noreply.github.com>
This commit is contained in:
parent
e2dff2ff42
commit
9047db0ceb
1 changed files with 45 additions and 1 deletions
|
@ -13,6 +13,21 @@ import { resolveGridRow } from './utils/resolve_grid_row';
|
|||
import { GridPanelData, GridLayoutStateManager } from './types';
|
||||
import { isGridDataEqual } from './utils/equality_checks';
|
||||
|
||||
const scrollOnInterval = (direction: 'up' | 'down') => {
|
||||
let count = 0;
|
||||
const interval = setInterval(() => {
|
||||
// calculate the speed based on how long the interval has been going to create an ease effect
|
||||
// via the parabola formula `y = a(x - h)^2 + k`
|
||||
// - the starting speed is k = 50
|
||||
// - the maximum speed is 250
|
||||
// - the rate at which the speed increases is controlled by a = 0.75
|
||||
const speed = Math.min(0.75 * count ** 2 + 50, 250);
|
||||
window.scrollBy({ top: direction === 'down' ? speed : -speed, behavior: 'smooth' });
|
||||
count++;
|
||||
}, 100);
|
||||
return interval;
|
||||
};
|
||||
|
||||
export const useGridLayoutEvents = ({
|
||||
gridLayoutStateManager,
|
||||
}: {
|
||||
|
@ -20,14 +35,27 @@ export const useGridLayoutEvents = ({
|
|||
}) => {
|
||||
const mouseClientPosition = useRef({ x: 0, y: 0 });
|
||||
const lastRequestedPanelPosition = useRef<GridPanelData | undefined>(undefined);
|
||||
const scrollInterval = useRef<NodeJS.Timeout | null>(null);
|
||||
|
||||
// -----------------------------------------------------------------------------------------
|
||||
// Set up drag events
|
||||
// -----------------------------------------------------------------------------------------
|
||||
useEffect(() => {
|
||||
const { runtimeSettings$, interactionEvent$, gridLayout$ } = gridLayoutStateManager;
|
||||
|
||||
const stopAutoScrollIfNecessary = () => {
|
||||
if (scrollInterval.current) {
|
||||
clearInterval(scrollInterval.current);
|
||||
scrollInterval.current = null;
|
||||
}
|
||||
};
|
||||
|
||||
const calculateUserEvent = (e: Event) => {
|
||||
if (!interactionEvent$.value) return;
|
||||
if (!interactionEvent$.value) {
|
||||
// if no interaction event, stop auto scroll (if necessary) and return early
|
||||
stopAutoScrollIfNecessary();
|
||||
return;
|
||||
}
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
|
||||
|
@ -122,6 +150,20 @@ export const useGridLayoutEvents = ({
|
|||
requestedGridData.row = targetRow;
|
||||
}
|
||||
|
||||
// auto scroll when an event is happening close to the top or bottom of the screen
|
||||
const heightPercentage =
|
||||
100 - ((window.innerHeight - mouseTargetPixel.y) / window.innerHeight) * 100;
|
||||
const startScrollingUp = !isResize && heightPercentage < 5; // don't scroll up when resizing
|
||||
const startScrollingDown = heightPercentage > 95;
|
||||
if (startScrollingUp || startScrollingDown) {
|
||||
if (!scrollInterval.current) {
|
||||
// only start scrolling if it's not already happening
|
||||
scrollInterval.current = scrollOnInterval(startScrollingUp ? 'up' : 'down');
|
||||
}
|
||||
} else {
|
||||
stopAutoScrollIfNecessary();
|
||||
}
|
||||
|
||||
// resolve the new grid layout
|
||||
if (
|
||||
hasChangedGridRow ||
|
||||
|
@ -153,6 +195,8 @@ export const useGridLayoutEvents = ({
|
|||
};
|
||||
|
||||
const onMouseMove = (e: MouseEvent) => {
|
||||
// Note: When an item is being interacted with, `mousemove` events continue to be fired, even when the
|
||||
// mouse moves out of the window (i.e. when a panel is being dragged around outside the window).
|
||||
mouseClientPosition.current = { x: e.clientX, y: e.clientY };
|
||||
calculateUserEvent(e);
|
||||
};
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue