diff --git a/public/app/features/dashboard-scene/panel-edit/PanelDataPane/DetailView.tsx b/public/app/features/dashboard-scene/panel-edit/PanelDataPane/DetailView.tsx new file mode 100644 index 00000000000..5d2e585ed33 --- /dev/null +++ b/public/app/features/dashboard-scene/panel-edit/PanelDataPane/DetailView.tsx @@ -0,0 +1,81 @@ +import { css } from '@emotion/css'; +import { memo, useCallback } from 'react'; + +import { GrafanaTheme2 } from '@grafana/data'; +import { Trans } from '@grafana/i18n'; +import { VizPanel } from '@grafana/scenes'; +import { Container, ScrollContainer, useStyles2 } from '@grafana/ui'; + +import { PanelDataTransformationsTab, PanelDataTransformationsTabRendered } from './PanelDataTransformationsTab'; +import { QueryDetailView } from './QueryDetailView'; +import { QueryTransformItem } from './QueryTransformList'; +import { TabId } from './types'; + +interface DetailViewProps { + selectedItem: QueryTransformItem | undefined; + panel: VizPanel; + tabs: Array<{ tabId: TabId }>; +} + +export const DetailView = memo(({ selectedItem, panel, tabs }: DetailViewProps) => { + const styles = useStyles2(getStyles); + + const renderContent = useCallback(() => { + if (!selectedItem) { + return ( +
+

+ + Select a query or transformation to edit + +

+
+ ); + } + + if (selectedItem.type === 'query' && 'refId' in selectedItem.data) { + const query = selectedItem.data; + return ( + + + + ); + } else { + const transformsTab = tabs.find((t) => t.tabId === TabId.Transformations); + if (transformsTab instanceof PanelDataTransformationsTab && 'id' in selectedItem.data) { + return ( + + + + + + ); + } + } + + return null; + }, [selectedItem, panel, tabs, styles.emptyState]); + + return
{renderContent()}
; +}); + +DetailView.displayName = 'DetailView'; + +const getStyles = (theme: GrafanaTheme2) => { + return { + container: css({ + display: 'flex', + flexDirection: 'column', + height: '100%', + background: theme.colors.background.primary, + }), + emptyState: css({ + display: 'flex', + alignItems: 'center', + justifyContent: 'center', + height: '100%', + color: theme.colors.text.secondary, + fontSize: theme.typography.h5.fontSize, + }), + }; +}; diff --git a/public/app/features/dashboard-scene/panel-edit/PanelDataPane/PanelDataPane.tsx b/public/app/features/dashboard-scene/panel-edit/PanelDataPane/PanelDataPane.tsx index 29313dc1986..cbfb9b2e1a5 100644 --- a/public/app/features/dashboard-scene/panel-edit/PanelDataPane/PanelDataPane.tsx +++ b/public/app/features/dashboard-scene/panel-edit/PanelDataPane/PanelDataPane.tsx @@ -3,7 +3,6 @@ import { useCallback, useMemo, useState } from 'react'; import { DataTransformerConfig, GrafanaTheme2, SelectableValue } from '@grafana/data'; import { selectors } from '@grafana/e2e-selectors'; -import { Trans } from '@grafana/i18n'; import { SceneComponentProps, SceneObjectBase, @@ -14,7 +13,7 @@ import { VizPanel, SceneDataTransformer, } from '@grafana/scenes'; -import { Container, ScrollContainer, useStyles2 } from '@grafana/ui'; +import { useStyles2 } from '@grafana/ui'; import { getConfig } from 'app/core/config'; import { contextSrv } from 'app/core/services/context_srv'; import { getRulesPermissions } from 'app/features/alerting/unified/utils/access-control'; @@ -22,11 +21,11 @@ import { GRAFANA_RULES_SOURCE_NAME } from 'app/features/alerting/unified/utils/d import { getQueryRunnerFor } from '../../utils/utils'; +import { DetailView } from './DetailView'; import { PanelDataAlertingTab } from './PanelDataAlertingTab'; import { PanelDataQueriesTab } from './PanelDataQueriesTab'; -import { PanelDataTransformationsTab, PanelDataTransformationsTabRendered } from './PanelDataTransformationsTab'; +import { PanelDataTransformationsTab } from './PanelDataTransformationsTab'; import { QueryTransformList, QueryTransformItem } from './QueryTransformList'; -import { SceneQueryDetailView } from './SceneQueryDetailView'; import { TransformationsDrawer } from './TransformationsDrawer'; import { PanelDataPaneTab, TabId } from './types'; @@ -286,46 +285,6 @@ function PanelDataPaneRendered({ model }: SceneComponentProps) { [tabs, selectedId] ); - const renderDetailPanel = useCallback(() => { - if (!selectedItem) { - return ( -
-

- - Select a query or transformation to edit - -

-
- ); - } - - if (selectedItem.type === 'query' && 'refId' in selectedItem.data) { - const query = selectedItem.data; - return ( -
- - - -
- ); - } else { - const transformsTab = tabs.find((t) => t.tabId === TabId.Transformations); - if (transformsTab instanceof PanelDataTransformationsTab && 'id' in selectedItem.data) { - return ( -
- - - - - -
- ); - } - } - - return null; - }, [selectedItem, tabs, styles, panel]); - // Get data for transformations drawer const sourceData = queryRunner?.useState(); const series = sourceData?.data?.series || []; @@ -347,7 +306,9 @@ function PanelDataPaneRendered({ model }: SceneComponentProps) { onRemoveTransform={handleRemoveTransform} /> -
{renderDetailPanel()}
+
+ +
(null); const [dsSettings, setDsSettings] = useState(null); @@ -129,7 +129,7 @@ export function SceneQueryDetailView({ panel, query, queryIndex }: SceneQueryDet if (!datasource || !dsSettings) { return (
- Loading data source... + Loading data source...
); } @@ -138,7 +138,7 @@ export function SceneQueryDetailView({ panel, query, queryIndex }: SceneQueryDet if (!QueryEditor) { return (
- + This data source does not have a query editor
@@ -170,7 +170,7 @@ export function SceneQueryDetailView({ panel, query, queryIndex }: SceneQueryDet diff --git a/public/locales/en-US/grafana.json b/public/locales/en-US/grafana.json index 6ceb8e3cead..4c943e42886 100644 --- a/public/locales/en-US/grafana.json +++ b/public/locales/en-US/grafana.json @@ -6235,6 +6235,11 @@ "see-docs": "See <2>documentation for more information about provisioning.", "title-cannot-delete-provisioned-dashboard": "Cannot delete provisioned dashboard" }, + "query-detail-view": { + "loading": "Loading data source...", + "no-editor": "This data source does not have a query editor", + "select-datasource": "Select data source" + }, "query-editor": { "query": "Query" }, @@ -6359,11 +6364,6 @@ "title-same-as-folder": "Dashboard name cannot be the same as the folder name", "title-validation-failed": "Dashboard title validation failed." }, - "scene-query-detail-view": { - "loading": "Loading data source...", - "no-editor": "This data source does not have a query editor", - "select-datasource": "Select data source" - }, "scenes-new-rule-from-panel-button": { "body-no-alerting-capable-query-found": "Cannot create alerts from this panel because no query to an alerting capable datasource is found.", "new-alert-rule": "New alert rule",