From dbb677f81835c34c6b91cd5f4e16958a7d850d25 Mon Sep 17 00:00:00 2001 From: Sergio Betanzos Date: Tue, 22 Jun 2021 09:16:48 +0200 Subject: [PATCH] F OpenNebula/one#5422: Fix table component --- .../components/Tables/Enhanced/index.js | 199 +++++++----------- .../components/Tables/Enhanced/pagination.js | 70 ++---- 2 files changed, 96 insertions(+), 173 deletions(-) diff --git a/src/fireedge/src/client/components/Tables/Enhanced/index.js b/src/fireedge/src/client/components/Tables/Enhanced/index.js index ba88848698..5270ecdfef 100644 --- a/src/fireedge/src/client/components/Tables/Enhanced/index.js +++ b/src/fireedge/src/client/components/Tables/Enhanced/index.js @@ -1,7 +1,7 @@ /* eslint-disable react/prop-types */ import * as React from 'react' -import { makeStyles, Box, CircularProgress, useMediaQuery } from '@material-ui/core' +import { makeStyles, Box, LinearProgress } from '@material-ui/core' import { useGlobalFilter, usePagination, @@ -9,9 +9,8 @@ import { useTable } from 'react-table' +import SplitPane from 'client/components/SplitPane' import Toolbar from 'client/components/Tables/Virtualized/toolbar' -import Header from 'client/components/Tables/Virtualized/header' -import Row from 'client/components/Tables/Enhanced/row' import Pagination from 'client/components/Tables/Enhanced/pagination' import { addOpacityToColor } from 'client/utils' @@ -22,90 +21,48 @@ const useStyles = makeStyles(({ palette, typography, breakpoints }) => ({ display: 'flex', flexDirection: 'column' }, - table: { - height: '100%', - overflow: 'auto', - [breakpoints.up('md')]: { - border: `1px solid ${palette.action.disabledBackground}`, - borderRadius: 6 - }, - // includes header row - '& *[role=row]': { - padding: '0.8em', - textAlign: 'start', - overflowWrap: 'break-word', - lineHeight: '1rem', - color: palette.text.primary, - [breakpoints.up('md')]: { - display: 'grid', - gridAutoFlow: 'column', - gridTemplateColumns: ({ columnsWidth }) => columnsWidth.join(' ') - } - } - }, - header: { - position: 'sticky', - top: 0, - zIndex: 2, - - textTransform: 'uppercase', - fontSize: '0.9em', - fontWeight: 700, - letterSpacing: '0.05em', - borderBottom: 'transparent', - backgroundColor: palette.grey[palette.type === 'light' ? 200 : 600], - - [breakpoints.down('sm')]: { - display: 'none' - } - }, body: { - [breakpoints.only('sm')]: { - display: 'grid', - gap: '1em', - gridTemplateColumns: '1fr 1fr' - }, - [breakpoints.only('xm')]: { - display: 'grid', - gap: '1em', - gridTemplateColumns: '1fr' - }, - '& *[role=row]': { - fontSize: '1em', - fontWeight: typography.fontWeightMedium, - borderTop: `1px solid ${palette.action.disabledBackground}`, + overflow: 'auto', + display: 'grid', + gap: '1em', + gridTemplateColumns: '1fr', + '& > [role=row]': { + padding: '0.8em', + cursor: 'pointer', + color: palette.text.primary, backgroundColor: palette.background.paper, + fontWeight: typography.fontWeightMedium, + fontSize: '1em', + borderRadius: 6, + display: 'flex', + gap: 8, '&:hover': { backgroundColor: palette.action.hover }, - '&:first-of-type': { - borderTopColor: 'transparent' - }, '&.selected': { - backgroundColor: addOpacityToColor(palette.secondary.main, 0.7) + backgroundColor: addOpacityToColor(palette.secondary.main, 0.2), + border: `1px solid ${palette.secondary.main}` } - }, - '& *[role=cell]': { - overflow: 'hidden', - textOverflow: 'ellipsis', - whiteSpace: 'nowrap' } }, toolbar: { ...typography.body1, color: palette.text.hint, marginBottom: 16, - display: 'flex', + flexWrap: 'wrap', alignItems: 'center', justifyContent: 'space-between', - gap: '1em' + gap: '1em', + '& > div:first-child': { + flexGrow: 1 + } }, - total: { + pagination: { display: 'flex', alignItems: 'center', gap: '1em', - transition: 200 + transition: '200ms' } })) @@ -118,17 +75,14 @@ const EnhancedTable = ({ pageSize = 10, isLoading, showPageCount, + getRowId, + RowComponent, + renderDetail, + renderAllSelected = true, fetchMore, - canFetchMore, - MobileComponentRow + canFetchMore }) => { - const columnsWidth = React.useMemo(() => - columns.map(({ width = '1fr' }) => { - return Number.isInteger(width) ? `${width}px` : width - }), []) - - const isMobile = useMediaQuery(theme => theme.breakpoints.down('sm')) - const classes = useStyles({ columnsWidth }) + const classes = useStyles() const defaultColumn = React.useMemo(() => ({ // Filter: DefaultFilter, @@ -140,6 +94,7 @@ const EnhancedTable = ({ columns, data, defaultColumn, + getRowId, autoResetPage: false, initialState: { pageSize @@ -157,9 +112,12 @@ const EnhancedTable = ({ page, gotoPage, pageCount, + selectedFlatRows, state: { pageIndex } } = useTableProps + const justOneSelected = selectedFlatRows.length === 1 + const handleChangePage = newPage => { gotoPage(newPage) @@ -169,59 +127,58 @@ const EnhancedTable = ({ } return ( - - -
- -
- {isLoading && } - Total loaded: {rows.length} + + +
+ +
+ {page?.length > 0 && ( + + )} +
-
-
-
-
-
+ {isLoading && }
- { - page.map(row => { - prepareRow(row) + {page.map(row => { + prepareRow(row) - /** @type {import('react-table').UseRowSelectRowProps} */ - const { getRowProps, original, toggleRowSelected, isSelected } = row + /** @type {import('react-table').UseRowSelectRowProps} */ + const { getRowProps, original, toggleRowSelected, isSelected } = row + const { key, ...rowProps } = getRowProps() - const key = getRowProps().key - const handleSelect = () => toggleRowSelected(!isSelected) - - return isMobile && MobileComponentRow ? ( - - ) : ( - - ) - })} + return ( + toggleRowSelected(!isSelected)} + /> + ) + })}
-
- {page?.length > 0 && ( - - )} - + +
+ {justOneSelected && renderDetail + ? renderDetail(selectedFlatRows[0]?.original) + : renderAllSelected && ( +
+              
+                {JSON.stringify(selectedFlatRows?.map(({ id }) => id)?.join(', '), null, 2)}
+              
+            
+ ) + } +
+ ) } diff --git a/src/fireedge/src/client/components/Tables/Enhanced/pagination.js b/src/fireedge/src/client/components/Tables/Enhanced/pagination.js index dfbcc89dce..5326fe43d6 100644 --- a/src/fireedge/src/client/components/Tables/Enhanced/pagination.js +++ b/src/fireedge/src/client/components/Tables/Enhanced/pagination.js @@ -1,20 +1,10 @@ import React from 'react' import PropTypes from 'prop-types' -import { makeStyles, IconButton } from '@material-ui/core' +import { Button } from '@material-ui/core' +import { NavArrowLeft, NavArrowRight } from 'iconoir-react' -import { - FastArrowLeft as FirstPageIcon, - NavArrowLeft as PreviousPageIcon, - NavArrowRight as NextPageIcon, - FastArrowRight as LastPageIcon -} from 'iconoir-react' - -const useStyles = makeStyles(theme => ({ - root: { - margin: '10px auto' - } -})) +import { T } from 'client/constants' const Pagination = ({ count = 0, @@ -22,17 +12,11 @@ const Pagination = ({ useTableProps, showPageCount = true }) => { - const classes = useStyles() - /** @type {import('react-table').UsePaginationState} */ const { pageIndex, pageSize } = useTableProps.state const pageCount = React.useMemo(() => Math.ceil(count / pageSize), [count]) - const handleFirstPageButtonClick = () => { - handleChangePage(0) - } - const handleBackButtonClick = () => { handleChangePage(pageIndex - 1) } @@ -41,46 +25,28 @@ const Pagination = ({ handleChangePage(pageIndex + 1) } - const handleLastPageButtonClick = () => { - handleChangePage(Math.max(0, pageCount - 1)) - } - return ( -
- {/* - - */} - + + + {`${pageIndex + 1} of ${showPageCount ? pageCount : 'many'}`} + +
+ {T.Next} + + + ) }