Skip to content

Commit

Permalink
Fix SwiftUI Text verbatim usage and missing localization (#3450)
Browse files Browse the repository at this point in the history
<!-- Thank you for submitting a Pull Request and helping to improve Home
Assistant. Please complete the following sections to help the processing
and review of your changes. Please do not delete anything from this
template. -->

## Summary
<!-- Provide a brief summary of the changes you have made and most
importantly what they aim to achieve -->

## Screenshots
<!-- If this is a user-facing change not in the frontend, please include
screenshots in light and dark mode. -->

## Link to pull request in Documentation repository
<!-- Pull requests that add, change or remove functionality must have a
corresponding pull request in the Companion App Documentation repository
(https://github.com/home-assistant/companion.home-assistant). Please add
the number of this pull request after the "#" -->
Documentation: home-assistant/companion.home-assistant#

## Any other notes
<!-- If there is any other information of note, like if this Pull
Request is part of a bigger change, please include it here. -->
  • Loading branch information
bgoncal authored Feb 20, 2025
1 parent d90a4f7 commit 638117f
Show file tree
Hide file tree
Showing 34 changed files with 117 additions and 98 deletions.
4 changes: 0 additions & 4 deletions HomeAssistant.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -713,7 +713,6 @@
428338452BA1BB4F004798C2 /* Spaces.swift in Sources */ = {isa = PBXBuildFile; fileRef = 428338422BA1BAFB004798C2 /* Spaces.swift */; };
4285C5512D355F9900DADE45 /* WidgetCreationView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 4285C5502D355F9900DADE45 /* WidgetCreationView.swift */; };
4285C5532D35658000DADE45 /* TileCard.swift in Sources */ = {isa = PBXBuildFile; fileRef = 4285C5522D35658000DADE45 /* TileCard.swift */; };
4285C5552D3568A100DADE45 /* WidgetAddItemView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 4285C5542D3568A100DADE45 /* WidgetAddItemView.swift */; };
428830EB2C6E3A8D0012373D /* WatchHomeView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 428830EA2C6E3A8D0012373D /* WatchHomeView.swift */; };
428830ED2C6E3A9A0012373D /* WatchHomeViewModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 428830EC2C6E3A9A0012373D /* WatchHomeViewModel.swift */; };
4289DDAA2C85AB4C003591C2 /* AssistAppIntent.swift in Sources */ = {isa = PBXBuildFile; fileRef = 425FF0552C8216B3000AA641 /* AssistAppIntent.swift */; };
Expand Down Expand Up @@ -2068,7 +2067,6 @@
428338422BA1BAFB004798C2 /* Spaces.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Spaces.swift; sourceTree = "<group>"; };
4285C5502D355F9900DADE45 /* WidgetCreationView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WidgetCreationView.swift; sourceTree = "<group>"; };
4285C5522D35658000DADE45 /* TileCard.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TileCard.swift; sourceTree = "<group>"; };
4285C5542D3568A100DADE45 /* WidgetAddItemView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WidgetAddItemView.swift; sourceTree = "<group>"; };
428830EA2C6E3A8D0012373D /* WatchHomeView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WatchHomeView.swift; sourceTree = "<group>"; };
428830EC2C6E3A9A0012373D /* WatchHomeViewModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WatchHomeViewModel.swift; sourceTree = "<group>"; };
4289DDAE2C85D5C4003591C2 /* ControlScene.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ControlScene.swift; sourceTree = "<group>"; };
Expand Down Expand Up @@ -4104,7 +4102,6 @@
421B1C172BD6524E001ED18C /* WidgetBuilderViewModel.swift */,
4285C5502D355F9900DADE45 /* WidgetCreationView.swift */,
42B74A652D37C2C000C37304 /* WidgetCreationViewModel.swift */,
4285C5542D3568A100DADE45 /* WidgetAddItemView.swift */,
);
path = Builder;
sourceTree = "<group>";
Expand Down Expand Up @@ -7128,7 +7125,6 @@
1185DF94271FBA6100ED7D9A /* OnboardingAuthDetails.swift in Sources */,
42BE698D2C4691EA00745ECA /* WebViewAccessoryViews.swift in Sources */,
4273C48B2C8858470065A5B4 /* ControlOpenPageValueProvider.swift in Sources */,
4285C5552D3568A100DADE45 /* WidgetAddItemView.swift in Sources */,
420FE84B2B556BB100878E06 /* CarPlayActionsTemplate+Build.swift in Sources */,
42DF6B2F2CCF918D00D7EC14 /* BluetoothPermissionView.swift in Sources */,
425573C72B5572AD00145217 /* CarPlayServerListTemplate+Build.swift in Sources */,
Expand Down
4 changes: 2 additions & 2 deletions Sources/App/Assist/AssistView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -58,9 +58,9 @@ struct AssistView: View {
}
.alert(isPresented: $viewModel.showError) {
.init(
title: Text(L10n.errorLabel),
title: Text(verbatim: L10n.errorLabel),
message: Text(viewModel.errorMessage),
dismissButton: .default(Text(L10n.okLabel))
dismissButton: .default(Text(verbatim: L10n.okLabel))
)
}
}
Expand Down
2 changes: 1 addition & 1 deletion Sources/App/Assist/Views/AssistMicAnimationView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ struct AssistMicAnimationView: View {
VStack(spacing: Spaces.one) {
icon
.foregroundStyle(Color.asset(Asset.Colors.haPrimary))
Text(L10n.Assist.Button.Listening.title)
Text(verbatim: L10n.Assist.Button.Listening.title)
.opacity(0.5)
}
}
Expand Down
4 changes: 2 additions & 2 deletions Sources/App/Improv/ImprovDiscoverView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -128,7 +128,7 @@ struct ImprovDiscoverView<Manager>: View where Manager: ImprovManagerProtocol {
cancelWifiInput()
}
} message: {
Text(L10n.Improv.Wifi.Alert.description)
Text(verbatim: L10n.Improv.Wifi.Alert.description)
}
}

Expand Down Expand Up @@ -196,7 +196,7 @@ struct ImprovDiscoverView<Manager>: View where Manager: ImprovManagerProtocol {
}
}, header: {
HStack(spacing: Spaces.two) {
Text(L10n.Improv.List.title)
Text(verbatim: L10n.Improv.List.title)
.textCase(.uppercase)
.font(.footnote)
.foregroundStyle(Color(uiColor: .secondaryLabel))
Expand Down
2 changes: 1 addition & 1 deletion Sources/App/Improv/Views/ImprovFailureView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ struct ImprovFailureView: View {
Button {
action()
} label: {
Text(L10n.Improv.Button.continue)
Text(verbatim: L10n.Improv.Button.continue)
.padding()
.foregroundColor(Color(uiColor: .secondaryLabel))
}
Expand Down
4 changes: 2 additions & 2 deletions Sources/App/Improv/Views/ImprovSuccessView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ struct ImprovSuccessView: View {
.stroke(.regularMaterial, lineWidth: 5)
)
}
Text(L10n.Improv.State.success)
Text(verbatim: L10n.Improv.State.success)
.font(.title3.bold())
.foregroundStyle(Color(uiColor: .secondaryLabel))
}
Expand All @@ -31,7 +31,7 @@ struct ImprovSuccessView: View {
Button {
action()
} label: {
Text(L10n.Improv.Button.continue)
Text(verbatim: L10n.Improv.Button.continue)
.foregroundStyle(Color(uiColor: .label))
.padding()
}
Expand Down
2 changes: 1 addition & 1 deletion Sources/App/Onboarding/Screens/OnboardingErrorView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ struct OnboardingErrorView: View {

var body: some View {
VStack(spacing: Spaces.two) {
Text(L10n.Onboarding.ConnectionError.title)
Text(verbatim: L10n.Onboarding.ConnectionError.title)
.font(.title.bold())
Image(systemSymbol: .xmarkCircleFill)
.font(.system(size: 60))
Expand Down
6 changes: 3 additions & 3 deletions Sources/App/Onboarding/Screens/OnboardingWelcomeView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -27,11 +27,11 @@ struct OnboardingWelcomeView: View {
private var textBlock: some View {
ScrollView {
VStack(spacing: Spaces.two) {
Text(L10n.Onboarding.Welcome.title(Current.device.systemName()))
Text(verbatim: L10n.Onboarding.Welcome.title(Current.device.systemName()))
.font(.title.bold())
.frame(maxWidth: .infinity, alignment: .center)
.multilineTextAlignment(.center)
Text(L10n.Onboarding.Welcome.description)
Text(verbatim: L10n.Onboarding.Welcome.description)
.foregroundStyle(Color(uiColor: .secondaryLabel))
Button(L10n.Onboarding.Welcome.learnMore) {
showLearnMore = true
Expand All @@ -44,7 +44,7 @@ struct OnboardingWelcomeView: View {

private var continueButton: some View {
NavigationLink(destination: OnboardingScanningView()) {
Text(L10n.continueLabel)
Text(verbatim: L10n.continueLabel)
.font(.callout.bold())
.foregroundColor(.white)
.frame(maxWidth: .infinity)
Expand Down
6 changes: 3 additions & 3 deletions Sources/App/Onboarding/Screens/PermissionRequestView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -44,22 +44,22 @@ struct PermissionRequestView: View {
Button {
continueAction()
} label: {
Text(L10n.continueLabel)
Text(verbatim: L10n.continueLabel)
}
.buttonStyle(.primaryButton)
if showSkipButton {
Button {
dismissAction?()
dismiss()
} label: {
Text(L10n.Permission.Screen.Bluetooth.secondaryButton)
Text(verbatim: L10n.Permission.Screen.Bluetooth.secondaryButton)
}
.buttonStyle(.secondaryButton)
} else {
Button {
/* no-op */
} label: {
Text(L10n.Onboarding.Permissions.changeLaterNote)
Text(verbatim: L10n.Onboarding.Permissions.changeLaterNote)
}
.buttonStyle(.linkButton)
}
Expand Down
4 changes: 4 additions & 0 deletions Sources/App/Resources/en.lproj/Localizable.strings
Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,9 @@
"carplay.navigation.button.next" = "Next";
"carplay.navigation.button.previous" = "Previous";
"carplay.unlock.confirmation.title" = "Are you sure you want to perform unlock action on %@?";
"carPlay.tabs.active.title" = "Active";
"carPlay.tabs.inactive.title" = "Inactive";
"carPlay.tabs.active.delete_action.title" = "Swipe left to remove tab";
"cl_error.description.deferred_accuracy_too_low" = "Deferred mode is not supported for the requested accuracy.";
"cl_error.description.deferred_canceled" = "The request for deferred updates was canceled by your app or by the location manager.";
"cl_error.description.deferred_distance_filtered" = "Deferred mode does not support distance filters.";
Expand Down Expand Up @@ -1170,6 +1173,7 @@ Home Assistant is free and open source home automation software with a focus on
"widgets.sensors.description" = "Display state of sensors";
"widgets.sensors.not_configured" = "No Sensors Configured";
"widgets.sensors.title" = "Sensors";
"connection_error.advanced_section.title" = "Advanced";
"widgets.custom.show_last_update_time.param.title" = "Show last update time";
"widgets.custom.show_states.param.title" = "Show states (BETA)";
"connection_error.open_settings.title" = "Open settings";
Expand Down
2 changes: 1 addition & 1 deletion Sources/App/Settings/AppIcon/AppIconSelectorView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ struct AppIconSelectorView: View {

var body: some View {
List {
Text(L10n.SettingsDetails.General.AppIcon.Explanation.title)
Text(verbatim: L10n.SettingsDetails.General.AppIcon.Explanation.title)
.font(.footnote)
ForEach(AppIcon.allCases, id: \.self) { icon in
makeRow(name: sectionNameForIcon(icon), icons: [
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ struct WatchConfigurationView: View {
Button(action: {
dismiss()
}, label: {
Text(L10n.cancelLabel)
Text(verbatim: L10n.cancelLabel)
})
}
ToolbarItem(placement: .topBarTrailing) {
Expand All @@ -34,7 +34,7 @@ struct WatchConfigurationView: View {
}
}
}, label: {
Text(L10n.Watch.Configuration.Save.title)
Text(verbatim: L10n.Watch.Configuration.Save.title)
})
}
})
Expand All @@ -53,7 +53,7 @@ struct WatchConfigurationView: View {
})
.alert(viewModel.errorMessage ?? L10n.errorLabel, isPresented: $viewModel.showError) {
Button(action: {}, label: {
Text(L10n.okLabel)
Text(verbatim: L10n.okLabel)
})
}
}
Expand Down Expand Up @@ -116,7 +116,7 @@ struct WatchConfigurationView: View {
private var assistSection: some View {
Section("Assist") {
Toggle(isOn: $viewModel.watchConfig.assist.showAssist, label: {
Text(L10n.Watch.Configuration.ShowAssist.title)
Text(verbatim: L10n.Watch.Configuration.ShowAssist.title)
})
if viewModel.watchConfig.assist.showAssist {
Picker(L10n.Watch.Config.Assist.selectServer, selection: $viewModel.watchConfig.assist.serverId) {
Expand Down Expand Up @@ -287,7 +287,7 @@ struct WatchConfigurationView: View {
}

private var noItemsWatchView: some View {
Text(L10n.Watch.Settings.NoItems.Phone.title)
Text(verbatim: L10n.Watch.Settings.NoItems.Phone.title)
.frame(maxWidth: .infinity, alignment: .center)
.font(.footnote)
.padding(Spaces.one)
Expand Down
12 changes: 6 additions & 6 deletions Sources/App/Settings/CarPlay/CarPlayConfigurationView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ struct CarPlayConfigurationView: View {
Button(action: {
dismiss()
}, label: {
Text(L10n.cancelLabel)
Text(verbatim: L10n.cancelLabel)
})
}
ToolbarItem(placement: .topBarTrailing) {
Expand All @@ -35,7 +35,7 @@ struct CarPlayConfigurationView: View {
}
}
}, label: {
Text(L10n.Watch.Configuration.Save.title)
Text(verbatim: L10n.Watch.Configuration.Save.title)
})
}
})
Expand All @@ -53,7 +53,7 @@ struct CarPlayConfigurationView: View {
})
.alert(viewModel.errorMessage ?? L10n.errorLabel, isPresented: $viewModel.showError) {
Button(action: {}, label: {
Text(L10n.okLabel)
Text(verbatim: L10n.okLabel)
})
}
}
Expand Down Expand Up @@ -182,12 +182,12 @@ struct CarPlayConfigurationView: View {
viewModel.deleteTab(at: indexSet)
}
} header: {
Text("Active")
Text(L10n.CarPlay.Tabs.Active.title)
} footer: {
Text("Swipe left to remove tab")
Text(L10n.CarPlay.Tabs.Active.DeleteAction.title)
}
if viewModel.config.tabs.count != CarPlayTab.allCases.count {
Section("Inactive") {
Section(L10n.CarPlay.Tabs.Inactive.title) {
ForEach(CarPlayTab.allCases.filter({ tab in
!viewModel.config.tabs.contains(tab)
}), id: \.rawValue) { tab in
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ struct ClientEventsLogView: View {
Button {
showClearConfirmation = true
} label: {
Text(L10n.ClientEvents.View.clear)
Text(verbatim: L10n.ClientEvents.View.clear)
}
.confirmationDialog(
L10n.ClientEvents.View.ClearConfirm.title,
Expand Down Expand Up @@ -51,7 +51,7 @@ struct ClientEventsLogView: View {
listItem(event)
}
if filteredEvents.isEmpty {
Text(L10n.ClientEvents.noEvents)
Text(verbatim: L10n.ClientEvents.noEvents)
.frame(maxWidth: .infinity, alignment: .center)
.listRowBackground(Color.clear)
.font(.headline)
Expand Down
20 changes: 10 additions & 10 deletions Sources/App/Settings/DebugView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,7 @@ struct DebugView: View {
}
.alert(L10n.Alert.Confirmation.Generic.title, isPresented: $showDeleteEntitiesAlert) {
Button(role: .cancel, action: { /* no-op */ }) {
Text(L10n.cancelLabel)
Text(verbatim: L10n.cancelLabel)
}
Button(role: .destructive, action: {
do {
Expand All @@ -186,10 +186,10 @@ struct DebugView: View {
Current.Log.error("Failed to reset app entities, error: \(error)")
}
}) {
Text(L10n.yesLabel)
Text(verbatim: L10n.yesLabel)
}
} message: {
Text(L10n.Alert.Confirmation.DeleteEntities.message)
Text(verbatim: L10n.Alert.Confirmation.DeleteEntities.message)
}
Button {
loadingCleaningWebCache = true
Expand Down Expand Up @@ -224,21 +224,21 @@ struct DebugView: View {
}
.alert(L10n.Alert.Confirmation.Generic.title, isPresented: $showResetAppAlert) {
Button(role: .cancel, action: { /* no-op */ }) {
Text(L10n.cancelLabel)
Text(verbatim: L10n.cancelLabel)
}
Button(role: .destructive, action: {
Task {
await resetApp()
}
}) {
Text(L10n.yesLabel)
Text(verbatim: L10n.yesLabel)
}
} message: {
Text(L10n.Settings.ResetSection.ResetAlert.title)
Text(verbatim: L10n.Settings.ResetSection.ResetAlert.title)
}

} footer: {
Text(L10n.Settings.Debugging.CriticalSection.footer)
Text(verbatim: L10n.Settings.Debugging.CriticalSection.footer)
}
}

Expand All @@ -257,7 +257,7 @@ struct DebugView: View {
}
.alert(L10n.errorLabel, isPresented: $showWatchSyncError) {
Button(role: .cancel, action: { /* no-op */ }) {
Text(L10n.okLabel)
Text(verbatim: L10n.okLabel)
}
} message: {
Text(watchSyncErrorMessage ?? "Unknown")
Expand Down Expand Up @@ -312,9 +312,9 @@ struct DebugView: View {
}

} header: {
Text(L10n.Settings.Developer.header)
Text(verbatim: L10n.Settings.Developer.header)
} footer: {
Text(L10n.Settings.Developer.footer)
Text(verbatim: L10n.Settings.Developer.footer)
}
}

Expand Down
10 changes: 5 additions & 5 deletions Sources/App/Settings/MagicItem/Add/MagicItemAddView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -86,16 +86,16 @@ struct MagicItemAddView: View {
ForEach(visiblePickerOptions, id: \.self) { option in
switch option {
case .entities:
Text(L10n.MagicItem.ItemType.Entity.List.title)
Text(verbatim: L10n.MagicItem.ItemType.Entity.List.title)
.tag(MagicItemAddType.entities)
case .legacyiOSActions:
Text(L10n.MagicItem.ItemType.Action.List.title)
Text(verbatim: L10n.MagicItem.ItemType.Action.List.title)
.tag(MagicItemAddType.actions)
case .scripts:
Text(L10n.MagicItem.ItemType.Script.List.title)
Text(verbatim: L10n.MagicItem.ItemType.Script.List.title)
.tag(MagicItemAddType.scripts)
case .scenes:
Text(L10n.MagicItem.ItemType.Scene.List.title)
Text(verbatim: L10n.MagicItem.ItemType.Scene.List.title)
.tag(MagicItemAddType.scenes)
}
}
Expand Down Expand Up @@ -135,7 +135,7 @@ struct MagicItemAddView: View {
Button {
viewModel.selectedItemType = .scripts
} label: {
Text(L10n.MagicItem.ItemType.Action.List.Warning.title)
Text(verbatim: L10n.MagicItem.ItemType.Action.List.Warning.title)
}
.buttonStyle(.bordered)
.tint(.red)
Expand Down
2 changes: 1 addition & 1 deletion Sources/App/Settings/MagicItem/AssistPipelinePicker.swift
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ struct AssistPipelinePicker: View {
if selectedServerId != nil, let selectedPipelineId, !assistConfigs.isEmpty {
Text(nameForSelectedPipeline() ?? selectedPipelineId)
} else {
Text(L10n.AssistPipelinePicker.placeholder)
Text(verbatim: L10n.AssistPipelinePicker.placeholder)
}
})
.onAppear {
Expand Down
Loading

0 comments on commit 638117f

Please sign in to comment.