Allows holding shift and selecting rows.

This commit is contained in:
SergeantPanda 2025-04-29 12:20:26 -05:00
parent 342797d2ec
commit 7503ef9dd2
2 changed files with 45 additions and 8 deletions

View file

@ -1,6 +1,6 @@
import { Box, Flex } from '@mantine/core';
import CustomTableHeader from './CustomTableHeader';
import { useCallback, useState } from 'react';
import { useCallback, useState, useRef } from 'react';
import { flexRender } from '@tanstack/react-table';
import table from '../../../helpers/table';
import CustomTableBody from './CustomTableBody';
@ -11,7 +11,6 @@ const CustomTable = ({ table }) => {
className="divTable table-striped"
style={{
width: '100%',
// height: '100%', // ONLY required when using virtual tables
display: 'flex',
flexDirection: 'column',
}}

View file

@ -21,6 +21,7 @@ const useTable = ({
}) => {
const [selectedTableIds, setSelectedTableIds] = useState([]);
const [expandedRowIds, setExpandedRowIds] = useState([]);
const [lastClickedId, setLastClickedId] = useState(null);
const rowCount = allRowIds.length;
@ -77,6 +78,34 @@ const useTable = ({
updateSelectedTableIds([row.original.id]);
};
// Handle the shift+click selection
const handleShiftSelect = (rowId, isShiftKey) => {
if (!isShiftKey || lastClickedId === null) {
// Normal selection behavior
setLastClickedId(rowId);
return false; // Return false to indicate we're not handling it
}
// Handle shift-click range selection
const currentIndex = allRowIds.indexOf(rowId);
const lastIndex = allRowIds.indexOf(lastClickedId);
if (currentIndex === -1 || lastIndex === -1) return false;
// Determine range
const startIndex = Math.min(currentIndex, lastIndex);
const endIndex = Math.max(currentIndex, lastIndex);
const rangeIds = allRowIds.slice(startIndex, endIndex + 1);
// Preserve existing selections outside the range
const idsOutsideRange = selectedTableIds.filter(id => !rangeIds.includes(id));
const newSelection = [...new Set([...rangeIds, ...idsOutsideRange])];
updateSelectedTableIds(newSelection);
setLastClickedId(rowId);
return true; // Return true to indicate we've handled it
};
const renderBodyCell = ({ row, cell }) => {
if (bodyCellRenderFns[cell.column.id]) {
return bodyCellRenderFns[cell.column.id]({ row, cell });
@ -91,13 +120,22 @@ const useTable = ({
size="xs"
checked={selectedTableIdsSet.has(row.original.id)}
onChange={(e) => {
const newSet = new Set(selectedTableIds);
if (e.target.checked) {
newSet.add(row.original.id);
} else {
newSet.delete(row.original.id);
const rowId = row.original.id;
// Get shift key state from the event
const isShiftKey = e.nativeEvent.shiftKey;
// Try to handle with shift-select logic first
if (!handleShiftSelect(rowId, isShiftKey)) {
// If not handled by shift-select, do regular toggle
const newSet = new Set(selectedTableIds);
if (e.target.checked) {
newSet.add(rowId);
} else {
newSet.delete(rowId);
}
updateSelectedTableIds([...newSet]);
}
updateSelectedTableIds([...newSet]);
}}
/>
</Center>