Redesign Hope iOS UI, harden playback, and document project handoff
This commit is contained in:
1 parent
40aaf4fea7
commit
24f95639dc
24 files changed
+1470
-594
No files matched your search
@@ -3,19 +3,19 @@ import Combine
|
||||
|
||||
final class SettingsStore: ObservableObject {
|
||||
@Published var serverURL: String {
|
||||
didSet { UserDefaults.standard.set(serverURL, forKey: Keys.serverURL) }
|
||||
didSet { AppPreferences.store.set(serverURL, forKey: Keys.serverURL) }
|
||||
}
|
||||
@Published var voiceID: String {
|
||||
didSet { UserDefaults.standard.set(voiceID, forKey: Keys.voiceID) }
|
||||
didSet { AppPreferences.store.set(voiceID, forKey: Keys.voiceID) }
|
||||
}
|
||||
@Published var modelID: String? {
|
||||
didSet { UserDefaults.standard.set(modelID, forKey: Keys.modelID) }
|
||||
didSet { AppPreferences.store.set(modelID, forKey: Keys.modelID) }
|
||||
}
|
||||
@Published var textMode: Bool {
|
||||
didSet { UserDefaults.standard.set(textMode, forKey: Keys.textMode) }
|
||||
didSet { AppPreferences.store.set(textMode, forKey: Keys.textMode) }
|
||||
}
|
||||
@Published var volume: Double {
|
||||
didSet { UserDefaults.standard.set(volume, forKey: Keys.volume) }
|
||||
didSet { AppPreferences.store.set(volume, forKey: Keys.volume) }
|
||||
}
|
||||
|
||||
private enum Keys {
|
||||
@@ -29,7 +29,7 @@ final class SettingsStore: ObservableObject {
|
||||
static let defaultServerURL = "https://192.168.86.2:9178"
|
||||
|
||||
init() {
|
||||
let d = UserDefaults.standard
|
||||
let d = AppPreferences.store
|
||||
// Sanitize legacy values: earlier versions wrote the field to storage on
|
||||
// every keystroke, so an invalid half-typed URL could be persisted and
|
||||
// shipped to the network layer. Fall back to the documented default and
|
||||
@@ -54,3 +54,26 @@ final class SettingsStore: ObservableObject {
|
||||
serverURL.trimmingCharacters(in: .whitespacesAndNewlines)
|
||||
}
|
||||
}
|
||||
|
||||
enum AppPreferences {
|
||||
static let store: UserDefaults = {
|
||||
#if DEBUG
|
||||
if ProcessInfo.processInfo.arguments.contains("--ui-testing") {
|
||||
let suite = "dev.shane.voice.ui-testing"
|
||||
let defaults = UserDefaults(suiteName: suite)!
|
||||
if ProcessInfo.processInfo.arguments.contains("--reset-ui-testing") {
|
||||
defaults.removePersistentDomain(forName: suite)
|
||||
// Deterministic offline errors; UI tests must not contact the NAS.
|
||||
defaults.set("https://127.0.0.1:1", forKey: "serverURL")
|
||||
}
|
||||
if ProcessInfo.processInfo.arguments.contains("--live-testing") {
|
||||
defaults.set(SettingsStore.defaultServerURL, forKey: "serverURL")
|
||||
defaults.set(true, forKey: "textMode")
|
||||
defaults.set("qwen2.5-vl-3b", forKey: "modelID")
|
||||
}
|
||||
return defaults
|
||||
}
|
||||
#endif
|
||||
return .standard
|
||||
}()
|
||||
}
|
||||
@@ -12,7 +12,15 @@ struct VoiceApp: App {
|
||||
var body: some Scene {
|
||||
WindowGroup {
|
||||
ConversationView(settings: settings)
|
||||
.preferredColorScheme(.dark)
|
||||
.tint(HopeStyle.tint)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
enum HopeStyle {
|
||||
static let tint = Color(uiColor: UIColor { traits in
|
||||
traits.userInterfaceStyle == .dark
|
||||
? UIColor(red: 0.43, green: 0.68, blue: 1, alpha: 1)
|
||||
: UIColor(red: 0.12, green: 0.32, blue: 0.68, alpha: 1)
|
||||
})
|
||||
}
|
||||
Reference in new issue
Block a user