diff --git a/src/renderer/src/i18n/label.ts b/src/renderer/src/i18n/label.ts index ce36282b22..f60852be6b 100644 --- a/src/renderer/src/i18n/label.ts +++ b/src/renderer/src/i18n/label.ts @@ -210,6 +210,7 @@ const shortcutKeyMap = { reset_to_default: 'settings.shortcuts.reset_to_default', search_message: 'settings.shortcuts.search_message', search_message_in_chat: 'settings.shortcuts.search_message_in_chat', + send_shortcuts: 'settings.shortcuts.send_shortcuts', selection_assistant_select_text: 'settings.shortcuts.selection_assistant_select_text', selection_assistant_toggle: 'settings.shortcuts.selection_assistant_toggle', show_app: 'settings.shortcuts.show_app', diff --git a/src/renderer/src/i18n/locales/en-us.json b/src/renderer/src/i18n/locales/en-us.json index 08c2827200..0976c0d037 100644 --- a/src/renderer/src/i18n/locales/en-us.json +++ b/src/renderer/src/i18n/locales/en-us.json @@ -4666,6 +4666,7 @@ "search_message_in_chat": "Search Message in Current Chat", "selection_assistant_select_text": "Selection Assistant: Select Text", "selection_assistant_toggle": "Toggle Selection Assistant", + "send_shortcuts": "Send shortcuts", "show_app": "Show/Hide App", "show_settings": "Open Settings", "title": "Keyboard Shortcuts", diff --git a/src/renderer/src/i18n/locales/zh-cn.json b/src/renderer/src/i18n/locales/zh-cn.json index fa73a46499..7140edd34b 100644 --- a/src/renderer/src/i18n/locales/zh-cn.json +++ b/src/renderer/src/i18n/locales/zh-cn.json @@ -4666,6 +4666,7 @@ "search_message_in_chat": "在当前对话中搜索消息", "selection_assistant_select_text": "划词助手:取词", "selection_assistant_toggle": "开关划词助手", + "send_shortcuts": "发送快捷键", "show_app": "显示 / 隐藏应用", "show_settings": "打开设置", "title": "快捷键", diff --git a/src/renderer/src/i18n/locales/zh-tw.json b/src/renderer/src/i18n/locales/zh-tw.json index e8128f33a9..be53938765 100644 --- a/src/renderer/src/i18n/locales/zh-tw.json +++ b/src/renderer/src/i18n/locales/zh-tw.json @@ -4666,6 +4666,7 @@ "search_message_in_chat": "在目前對話中搜尋訊息", "selection_assistant_select_text": "劃詞助手:取詞", "selection_assistant_toggle": "開關劃詞助手", + "send_shortcuts": "傳送快捷鍵", "show_app": "顯示 / 隱藏應用程式", "show_settings": "開啟設定", "title": "快捷鍵", diff --git a/src/renderer/src/pages/home/Tabs/SettingsTab.tsx b/src/renderer/src/pages/home/Tabs/SettingsTab.tsx index f76971e99d..bcf9a4a1b5 100644 --- a/src/renderer/src/pages/home/Tabs/SettingsTab.tsx +++ b/src/renderer/src/pages/home/Tabs/SettingsTab.tsx @@ -15,7 +15,6 @@ import { SettingDivider, SettingRow, SettingRowTitle } from '@renderer/pages/set import { CollapsibleSettingGroup } from '@renderer/pages/settings/SettingGroup' import { getDefaultModel } from '@renderer/services/AssistantService' import { useAppDispatch } from '@renderer/store' -import type { SendMessageShortcut } from '@renderer/store/settings' import { setAutoTranslateWithSpace, setCodeCollapsible, @@ -47,7 +46,6 @@ import { } from '@renderer/store/settings' import type { Assistant, CodeStyleVarious, MathEngine } from '@renderer/types' import { isGroqSystemProvider, ThemeMode } from '@renderer/types' -import { getSendMessageShortcutLabel } from '@renderer/utils/input' import { isOpenAICompatibleProvider, isSupportServiceTierProvider, @@ -86,8 +84,6 @@ const SettingsTab: FC = (props) => { showPrompt, messageFont, showInputEstimatedTokens, - sendMessageShortcut, - setSendMessageShortcut, targetLanguage, setTargetLanguage, pasteLongTextAsFile, @@ -561,21 +557,6 @@ const SettingsTab: FC = (props) => { })} /> - - - {t('settings.messages.input.send_shortcuts')} - setSendMessageShortcut(value as SendMessageShortcut)} - options={[ - { value: 'Enter', label: getSendMessageShortcutLabel('Enter') }, - { value: 'Ctrl+Enter', label: getSendMessageShortcutLabel('Ctrl+Enter') }, - { value: 'Alt+Enter', label: getSendMessageShortcutLabel('Alt+Enter') }, - { value: 'Command+Enter', label: getSendMessageShortcutLabel('Command+Enter') }, - { value: 'Shift+Enter', label: getSendMessageShortcutLabel('Shift+Enter') } - ]} - /> - diff --git a/src/renderer/src/pages/settings/ShortcutSettings.tsx b/src/renderer/src/pages/settings/ShortcutSettings.tsx index 72bb3c376c..ba4b4df61a 100644 --- a/src/renderer/src/pages/settings/ShortcutSettings.tsx +++ b/src/renderer/src/pages/settings/ShortcutSettings.tsx @@ -1,11 +1,14 @@ import { ClearOutlined, UndoOutlined } from '@ant-design/icons' import { HStack } from '@renderer/components/Layout' +import Selector from "@renderer/components/Selector"; import { isMac, isWin } from '@renderer/config/constant' import { useTheme } from '@renderer/context/ThemeProvider' +import { useSettings} from "@renderer/hooks/useSettings"; import { useShortcuts } from '@renderer/hooks/useShortcuts' import { useTimer } from '@renderer/hooks/useTimer' import { getShortcutLabel } from '@renderer/i18n/label' import { useAppDispatch } from '@renderer/store' +import type {SendMessageShortcut} from "@renderer/store/settings"; import { initialState, resetShortcuts, toggleShortcut, updateShortcut } from '@renderer/store/shortcuts' import type { Shortcut } from '@renderer/types' import type { InputRef } from 'antd' @@ -16,12 +19,15 @@ import React, { useRef, useState } from 'react' import { useTranslation } from 'react-i18next' import styled from 'styled-components' -import { SettingContainer, SettingDivider, SettingGroup, SettingTitle } from '.' +import {SettingContainer, SettingDivider, SettingGroup, SettingTitle} from '.' const ShortcutSettings: FC = () => { const { t } = useTranslation() const { theme } = useTheme() const dispatch = useAppDispatch() + const { + setSendMessageShortcut, + } = useSettings() const { shortcuts: originalShortcuts } = useShortcuts() const inputRefs = useRef>({}) const [editingKey, setEditingKey] = useState(null) @@ -304,7 +310,44 @@ const ShortcutSettings: FC = () => { return } + dispatch(updateShortcut({...record, shortcut: keys})) + setEditingKey(null) + } + + const handleKeyChange = (value: string, record: Shortcut) => { + const parts = value.split('+').map(part => part.trim()) + const keys: string[] = [] + // Convert the string parts to the internal key format + for (const part of parts) { + switch (part) { + case 'Command': + case 'Cmd': + keys.push('CommandOrControl') + break + case 'Ctrl': + case 'Control': + keys.push(isMac ? 'Ctrl' : 'CommandOrControl') + break + case 'Alt': + keys.push('Alt') + break + case 'Shift': + keys.push('Shift') + break + case 'Meta': + case 'Win': + case 'Super': + keys.push('Meta') + break + default: + keys.push(part) + } + } + if (isDuplicateShortcut(keys, record.key)) { + return + } dispatch(updateShortcut({ ...record, shortcut: keys })) + setSendMessageShortcut(value as SendMessageShortcut) setEditingKey(null) } @@ -332,11 +375,24 @@ const ShortcutSettings: FC = () => { const isEditing = editingKey === record.key const shortcutConfig = shortcuts.find((s) => s.key === record.key) const isEditable = shortcutConfig?.editable !== false + const isSelector = !!shortcutConfig?.isSelector return ( - {isEditing ? ( + {isEditing ? isSelector ? ( + handleKeyChange(value, record)} + options={[ + {value: 'Enter', label: formatShortcut(['Enter'])}, + {value: 'Ctrl+Enter', label: formatShortcut(['Ctrl','Enter'])}, + {value: 'Alt+Enter', label: formatShortcut(['Alt','Enter'])}, + {value: 'Command+Enter', label: formatShortcut(['Command','Enter'])}, + {value: 'Shift+Enter', label: formatShortcut(['Shift','Enter'])} + ]} + /> + ) : ( { if (el) { diff --git a/src/renderer/src/store/shortcuts.ts b/src/renderer/src/store/shortcuts.ts index 9b4cc1341a..28ba64c220 100644 --- a/src/renderer/src/store/shortcuts.ts +++ b/src/renderer/src/store/shortcuts.ts @@ -124,6 +124,14 @@ const initialState: ShortcutsState = { editable: false, enabled: true, system: true + }, + { + key: 'send_shortcuts', + shortcut: ['Enter'], + editable: true, + enabled: true, + system: true, + isSelector: true } ] } diff --git a/src/renderer/src/types/index.ts b/src/renderer/src/types/index.ts index 9ac3199f35..52be7e217d 100644 --- a/src/renderer/src/types/index.ts +++ b/src/renderer/src/types/index.ts @@ -503,6 +503,7 @@ export interface Shortcut { editable: boolean enabled: boolean system: boolean + isSelector?: boolean } export type ProcessingStatus = 'pending' | 'processing' | 'completed' | 'failed'