diff --git a/webapp/packages/plugin-data-spreadsheet-new/src/DataGrid/DataGridTable.tsx b/webapp/packages/plugin-data-spreadsheet-new/src/DataGrid/DataGridTable.tsx index f7bbbe9193..d35191a7a8 100644 --- a/webapp/packages/plugin-data-spreadsheet-new/src/DataGrid/DataGridTable.tsx +++ b/webapp/packages/plugin-data-spreadsheet-new/src/DataGrid/DataGridTable.tsx @@ -52,7 +52,6 @@ export const DataGridTable: React.FC = observer(function DataGridTable({ const [columnResize] = useState(() => new Executor()); const selectionAction = model.source.getAction(resultIndex, ResultSetSelectAction); - const modelResultData = model.getResult(resultIndex); const tableData = useTableData(model, resultIndex); @@ -79,7 +78,7 @@ export const DataGridTable: React.FC = observer(function DataGridTable({ }, }); - const { onKeydownHandler } = useGridSelectedCellsCopy(modelResultData, gridSelectionContext); + const { onKeydownHandler } = useGridSelectedCellsCopy(model, resultIndex, tableData, gridSelectionContext); const { onMouseDownHandler, onMouseMoveHandler } = useGridDragging({ onDragStart: startPosition => { dataGridRef.current?.selectCell({ idx: startPosition.colIdx, rowIdx: startPosition.rowIdx }); diff --git a/webapp/packages/plugin-data-spreadsheet-new/src/DataGrid/useGridSelectedCellsCopy.ts b/webapp/packages/plugin-data-spreadsheet-new/src/DataGrid/useGridSelectedCellsCopy.ts index 4314ed4c6d..02cb63fefa 100644 --- a/webapp/packages/plugin-data-spreadsheet-new/src/DataGrid/useGridSelectedCellsCopy.ts +++ b/webapp/packages/plugin-data-spreadsheet-new/src/DataGrid/useGridSelectedCellsCopy.ts @@ -9,66 +9,76 @@ import { useCallback } from 'react'; import { useObjectRef } from '@cloudbeaver/core-blocks'; -import type { SqlResultSet } from '@cloudbeaver/core-sdk'; import { copyToClipboard } from '@cloudbeaver/core-utils'; -import type { IDatabaseDataResult } from '@cloudbeaver/plugin-data-viewer'; +import { IDatabaseDataModel, IDatabaseResultSet, ResultSetFormatAction } from '@cloudbeaver/plugin-data-viewer'; import type { IDataGridSelectionContext } from './DataGridSelection/DataGridSelectionContext'; +import type { ITableData } from './TableDataContext'; const EVENT_KEY_CODE = { C: 'KeyC', }; -function copyGridSelectedDataToClipboard(modelData: SqlResultSet, selectedCells: Map) { - if (!modelData.rows) { - return; - } +function copyGridSelectedDataToClipboard( + model: IDatabaseDataModel, + resultIndex: number, + tableData: ITableData, + selectedCells: Map +) { + const format = model.source.getAction(resultIndex, ResultSetFormatAction); + const editor = model.source.getEditor(resultIndex); const orderedSelectedCells: Map = new Map([...selectedCells].sort((a, b) => a[0] - b[0])); const selectedColumns: Set = new Set(); - for (const colIndexes of orderedSelectedCells.values()) { for (const colIdx of colIndexes) { selectedColumns.add(colIdx); } } - const columns = [...selectedColumns].sort(); - - let data = ''; + const rowsValues: string[] = []; for (const [rowIdx, colIndexes] of orderedSelectedCells) { - for (const column of columns) { - if (column !== columns[0]) { - data += '\t'; + const rowCellsValues: string[] = []; + for (const column of tableData.columns) { + const columnIdx = tableData.getDataColumnIndexFromKey(column.key); + if (columnIdx === null || !selectedColumns.has(columnIdx)) { + continue; } - if (colIndexes.includes(column)) { - const value = modelData.rows?.[rowIdx][column]; - data += value; + if (colIndexes.includes(columnIdx)) { + const cell = editor.getCell(rowIdx, columnIdx); + const cellValue = format.get(cell); + rowCellsValues.push(cellValue ?? ''); + } else { + rowCellsValues.push(''); } } - data += '\r\n'; + rowsValues.push(rowCellsValues.join('\t')); } - copyToClipboard(data); + copyToClipboard(rowsValues.join('\r\n')); } // needed for event.code type IKeyboardEvent = React.KeyboardEvent & KeyboardEvent; export function useGridSelectedCellsCopy( - modelResultData: IDatabaseDataResult | null, + model: IDatabaseDataModel, + resultIndex: number, + tableData: ITableData, selectionContext: IDataGridSelectionContext ) { - const props = useObjectRef({ modelResultData, selectionContext }); - const onKeydownHandler = useCallback((event: IKeyboardEvent) => { - if (!props.modelResultData) { - return; - } + const props = useObjectRef({ model, resultIndex, tableData, selectionContext }); + const onKeydownHandler = useCallback((event: IKeyboardEvent) => { if ((event.ctrlKey || event.metaKey) && event.code === EVENT_KEY_CODE.C) { - copyGridSelectedDataToClipboard(props.modelResultData.data, props.selectionContext.selectedCells); + copyGridSelectedDataToClipboard( + props.model, + props.resultIndex, + props.tableData, + props.selectionContext.selectedCells + ); } }, []); diff --git a/webapp/packages/plugin-data-spreadsheet-new/src/styles/themes/_base-react-grid.scss b/webapp/packages/plugin-data-spreadsheet-new/src/styles/themes/_base-react-grid.scss index 52afbbd717..5ffd6cf884 100644 --- a/webapp/packages/plugin-data-spreadsheet-new/src/styles/themes/_base-react-grid.scss +++ b/webapp/packages/plugin-data-spreadsheet-new/src/styles/themes/_base-react-grid.scss @@ -16,9 +16,11 @@ $edited-color: #ff99006b; .rdg-cell-custom-selected:not(.rdg-cell-custom-editing) { background-color: rgba(0, 145, 234, 0.3); } + .rdg-cell-selected { box-shadow: inset 0 0 0 1px #0091ea; } + .rdg-cell-custom-editing { box-shadow: none; }