diff --git a/public/app/features/dashboard-scene/edit-pane/VizPanelEditableElement.tsx b/public/app/features/dashboard-scene/edit-pane/VizPanelEditableElement.tsx index 39ed9beaa52..8ed9bc2bb6f 100644 --- a/public/app/features/dashboard-scene/edit-pane/VizPanelEditableElement.tsx +++ b/public/app/features/dashboard-scene/edit-pane/VizPanelEditableElement.tsx @@ -2,8 +2,8 @@ import { useId, useMemo } from 'react'; import { Trans, t } from '@grafana/i18n'; import { locationService } from '@grafana/runtime'; -import { sceneGraph, VizPanel } from '@grafana/scenes'; -import { Stack, Button } from '@grafana/ui'; +import { VizPanel, sceneGraph } from '@grafana/scenes'; +import { Button, Stack } from '@grafana/ui'; import { appEvents } from 'app/core/app_events'; import { OptionsPaneCategoryDescriptor } from 'app/features/dashboard/components/PanelEditor/OptionsPaneCategoryDescriptor'; import { OptionsPaneItemDescriptor } from 'app/features/dashboard/components/PanelEditor/OptionsPaneItemDescriptor'; @@ -15,8 +15,7 @@ import { PanelFrameTitleInput, editPanelTitleAction, } from '../panel-edit/getPanelFrameOptions'; -import { AutoGridItem } from '../scene/layout-auto-grid/AutoGridItem'; -import { DashboardGridItem } from '../scene/layout-default/DashboardGridItem'; +import { scrollCanvasElementIntoView } from '../scene/layouts-shared/scrollCanvasElementIntoView'; import { BulkActionElement } from '../scene/types/BulkActionElement'; import { isDashboardLayoutItem } from '../scene/types/DashboardLayoutItem'; import { EditableDashboardElement, EditableDashboardElementInfo } from '../scene/types/EditableDashboardElement'; @@ -138,9 +137,7 @@ export class VizPanelEditableElement implements EditableDashboardElement, BulkAc } public scrollIntoView() { - if (this.panel.parent instanceof AutoGridItem || this.panel.parent instanceof DashboardGridItem) { - this.panel.parent.scrollIntoView(); - } + scrollCanvasElementIntoView(this.panel, `[data-viz-panel-key="${this.panel.state.key}"`); } } diff --git a/public/app/features/dashboard-scene/scene/layouts-shared/scrollCanvasElementIntoView.ts b/public/app/features/dashboard-scene/scene/layouts-shared/scrollCanvasElementIntoView.ts index e87b7e269f0..496f13bea01 100644 --- a/public/app/features/dashboard-scene/scene/layouts-shared/scrollCanvasElementIntoView.ts +++ b/public/app/features/dashboard-scene/scene/layouts-shared/scrollCanvasElementIntoView.ts @@ -8,12 +8,40 @@ import { TabsLayoutManager } from '../layout-tabs/TabsLayoutManager'; * Will scroll element into view. If element is not connected yet, it will try to expand rows * and switch tabs to make it visible. */ -export function scrollCanvasElementIntoView(sceneObject: SceneObject, ref: React.RefObject) { - if (ref.current?.isConnected) { - scrollIntoView(ref.current); +export function scrollCanvasElementIntoView( + sceneObject: SceneObject, + refOrSelector: React.RefObject | string +) { + if (tryScroll(refOrSelector)) { return; } + openParentLayouts(sceneObject); + + // now try to scroll into view + setTimeout(() => { + tryScroll(refOrSelector); + }, 10); +} + +function tryScroll(refOrSelector: React.RefObject | string): boolean { + if (typeof refOrSelector === 'string') { + const element = document.querySelector(refOrSelector); + if (element instanceof HTMLElement) { + scrollIntoView(element); + return true; + } + return false; + } + + if (refOrSelector.current?.isConnected) { + scrollIntoView(refOrSelector.current); + return true; + } + return false; +} + +function openParentLayouts(sceneObject: SceneObject) { // try expanding rows and switching tabs let parent = sceneObject.parent; while (parent) { @@ -33,13 +61,6 @@ export function scrollCanvasElementIntoView(sceneObject: SceneObject, ref: React } parent = parent.parent; } - - // now try to scroll into view - setTimeout(() => { - if (ref.current?.isConnected) { - scrollIntoView(ref.current); - } - }, 10); } export function scrollIntoView(element: HTMLElement) {