mirror of
https://github.com/Dispatcharr/Dispatcharr.git
synced 2026-07-25 11:04:07 +00:00
Don't select text when shift is held
This commit is contained in:
parent
7503ef9dd2
commit
9be42ce532
2 changed files with 194 additions and 75 deletions
|
|
@ -7,7 +7,7 @@ import {
|
|||
getCoreRowModel,
|
||||
flexRender,
|
||||
} from '@tanstack/react-table';
|
||||
import { useCallback, useMemo, useState } from 'react';
|
||||
import { useCallback, useMemo, useState, useEffect } from 'react';
|
||||
import { ChevronDown, ChevronRight } from 'lucide-react';
|
||||
|
||||
const useTable = ({
|
||||
|
|
@ -22,6 +22,63 @@ const useTable = ({
|
|||
const [selectedTableIds, setSelectedTableIds] = useState([]);
|
||||
const [expandedRowIds, setExpandedRowIds] = useState([]);
|
||||
const [lastClickedId, setLastClickedId] = useState(null);
|
||||
const [isShiftKeyDown, setIsShiftKeyDown] = useState(false);
|
||||
|
||||
// Event handlers for shift key detection with improved handling
|
||||
const handleKeyDown = useCallback((e) => {
|
||||
if (e.key === 'Shift') {
|
||||
setIsShiftKeyDown(true);
|
||||
// Apply the class to disable text selection immediately
|
||||
document.body.classList.add('shift-key-active');
|
||||
// Set a style attribute directly on body for extra assurance
|
||||
document.body.style.userSelect = 'none';
|
||||
document.body.style.webkitUserSelect = 'none';
|
||||
document.body.style.msUserSelect = 'none';
|
||||
document.body.style.cursor = 'pointer';
|
||||
}
|
||||
}, []);
|
||||
|
||||
const handleKeyUp = useCallback((e) => {
|
||||
if (e.key === 'Shift') {
|
||||
setIsShiftKeyDown(false);
|
||||
// Remove the class when shift is released
|
||||
document.body.classList.remove('shift-key-active');
|
||||
// Reset the style attributes
|
||||
document.body.style.removeProperty('user-select');
|
||||
document.body.style.removeProperty('-webkit-user-select');
|
||||
document.body.style.removeProperty('-ms-user-select');
|
||||
document.body.style.removeProperty('cursor');
|
||||
}
|
||||
}, []);
|
||||
|
||||
// Add global event listeners for shift key detection with improved cleanup
|
||||
useEffect(() => {
|
||||
window.addEventListener('keydown', handleKeyDown);
|
||||
window.addEventListener('keyup', handleKeyUp);
|
||||
|
||||
// Also detect blur/focus events to handle cases where shift is held and window loses focus
|
||||
window.addEventListener('blur', () => {
|
||||
setIsShiftKeyDown(false);
|
||||
document.body.classList.remove('shift-key-active');
|
||||
document.body.style.removeProperty('user-select');
|
||||
document.body.style.removeProperty('-webkit-user-select');
|
||||
document.body.style.removeProperty('-ms-user-select');
|
||||
document.body.style.removeProperty('cursor');
|
||||
});
|
||||
|
||||
return () => {
|
||||
window.removeEventListener('keydown', handleKeyDown);
|
||||
window.removeEventListener('keyup', handleKeyUp);
|
||||
window.removeEventListener('blur', () => {
|
||||
setIsShiftKeyDown(false);
|
||||
document.body.classList.remove('shift-key-active');
|
||||
document.body.style.removeProperty('user-select');
|
||||
document.body.style.removeProperty('-webkit-user-select');
|
||||
document.body.style.removeProperty('-ms-user-select');
|
||||
document.body.style.removeProperty('cursor');
|
||||
});
|
||||
};
|
||||
}, [handleKeyDown, handleKeyUp]);
|
||||
|
||||
const rowCount = allRowIds.length;
|
||||
|
||||
|
|
@ -175,8 +232,9 @@ const useTable = ({
|
|||
expandedRowIds,
|
||||
expandedRowRenderer,
|
||||
setSelectedTableIds,
|
||||
isShiftKeyDown, // Include shift key state in the table instance
|
||||
}),
|
||||
[selectedTableIdsSet, expandedRowIds, allRowIds]
|
||||
[selectedTableIdsSet, expandedRowIds, allRowIds, isShiftKeyDown]
|
||||
);
|
||||
|
||||
return {
|
||||
|
|
|
|||
|
|
@ -1,94 +1,155 @@
|
|||
* {
|
||||
/* box-sizing: border-box; */
|
||||
}
|
||||
/* box-sizing: border-box; */
|
||||
}
|
||||
|
||||
html {
|
||||
font-family: sans-serif;
|
||||
/* font-size: 14px; */
|
||||
}
|
||||
html {
|
||||
font-family: sans-serif;
|
||||
/* font-size: 14px; */
|
||||
}
|
||||
|
||||
.divTable {
|
||||
/* border: 1px solid lightgray; */
|
||||
/* width: fit-content; */
|
||||
/* display: flex;
|
||||
.divTable {
|
||||
/* border: 1px solid lightgray; */
|
||||
/* width: fit-content; */
|
||||
/* display: flex;
|
||||
flex-direction: column; */
|
||||
}
|
||||
}
|
||||
|
||||
.tr {
|
||||
display: flex;
|
||||
}
|
||||
.tr {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.table-striped .tbody .tr:hover {
|
||||
background-color: rgb(68,68,68);
|
||||
}
|
||||
.table-striped .tbody .tr:hover {
|
||||
background-color: rgb(68, 68, 68);
|
||||
}
|
||||
|
||||
.tr {
|
||||
/* width: fit-content;
|
||||
.tr {
|
||||
/* width: fit-content;
|
||||
width: 100%; */
|
||||
/* height: 30px; */
|
||||
}
|
||||
/* height: 30px; */
|
||||
}
|
||||
|
||||
.th,
|
||||
.td {
|
||||
/* box-shadow: inset 0 0 0 1px lightgray; */
|
||||
/* padding: 0.25rem; */
|
||||
padding-left: 4px;
|
||||
padding-right: 4px;
|
||||
}
|
||||
.th,
|
||||
.td {
|
||||
/* box-shadow: inset 0 0 0 1px lightgray; */
|
||||
/* padding: 0.25rem; */
|
||||
padding-left: 4px;
|
||||
padding-right: 4px;
|
||||
}
|
||||
|
||||
.th {
|
||||
/* padding: 2px 4px; */
|
||||
position: relative;
|
||||
font-weight: bold;
|
||||
text-align: center;
|
||||
/* height: 30px; */
|
||||
}
|
||||
.th {
|
||||
/* padding: 2px 4px; */
|
||||
position: relative;
|
||||
font-weight: bold;
|
||||
text-align: center;
|
||||
/* height: 30px; */
|
||||
}
|
||||
|
||||
.td {
|
||||
height: 28px;
|
||||
border-bottom: solid 1px rgb(68,68,68);
|
||||
}
|
||||
.td {
|
||||
height: 28px;
|
||||
border-bottom: solid 1px rgb(68, 68, 68);
|
||||
}
|
||||
|
||||
.resizer {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
height: 100%;
|
||||
width: 5px;
|
||||
background: rgba(0, 0, 0, 0.5);
|
||||
cursor: col-resize;
|
||||
user-select: none;
|
||||
touch-action: none;
|
||||
}
|
||||
|
||||
.resizer.ltr {
|
||||
right: 0;
|
||||
}
|
||||
|
||||
.resizer.rtl {
|
||||
left: 0;
|
||||
}
|
||||
|
||||
.resizer.isResizing {
|
||||
background: blue;
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
@media (hover: hover) {
|
||||
.resizer {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
height: 100%;
|
||||
width: 5px;
|
||||
background: rgba(0, 0, 0, 0.5);
|
||||
cursor: col-resize;
|
||||
user-select: none;
|
||||
touch-action: none;
|
||||
opacity: 0;
|
||||
}
|
||||
|
||||
.resizer.ltr {
|
||||
right: 0;
|
||||
}
|
||||
|
||||
.resizer.rtl {
|
||||
left: 0;
|
||||
}
|
||||
|
||||
.resizer.isResizing {
|
||||
background: blue;
|
||||
*:hover>.resizer {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
|
||||
@media (hover: hover) {
|
||||
.resizer {
|
||||
opacity: 0;
|
||||
}
|
||||
/* .table-striped .tbody .tr:nth-child(odd), */
|
||||
.table-striped .tbody .tr-odd {
|
||||
background-color: #18181b;
|
||||
}
|
||||
|
||||
*:hover > .resizer {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
/* .table-striped .tbody .tr:nth-child(even), */
|
||||
.table-striped .tbody .tr-even {
|
||||
background-color: #27272A;
|
||||
}
|
||||
|
||||
/* .table-striped .tbody .tr:nth-child(odd), */
|
||||
.table-striped .tbody .tr-odd {
|
||||
background-color: #18181b;
|
||||
}
|
||||
/* Prevent text selection when shift key is pressed */
|
||||
.shift-key-active {
|
||||
cursor: pointer !important;
|
||||
}
|
||||
|
||||
/* .table-striped .tbody .tr:nth-child(even), */
|
||||
.table-striped .tbody .tr-even {
|
||||
background-color: #27272A;
|
||||
}
|
||||
.shift-key-active *,
|
||||
.shift-key-active .tr,
|
||||
.shift-key-active .td,
|
||||
.shift-key-active .tbody {
|
||||
user-select: none !important;
|
||||
-webkit-user-select: none !important;
|
||||
-moz-user-select: none !important;
|
||||
-ms-user-select: none !important;
|
||||
}
|
||||
|
||||
/* Always allow text selection in editable elements */
|
||||
.shift-key-active input,
|
||||
.shift-key-active textarea,
|
||||
.shift-key-active [contenteditable="true"],
|
||||
.shift-key-active .table-input-header input {
|
||||
user-select: text !important;
|
||||
-webkit-user-select: text !important;
|
||||
-moz-user-select: text !important;
|
||||
-ms-user-select: text !important;
|
||||
cursor: text !important;
|
||||
}
|
||||
|
||||
/* Improve specificity and ensure text selection is disabled when shift is pressed */
|
||||
.shift-key-active,
|
||||
.shift-key-active * {
|
||||
user-select: none !important;
|
||||
-webkit-user-select: none !important;
|
||||
-moz-user-select: none !important;
|
||||
-ms-user-select: none !important;
|
||||
cursor: pointer !important;
|
||||
}
|
||||
|
||||
/* Add a visual indicator when shift is pressed */
|
||||
.shift-key-active .tbody .tr {
|
||||
transition: background-color 0.1s;
|
||||
}
|
||||
|
||||
.shift-key-active .tbody .tr:hover {
|
||||
background-color: rgba(68, 68, 68, 0.7) !important;
|
||||
}
|
||||
|
||||
/* Always allow text selection in inputs even when shift is pressed */
|
||||
.shift-key-active input,
|
||||
.shift-key-active textarea,
|
||||
.shift-key-active [contenteditable="true"],
|
||||
.shift-key-active select,
|
||||
.shift-key-active .mantine-Select-input,
|
||||
.shift-key-active .mantine-MultiSelect-input,
|
||||
.shift-key-active .table-input-header input {
|
||||
user-select: text !important;
|
||||
-webkit-user-select: text !important;
|
||||
-moz-user-select: text !important;
|
||||
-ms-user-select: text !important;
|
||||
cursor: text !important;
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue