refactor: Update input styles and enhance keyboard shortcut handling
This commit is contained in:
@@ -7,14 +7,28 @@ input {
|
||||
width: 100%;
|
||||
padding: 2px 4px;
|
||||
border-radius: #{$border-radius-small};
|
||||
border: 1px solid var(--border-color);
|
||||
outline: none;
|
||||
outline: 2px solid var(--border-color);
|
||||
outline-offset: -2px;
|
||||
border: none;
|
||||
background: transparent;
|
||||
color: var(--input-text-color);
|
||||
|
||||
&:focus,
|
||||
&:active {
|
||||
border: 1px solid var(--accent-color);
|
||||
outline: 1px solid var(--accent-color);
|
||||
}
|
||||
|
||||
&:-webkit-autofill,
|
||||
&:-webkit-autofill:hover,
|
||||
&:-webkit-autofill:focus,
|
||||
&:-webkit-autofill:active {
|
||||
// Text styles
|
||||
-webkit-text-fill-color: var(--input-text-color) !important;
|
||||
caret-color: var(--input-text-color);
|
||||
|
||||
// Background styles
|
||||
background-color: var(--background-color) !important;
|
||||
-webkit-box-shadow: 0 0 0px 1000px var(--background-color) inset !important;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -615,6 +629,7 @@ input {
|
||||
|
||||
input {
|
||||
border: none;
|
||||
outline: none;
|
||||
background: transparent;
|
||||
|
||||
&::placeholder {
|
||||
|
||||
30
app/src/utils/shortcutkeys/detectModifierKeys.ts
Normal file
30
app/src/utils/shortcutkeys/detectModifierKeys.ts
Normal file
@@ -0,0 +1,30 @@
|
||||
// Function to detect if Shift, Ctrl, Alt, or combinations are pressed
|
||||
// and return the corresponding key combination string
|
||||
export const detectModifierKeys = (event: KeyboardEvent): string => {
|
||||
const modifiers = [
|
||||
event.ctrlKey ? "Ctrl" : "",
|
||||
event.altKey ? "Alt" : "",
|
||||
event.shiftKey ? "Shift" : "",
|
||||
event.metaKey ? "Meta" : "" // Add support for Command/Win key
|
||||
].filter(Boolean);
|
||||
|
||||
// Ignore modifier keys when they're pressed alone
|
||||
const isModifierKey = [
|
||||
"Control", "Shift", "Alt", "Meta",
|
||||
"Ctrl", "AltGraph", "OS" // Additional modifier key aliases
|
||||
].includes(event.key);
|
||||
|
||||
const mainKey = isModifierKey ? "" : event.key.toUpperCase();
|
||||
|
||||
// Handle special cases for keys with different representations
|
||||
const normalizedKey = mainKey === " " ? "Space" : mainKey;
|
||||
|
||||
// Build the combination string
|
||||
if (modifiers.length > 0 && normalizedKey) {
|
||||
return `${modifiers.join("+")}+${normalizedKey}`;
|
||||
} else if (modifiers.length > 0) {
|
||||
return modifiers.join("+");
|
||||
} else {
|
||||
return normalizedKey;
|
||||
}
|
||||
};
|
||||
@@ -1,85 +1,70 @@
|
||||
// Importing React and useEffect from React library
|
||||
import React, { useEffect } from "react";
|
||||
// Importing the necessary hooks and types from React and TypeScript
|
||||
|
||||
// Importing the necessary hooks and types from the application's state management stores
|
||||
import useModuleStore, { useThreeDStore } from "../../store/useModuleStore";
|
||||
import useToggleStore from "../../store/useUIToggleStore";
|
||||
import { useActiveSubTool, useActiveTool, useAddAction, useDeleteTool, useSelectedWallItem, useToggleView, useToolMode } from "../../store/store";
|
||||
import {
|
||||
useActiveSubTool,
|
||||
useActiveTool,
|
||||
useAddAction,
|
||||
useDeleteTool,
|
||||
useSelectedWallItem,
|
||||
useToggleView,
|
||||
useToolMode,
|
||||
} from "../../store/store";
|
||||
import { usePlayButtonStore } from "../../store/usePlayButtonStore";
|
||||
|
||||
// Utility function to detect modifier keys (Ctrl, Alt, Shift) and key combinations
|
||||
import { detectModifierKeys } from "./detectModifierKeys";
|
||||
|
||||
// KeyPressListener component to handle global keyboard shortcuts
|
||||
const KeyPressListener: React.FC = () => {
|
||||
// Function to detect if Shift, Ctrl, Alt, or combinations are pressed
|
||||
const detectModifierKeys = (event: KeyboardEvent): string => {
|
||||
const modifiers = [
|
||||
event.ctrlKey ? "Ctrl" : "",
|
||||
event.altKey ? "Alt" : "",
|
||||
event.shiftKey ? "Shift" : "",
|
||||
event.metaKey ? "Meta" : "" // Add support for Command/Win key
|
||||
].filter(Boolean);
|
||||
// Accessing state and actions from different stores
|
||||
const { activeModule, setActiveModule } = useModuleStore(); // Module management (e.g., builder, simulation, visualization)
|
||||
const { setActiveSubTool } = useActiveSubTool(); // Sub-tool management
|
||||
const { toggleUI, setToggleUI } = useToggleStore(); // UI visibility toggle
|
||||
const { setToggleThreeD } = useThreeDStore(); // 3D view toggle
|
||||
const { setToolMode } = useToolMode(); // Tool mode management
|
||||
const { setIsPlaying } = usePlayButtonStore(); // Play button state management
|
||||
|
||||
// Ignore modifier keys when they're pressed alone
|
||||
const isModifierKey = [
|
||||
"Control", "Shift", "Alt", "Meta",
|
||||
"Ctrl", "AltGraph", "OS" // Additional modifier key aliases
|
||||
].includes(event.key);
|
||||
|
||||
const mainKey = isModifierKey ? "" : event.key.toUpperCase();
|
||||
|
||||
// Handle special cases for keys with different representations
|
||||
const normalizedKey = mainKey === " " ? "Space" : mainKey;
|
||||
|
||||
// Build the combination string
|
||||
if (modifiers.length > 0 && normalizedKey) {
|
||||
return `${modifiers.join("+")}+${normalizedKey}`;
|
||||
} else if (modifiers.length > 0) {
|
||||
return modifiers.join("+");
|
||||
} else {
|
||||
return normalizedKey;
|
||||
}
|
||||
};
|
||||
|
||||
// Importing the necessary hooks from the store
|
||||
const { activeModule, setActiveModule } = useModuleStore();
|
||||
const { setActiveSubTool } = useActiveSubTool();
|
||||
const { toggleUI, setToggleUI } = useToggleStore();
|
||||
const { setToggleThreeD } = useThreeDStore();
|
||||
const { setToolMode } = useToolMode();
|
||||
const { setIsPlaying } = usePlayButtonStore();
|
||||
|
||||
// wall options
|
||||
const { toggleView, setToggleView } = useToggleView();
|
||||
const { setDeleteTool } = useDeleteTool();
|
||||
const { setAddAction } = useAddAction();
|
||||
const { setSelectedWallItem } = useSelectedWallItem();
|
||||
const { setActiveTool } = useActiveTool();
|
||||
// Wall and tool-related actions
|
||||
const { toggleView, setToggleView } = useToggleView(); // 2D/3D toggle state
|
||||
const { setDeleteTool } = useDeleteTool(); // Delete tool action
|
||||
const { setAddAction } = useAddAction(); // Add action management
|
||||
const { setSelectedWallItem } = useSelectedWallItem(); // Selected wall item management
|
||||
const { setActiveTool } = useActiveTool(); // Active tool management
|
||||
|
||||
// useEffect to manage global keyboard shortcuts
|
||||
useEffect(() => {
|
||||
// Function to handle keydown events
|
||||
const handleKeyPress = (event: KeyboardEvent) => {
|
||||
|
||||
// Identify the currently focused element
|
||||
const activeElement = document.activeElement;
|
||||
|
||||
const isTyping =
|
||||
activeElement instanceof HTMLInputElement ||
|
||||
activeElement instanceof HTMLTextAreaElement ||
|
||||
(activeElement && activeElement.getAttribute('contenteditable') === 'true');
|
||||
|
||||
// Check if the user is typing in an input field, textarea, or contenteditable element
|
||||
const isTyping =
|
||||
activeElement instanceof HTMLInputElement ||
|
||||
activeElement instanceof HTMLTextAreaElement ||
|
||||
(activeElement && activeElement.getAttribute("contenteditable") === "true");
|
||||
|
||||
if (isTyping) {
|
||||
return; // Don't trigger shortcuts while typing
|
||||
return; // Skip shortcut handling while typing
|
||||
}
|
||||
|
||||
// Detect the combination of keys pressed
|
||||
const keyCombination = detectModifierKeys(event);
|
||||
|
||||
// Allow default behavior for F5 and F12
|
||||
|
||||
// Allow browser default behavior for specific keys (e.g., F5 for refresh)
|
||||
if (["F5", "F11", "F12"].includes(event.key) || keyCombination === "Ctrl+R") {
|
||||
return;
|
||||
}
|
||||
|
||||
// Prevent default action for the key press
|
||||
// Prevent the default browser action for other handled key presses
|
||||
event.preventDefault();
|
||||
|
||||
// Detect the key combination pressed
|
||||
if (keyCombination) {
|
||||
// Check for specific key combinations to switch modules
|
||||
// Switch between different modules (e.g., builder, simulation)
|
||||
if (keyCombination === "1" && !toggleView) {
|
||||
setActiveTool("cursor");
|
||||
setActiveSubTool("cursor");
|
||||
@@ -102,12 +87,12 @@ const KeyPressListener: React.FC = () => {
|
||||
setActiveModule("market");
|
||||
}
|
||||
|
||||
// sidebar toggle
|
||||
// Toggle UI visibility
|
||||
if (keyCombination === "Ctrl+." && activeModule !== "market") {
|
||||
setToggleUI(!toggleUI);
|
||||
}
|
||||
|
||||
// tools toggle
|
||||
// Tool selection shortcuts
|
||||
if (keyCombination === "V") {
|
||||
setActiveTool("cursor");
|
||||
setActiveSubTool("cursor");
|
||||
@@ -121,14 +106,15 @@ const KeyPressListener: React.FC = () => {
|
||||
setActiveSubTool("free-hand");
|
||||
}
|
||||
|
||||
// player toggle
|
||||
// Toggle play mode
|
||||
if (keyCombination === "Ctrl+P" && !toggleView) {
|
||||
setIsPlaying(true);
|
||||
}
|
||||
|
||||
// builder key combination
|
||||
// Builder-specific shortcuts
|
||||
if (activeModule === "builder") {
|
||||
if (keyCombination === "TAB") {
|
||||
// Switch between 2D and 3D views
|
||||
if (toggleView) {
|
||||
setToggleView(false);
|
||||
setToggleThreeD(true);
|
||||
@@ -142,7 +128,8 @@ const KeyPressListener: React.FC = () => {
|
||||
setActiveTool("cursor");
|
||||
}
|
||||
}
|
||||
// builder tools
|
||||
|
||||
// Wall-related tools
|
||||
if (toggleView) {
|
||||
if (keyCombination === "Q" || keyCombination === "6") {
|
||||
setActiveTool("draw-wall");
|
||||
@@ -161,21 +148,34 @@ const KeyPressListener: React.FC = () => {
|
||||
setToolMode("Floor");
|
||||
}
|
||||
}
|
||||
|
||||
// Measurement tool
|
||||
if (keyCombination === "M") {
|
||||
setActiveTool("measure");
|
||||
setToolMode("MeasurementScale");
|
||||
}
|
||||
}
|
||||
|
||||
// Undo redo
|
||||
// Undo and redo actions
|
||||
if (keyCombination === "Ctrl+Z") {
|
||||
// Handle undo action here
|
||||
// Handle undo action
|
||||
}
|
||||
if (keyCombination === "Ctrl+Y" || keyCombination === "Ctrl+Shift+Z") {
|
||||
// Handle redo action here
|
||||
// Handle redo action
|
||||
}
|
||||
|
||||
// cleanup function to remove event listener
|
||||
// Helper actions
|
||||
if (keyCombination === "Ctrl+H") {
|
||||
// Open help
|
||||
}
|
||||
if (keyCombination === "Ctrl+F") {
|
||||
// Open find functionality
|
||||
}
|
||||
if (keyCombination === "Ctrl+?") {
|
||||
// Show shortcuts info
|
||||
}
|
||||
|
||||
// Reset to cursor tool and stop play mode
|
||||
if (keyCombination === "ESCAPE") {
|
||||
setActiveTool("cursor");
|
||||
setIsPlaying(false);
|
||||
@@ -183,16 +183,16 @@ const KeyPressListener: React.FC = () => {
|
||||
}
|
||||
};
|
||||
|
||||
// Add event listener for keydown
|
||||
// Add keydown event listener
|
||||
window.addEventListener("keydown", handleKeyPress);
|
||||
|
||||
// Cleanup function to remove event listener
|
||||
// Cleanup function to remove the event listener
|
||||
return () => {
|
||||
window.removeEventListener("keydown", handleKeyPress);
|
||||
};
|
||||
}, [activeModule, toggleUI, toggleView]); // Empty dependency array ensures this runs only once
|
||||
}, [activeModule, toggleUI, toggleView]); // Dependencies to reapply effect if these values change
|
||||
|
||||
return null; // No UI component to render, so return null
|
||||
return null; // This component does not render any UI
|
||||
};
|
||||
|
||||
export default KeyPressListener;
|
||||
|
||||
Reference in New Issue
Block a user