Improve resizing with draggable and hotkeys

This commit is contained in:
2026-03-12 23:57:31 +11:00
parent 9d05bc586a
commit 256998eb9f
9 changed files with 517 additions and 50 deletions

View File

@@ -1,4 +1,5 @@
import SwiftUI
import AppKit
/// Tabbed settings panel with General, Appearance, Animation, Terminal, Hotkeys, and About.
struct SettingsView: View {
@@ -85,6 +86,14 @@ struct GeneralSettingsView: View {
@AppStorage(NotchSettings.Keys.openWidth) private var openWidth = NotchSettings.Defaults.openWidth
@AppStorage(NotchSettings.Keys.openHeight) private var openHeight = NotchSettings.Defaults.openHeight
private var maxOpenWidth: Double {
max(openWidth, Double((NSScreen.screens.map { $0.frame.width - 40 }.max() ?? 1600).rounded()))
}
private var maxOpenHeight: Double {
max(openHeight, Double((NSScreen.screens.map { $0.frame.height - 20 }.max() ?? 900).rounded()))
}
var body: some View {
Form {
Section("Display") {
@@ -146,12 +155,12 @@ struct GeneralSettingsView: View {
Section("Open Notch Size") {
HStack {
Text("Width")
Slider(value: $openWidth, in: 300...1200, step: 10)
Slider(value: $openWidth, in: 320...maxOpenWidth, step: 10)
Text("\(Int(openWidth))pt").monospacedDigit().frame(width: 60)
}
HStack {
Text("Height")
Slider(value: $openHeight, in: 100...600, step: 10)
Slider(value: $openHeight, in: 140...maxOpenHeight, step: 10)
Text("\(Int(openHeight))pt").monospacedDigit().frame(width: 60)
}
}
@@ -266,6 +275,10 @@ struct TerminalSettingsView: View {
@AppStorage(NotchSettings.Keys.terminalFontSize) private var fontSize = NotchSettings.Defaults.terminalFontSize
@AppStorage(NotchSettings.Keys.terminalShell) private var shellPath = NotchSettings.Defaults.terminalShell
@AppStorage(NotchSettings.Keys.terminalTheme) private var theme = NotchSettings.Defaults.terminalTheme
@AppStorage(NotchSettings.Keys.openWidth) private var openWidth = NotchSettings.Defaults.openWidth
@AppStorage(NotchSettings.Keys.openHeight) private var openHeight = NotchSettings.Defaults.openHeight
@State private var sizePresets = TerminalSizePresetStore.load()
var body: some View {
Form {
@@ -298,8 +311,54 @@ struct TerminalSettingsView: View {
.font(.caption)
.foregroundStyle(.secondary)
}
Section("Size Presets") {
ForEach($sizePresets) { $preset in
TerminalSizePresetEditor(
preset: $preset,
currentOpenWidth: openWidth,
currentOpenHeight: openHeight,
onDelete: { deletePreset(id: preset.id) },
onApply: { applyPreset(preset) }
)
}
HStack {
Button("Add Preset") {
sizePresets.append(
TerminalSizePreset(
name: "Preset \(sizePresets.count + 1)",
width: openWidth,
height: openHeight,
hotkey: TerminalSizePresetStore.suggestedHotkey(for: sizePresets)
)
)
}
Button("Reset Presets") {
sizePresets = TerminalSizePresetStore.loadDefaults()
}
}
Text("Size preset hotkeys are active when the notch is open. Default presets use ⌘⇧1, ⌘⇧2, and ⌘⇧3.")
.font(.caption)
.foregroundStyle(.secondary)
}
}
.formStyle(.grouped)
.onChange(of: sizePresets) { _, newValue in
TerminalSizePresetStore.save(newValue)
}
}
private func deletePreset(id: UUID) {
sizePresets.removeAll { $0.id == id }
}
private func applyPreset(_ preset: TerminalSizePreset) {
openWidth = preset.width
openHeight = preset.height
ScreenManager.shared.applySizePreset(preset)
}
}
@@ -329,7 +388,7 @@ struct HotkeySettingsView: View {
}
Section {
Text("⌘19 always switch to tab by number.")
Text("⌘19 always switch to tab by number. Size preset hotkeys are configured in Terminal > Size Presets.")
.font(.caption)
.foregroundStyle(.secondary)
}
@@ -377,6 +436,52 @@ struct HotkeySettingsView: View {
}
}
private struct TerminalSizePresetEditor: View {
@Binding var preset: TerminalSizePreset
let currentOpenWidth: Double
let currentOpenHeight: Double
let onDelete: () -> Void
let onApply: () -> Void
var body: some View {
VStack(alignment: .leading, spacing: 10) {
HStack {
TextField("Preset name", text: $preset.name)
.textFieldStyle(.roundedBorder)
Button(role: .destructive, action: onDelete) {
Image(systemName: "trash")
}
.buttonStyle(.borderless)
}
HStack {
Text("Width")
TextField("Width", value: $preset.width, format: .number.precision(.fractionLength(0)))
.textFieldStyle(.roundedBorder)
.frame(width: 90)
Text("Height")
TextField("Height", value: $preset.height, format: .number.precision(.fractionLength(0)))
.textFieldStyle(.roundedBorder)
.frame(width: 90)
Spacer()
Button("Use Current Size") {
preset.width = currentOpenWidth
preset.height = currentOpenHeight
}
Button("Apply", action: onApply)
}
OptionalHotkeyRecorderView(label: "Hotkey", binding: $preset.hotkey)
}
.padding(.vertical, 4)
}
}
// MARK: - About
struct AboutSettingsView: View {