英文:
Checking the checkBox does not work when DataTable of react-data-table-component has a onSelectedRowsChange callback withs state change
问题
以下是您要的代码部分的中文翻译:
我有以下的代码,我想要在选中一行时启用编辑按钮。
所以我将editButtonDisabled设置为一个状态变量来处理按钮的禁用属性。
现在的问题是,当我选中未选中的行的复选框时,编辑按钮会被启用,但未选中的复选框仍然保持未选中。如果我再次选中它,然后它就会被选中。当我取消选中它时,按钮会被禁用。
如果我移除回调,它就正常工作。所以我猜测改变变量的状态可能会影响我的复选框。有什么办法可以解决这个问题?
import { useEffect, useState, useRef, useCallback } from 'react';
import { getDocs, query, collection, orderBy, doc } from 'firebase/firestore';
import DataTable from 'react-data-table-component';
import { Button, Checkbox } from '@mui/material';
import { FcInspection } from 'react-icons/fc';
import { IoAdd } from 'react-icons/io5';
import { VscEdit } from 'react-icons/vsc';
import { db } from '../../../services/firebase';
import { Layout } from '../../layout';
export default function InstituteList() {
const [retrievedFlag, setRetrievedFlag] = useState(false);
const [institutes, setInstitutes] = useState([]);
const [editButtonDisabled, setEditButtonDisabled] = useState(true);
useEffect(() => {
if (retrievedFlag === false) retrieveData();
}, []);
useEffect(() => {
console.log(editButtonDisabled);
}, [editButtonDisabled]);
function retrieveData() {
try {
let tmpInstitutes = [];
const institutesRef = collection(db, 'Institutes');
const institutesQuery = query(institutesRef, orderBy('title'));
getDocs(institutesQuery)
.then(snapshot => {
snapshot.forEach(doc => {
let institute = doc.data();
institute.id = doc.id;
tmpInstitutes.push(institute);
});
setInstitutes(tmpInstitutes);
setRetrievedFlag(true);
});
} catch (error) {
console.log(error);
}
}
const columns = [
{ name: 'id', selector: row => row.id, omit: true },
{ name: '조직명', selector: row => row.title, sortable: true, grow: 1 },
{ name: '등록일', selector: row => row.date, sortable: true, grow: 1 },
{ name: '주소', selector: row => row.location, sortable: true, grow: 4 },
];
const handleSelectedRowChange = useCallback(state => {
console.log('设置编辑按钮禁用状态', state);
setEditButtonDisabled(state.selectedCount === 0);
});
const paginationComponentOptions = {
rowsPerPageText: '페이지당 조회 갯수',
rangeSeparatorText: '중',
selectAllRowsItem: true,
selectAllRowsItemText: '전체',
};
const PageHeader = userInfo => {
const today = new Date();
return (
<div className="page-header">
<div className="page-header__title">
<FcInspection />
조직목록조회
</div>
</div>
);
};
const DataTableHeader = () => {
return (
<div className="page-body__datatable_header">
<div className="page-body__datatable_header__title">조직목록</div>
<div className="page-body__datatable_header__title"></div>
</div>
);
};
const PageDataTable = () => {
return (
<div className="page-body__card_datatable">
<DataTable
title='조직목록'
noDataComponent='조회 할 데이터 없습니다.'
columns={columns}
data={institutes}
persistTableHead={true}
noContextMenu={true}
selectableRows={true}
selectableRowsHighlight={true}
selectableRowsComponent={Checkbox}
selectableRowsSingle={true}
onSelectedRowsChange={handleSelectedRowChange}
pagination
paginationComponentOptions={paginationComponentOptions}
/>
</div>
);
};
const PageDataTableButtons = () => {
console.log("Render PageDataTableButtons");
return (
<div className="page-body__card_buttons">
<Button variant="contained" id="datatable_button_add" startIcon={<IoAdd />}>추가</Button>
<Button variant="contained" id="datatable_button_modify" startIcon={<VscEdit />} disabled={editButtonDisabled}>수정</Button>
</div>
);
};
const PageBody = () => {
return (
<div className="page-body">
<div className="page-body__card">
<PageDataTable />
<PageDataTableButtons />
</div>
</div>
);
};
return (
<Layout>
{userInfo => (
<main className="main">
<PageHeader />
<PageBody />
</main>
)}
</Layout>
);
}
英文:
I have the following code, where I want to enable the edit button when a row is checked.
So I have set editButtonDisabled as a state variable to handle the disable attribute of the button.
Now the problem is when I check the unchecked checkBox of the row, the edit button gets enabled, but the uncheck checkbox remains unchecked. If I check it again, then it becomes checked. When I uncheck it, it becomes unchecked with the button being disabled.
If I remove the callback, it works fine. So I am guessing that the changing the state of the variable is messing with my checkbox. What can be done to resolve this problem?
import { useEffect, useState, useRef, useCallback } from 'react';
import { getDocs, query, collection, orderBy, doc } from 'firebase/firestore';
import DataTable from 'react-data-table-component';
import { Button, Checkbox } from '@mui/material';
import { FcInspection } from 'react-icons/fc';
import { IoAdd } from 'react-icons/io5';
import { VscEdit } from 'react-icons/vsc';
import { db } from '../../../services/firebase';
import { Layout } from '../../layout';
export default function InstituteList() {
const [retrievedFlag, setRetrievedFlag] = useState(false);
const [institutes, setInstitutes] = useState([]);
const [editButtonDisabled, setEditButtonDisabled] = useState(true);
useEffect(() => {
if (retrievedFlag === false) retrieveData();
}, [])
useEffect(() => {
console.log(editButtonDisabled);
}, [editButtonDisabled])
function retrieveData() {
try {
let tmpInstitutes = [];
const institutesRef = collection(db, 'Institutes');
const institutesQuery = query(institutesRef, orderBy('title'));
getDocs(institutesQuery)
.then(snapshot => {
snapshot.forEach((doc) => {
let institute = doc.data();
institute.id = doc.id;
tmpInstitutes.push(institute);
});
setInstitutes(tmpInstitutes);
setRetrievedFlag(true);
});
} catch (error) {
console.log(error);
}
}
const columns = [
{ name: 'id', selector: row => row.id, omit: true },
{ name: '조직명', selector: row => row.title, sortable: true, grow: 1 },
{ name: '등록일', selector: row => row.date, sortable: true, grow: 1 },
{ name: '주소', selector: row => row.location, sortable: true, grow: 4 },
];
const handleSelectedRowChange = useCallback((state) => {
console.log('Set edit button disable state', state);
setEditButtonDisabled(state.selectedCount == 0);
});
const paginationComponentOptions = {
rowsPerPageText: '페이지당 조회 갯수',
rangeSeparatorText: '중',
selectAllRowsItem: true,
selectAllRowsItemText: '전체',
}
const PageHeader = (userInfo) => {
const today = new Date();
return (
<div className="page-header">
<div className="page-header__title">
<FcInspection />
조직목록조회
</div>
</div>
)
}
const DataTableHeader = () => {
return (
<div className="page-body__datatable_header">
<div className="page-body__datatable_header__title">조직목록</div>
<div className="page-body__datatable_header__title"></div>
</div>
);
}
const PageDataTable = () => {
return (
<div className="page-body__card_datatable">
<DataTable
title='조직목록'
noDataComponent='조회 할 데이터 없습니다.'
columns={columns}
data={institutes}
persistTableHead={true}
noContextMenu={true}
selectableRows={true}
selectableRowsHighlight={true}
selectableRowsComponent={Checkbox}
selectableRowsSingle={true}
onSelectedRowsChange={handleSelectedRowChange}
pagination
paginationComponentOptions={paginationComponentOptions}
/>
</div>
);
}
const PageDataTableButtons = () => {
console.log("Render PageDataTableButtons");
return (
<div className="page-body__card_buttons">
<Button variant="contained" id="datatable_button_add" startIcon={<IoAdd />}>추가</Button>
<Button variant="contained" id="datatable_button_modify" startIcon={<VscEdit />} disabled={editButtonDisabled}>수정</Button>
</div>
)
}
const PageBody = () => {
return (
<div className="page-body">
<div className="page-body__card">
<PageDataTable />
<PageDataTableButtons />
</div>
</div>
);
}
return (
<Layout>
{userInfo => (
<main className="main">
<PageHeader />
<PageBody />
</main>
)}
</Layout>
);
}
答案1
得分: 0
看起来是 useEffect 导致了问题。
我已经为 datatable 相关的组件创建了一个单独的组件文件,问题得到了解决。
但我仍然想知道为什么它导致了问题。
英文:
It seems that useEffect is causing the problem.
I have created a separate component file for datatable related components, and the problem was resolved.
But I would still love to know why it was causing the problem.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论