From de4acb27ce203c4755771a195ab7ba533ec939dc Mon Sep 17 00:00:00 2001 From: Galen Kistler <109082771+gtk-grafana@users.noreply.github.com> Date: Fri, 9 Feb 2024 07:49:48 -0600 Subject: [PATCH] Table: Add initial row index (#82200) * Add initial row index prop in table --- .../grafana-ui/src/components/Table/RowsList.tsx | 11 ++++++++--- .../src/components/Table/Table.test.tsx | 16 ++++++++++++++++ .../grafana-ui/src/components/Table/Table.tsx | 2 ++ .../grafana-ui/src/components/Table/types.ts | 2 ++ 4 files changed, 28 insertions(+), 3 deletions(-) diff --git a/packages/grafana-ui/src/components/Table/RowsList.tsx b/packages/grafana-ui/src/components/Table/RowsList.tsx index 878aa1cf69e..6b16f4430a2 100644 --- a/packages/grafana-ui/src/components/Table/RowsList.tsx +++ b/packages/grafana-ui/src/components/Table/RowsList.tsx @@ -44,6 +44,7 @@ interface RowsListProps { onCellFilterAdded?: TableFilterActionCallback; timeRange?: TimeRange; footerPaginationEnabled: boolean; + initialRowIndex?: number; } export const RowsList = (props: RowsListProps) => { @@ -66,9 +67,10 @@ export const RowsList = (props: RowsListProps) => { listHeight, listRef, enableSharedCrosshair = false, + initialRowIndex = undefined, } = props; - const [rowHighlightIndex, setRowHighlightIndex] = useState(undefined); + const [rowHighlightIndex, setRowHighlightIndex] = useState(initialRowIndex); const theme = useTheme2(); const panelContext = usePanelContext(); @@ -203,6 +205,7 @@ export const RowsList = (props: RowsListProps) => { ({ index, style, rowHighlightIndex }: { index: number; style: CSSProperties; rowHighlightIndex?: number }) => { const indexForPagination = rowIndexForPagination(index); const row = rows[indexForPagination]; + let additionalProps: React.HTMLAttributes = {}; prepareRow(row); @@ -210,11 +213,13 @@ export const RowsList = (props: RowsListProps) => { if (rowHighlightIndex !== undefined && row.index === rowHighlightIndex) { style = { ...style, backgroundColor: theme.components.table.rowHoverBackground }; + additionalProps = { + 'aria-selected': 'true', + }; } - return (
onRowHover(index, data)} onMouseLeave={onRowLeave} diff --git a/packages/grafana-ui/src/components/Table/Table.test.tsx b/packages/grafana-ui/src/components/Table/Table.test.tsx index 4b2322923d4..5d855d25a4c 100644 --- a/packages/grafana-ui/src/components/Table/Table.test.tsx +++ b/packages/grafana-ui/src/components/Table/Table.test.tsx @@ -89,6 +89,7 @@ function getTestContext(propOverrides: Partial = {}) { onSortByChange, onCellFilterAdded, onColumnResize, + initialRowIndex: undefined, }; Object.assign(props, propOverrides); @@ -657,4 +658,19 @@ describe('Table', () => { expect(subTable.style.height).toBe('108px'); }); }); + + describe('when mounted with scrolled to specific row', () => { + it('the row should be visible', async () => { + getTestContext({ + initialRowIndex: 2, + }); + expect(getTable()).toBeInTheDocument(); + + const rows = within(getTable()).getAllByRole('row'); + expect(rows).toHaveLength(5); + + let selected = within(getTable()).getByRole('row', { selected: true }); + expect(selected).toBeVisible(); + }); + }); }); diff --git a/packages/grafana-ui/src/components/Table/Table.tsx b/packages/grafana-ui/src/components/Table/Table.tsx index 7f65db3f71d..7bb9e9cf976 100644 --- a/packages/grafana-ui/src/components/Table/Table.tsx +++ b/packages/grafana-ui/src/components/Table/Table.tsx @@ -48,6 +48,7 @@ export const Table = memo((props: Props) => { cellHeight = TableCellHeight.Sm, timeRange, enableSharedCrosshair = false, + initialRowIndex = undefined, } = props; const listRef = useRef(null); @@ -307,6 +308,7 @@ export const Table = memo((props: Props) => { tableStyles={tableStyles} footerPaginationEnabled={Boolean(enablePagination)} enableSharedCrosshair={enableSharedCrosshair} + initialRowIndex={initialRowIndex} />
) : ( diff --git a/packages/grafana-ui/src/components/Table/types.ts b/packages/grafana-ui/src/components/Table/types.ts index b99a3cad619..62a6d1471ee 100644 --- a/packages/grafana-ui/src/components/Table/types.ts +++ b/packages/grafana-ui/src/components/Table/types.ts @@ -97,6 +97,8 @@ export interface Props { /** @alpha Used by SparklineCell when provided */ timeRange?: TimeRange; enableSharedCrosshair?: boolean; + // The index of the field value that the table will initialize scrolled to + initialRowIndex?: number; } /**