mirror of
https://github.com/elastic/kibana.git
synced 2025-04-24 17:59:23 -04:00
# Backport This will backport the following commits from `main` to `8.x`: - [[Dashboard] [Collapsable Panels] Add embeddable support (#198413)](https://github.com/elastic/kibana/pull/198413) <!--- 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-12-10T17:14:31Z","message":"[Dashboard] [Collapsable Panels] Add embeddable support (#198413)\n\nCloses https://github.com/elastic/kibana/issues/190379\r\n\r\n## Summary\r\n\r\nThis PR switches the example grid layout app to render embeddables as\r\npanels rather than the simplified mock panel we were using previously.\r\nIn doing so, I had to add the ability for custom panels to add a custom\r\ndrag handle via the `renderPanelContents` callback - this required\r\nadding a `setDragHandles` callback to the `ReactEmbeddableRenderer` that\r\ncould be passed down to the `PresentationPanel` component.\r\n\r\n\r\n\r\n\r\nhttps://github.com/user-attachments/assets/9e2c68f9-34af-4360-a978-9113701a5ea2\r\n\r\n\r\n\r\n#### New scroll behaviour\r\n\r\nIn https://github.com/elastic/kibana/pull/201867, I introduced a small\r\n\"ease\" to the auto-scroll effect that happens when you drag a panel to\r\nthe top or bottom of the window. However, in that PR, I was using the\r\n`smooth` scrolling behaviour, which unfortunately became **very**\r\njittery once I switched to embeddables rather than simple panels\r\n(specifically in Chrome - it worked fine in Firefox).\r\n\r\nThe only way to prevent this jittery scroll was to switch to the default\r\nscroll behaviour, but this lead to a very **abrupt** stop when the\r\nscrollbar reached the top and/or bottom of the page - so, to give the\r\nsame \"gentle\" stop that the `smooth` scroll had, I decided to recreate\r\nthis effect by adding a slow down \"ease\" when close to the top or bottom\r\nof the page:\r\n\r\n\r\nhttps://github.com/user-attachments/assets/cb7bf03f-4a9e-4446-be4f-8f54c0bc88ac\r\n\r\nThis effect is accomplished via the parabola formula `y = a(x-h)2 + k`\r\nand can be roughly visualized with the following, which shows that the\r\n\"speed up\" ease happens at a much slower pace than the \"slow down\" ease:\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n#### Notes about parent changes\r\nAs I investigated improving the efficiency of the grid layout with\r\nembeddables, one of the main things I noticed was that the grid panel\r\nwas **always** remounted when moving a panel from one collapsible\r\nsection to another. This lead me (and @ThomThomson) down a rabbit hole\r\nof React-reparenting, and we explored a few different options to see if\r\nwe could change the parent of a component **without** having it remount.\r\n\r\nIn summary, after various experiments and a whole bunch of research, we\r\ndetermined that, due to the reconciliation of the React tree, this is\r\nunfortunately impossible. So our priorities will instead have to move to\r\nmaking the remount of `ReactEmbeddableRenderer` **as efficient as\r\npossible** via caching, since the remount is inevitable.\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 the most significant work is\r\ncontained in the `examples` plugin. Some changes were made to the\r\npresentation panel to allow for custom drag handles, but this isn't\r\nactually used in Dashboard - so for now, this code is only called in the\r\nexample plugin, as well.\r\n\r\n---------\r\n\r\nCo-authored-by: kibanamachine <42973632+kibanamachine@users.noreply.github.com>","sha":"2a76fe3ee432d0b6746eae660cfe31fc71d15547","branchLabelMapping":{"^v9.0.0$":"main","^v8.18.0$":"8.x","^v(\\d+).(\\d+).\\d+$":"$1.$2"}},"sourcePullRequest":{"labels":["Feature:Dashboard","Feature:Embedding","Team:Presentation","loe:medium","release_note:skip","impact:high","v9.0.0","backport:prev-minor","Project:Collapsable Panels"],"title":"[Dashboard] [Collapsable Panels] Add embeddable support","number":198413,"url":"https://github.com/elastic/kibana/pull/198413","mergeCommit":{"message":"[Dashboard] [Collapsable Panels] Add embeddable support (#198413)\n\nCloses https://github.com/elastic/kibana/issues/190379\r\n\r\n## Summary\r\n\r\nThis PR switches the example grid layout app to render embeddables as\r\npanels rather than the simplified mock panel we were using previously.\r\nIn doing so, I had to add the ability for custom panels to add a custom\r\ndrag handle via the `renderPanelContents` callback - this required\r\nadding a `setDragHandles` callback to the `ReactEmbeddableRenderer` that\r\ncould be passed down to the `PresentationPanel` component.\r\n\r\n\r\n\r\n\r\nhttps://github.com/user-attachments/assets/9e2c68f9-34af-4360-a978-9113701a5ea2\r\n\r\n\r\n\r\n#### New scroll behaviour\r\n\r\nIn https://github.com/elastic/kibana/pull/201867, I introduced a small\r\n\"ease\" to the auto-scroll effect that happens when you drag a panel to\r\nthe top or bottom of the window. However, in that PR, I was using the\r\n`smooth` scrolling behaviour, which unfortunately became **very**\r\njittery once I switched to embeddables rather than simple panels\r\n(specifically in Chrome - it worked fine in Firefox).\r\n\r\nThe only way to prevent this jittery scroll was to switch to the default\r\nscroll behaviour, but this lead to a very **abrupt** stop when the\r\nscrollbar reached the top and/or bottom of the page - so, to give the\r\nsame \"gentle\" stop that the `smooth` scroll had, I decided to recreate\r\nthis effect by adding a slow down \"ease\" when close to the top or bottom\r\nof the page:\r\n\r\n\r\nhttps://github.com/user-attachments/assets/cb7bf03f-4a9e-4446-be4f-8f54c0bc88ac\r\n\r\nThis effect is accomplished via the parabola formula `y = a(x-h)2 + k`\r\nand can be roughly visualized with the following, which shows that the\r\n\"speed up\" ease happens at a much slower pace than the \"slow down\" ease:\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n#### Notes about parent changes\r\nAs I investigated improving the efficiency of the grid layout with\r\nembeddables, one of the main things I noticed was that the grid panel\r\nwas **always** remounted when moving a panel from one collapsible\r\nsection to another. This lead me (and @ThomThomson) down a rabbit hole\r\nof React-reparenting, and we explored a few different options to see if\r\nwe could change the parent of a component **without** having it remount.\r\n\r\nIn summary, after various experiments and a whole bunch of research, we\r\ndetermined that, due to the reconciliation of the React tree, this is\r\nunfortunately impossible. So our priorities will instead have to move to\r\nmaking the remount of `ReactEmbeddableRenderer` **as efficient as\r\npossible** via caching, since the remount is inevitable.\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 the most significant work is\r\ncontained in the `examples` plugin. Some changes were made to the\r\npresentation panel to allow for custom drag handles, but this isn't\r\nactually used in Dashboard - so for now, this code is only called in the\r\nexample plugin, as well.\r\n\r\n---------\r\n\r\nCo-authored-by: kibanamachine <42973632+kibanamachine@users.noreply.github.com>","sha":"2a76fe3ee432d0b6746eae660cfe31fc71d15547"}},"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/198413","number":198413,"mergeCommit":{"message":"[Dashboard] [Collapsable Panels] Add embeddable support (#198413)\n\nCloses https://github.com/elastic/kibana/issues/190379\r\n\r\n## Summary\r\n\r\nThis PR switches the example grid layout app to render embeddables as\r\npanels rather than the simplified mock panel we were using previously.\r\nIn doing so, I had to add the ability for custom panels to add a custom\r\ndrag handle via the `renderPanelContents` callback - this required\r\nadding a `setDragHandles` callback to the `ReactEmbeddableRenderer` that\r\ncould be passed down to the `PresentationPanel` component.\r\n\r\n\r\n\r\n\r\nhttps://github.com/user-attachments/assets/9e2c68f9-34af-4360-a978-9113701a5ea2\r\n\r\n\r\n\r\n#### New scroll behaviour\r\n\r\nIn https://github.com/elastic/kibana/pull/201867, I introduced a small\r\n\"ease\" to the auto-scroll effect that happens when you drag a panel to\r\nthe top or bottom of the window. However, in that PR, I was using the\r\n`smooth` scrolling behaviour, which unfortunately became **very**\r\njittery once I switched to embeddables rather than simple panels\r\n(specifically in Chrome - it worked fine in Firefox).\r\n\r\nThe only way to prevent this jittery scroll was to switch to the default\r\nscroll behaviour, but this lead to a very **abrupt** stop when the\r\nscrollbar reached the top and/or bottom of the page - so, to give the\r\nsame \"gentle\" stop that the `smooth` scroll had, I decided to recreate\r\nthis effect by adding a slow down \"ease\" when close to the top or bottom\r\nof the page:\r\n\r\n\r\nhttps://github.com/user-attachments/assets/cb7bf03f-4a9e-4446-be4f-8f54c0bc88ac\r\n\r\nThis effect is accomplished via the parabola formula `y = a(x-h)2 + k`\r\nand can be roughly visualized with the following, which shows that the\r\n\"speed up\" ease happens at a much slower pace than the \"slow down\" ease:\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n#### Notes about parent changes\r\nAs I investigated improving the efficiency of the grid layout with\r\nembeddables, one of the main things I noticed was that the grid panel\r\nwas **always** remounted when moving a panel from one collapsible\r\nsection to another. This lead me (and @ThomThomson) down a rabbit hole\r\nof React-reparenting, and we explored a few different options to see if\r\nwe could change the parent of a component **without** having it remount.\r\n\r\nIn summary, after various experiments and a whole bunch of research, we\r\ndetermined that, due to the reconciliation of the React tree, this is\r\nunfortunately impossible. So our priorities will instead have to move to\r\nmaking the remount of `ReactEmbeddableRenderer` **as efficient as\r\npossible** via caching, since the remount is inevitable.\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 the most significant work is\r\ncontained in the `examples` plugin. Some changes were made to the\r\npresentation panel to allow for custom drag handles, but this isn't\r\nactually used in Dashboard - so for now, this code is only called in the\r\nexample plugin, as well.\r\n\r\n---------\r\n\r\nCo-authored-by: kibanamachine <42973632+kibanamachine@users.noreply.github.com>","sha":"2a76fe3ee432d0b6746eae660cfe31fc71d15547"}}]}] BACKPORT--> Co-authored-by: Hannah Mudge <Heenawter@users.noreply.github.com>
63 lines
1.9 KiB
TypeScript
63 lines
1.9 KiB
TypeScript
/*
|
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
|
* or more contributor license agreements. Licensed under the "Elastic License
|
|
* 2.0", the "GNU Affero General Public License v3.0 only", and the "Server Side
|
|
* Public License v 1"; you may not use this file except in compliance with, at
|
|
* your election, the "Elastic License 2.0", the "GNU Affero General Public
|
|
* License v3.0 only", or the "Server Side Public License, v 1".
|
|
*/
|
|
|
|
import { GridLayoutData } from '@kbn/grid-layout';
|
|
import { MockedDashboardPanelMap, MockedDashboardRowMap } from './types';
|
|
|
|
export const gridLayoutToDashboardPanelMap = (
|
|
panelState: MockedDashboardPanelMap,
|
|
layout: GridLayoutData
|
|
): { panels: MockedDashboardPanelMap; rows: MockedDashboardRowMap } => {
|
|
const panels: MockedDashboardPanelMap = {};
|
|
const rows: MockedDashboardRowMap = [];
|
|
layout.forEach((row, rowIndex) => {
|
|
rows.push({ title: row.title, collapsed: row.isCollapsed });
|
|
Object.values(row.panels).forEach((panelGridData) => {
|
|
panels[panelGridData.id] = {
|
|
...panelState[panelGridData.id],
|
|
gridData: {
|
|
i: panelGridData.id,
|
|
y: panelGridData.row,
|
|
x: panelGridData.column,
|
|
w: panelGridData.width,
|
|
h: panelGridData.height,
|
|
row: rowIndex,
|
|
},
|
|
};
|
|
});
|
|
});
|
|
return { panels, rows };
|
|
};
|
|
|
|
export const dashboardInputToGridLayout = ({
|
|
panels,
|
|
rows,
|
|
}: {
|
|
panels: MockedDashboardPanelMap;
|
|
rows: MockedDashboardRowMap;
|
|
}): GridLayoutData => {
|
|
const layout: GridLayoutData = [];
|
|
|
|
rows.forEach((row) => {
|
|
layout.push({ title: row.title, isCollapsed: row.collapsed, panels: {} });
|
|
});
|
|
|
|
Object.keys(panels).forEach((panelId) => {
|
|
const gridData = panels[panelId].gridData;
|
|
layout[gridData.row ?? 0].panels[panelId] = {
|
|
id: panelId,
|
|
row: gridData.y,
|
|
column: gridData.x,
|
|
width: gridData.w,
|
|
height: gridData.h,
|
|
};
|
|
});
|
|
|
|
return layout;
|
|
};
|