diff --git a/VoiceInk/Services/CustomVocabularyService.swift b/VoiceInk/Services/CustomVocabularyService.swift index 8181727..fc6706d 100644 --- a/VoiceInk/Services/CustomVocabularyService.swift +++ b/VoiceInk/Services/CustomVocabularyService.swift @@ -24,7 +24,7 @@ class CustomVocabularyService { } do { - let items = try JSONDecoder().decode([DictionaryItem].self, from: data) + let items = try JSONDecoder().decode([VocabularyWord].self, from: data) let words = items.map { $0.word } return words.isEmpty ? nil : words } catch { diff --git a/VoiceInk/Services/DictionaryImportExportService.swift b/VoiceInk/Services/DictionaryImportExportService.swift index 2831268..aaa9ee6 100644 --- a/VoiceInk/Services/DictionaryImportExportService.swift +++ b/VoiceInk/Services/DictionaryImportExportService.swift @@ -4,7 +4,7 @@ import UniformTypeIdentifiers struct DictionaryExportData: Codable { let version: String - let dictionaryItems: [String] + let vocabularyWords: [String] let wordReplacements: [String: String] let exportDate: Date } @@ -19,7 +19,7 @@ class DictionaryImportExportService { func exportDictionary() { var dictionaryWords: [String] = [] if let data = UserDefaults.standard.data(forKey: dictionaryItemsKey), - let items = try? JSONDecoder().decode([DictionaryItem].self, from: data) { + let items = try? JSONDecoder().decode([VocabularyWord].self, from: data) { dictionaryWords = items.map { $0.word } } @@ -29,7 +29,7 @@ class DictionaryImportExportService { let exportData = DictionaryExportData( version: version, - dictionaryItems: dictionaryWords, + vocabularyWords: dictionaryWords, wordReplacements: wordReplacements, exportDate: Date() ) @@ -45,7 +45,7 @@ class DictionaryImportExportService { savePanel.allowedContentTypes = [UTType.json] savePanel.nameFieldStringValue = "VoiceInk_Dictionary.json" savePanel.title = "Export Dictionary Data" - savePanel.message = "Choose a location to save your dictionary items and word replacements." + savePanel.message = "Choose a location to save your vocabulary and word replacements." DispatchQueue.main.async { if savePanel.runModal() == .OK { @@ -88,9 +88,9 @@ class DictionaryImportExportService { decoder.dateDecodingStrategy = .iso8601 let importedData = try decoder.decode(DictionaryExportData.self, from: jsonData) - var existingItems: [DictionaryItem] = [] + var existingItems: [VocabularyWord] = [] if let data = UserDefaults.standard.data(forKey: self.dictionaryItemsKey), - let items = try? JSONDecoder().decode([DictionaryItem].self, from: data) { + let items = try? JSONDecoder().decode([VocabularyWord].self, from: data) { existingItems = items } @@ -98,9 +98,9 @@ class DictionaryImportExportService { let originalExistingCount = existingItems.count var newWordsAdded = 0 - for importedWord in importedData.dictionaryItems { + for importedWord in importedData.vocabularyWords { if !existingWordsLower.contains(importedWord.lowercased()) { - existingItems.append(DictionaryItem(word: importedWord)) + existingItems.append(VocabularyWord(word: importedWord)) newWordsAdded += 1 } } @@ -147,7 +147,7 @@ class DictionaryImportExportService { UserDefaults.standard.set(existingReplacements, forKey: self.wordReplacementsKey) var message = "Dictionary data imported successfully from \(url.lastPathComponent).\n\n" - message += "Dictionary Items: \(newWordsAdded) added, \(originalExistingCount) kept\n" + message += "Vocabulary Words: \(newWordsAdded) added, \(originalExistingCount) kept\n" message += "Word Replacements: \(addedCount) added, \(updatedCount) updated" self.showAlert(title: "Import Successful", message: message) diff --git a/VoiceInk/Services/ImportExportService.swift b/VoiceInk/Services/ImportExportService.swift index 81c4335..847afb5 100644 --- a/VoiceInk/Services/ImportExportService.swift +++ b/VoiceInk/Services/ImportExportService.swift @@ -32,7 +32,7 @@ struct VoiceInkExportedSettings: Codable { let version: String let customPrompts: [CustomPrompt] let powerModeConfigs: [PowerModeConfig] - let dictionaryItems: [DictionaryItem]? + let vocabularyWords: [VocabularyWord]? let wordReplacements: [String: String]? let generalSettings: GeneralSettings? let customEmojis: [String]? @@ -78,9 +78,9 @@ class ImportExportService { // Export custom models let customModels = CustomModelManager.shared.customModels - var exportedDictionaryItems: [DictionaryItem]? = nil + var exportedDictionaryItems: [VocabularyWord]? = nil if let data = UserDefaults.standard.data(forKey: dictionaryItemsKey), - let items = try? JSONDecoder().decode([DictionaryItem].self, from: data) { + let items = try? JSONDecoder().decode([VocabularyWord].self, from: data) { exportedDictionaryItems = items } @@ -114,7 +114,7 @@ class ImportExportService { version: currentSettingsVersion, customPrompts: exportablePrompts, powerModeConfigs: powerConfigs, - dictionaryItems: exportedDictionaryItems, + vocabularyWords: exportedDictionaryItems, wordReplacements: exportedWordReplacements, generalSettings: generalSettingsToExport, customEmojis: emojiManager.customEmojis, @@ -203,12 +203,12 @@ class ImportExportService { } } - if let itemsToImport = importedSettings.dictionaryItems { + if let itemsToImport = importedSettings.vocabularyWords { if let encoded = try? JSONEncoder().encode(itemsToImport) { UserDefaults.standard.set(encoded, forKey: "CustomVocabularyItems") } } else { - print("No custom vocabulary items (for spelling) found in the imported file. Existing items remain unchanged.") + print("No vocabulary words found in the imported file. Existing items remain unchanged.") } if let replacementsToImport = importedSettings.wordReplacements { diff --git a/VoiceInk/Views/Dictionary/DictionarySettingsView.swift b/VoiceInk/Views/Dictionary/DictionarySettingsView.swift index 7fa9b8f..d7fb14c 100644 --- a/VoiceInk/Views/Dictionary/DictionarySettingsView.swift +++ b/VoiceInk/Views/Dictionary/DictionarySettingsView.swift @@ -6,7 +6,7 @@ struct DictionarySettingsView: View { enum DictionarySection: String, CaseIterable { case replacements = "Word Replacements" - case spellings = "Correct Spellings" + case spellings = "Vocabulary" var description: String { switch self { @@ -90,7 +90,7 @@ struct DictionarySettingsView: View { .foregroundColor(.blue) } .buttonStyle(.plain) - .help("Import dictionary items and word replacements") + .help("Import vocabulary and word replacements") Button(action: { DictionaryImportExportService.shared.exportDictionary() @@ -100,7 +100,7 @@ struct DictionarySettingsView: View { .foregroundColor(.blue) } .buttonStyle(.plain) - .help("Export dictionary items and word replacements") + .help("Export vocabulary and word replacements") } } @@ -120,7 +120,7 @@ struct DictionarySettingsView: View { VStack(alignment: .leading, spacing: 20) { switch selectedSection { case .spellings: - DictionaryView(whisperPrompt: whisperPrompt) + VocabularyView(whisperPrompt: whisperPrompt) .background(CardBackground(isSelected: false)) case .replacements: WordReplacementView() diff --git a/VoiceInk/Views/Dictionary/DictionaryView.swift b/VoiceInk/Views/Dictionary/VocabularyView.swift similarity index 81% rename from VoiceInk/Views/Dictionary/DictionaryView.swift rename to VoiceInk/Views/Dictionary/VocabularyView.swift index 9bd67dc..9ebdb42 100644 --- a/VoiceInk/Views/Dictionary/DictionaryView.swift +++ b/VoiceInk/Views/Dictionary/VocabularyView.swift @@ -1,6 +1,6 @@ import SwiftUI -struct DictionaryItem: Identifiable, Hashable, Codable { +struct VocabularyWord: Identifiable, Hashable, Codable { var word: String var id: String { word } @@ -27,13 +27,13 @@ struct DictionaryItem: Identifiable, Hashable, Codable { } } -enum DictionarySortMode: String { +enum VocabularySortMode: String { case wordAsc = "wordAsc" case wordDesc = "wordDesc" } -class DictionaryManager: ObservableObject { - @Published var items: [DictionaryItem] = [] +class VocabularyManager: ObservableObject { + @Published var items: [VocabularyWord] = [] private let saveKey = "CustomVocabularyItems" private let whisperPrompt: WhisperPrompt @@ -45,7 +45,7 @@ class DictionaryManager: ObservableObject { private func loadItems() { guard let data = UserDefaults.standard.data(forKey: saveKey) else { return } - if let savedItems = try? JSONDecoder().decode([DictionaryItem].self, from: data) { + if let savedItems = try? JSONDecoder().decode([VocabularyWord].self, from: data) { items = savedItems } } @@ -62,7 +62,7 @@ class DictionaryManager: ObservableObject { return } - let newItem = DictionaryItem(word: normalizedWord) + let newItem = VocabularyWord(word: normalizedWord) items.insert(newItem, at: 0) saveItems() } @@ -77,36 +77,36 @@ class DictionaryManager: ObservableObject { } } -struct DictionaryView: View { - @StateObject private var dictionaryManager: DictionaryManager +struct VocabularyView: View { + @StateObject private var vocabularyManager: VocabularyManager @ObservedObject var whisperPrompt: WhisperPrompt @State private var newWord = "" @State private var showAlert = false @State private var alertMessage = "" - @State private var sortMode: DictionarySortMode = .wordAsc + @State private var sortMode: VocabularySortMode = .wordAsc init(whisperPrompt: WhisperPrompt) { self.whisperPrompt = whisperPrompt - _dictionaryManager = StateObject(wrappedValue: DictionaryManager(whisperPrompt: whisperPrompt)) + _vocabularyManager = StateObject(wrappedValue: VocabularyManager(whisperPrompt: whisperPrompt)) - if let savedSort = UserDefaults.standard.string(forKey: "dictionarySortMode"), - let mode = DictionarySortMode(rawValue: savedSort) { + if let savedSort = UserDefaults.standard.string(forKey: "vocabularySortMode"), + let mode = VocabularySortMode(rawValue: savedSort) { _sortMode = State(initialValue: mode) } } - private var sortedItems: [DictionaryItem] { + private var sortedItems: [VocabularyWord] { switch sortMode { case .wordAsc: - return dictionaryManager.items.sorted { $0.word.localizedCaseInsensitiveCompare($1.word) == .orderedAscending } + return vocabularyManager.items.sorted { $0.word.localizedCaseInsensitiveCompare($1.word) == .orderedAscending } case .wordDesc: - return dictionaryManager.items.sorted { $0.word.localizedCaseInsensitiveCompare($1.word) == .orderedDescending } + return vocabularyManager.items.sorted { $0.word.localizedCaseInsensitiveCompare($1.word) == .orderedDescending } } } private func toggleSort() { sortMode = (sortMode == .wordAsc) ? .wordDesc : .wordAsc - UserDefaults.standard.set(sortMode.rawValue, forKey: "dictionarySortMode") + UserDefaults.standard.set(sortMode.rawValue, forKey: "vocabularySortMode") } var body: some View { @@ -124,7 +124,7 @@ struct DictionaryView: View { } HStack(spacing: 8) { - TextField("Add word to dictionary", text: $newWord) + TextField("Add word to vocabulary", text: $newWord) .textFieldStyle(.roundedBorder) .font(.system(size: 13)) .onSubmit { addWords() } @@ -140,11 +140,11 @@ struct DictionaryView: View { .help("Add word") } - if !dictionaryManager.items.isEmpty { + if !vocabularyManager.items.isEmpty { VStack(alignment: .leading, spacing: 12) { Button(action: toggleSort) { HStack(spacing: 4) { - Text("Dictionary Items (\(dictionaryManager.items.count))") + Text("Vocabulary Words (\(vocabularyManager.items.count))") .font(.system(size: 12, weight: .medium)) .foregroundColor(.secondary) @@ -159,8 +159,8 @@ struct DictionaryView: View { ScrollView { LazyVGrid(columns: [GridItem(.adaptive(minimum: 240, maximum: .infinity), spacing: 12)], alignment: .leading, spacing: 12) { ForEach(sortedItems) { item in - DictionaryItemView(item: item) { - dictionaryManager.removeWord(item.word) + VocabularyWordView(item: item) { + vocabularyManager.removeWord(item.word) } } } @@ -172,7 +172,7 @@ struct DictionaryView: View { } } .padding() - .alert("Dictionary", isPresented: $showAlert) { + .alert("Vocabulary", isPresented: $showAlert) { Button("OK", role: .cancel) {} } message: { Text(alertMessage) @@ -191,28 +191,28 @@ struct DictionaryView: View { guard !parts.isEmpty else { return } if parts.count == 1, let word = parts.first { - if dictionaryManager.items.contains(where: { $0.word.lowercased() == word.lowercased() }) { - alertMessage = "'\(word)' is already in the dictionary" + if vocabularyManager.items.contains(where: { $0.word.lowercased() == word.lowercased() }) { + alertMessage = "'\(word)' is already in the vocabulary" showAlert = true return } - dictionaryManager.addWord(word) + vocabularyManager.addWord(word) newWord = "" return } for word in parts { let lower = word.lowercased() - if !dictionaryManager.items.contains(where: { $0.word.lowercased() == lower }) { - dictionaryManager.addWord(word) + if !vocabularyManager.items.contains(where: { $0.word.lowercased() == lower }) { + vocabularyManager.addWord(word) } } newWord = "" } } -struct DictionaryItemView: View { - let item: DictionaryItem +struct VocabularyWordView: View { + let item: VocabularyWord let onDelete: () -> Void @State private var isHovered = false