optimalization of grid rendering

This commit is contained in:
Jan Prochazka
2020-04-04 07:49:39 +02:00
parent f41383aa08
commit 87b9d87db9
3 changed files with 47 additions and 12 deletions

View File

@@ -24,7 +24,7 @@ import {
import keycodes from '../utility/keycodes'; import keycodes from '../utility/keycodes';
import InplaceEditor from './InplaceEditor'; import InplaceEditor from './InplaceEditor';
import DataGridRow from './DataGridRow'; import DataGridRow from './DataGridRow';
import { countColumnSizes, countVisibleRealColumns } from './gridutil'; import { countColumnSizes, countVisibleRealColumns, filterCellForRow, filterCellsForRow } from './gridutil';
import useModalState from '../modals/useModalState'; import useModalState from '../modals/useModalState';
import ConfirmSqlModal from '../modals/ConfirmSqlModal'; import ConfirmSqlModal from '../modals/ConfirmSqlModal';
import { import {
@@ -100,7 +100,7 @@ const FocusField = styled.input`
/** @param props {import('./types').DataGridProps} */ /** @param props {import('./types').DataGridProps} */
export default function DataGridCore(props) { export default function DataGridCore(props) {
const { conid, database, display, changeSetState, dispatchChangeSet, tabVisible } = props; const { conid, database, display, changeSetState, dispatchChangeSet, tabVisible } = props;
const columns = display.getGridColumns(); const columns = React.useMemo(() => display.getGridColumns(), [display]);
// usePropsCompare(props); // usePropsCompare(props);
@@ -135,7 +135,7 @@ export default function DataGridCore(props) {
// const [inplaceEditorChangedOnCreate, setInplaceEditorChangedOnCreate] = React.useState(false); // const [inplaceEditorChangedOnCreate, setInplaceEditorChangedOnCreate] = React.useState(false);
const changeSet = changeSetState.value; const changeSet = changeSetState.value;
const setChangeSet = value => dispatchChangeSet({ type: 'set', value }); const setChangeSet = React.useCallback(value => dispatchChangeSet({ type: 'set', value }), [dispatchChangeSet]);
const changeSetRef = React.useRef(changeSet); const changeSetRef = React.useRef(changeSet);
@@ -238,6 +238,8 @@ export default function DataGridCore(props) {
return {}; return {};
}, {}); }, {});
// usePropsCompare({ loadedRows, columns, containerWidth, display });
const columnSizes = React.useMemo(() => countColumnSizes(loadedRows, columns, containerWidth, display), [ const columnSizes = React.useMemo(() => countColumnSizes(loadedRows, columns, containerWidth, display), [
loadedRows, loadedRows,
columns, columns,
@@ -304,6 +306,8 @@ export default function DataGridCore(props) {
// [tableElement, currentCell] // [tableElement, currentCell]
// ); // );
// usePropsCompare({ columnSizes, firstVisibleColumnScrollIndex, gridScrollAreaWidth, columns });
const visibleRealColumns = React.useMemo( const visibleRealColumns = React.useMemo(
() => countVisibleRealColumns(columnSizes, firstVisibleColumnScrollIndex, gridScrollAreaWidth, columns), () => countVisibleRealColumns(columnSizes, firstVisibleColumnScrollIndex, gridScrollAreaWidth, columns),
[columnSizes, firstVisibleColumnScrollIndex, gridScrollAreaWidth, columns] [columnSizes, firstVisibleColumnScrollIndex, gridScrollAreaWidth, columns]
@@ -878,13 +882,13 @@ export default function DataGridCore(props) {
inplaceEditorState={inplaceEditorState} inplaceEditorState={inplaceEditorState}
dispatchInsplaceEditor={dispatchInsplaceEditor} dispatchInsplaceEditor={dispatchInsplaceEditor}
autofillSelectedCells={autofillSelectedCells} autofillSelectedCells={autofillSelectedCells}
selectedCells={selectedCells} selectedCells={filterCellsForRow(selectedCells, firstVisibleRowScrollIndex + index)}
insertedRowIndex={ insertedRowIndex={
firstVisibleRowScrollIndex + index >= loadedRows.length firstVisibleRowScrollIndex + index >= loadedRows.length
? firstVisibleRowScrollIndex + index - loadedRows.length ? firstVisibleRowScrollIndex + index - loadedRows.length
: null : null
} }
autofillMarkerCell={autofillMarkerCell} autofillMarkerCell={filterCellForRow(autofillMarkerCell, firstVisibleRowScrollIndex + index)}
changeSet={changeSet} changeSet={changeSet}
setChangeSet={setChangeSet} setChangeSet={setChangeSet}
display={display} display={display}

View File

@@ -15,6 +15,7 @@ import { getFilterType } from '@dbgate/filterparser';
import { findExistingChangeSetItem } from '@dbgate/datalib'; import { findExistingChangeSetItem } from '@dbgate/datalib';
import keycodes from '../utility/keycodes'; import keycodes from '../utility/keycodes';
import InplaceEditor from './InplaceEditor'; import InplaceEditor from './InplaceEditor';
import usePropsCompare from '../utility/usePropsCompare';
const TableBodyCell = styled.td` const TableBodyCell = styled.td`
font-weight: normal; font-weight: normal;
@@ -40,12 +41,12 @@ const TableBodyCell = styled.td`
color: white;`} color: white;`}
${props => ${props =>
props.isModifiedRow && props.isModifiedRow &&
!props.isInsertedRow && !props.isInsertedRow &&
!props.isSelected && !props.isSelected &&
!props.isAutofillSelected && !props.isAutofillSelected &&
!props.isModifiedCell && !props.isModifiedCell &&
` `
background-color: #FFFFDB;`} background-color: #FFFFDB;`}
${props => ${props =>
!props.isSelected && !props.isSelected &&
@@ -126,6 +127,7 @@ function CellFormattedValue({ value }) {
} }
function cellIsSelected(row, col, selectedCells) { function cellIsSelected(row, col, selectedCells) {
if (!selectedCells) return false;
for (const [selectedRow, selectedCol] of selectedCells) { for (const [selectedRow, selectedCol] of selectedCells) {
if (row == selectedRow && col == selectedCol) return true; if (row == selectedRow && col == selectedCol) return true;
if (selectedRow == 'header' && col == selectedCol) return true; if (selectedRow == 'header' && col == selectedCol) return true;
@@ -135,7 +137,7 @@ function cellIsSelected(row, col, selectedCells) {
return false; return false;
} }
export default function DataGridRow({ function DataGridRow({
rowHeight, rowHeight,
rowIndex, rowIndex,
visibleRealColumns, visibleRealColumns,
@@ -150,7 +152,24 @@ export default function DataGridRow({
selectedCells, selectedCells,
autofillSelectedCells, autofillSelectedCells,
}) { }) {
// usePropsCompare({
// rowHeight,
// rowIndex,
// visibleRealColumns,
// inplaceEditorState,
// dispatchInsplaceEditor,
// row,
// display,
// changeSet,
// setChangeSet,
// insertedRowIndex,
// autofillMarkerCell,
// selectedCells,
// autofillSelectedCells,
// });
// console.log('RENDER ROW', rowIndex); // console.log('RENDER ROW', rowIndex);
const rowDefinition = display.getChangeSetRow(row, insertedRowIndex); const rowDefinition = display.getChangeSetRow(row, insertedRowIndex);
const [matchedField, matchedChangeSetItem] = findExistingChangeSetItem(changeSet, rowDefinition); const [matchedField, matchedChangeSetItem] = findExistingChangeSetItem(changeSet, rowDefinition);
const rowUpdated = matchedChangeSetItem ? { ...row, ...matchedChangeSetItem.fields } : row; const rowUpdated = matchedChangeSetItem ? { ...row, ...matchedChangeSetItem.fields } : row;
@@ -214,3 +233,5 @@ export default function DataGridRow({
</TableBodyRow> </TableBodyRow>
); );
} }
export default React.memo(DataGridRow);

View File

@@ -1,4 +1,5 @@
import { SeriesSizes } from './SeriesSizes'; import { SeriesSizes } from './SeriesSizes';
import { CellAddress } from './selection';
export function countColumnSizes(loadedRows, columns, containerWidth, display) { export function countColumnSizes(loadedRows, columns, containerWidth, display) {
let canvas = document.createElement('canvas'); let canvas = document.createElement('canvas');
@@ -105,3 +106,12 @@ export function countVisibleRealColumns(columnSizes, firstVisibleColumnScrollInd
} }
return realColumns; return realColumns;
} }
export function filterCellForRow(cell, row: number): CellAddress | null {
return cell && cell[0] == row ? cell : null;
}
export function filterCellsForRow(cells, row: number): CellAddress[] | null {
const res = (cells || []).filter(x => x[0] == row);
return res.length > 0 ? res : null;
}