Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
52 changes: 51 additions & 1 deletion src/components/appearance-provider.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import {
ZOOM_LEVELS,
DEFAULT_ZOOM_LEVEL,
type ZoomLevel,
stepZoom,
} from "@/lib/theme-presets"
import {
resolveFontStack,
Expand Down Expand Up @@ -65,7 +66,11 @@ import {
type CustomThemeToken,
} from "@/lib/custom-style"
import { useShortcutSettings } from "@/hooks/use-shortcut-settings"
import { matchShortcutEvent } from "@/lib/keyboard-shortcuts"
import {
isShortcutRecorderArmed,
matchShortcutEvent,
resolveWindowZoomAction,
} from "@/lib/keyboard-shortcuts"
import {
DEFAULT_WORKSPACE_BG_ENABLED,
DEFAULT_WORKSPACE_BG_MASK_OPACITY,
Expand Down Expand Up @@ -472,6 +477,10 @@ export function AppearanceProvider({
syncTrafficLightPosition(zoom)
persist(STORAGE_KEY_ZOOM_LEVEL, String(zoom))
}, [])
const zoomLevelRef = useRef(zoomLevel)
useEffect(() => {
zoomLevelRef.current = zoomLevel
}, [zoomLevel])

const setShowWelcomeQuickActions = useCallback((on: boolean) => {
setShowWelcomeQuickActionsState(on)
Expand Down Expand Up @@ -744,6 +753,9 @@ export function AppearanceProvider({
// 或某个组件吞掉了冒泡,这一路依然能把自定义样式整体停用。
const { shortcuts } = useShortcutSettings()
const toggleCustomStyleShortcut = shortcuts.toggle_custom_style
const zoomInShortcut = shortcuts.zoom_in
const zoomOutShortcut = shortcuts.zoom_out
const zoomResetShortcut = shortcuts.zoom_reset
useEffect(() => {
if (!toggleCustomStyleShortcut) return
const onKeyDown = (event: KeyboardEvent) => {
Expand All @@ -756,6 +768,44 @@ export function AppearanceProvider({
return () => window.removeEventListener("keydown", onKeyDown, true)
}, [toggleCustomStyleShortcut, customStyleSuspended, setCustomStyleSuspended])

// Same levels as Settings → Window zoom. Capture-phase so the webview
// does not eat Ctrl/Cmd +/- as its own page zoom.
useEffect(() => {
const onKeyDown = (event: KeyboardEvent) => {
if (event.isComposing) return
if (isShortcutRecorderArmed()) return
if (
event.target instanceof Element &&
event.target.closest('[data-terminal-panel-region="true"]')
) {
return
}

const action = resolveWindowZoomAction(event, {
zoom_in: zoomInShortcut,
zoom_out: zoomOutShortcut,
zoom_reset: zoomResetShortcut,
})
if (!action) return

// Match first, then preventDefault, including on repeats. A held
// key should walk the zoom levels, and in the browser the un-
// prevented repeat would also trigger the page's own zoom.
event.preventDefault()
if (action === "in") {
setZoomLevel(stepZoom(zoomLevelRef.current, 1))
return
}
if (action === "out") {
setZoomLevel(stepZoom(zoomLevelRef.current, -1))
return
}
setZoomLevel(DEFAULT_ZOOM_LEVEL)
}
window.addEventListener("keydown", onKeyDown, true)
return () => window.removeEventListener("keydown", onKeyDown, true)
}, [setZoomLevel, zoomInShortcut, zoomOutShortcut, zoomResetShortcut])

// 跨标签页同步:用户在另一个窗口改了设置时,本窗口实时跟进
useEffect(() => {
const FONT_KEYS = new Set<string>([
Expand Down
7 changes: 7 additions & 0 deletions src/components/settings/shortcut-settings.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import {
SHORTCUT_DEFINITIONS,
type ShortcutActionId,
formatShortcutLabel,
setShortcutRecorderArmed,
shortcutFromKeyboardEvent,
} from "@/lib/keyboard-shortcuts"
import { Button } from "@/components/ui/button"
Expand Down Expand Up @@ -53,13 +54,19 @@ export function ShortcutSettings() {
[shortcuts]
)

useEffect(() => {
setShortcutRecorderArmed(Boolean(recordingAction))
return () => setShortcutRecorderArmed(false)
}, [recordingAction])

useEffect(() => {
if (!recordingAction) return

const onKeyDown = (event: KeyboardEvent) => {
if (event.repeat) return
event.preventDefault()
event.stopPropagation()
event.stopImmediatePropagation()

if (event.key === "Escape") {
setRecordingAction(null)
Expand Down
14 changes: 13 additions & 1 deletion src/i18n/messages/ar.json
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@
},
"zoomLevel": {
"sectionTitle": "تكبير النافذة",
"sectionDescription": "تكبير أو تصغير الواجهة بالكامل. يتم تطبيقه فوراً ويُحفظ لكل جهاز على حدة.",
"sectionDescription": "تكبير أو تصغير الواجهة بالكامل. يتم تطبيقه فوراً ويُحفظ لكل جهاز على حدة. ⌘/Ctrl + و - ينتقلان بين نفس مستويات التكبير في هذه القائمة (⌘/Ctrl 0 يعيد الضبط إلى 100%).",
"placeholder": "اختر مستوى التكبير",
"default": "افتراضي",
"current": "التكبير الحالي: {zoom}%"
Expand Down Expand Up @@ -415,6 +415,18 @@
"toggle_custom_style": {
"title": "إيقاف/استئناف النمط المخصص",
"description": "مخرج طوارئ: يوقف كل الألوان المخصصة وCSS، ويعيد تفعيلها"
},
"zoom_in": {
"title": "تكبير",
"description": "اجعل النافذة أكبر بدرجة واحدة"
},
"zoom_out": {
"title": "تصغير",
"description": "اجعل النافذة أصغر بدرجة واحدة"
},
"zoom_reset": {
"title": "إعادة ضبط التكبير",
"description": "أعد تكبير النافذة إلى 100%"
}
}
},
Expand Down
14 changes: 13 additions & 1 deletion src/i18n/messages/de.json
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@
},
"zoomLevel": {
"sectionTitle": "Fensterzoom",
"sectionDescription": "Skaliert die gesamte Oberfläche. Wird sofort übernommen und pro Gerät gespeichert.",
"sectionDescription": "Skaliert die gesamte Oberfläche. Wird sofort übernommen und pro Gerät gespeichert. ⌘/Ctrl + und - durchlaufen dieselben Zoomstufen wie dieses Menü (⌘/Ctrl 0 setzt auf 100% zurück).",
"placeholder": "Zoomstufe wählen",
"default": "Standard",
"current": "Aktueller Zoom: {zoom}%"
Expand Down Expand Up @@ -415,6 +415,18 @@
"toggle_custom_style": {
"title": "Eigenen Stil aussetzen/fortsetzen",
"description": "Notausstieg: schaltet alle eigenen Farben und CSS aus und wieder ein"
},
"zoom_in": {
"title": "Vergrößern",
"description": "Das Fenster eine Stufe größer machen"
},
"zoom_out": {
"title": "Verkleinern",
"description": "Das Fenster eine Stufe kleiner machen"
},
"zoom_reset": {
"title": "Zoom zurücksetzen",
"description": "Fensterzoom auf 100% zurücksetzen"
}
}
},
Expand Down
14 changes: 13 additions & 1 deletion src/i18n/messages/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@
},
"zoomLevel": {
"sectionTitle": "Window zoom",
"sectionDescription": "Scale the entire interface. Applies immediately and persists per device.",
"sectionDescription": "Scale the entire interface. Applies immediately and persists per device. ⌘/Ctrl + and - move through the same zoom levels as this menu (⌘/Ctrl 0 resets to 100%).",
"placeholder": "Select zoom level",
"default": "Default",
"current": "Current zoom: {zoom}%"
Expand Down Expand Up @@ -415,6 +415,18 @@
"toggle_custom_style": {
"title": "Suspend/resume custom style",
"description": "Escape hatch: turns all custom colors and CSS off, and back on"
},
"zoom_in": {
"title": "Zoom in",
"description": "Make the window one step larger"
},
"zoom_out": {
"title": "Zoom out",
"description": "Make the window one step smaller"
},
"zoom_reset": {
"title": "Reset zoom",
"description": "Set the window zoom back to 100%"
}
}
},
Expand Down
14 changes: 13 additions & 1 deletion src/i18n/messages/es.json
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@
},
"zoomLevel": {
"sectionTitle": "Zoom de ventana",
"sectionDescription": "Escala toda la interfaz. Se aplica al instante y se guarda por dispositivo.",
"sectionDescription": "Escala toda la interfaz. Se aplica al instante y se guarda por dispositivo. ⌘/Ctrl + y - recorren los mismos niveles de zoom que este menú (⌘/Ctrl 0 vuelve al 100%).",
"placeholder": "Selecciona el nivel de zoom",
"default": "Predeterminado",
"current": "Zoom actual: {zoom}%"
Expand Down Expand Up @@ -415,6 +415,18 @@
"toggle_custom_style": {
"title": "Suspender/reanudar estilo personalizado",
"description": "Vía de escape: desactiva todos los colores y el CSS personalizados, y los vuelve a activar"
},
"zoom_in": {
"title": "Acercar",
"description": "Amplía la ventana un nivel"
},
"zoom_out": {
"title": "Alejar",
"description": "Reduce la ventana un nivel"
},
"zoom_reset": {
"title": "Restablecer zoom",
"description": "Restaura el zoom de la ventana al 100%"
}
}
},
Expand Down
14 changes: 13 additions & 1 deletion src/i18n/messages/fr.json
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@
},
"zoomLevel": {
"sectionTitle": "Zoom de la fenêtre",
"sectionDescription": "Met à l'échelle toute l'interface. S'applique immédiatement et est enregistré par appareil.",
"sectionDescription": "Met à l'échelle toute l'interface. S'applique immédiatement et est enregistré par appareil. ⌘/Ctrl + et - parcourent les mêmes niveaux de zoom que ce menu (⌘/Ctrl 0 rétablit 100%).",
"placeholder": "Sélectionnez le niveau de zoom",
"default": "Par défaut",
"current": "Zoom actuel : {zoom}%"
Expand Down Expand Up @@ -415,6 +415,18 @@
"toggle_custom_style": {
"title": "Suspendre/réactiver le style personnalisé",
"description": "Issue de secours : désactive toutes les couleurs et le CSS personnalisés, puis les réactive"
},
"zoom_in": {
"title": "Zoom avant",
"description": "Agrandit la fenêtre d'un cran"
},
"zoom_out": {
"title": "Zoom arrière",
"description": "Réduit la fenêtre d'un cran"
},
"zoom_reset": {
"title": "Réinitialiser le zoom",
"description": "Remet le zoom de la fenêtre à 100%"
}
}
},
Expand Down
14 changes: 13 additions & 1 deletion src/i18n/messages/ja.json
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@
},
"zoomLevel": {
"sectionTitle": "ウィンドウズーム",
"sectionDescription": "インターフェイス全体を拡大・縮小します。すぐに反映され、デバイスごとに保存されます。",
"sectionDescription": "インターフェイス全体を拡大・縮小します。すぐに反映され、デバイスごとに保存されます。⌘/Ctrl + と - で、このメニューと同じ段階で拡大縮小します(⌘/Ctrl 0 で 100% に戻します)。",
"placeholder": "ズームレベルを選択",
"default": "デフォルト",
"current": "現在のズーム:{zoom}%"
Expand Down Expand Up @@ -415,6 +415,18 @@
"toggle_custom_style": {
"title": "カスタムスタイルの停止/再開",
"description": "緊急脱出用: カスタム配色と CSS をすべてオフにし、再度押すと元に戻します"
},
"zoom_in": {
"title": "拡大",
"description": "ウィンドウの表示倍率を一段階上げます"
},
"zoom_out": {
"title": "縮小",
"description": "ウィンドウの表示倍率を一段階下げます"
},
"zoom_reset": {
"title": "ズームをリセット",
"description": "ウィンドウのズームを 100% に戻します"
}
}
},
Expand Down
14 changes: 13 additions & 1 deletion src/i18n/messages/ko.json
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@
},
"zoomLevel": {
"sectionTitle": "창 확대/축소",
"sectionDescription": "전체 인터페이스를 확대하거나 축소합니다. 즉시 적용되며 장치별로 저장됩니다.",
"sectionDescription": "전체 인터페이스를 확대하거나 축소합니다. 즉시 적용되며 장치별로 저장됩니다. ⌘/Ctrl +와 -는 이 메뉴와 같은 단계로 확대/축소합니다(⌘/Ctrl 0은 100%로 되돌립니다).",
"placeholder": "확대/축소 단계 선택",
"default": "기본값",
"current": "현재 확대/축소: {zoom}%"
Expand Down Expand Up @@ -415,6 +415,18 @@
"toggle_custom_style": {
"title": "사용자 지정 스타일 중지/재개",
"description": "비상 탈출구: 모든 사용자 지정 색상과 CSS를 끄고, 다시 누르면 되돌립니다"
},
"zoom_in": {
"title": "확대",
"description": "창을 한 단계 더 크게 만듭니다"
},
"zoom_out": {
"title": "축소",
"description": "창을 한 단계 더 작게 만듭니다"
},
"zoom_reset": {
"title": "확대/축소 초기화",
"description": "창 확대/축소를 100%로 되돌립니다"
}
}
},
Expand Down
14 changes: 13 additions & 1 deletion src/i18n/messages/pt.json
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@
},
"zoomLevel": {
"sectionTitle": "Zoom da janela",
"sectionDescription": "Dimensiona toda a interface. Aplica imediatamente e é salvo por dispositivo.",
"sectionDescription": "Dimensiona toda a interface. Aplica imediatamente e é salvo por dispositivo. ⌘/Ctrl + e - percorrem os mesmos níveis de zoom deste menu (⌘/Ctrl 0 volta para 100%).",
"placeholder": "Selecione o nível de zoom",
"default": "Padrão",
"current": "Zoom atual: {zoom}%"
Expand Down Expand Up @@ -415,6 +415,18 @@
"toggle_custom_style": {
"title": "Suspender/retomar estilo personalizado",
"description": "Saída de emergência: desliga todas as cores e o CSS personalizados e volta a ligá-los"
},
"zoom_in": {
"title": "Aumentar zoom",
"description": "Aumenta a janela em um nível"
},
"zoom_out": {
"title": "Diminuir zoom",
"description": "Diminui a janela em um nível"
},
"zoom_reset": {
"title": "Redefinir zoom",
"description": "Restaura o zoom da janela para 100%"
}
}
},
Expand Down
14 changes: 13 additions & 1 deletion src/i18n/messages/zh-CN.json
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@
},
"zoomLevel": {
"sectionTitle": "窗口缩放",
"sectionDescription": "整体放大或缩小界面,立即生效,按设备分别保存。",
"sectionDescription": "整体放大或缩小界面,立即生效,按设备分别保存。⌘/Ctrl + 和 - 按与此菜单相同的档位调节(⌘/Ctrl 0 恢复为 100%)。",
"placeholder": "请选择缩放档位",
"default": "默认",
"current": "当前缩放:{zoom}%"
Expand Down Expand Up @@ -415,6 +415,18 @@
"toggle_custom_style": {
"title": "停用/恢复自定义样式",
"description": "逃生舱:一键关闭全部自定义配色与 CSS,再按一次恢复"
},
"zoom_in": {
"title": "放大",
"description": "把窗口缩放提高一档"
},
"zoom_out": {
"title": "缩小",
"description": "把窗口缩放降低一档"
},
"zoom_reset": {
"title": "重置缩放",
"description": "把窗口缩放恢复为 100%"
}
}
},
Expand Down
14 changes: 13 additions & 1 deletion src/i18n/messages/zh-TW.json
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@
},
"zoomLevel": {
"sectionTitle": "視窗縮放",
"sectionDescription": "整體放大或縮小介面,立即生效,依裝置分別儲存。",
"sectionDescription": "整體放大或縮小介面,立即生效,依裝置分別儲存。⌘/Ctrl + 和 - 依與此選單相同的檔位調節(⌘/Ctrl 0 恢復為 100%)。",
"placeholder": "請選擇縮放檔位",
"default": "預設",
"current": "目前縮放:{zoom}%"
Expand Down Expand Up @@ -415,6 +415,18 @@
"toggle_custom_style": {
"title": "停用/恢復自訂樣式",
"description": "逃生艙:一鍵關閉全部自訂配色與 CSS,再按一次恢復"
},
"zoom_in": {
"title": "放大",
"description": "把視窗縮放提高一檔"
},
"zoom_out": {
"title": "縮小",
"description": "把視窗縮放降低一檔"
},
"zoom_reset": {
"title": "重設縮放",
"description": "把視窗縮放恢復為 100%"
}
}
},
Expand Down
Loading
Loading