Я работаю над проектом React (NextJS), используя пользовательский интерфейс материала. У меня есть несколько таблиц (компонент DataGrid из пользовательского интерфейса материала) с разными цветами фона в заголовках столбцов, например:
Моя проблема заключается в том, что когда я прокручиваю по горизонтали очень быстро (не медленно, а очень быстро), цвет перемещается на 1 пробел/столбец, поэтому на предыдущем изображении вы можете видеть, что столбец «ранг», например, должен быть желтым, и если я прокручиваю горизонтально очень быстро, он становится красным:
Как вы можете видеть, цвета перемещаются на 1 пробел/столбец, мне это кажется ошибкой пользовательского интерфейса материала, но я не уверен...
Это мой компонент React:
import React, { useState, useEffect } from 'react'
import { css } from '@emotion/react'
import PropTypes from 'prop-types'
import { cardCss } from '../CavMortal/grid/Grid'
import { fullHeight } from '../CavMortal/ScoreItem'
import { CardElevation } from '@findep/mf-landings-core'
import Grid from '@material-ui/core/Grid'
import { DataGrid } from '@mui/x-data-grid';
import { splitString} from '../../helpers/splitString'
const customCardCss = css`
${cardCss}
${fullHeight}
& [class* = "MuiCardContent-root"] {
${fullHeight}
}
`
function TablaSubdireccion({ dataSubdirecciones, headerStyles }) {
const [columnsName, setColumnsName] = useState([])
const [rows, setRows] = useState([])
const getColumns = () => {
let columns = []
for(let i = 0; i < dataSubdirecciones.length; i++){
for(let j = 0; j < dataSubdirecciones[i].datosAgrupadorList.length; j++){
columns.push({
field: dataSubdirecciones[i].datosAgrupadorList[j].nombreDato,
headerName: dataSubdirecciones[i].datosAgrupadorList[j].nombreDato,
width: 130,
renderHeader: (params) => (
<div>
{
splitString(dataSubdirecciones[i].datosAgrupadorList[j].nombreDato).map((word) => (
<React.Fragment key = {word}>
{word}
<br />
</React.Fragment>
))
}
</div>
),
})
}
}
return columns
}
const getRows = () => {
let rows = []
for (let i = 0; i < dataSubdirecciones.length; i++) {
let rowData = { id: i }
for (let j = 0; j < dataSubdirecciones[i].datosAgrupadorList.length; j++) {
rowData[dataSubdirecciones[i].datosAgrupadorList[j].nombreDato] = dataSubdirecciones[i].datosAgrupadorList[j].valorDato
}
rows.push(rowData)
}
return rows
}
useEffect(() => {
setColumnsName(getColumns())
setRows(getRows())
}, [dataSubdirecciones])
return(
<Grid item css = {css`flex-grow: 1;`}>
<div style = {{ height: 500, width: '99%' }}>
<CardElevation fullWidth noPadding css = {customCardCss}>
<DataGrid
sx = {headerStyles}
rows = {getRows()}
columns = {getColumns()}
hideFooterPagination = {true}
hideFooter = {true}
headerHeight = {50}
pageSize = {10}
/>
</CardElevation>
</div>
</Grid>
)
}
TablaSubdireccion.propTypes = {
dataSubdirecciones: PropTypes.array,
headerStyles: PropTypes.object,
}
export default TablaSubdireccion
А это объект headerStyles, который принимается в качестве реквизита и содержит цвета для каждого n-го дочернего элемента/столбца:
const MAIN_TABLES_HEADER_STYLES = {
'& .MuiDataGrid-columnHeaderTitleContainer': {
lineHeight: 1.5,
},
'.MuiDataGrid-columnSeparator': { display: 'none' },
'&.MuiDataGrid-root': { border: 'none' },
'& .MuiDataGrid-columnHeader:nth-child(1)': {
backgroundColor: '#000000',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(2)': {
backgroundColor: '#000000',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(3)': {
backgroundColor: '#9e9e9e',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(4)': {
backgroundColor: '#9e9e9e',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(5)': {
backgroundColor: '#9e9e9e',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(6)': {
backgroundColor: '#9e9e9e',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(7)': {
backgroundColor: '#6f0000',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(8)': {
backgroundColor: '#0075ad',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(9)': {
backgroundColor: '#d20000',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(10)': {
backgroundColor: '#ffd600',
color: '#000000',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(11)': {
backgroundColor: '#ffd600',
color: '#000000',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(12)': {
backgroundColor: '#ffd600',
color: '#000000',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(13)': {
backgroundColor: '#70b7bc',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(14)': {
backgroundColor: '#70b7bc',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(15)': {
backgroundColor: '#009f94',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(16)': {
backgroundColor: '#1e9a00',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(17)': {
backgroundColor: '#1e9a00',
color: '#ffffff',
fontWeight: 'bold',
},
'& .MuiDataGrid-columnHeader:nth-child(18)': {
backgroundColor: '#1e9a00',
color: '#ffffff',
fontWeight: 'bold',
},
}
Кто-нибудь знает, почему это происходит или как это исправить?
Спасибо.
Использование стиля nth-child
не будет надежным, когда используется горизонтальная прокрутка. Сетка данных виртуализирует столбцы при горизонтальной прокрутке, поэтому не все столбцы всегда визуализируются, что затем отбрасывает стиль nth-child
.
Вы можете увидеть это в действии в этом крайнем примере с 30 столбцами с настроенными цветами на 3-м и 4-м с помощью nth-child
селекторов CSS: https://codesandbox.io/s/horizontal-scrolling-tlmqeh?file=/demo.tsx.
В этом примере стиль выполнен аналогично вашему CSS:
<DataGridPro
sx = {{
"& .MuiDataGrid-columnHeader:nth-child(3)": {
backgroundColor: "red",
color: "#ffffff",
fontWeight: "bold"
},
"& .MuiDataGrid-columnHeader:nth-child(4)": {
backgroundColor: "purple",
color: "#ffffff",
fontWeight: "bold"
}
}}
apiRef = {apiRef}
onCellClick = {handleCellClick}
hideFooter
{...data}
/>
Вы можете исправить это, используя headerClassName
в определениях столбцов, как показано в документации здесь: https://mui.com/x/react-data-grid/style/#styling-column-headers.
Вот модификация моего предыдущего примера, в котором используется headerClassName
: https://codesandbox.io/s/horizontal-scrolling-087h4m?file=/demo.tsx
const { data } = useDemoData({
dataSet: "Commodity",
rowLength: 100
});
// data.columns[0] is the hidden id column, so data.columns[1] is the column
// definition for the first visible column.
data.columns[3].headerClassName = "red-header";
data.columns[4].headerClassName = "purple-header";
...
<DataGridPro
sx = {{
"& .MuiDataGrid-columnHeader.red-header": {
backgroundColor: "red",
color: "#ffffff",
fontWeight: "bold"
},
"& .MuiDataGrid-columnHeader.purple-header": {
backgroundColor: "purple",
color: "#ffffff",
fontWeight: "bold"
}
}}
apiRef = {apiRef}
onCellClick = {handleCellClick}
hideFooter
{...data}
/>
Спасибо за быстрый ответ, все работает. Я не знал о виртуализации.