这是我第一次开发React应用程序。请忍受我。
我打算在确认对话框中显示键(表中的值)。它可以按预期工作,但是当我勾选然后取消选中复选框时,该键似乎仍在地图中。
我通过检索其键并将其添加到数组中来显示checkedMap。但是,当我尝试取消选中然后调用对话框时,在调试视图中,checkedMap仍然具有未选中的键。
谢谢您的帮助。
import React, { useState, useEffect, useRef } from "react";
//import makeData from "../makeData";
import { useTableState } from "react-table";
import Table from "../TransactionPanelTable";
// Simulate a server
const getServerData = async ({ filters, sortBy, pageSize, pageIndex }) => {
await new Promise(resolve => setTimeout(resolve, 500));
// Ideally, you would pass this info to the server, but we'll do it here for convenience
const filtersArr = Object.entries(filters);
// Get our base data
let rows = [];
rows.push({
transaction_seq: 1555,
record_count: 300,
user_id: "test1",
updated_at: "09-MAY-19 10.01.45.371373000 PM",
duration: 5.7
});
rows.push({
transaction_seq: 2666,
rec_count: 1234,
user_id: "test2",
updated_at: "",
duration: 1.23
});
// Apply Filters
if (filtersArr.length) {
rows = rows.filter(row =>
filtersArr.every(([key, value]) => row[key].includes(value))
);
}
// Apply Sorting
if (sortBy.length) {
const [{ id, desc }] = sortBy;
rows = [...rows].sort(
(a, b) => (a[id] > b[id] ? 1 : a[id] === b[id] ? 0 : -1) * (desc ? -1 : 1)
);
}
// Get page counts
const pageCount = Math.ceil(rows.length / pageSize);
const rowStart = pageSize * pageIndex;
const rowEnd = rowStart + pageSize;
// Get the current page
rows = rows.slice(rowStart, rowEnd);
return {
rows,
pageCount
};
};
export default function({ infinite }) {
**const [checkedMap, setCheckedMap] = useState(new Map());**
const [data, setData] = useState([]);
const [loading, setLoading] = useState(false);
const currentRequestRef = useRef();
**let newMap = new Map();**
const fetchData = async () => {
setLoading(true);
// We can use a ref to disregard any outdated requests
const id = Date.now();
currentRequestRef.current = id;
// Call our server for the data
const { rows, pageCount } = await getServerData({
filters,
sortBy,
pageSize,
pageIndex
});
// If this is an outdated request, disregard the results
if (currentRequestRef.current !== id) {
return;
}
// Set the data and pageCount
setData(rows);
setState(old => ({
...old,
pageCount
}));
**rows.forEach(row => newMap.set(row, false));**
//setCheckedMap(newMap);
setLoading(false);
};
**const handleCheckedChange = transaction_seq => {
let modifiedMap = checkedMap;
modifiedMap.set(transaction_seq, !checkedMap.get(transaction_seq));
setCheckedMap(modifiedMap);
};**
const columns = [
{
Header: "Transaction(s)",
className: "left",
columns: [
{
id: "checkbox",
accessor: "checkbox",
Cell: ({ row }) => {
return (
<input
type="checkbox"
className="checkbox"
checked={checkedMap.get(row.original.transaction_seq)}
onChange={() =>
handleCheckedChange(row.original.transaction_seq)
}
/>
);
},
sortable: false,
width: 45
},
{
Header: "Transaction Sequence",
accessor: "transaction_seq",
id: "transaction_seq",
minWidth: 200,
maxWidth: 300
},
{
Header: "Record count",
accessor: "record_count",
width: 300
},
{
Header: "User Id",
accessor: "user_id",
width: 300
},
{
Header: "Updated At",
accessor: "updated_at",
width: 400
},
{
Header: "Duration",
accessor: "duration",
width: 400
}
]
}
];
// Make a new controllable table state instance
const state = useTableState({ pageCount: 0 });
const [{ sortBy, filters, pageIndex, pageSize }, setState] = state;
// When sorting, filters, pageSize, or pageIndex change, fetch new data
useEffect(() => {
fetchData();
}, [sortBy, filters, pageIndex, pageSize]);
return (
<React.Fragment>
<Table
{...{
data,
**checkedMap,**
columns,
infinite,
state, // Pass the state to the table
loading,
manualSorting: true, // Manual sorting
manualFilters: true, // Manual filters
manualPagination: true, // Manual pagination
disableMultiSort: true, // Disable multi-sort
disableGrouping: true, // Disable grouping
debug: true
}}
/>
</React.Fragment>
);
}
这是table.js
import styled, { css } from "styled-components";
import React, { useRef, useState, useEffect, useLayoutEffect } from "react";
import { FixedSizeList as List } from "react-window";
import {
useTable,
useColumns,
useRows,
useFilters,
useSortBy,
useExpanded,
usePagination,
useFlexLayout
} from "react-table";
export default function MyTable({ loading, infinite, checkedMap, ...props }) {
const instance = useTable(
{
...props
},
useColumns,
useRows,
useFilters,
useSortBy,
useExpanded,
usePagination,
useFlexLayout
);
const {
getTableProps,
headerGroups,
rows,
getRowProps,
pageOptions,
page,
state: [{ pageIndex, pageSize, sortBy, filters }],
gotoPage,
prepareRow,
previousPage,
nextPage,
setPageSize,
canPreviousPage,
canNextPage
} = instance;
const { listRef, rowHeight, height, overscan } = useInfiniteScroll({
enabled: infinite,
sortBy,
filters,
pageIndex,
pageSize
});
let tableBody;
const renderRow = (row, index, style = {}) => {
if (!row) {
return (
<Row {...{ style, even: index % 2 }}>
<Cell>Loading more...</Cell>
</Row>
);
}
prepareRow(row);
return (
<Row {...row.getRowProps({ style, even: index % 2 })}>
{row.cells.map(cell => {
const isPivot = row.groupByID === cell.column.id;
const showAggregate = row.subRows && !isPivot;
return (
<Cell {...cell.getCellProps()}>
{showAggregate ? (
cell.column.aggregate ? (
cell.render("Aggregated")
) : null
) : (
<span>
{isPivot ? (
<span
style={{
cursor: "pointer",
paddingLeft: `${row.depth * 2}rem`,
paddingRight: "1rem",
whiteSpace: "nowrap"
}}
onClick={() => row.toggleExpanded()}
/>
) : null}
{cell.render("Cell")}
{isPivot ? <span> ({row.subRows.length})</span> : null}
</span>
)}
</Cell>
);
})}
</Row>
);
};
if (infinite) {
tableBody = (
<List
ref={listRef}
height={height}
itemCount={rows.length + 1}
itemSize={rowHeight}
overscanCount={overscan}
scrollToAlignment="start"
{...getRowProps()}
>
{({ index, style }) => {
const row = rows[index];
return renderRow(row, index, style);
}}
</List>
);
} else {
tableBody =
page && page.length ? page.map((row, i) => renderRow(row, i)) : null;
}
let pagination;
pagination = pageOptions.length ? (
<Pagination {...getRowProps()}>
<Cell>
<Button onClick={() => previousPage()} disabled={!canPreviousPage}>
Previous
</Button>{" "}
<Button onClick={() => nextPage()} disabled={!canNextPage}>
Next
</Button>{" "}
<span>
Page{" "}
<strong>
{pageIndex + 1} of {pageOptions.length}
</strong>{" "}
</span>
<span>
| Go to page:{" "}
<Input
type="number"
defaultValue={pageIndex + 1}
onChange={e => {
const page = e.target.value ? Number(e.target.value) - 1 : 0;
gotoPage(page);
}}
style={{ width: "100px" }}
/>
</span>{" "}
<Select
value={pageSize}
onChange={e => {
setPageSize(Number(e.target.value));
}}
>
{[10, 20, 30, 40, 50].map(pageSize => (
<option key={pageSize} value={pageSize}>
Show {pageSize}
</option>
))}
</Select>{" "}
<Button onClick={() => reprocessConfirmation()}>Reprocess</Button>
</Cell>
</Pagination>
) : null;
function reprocessConfirmation() {
let confirmation = window.confirm(
"Do you want to reprocess transaction sequence " +
Array.from(checkedMap.keys())
);
if (confirmation === true) console.log(Array.from(checkedMap.keys()));
else console.log("CANCEL");
}
return (
<React.Fragment>
<Table {...getTableProps()}>
{headerGroups.map(headerGroup => (
<HeaderRow {...headerGroup.getRowProps()}>
{headerGroup.headers.map(column => (
<Header
{...column.getHeaderProps()}
sorted={column.sorted}
sortedDesc={column.sortedDesc}
sortedIndex={column.sortedIndex}
>
<div>
<span {...column.getSortByToggleProps()}>
{column.render("Header")}
</span>{" "}
</div>
{column.canFilter ? <div>{column.render("Filter")}</div> : null}
</Header>
))}
</HeaderRow>
))}
{tableBody}
<Row {...getRowProps()}>
{loading ? (
<Cell>
<strong>Loading...</strong>
</Cell>
) : (
<Cell>{rows.length} Total Records</Cell>
)}
</Row>
{pagination}
</Table>
</React.Fragment>
);
}