mirror of
https://github.com/grafana/grafana.git
synced 2025-02-25 18:55:37 -06:00
Datagrid: Refactor header column delete/clear (#67842)
* refactor header column delete/clear * fix tests, add clear option on header dropdown * fix e2e tests
This commit is contained in:
parent
a58de1f8d2
commit
5416ec4768
@ -29,7 +29,7 @@ e2e.scenario({
|
|||||||
cy.get('[data-testid="glide-cell-2-1"]').should('have.attr', 'aria-selected', 'true');
|
cy.get('[data-testid="glide-cell-2-1"]').should('have.attr', 'aria-selected', 'true');
|
||||||
cy.get('body').type('12{enter}', { delay: 500 });
|
cy.get('body').type('12{enter}', { delay: 500 });
|
||||||
|
|
||||||
cy.get('[aria-label="Confirm Modal Danger Button"]').click();
|
cy.get('[data-testid="data-testid Confirm Modal Danger Button"]').click();
|
||||||
|
|
||||||
cy.get('[data-testid="query-editor-row"]').contains('Snapshot');
|
cy.get('[data-testid="query-editor-row"]').contains('Snapshot');
|
||||||
},
|
},
|
||||||
|
@ -17,7 +17,7 @@ e2e.scenario({
|
|||||||
cy.get('[data-testid="glide-cell-2-1"]').should('have.attr', 'aria-selected', 'true');
|
cy.get('[data-testid="glide-cell-2-1"]').should('have.attr', 'aria-selected', 'true');
|
||||||
cy.get('body').type('123{enter}', { delay: 500 });
|
cy.get('body').type('123{enter}', { delay: 500 });
|
||||||
|
|
||||||
cy.get('[aria-label="Confirm Modal Danger Button"]').click();
|
cy.get('[data-testid="data-testid Confirm Modal Danger Button"]').click();
|
||||||
|
|
||||||
// Delete a cell
|
// Delete a cell
|
||||||
cy.get('.dvn-scroller').click(200, 200);
|
cy.get('.dvn-scroller').click(200, 200);
|
||||||
@ -57,7 +57,7 @@ e2e.scenario({
|
|||||||
cy.get('.dvn-scroller').click(20, 190, { waitForAnimations: true });
|
cy.get('.dvn-scroller').click(20, 190, { waitForAnimations: true });
|
||||||
cy.get('.dvn-scroller').click(20, 90, { shiftKey: true, waitForAnimations: true }); // with shift to select all rows between clicks
|
cy.get('.dvn-scroller').click(20, 90, { shiftKey: true, waitForAnimations: true }); // with shift to select all rows between clicks
|
||||||
cy.get('body').type('{del}');
|
cy.get('body').type('{del}');
|
||||||
cy.get('[aria-label="Confirm Modal Danger Button"]').click();
|
cy.get('[data-testid="data-testid Confirm Modal Danger Button"]').click();
|
||||||
cy.get('[data-testid="glide-cell-1-4"]').should('have.text', '');
|
cy.get('[data-testid="glide-cell-1-4"]').should('have.text', '');
|
||||||
cy.get('[data-testid="glide-cell-1-3"]').should('have.text', '');
|
cy.get('[data-testid="glide-cell-1-3"]').should('have.text', '');
|
||||||
cy.get('[data-testid="glide-cell-1-2"]').should('have.text', '');
|
cy.get('[data-testid="glide-cell-1-2"]').should('have.text', '');
|
||||||
@ -72,7 +72,7 @@ e2e.scenario({
|
|||||||
cy.get('.dvn-scroller').click(20, 90, { commandKey: true, waitForAnimations: true }); // with cmd to select only clicked rows
|
cy.get('.dvn-scroller').click(20, 90, { commandKey: true, waitForAnimations: true }); // with cmd to select only clicked rows
|
||||||
cy.get('body').type('{del}');
|
cy.get('body').type('{del}');
|
||||||
|
|
||||||
cy.get('[aria-label="Confirm Modal Danger Button"]').click();
|
cy.get('[data-testid="data-testid Confirm Modal Danger Button"]').click();
|
||||||
|
|
||||||
cy.get('[data-testid="glide-cell-1-1"]').should('have.text', '');
|
cy.get('[data-testid="glide-cell-1-1"]').should('have.text', '');
|
||||||
cy.get('[data-testid="glide-cell-2-1"]').should('have.text', 0);
|
cy.get('[data-testid="glide-cell-2-1"]').should('have.text', 0);
|
||||||
@ -89,7 +89,7 @@ e2e.scenario({
|
|||||||
// Delete column through header dropdown menu
|
// Delete column through header dropdown menu
|
||||||
cy.get('.dvn-scroller').click(250, 15); // click header dropdown
|
cy.get('.dvn-scroller').click(250, 15); // click header dropdown
|
||||||
cy.get('body').click(450, 420); // click delete column
|
cy.get('body').click(450, 420); // click delete column
|
||||||
cy.get('[aria-label="Confirm Modal Danger Button"]').click();
|
cy.get('[data-testid="data-testid Confirm Modal Danger Button"]').click();
|
||||||
cy.get(`[data-testid="${DATAGRID_CANVAS}"] th`).should('have.length', 1);
|
cy.get(`[data-testid="${DATAGRID_CANVAS}"] th`).should('have.length', 1);
|
||||||
|
|
||||||
// Delete row through context menu
|
// Delete row through context menu
|
||||||
@ -108,7 +108,7 @@ e2e.scenario({
|
|||||||
cy.get('.dvn-scroller').click(20, 90, { commandKey: true, waitForAnimations: true }); // with shift to select all rows between clicks
|
cy.get('.dvn-scroller').click(20, 90, { commandKey: true, waitForAnimations: true }); // with shift to select all rows between clicks
|
||||||
cy.get('.dvn-scroller').rightclick(40, 90);
|
cy.get('.dvn-scroller').rightclick(40, 90);
|
||||||
cy.get('[aria-label="Context menu"]').click(10, 10);
|
cy.get('[aria-label="Context menu"]').click(10, 10);
|
||||||
cy.get('[aria-label="Confirm Modal Danger Button"]').click();
|
cy.get('[data-testid="data-testid Confirm Modal Danger Button"]').click();
|
||||||
cy.get(`[data-testid="${DATAGRID_CANVAS}"] tbody tr`).should('have.length', 5); // there are 5 data rows + 1 for the add new row btns
|
cy.get(`[data-testid="${DATAGRID_CANVAS}"] tbody tr`).should('have.length', 5); // there are 5 data rows + 1 for the add new row btns
|
||||||
|
|
||||||
// Delete column through context menu
|
// Delete column through context menu
|
||||||
@ -121,7 +121,7 @@ e2e.scenario({
|
|||||||
|
|
||||||
// Add a new column
|
// Add a new column
|
||||||
cy.get('body').click(350, 200).type('New Column{enter}');
|
cy.get('body').click(350, 200).type('New Column{enter}');
|
||||||
cy.get('[aria-label="Confirm Modal Danger Button"]').click();
|
cy.get('[data-testid="data-testid Confirm Modal Danger Button"]').click();
|
||||||
cy.get('body')
|
cy.get('body')
|
||||||
.click(350, 230)
|
.click(350, 230)
|
||||||
.type('Value 1{enter}')
|
.type('Value 1{enter}')
|
||||||
@ -138,7 +138,7 @@ e2e.scenario({
|
|||||||
cy.get(`[data-testid="${DATAGRID_CANVAS}"] th`).contains('Renamed column');
|
cy.get(`[data-testid="${DATAGRID_CANVAS}"] th`).contains('Renamed column');
|
||||||
|
|
||||||
// Change column field type
|
// Change column field type
|
||||||
cy.get('.dvn-scroller').click(250, 15);
|
cy.get('.dvn-scroller').click(310, 15);
|
||||||
cy.get('[aria-label="Context menu"]').click(50, 50);
|
cy.get('[aria-label="Context menu"]').click(50, 50);
|
||||||
cy.get('.dvn-scroller').click(200, 100);
|
cy.get('.dvn-scroller').click(200, 100);
|
||||||
cy.get('body').type('Str Value{enter}');
|
cy.get('body').type('Str Value{enter}');
|
||||||
|
@ -111,14 +111,28 @@ describe('DataGrid', () => {
|
|||||||
expect(screen.getByText('Remove all data')).toBeInTheDocument();
|
expect(screen.getByText('Remove all data')).toBeInTheDocument();
|
||||||
expect(screen.getByText('Search...')).toBeInTheDocument();
|
expect(screen.getByText('Search...')).toBeInTheDocument();
|
||||||
|
|
||||||
// click on header cell should show only column options
|
// right clicking on header cell without clicking/selecting the cell should show only general options
|
||||||
|
fireEvent.contextMenu(scroller, {
|
||||||
|
clientX: 50,
|
||||||
|
clientY: 36,
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(screen.getByText('Remove all data')).toBeInTheDocument();
|
||||||
|
expect(screen.getByText('Search...')).toBeInTheDocument();
|
||||||
|
|
||||||
|
// selecting the header first and then right click on header cell should show only column options
|
||||||
|
const canvas = screen.getByTestId('data-grid-canvas');
|
||||||
|
sendClick(canvas, {
|
||||||
|
clientX: 50,
|
||||||
|
clientY: 36,
|
||||||
|
});
|
||||||
|
|
||||||
fireEvent.contextMenu(scroller, {
|
fireEvent.contextMenu(scroller, {
|
||||||
clientX: 50,
|
clientX: 50,
|
||||||
clientY: 36,
|
clientY: 36,
|
||||||
});
|
});
|
||||||
|
|
||||||
expect(screen.getByText('Delete column')).toBeInTheDocument();
|
expect(screen.getByText('Delete column')).toBeInTheDocument();
|
||||||
expect(screen.getByText('Clear column')).toBeInTheDocument();
|
|
||||||
expect(screen.getByText('Remove all data')).toBeInTheDocument();
|
expect(screen.getByText('Remove all data')).toBeInTheDocument();
|
||||||
expect(screen.getByText('Search...')).toBeInTheDocument();
|
expect(screen.getByText('Search...')).toBeInTheDocument();
|
||||||
|
|
||||||
|
@ -154,8 +154,29 @@ export function DataGridPanel({ options, data, id, fieldConfig, width, height }:
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (selection.rows) {
|
const rows = selection.rows.toArray();
|
||||||
updateSnapshot(deleteRows(frame, selection.rows.toArray()), onUpdateData);
|
const cols = selection.columns.toArray();
|
||||||
|
|
||||||
|
if (rows.length) {
|
||||||
|
updateSnapshot(deleteRows(frame, rows), onUpdateData);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (cols.length) {
|
||||||
|
const copiedFrame = {
|
||||||
|
...frame,
|
||||||
|
fields: frame.fields.map((field, index) => {
|
||||||
|
if (cols.includes(index)) {
|
||||||
|
return {
|
||||||
|
...field,
|
||||||
|
values: new Array(frame.length).fill(null),
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
return field;
|
||||||
|
}),
|
||||||
|
};
|
||||||
|
updateSnapshot(copiedFrame, onUpdateData);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -53,10 +53,11 @@ export const DatagridContextMenu = ({
|
|||||||
columnDeletionLabel = `Delete ${selectedColumns.length} columns`;
|
columnDeletionLabel = `Delete ${selectedColumns.length} columns`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Show delete/clear options on cell right click, but not on header right click, unless header column is specifically selected.
|
||||||
const showDeleteRow = (row !== undefined && row >= 0) || selectedRows.length;
|
const showDeleteRow = (row !== undefined && row >= 0) || selectedRows.length;
|
||||||
const showDeleteColumn = (column !== undefined && column >= 0) || selectedColumns.length;
|
const showDeleteColumn = (column !== undefined && column >= 0 && row !== undefined) || selectedColumns.length;
|
||||||
const showClearRow = row !== undefined && row >= 0 && !selectedRows.length;
|
const showClearRow = row !== undefined && row >= 0 && !selectedRows.length;
|
||||||
const showClearColumn = column !== undefined && column >= 0 && !selectedColumns.length;
|
const showClearColumn = column !== undefined && column >= 0 && row !== undefined && !selectedColumns.length;
|
||||||
|
|
||||||
const renderContextMenuItems = () => (
|
const renderContextMenuItems = () => (
|
||||||
<>
|
<>
|
||||||
@ -85,6 +86,7 @@ export const DatagridContextMenu = ({
|
|||||||
...data,
|
...data,
|
||||||
fields: data.fields.filter((_, index) => !selectedColumns.includes(index)),
|
fields: data.fields.filter((_, index) => !selectedColumns.includes(index)),
|
||||||
});
|
});
|
||||||
|
dispatch({ type: DatagridActionType.gridSelectionCleared });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -215,20 +217,25 @@ export const DatagridContextMenu = ({
|
|||||||
<MenuItem label="Rename column" onClick={renameColumnClicked} />
|
<MenuItem label="Rename column" onClick={renameColumnClicked} />
|
||||||
<MenuDivider />
|
<MenuDivider />
|
||||||
<MenuItem
|
<MenuItem
|
||||||
label={columnDeletionLabel}
|
label="Delete column"
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
if (selectedColumns.length) {
|
|
||||||
saveData({
|
|
||||||
...data,
|
|
||||||
fields: data.fields.filter((_, index) => !selectedColumns.includes(index)),
|
|
||||||
});
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
saveData({
|
saveData({
|
||||||
...data,
|
...data,
|
||||||
fields: data.fields.filter((_, index) => index !== column),
|
fields: data.fields.filter((_, index) => index !== column),
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// also clear selection since it will change it if the deleted column is selected or if indexes shift
|
||||||
|
dispatch({ type: DatagridActionType.gridSelectionCleared });
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
<MenuItem
|
||||||
|
label="Clear column"
|
||||||
|
onClick={() => {
|
||||||
|
const field = data.fields[column];
|
||||||
|
field.values = field.values.map(() => null);
|
||||||
|
saveData({
|
||||||
|
...data,
|
||||||
|
});
|
||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
</>
|
</>
|
||||||
|
Loading…
Reference in New Issue
Block a user