Move to enum-based model for UI language options

This commit is contained in:
Matt Nadareski
2025-10-16 20:28:37 -04:00
parent 99d26f177b
commit f63517bb52
8 changed files with 146 additions and 99 deletions

View File

@@ -14,6 +14,23 @@ namespace MPF.Frontend.Test
{
#region Long Name
[Theory]
[InlineData(null, "Unknown")]
[InlineData(InterfaceLanguage.AutoDetect, "Auto Detect")]
[InlineData(InterfaceLanguage.English, "English")]
[InlineData(InterfaceLanguage.Korean, "한국어")]
public void LongName_InterfaceLanguage(InterfaceLanguage? lang, string? expected)
{
string? actual = lang.LongName();
Assert.Equal(expected, actual);
if (lang != null)
{
actual = EnumExtensions.GetLongName(lang);
Assert.Equal(expected, actual);
}
}
[Theory]
[InlineData(null, "Unknown")]
[InlineData(InternalProgram.NONE, "Unknown")]
@@ -115,6 +132,17 @@ namespace MPF.Frontend.Test
#region Short Name
[Theory]
[InlineData(null, "Unknown")]
[InlineData(InterfaceLanguage.AutoDetect, "_AUTO")]
[InlineData(InterfaceLanguage.English, "eng")]
[InlineData(InterfaceLanguage.Korean, "kor")]
public void ShortName_InterfaceLanguage(InterfaceLanguage? lang, string? expected)
{
string? actual = lang.ShortName();
Assert.Equal(expected, actual);
}
[Theory]
[InlineData(null, "Unknown")]
[InlineData(InternalProgram.NONE, "Unknown")]
@@ -135,6 +163,19 @@ namespace MPF.Frontend.Test
#region From String
[Theory]
[InlineData(null, InterfaceLanguage.AutoDetect)]
[InlineData("", InterfaceLanguage.AutoDetect)]
[InlineData("_AUTO", InterfaceLanguage.AutoDetect)]
[InlineData("_auto", InterfaceLanguage.AutoDetect)]
[InlineData("eng", InterfaceLanguage.English)]
[InlineData("kor", InterfaceLanguage.Korean)]
public void ToInterfaceLanguageTest(string? interfaceLanguage, InterfaceLanguage expected)
{
InterfaceLanguage actual = interfaceLanguage.ToInterfaceLanguage();
Assert.Equal(expected, actual);
}
[Theory]
[InlineData(null, InternalProgram.NONE)]
[InlineData("", InternalProgram.NONE)]

View File

@@ -1,68 +0,0 @@
using System;
using System.Collections.Generic;
namespace MPF.Frontend.ComboBoxItems
{
/// <summary>
/// Represents a single item in the Default UI Language combo box
/// </summary>
public class UILanguageComboBoxItem : IEquatable<UILanguageComboBoxItem>, IElement
{
private readonly string UILanguage;
private static readonly string[] languages = { "ENG", "한국어" };
public UILanguageComboBoxItem(string language) => UILanguage = language;
/// <inheritdoc/>
public string Name
{
get
{
if (Array.Exists(languages, lang => lang == UILanguage))
return UILanguage;
else
return "Auto Detect";
}
}
public override string ToString() => Name;
/// <summary>
/// Generate all elements for the known system combo box
/// </summary>
/// <returns></returns>
public static List<UILanguageComboBoxItem> GenerateElements()
{
var langValues = new List<UILanguageComboBoxItem>()
{
new UILanguageComboBoxItem(""),
};
foreach (var lang in languages)
{
langValues.Add(new UILanguageComboBoxItem(lang));
}
return langValues;
}
/// <inheritdoc/>
public override bool Equals(object? obj)
{
return Equals(obj as UILanguageComboBoxItem);
}
/// <inheritdoc/>
public bool Equals(UILanguageComboBoxItem? other)
{
if (other == null)
return false;
return UILanguage == other.UILanguage;
}
/// <inheritdoc/>
public override int GetHashCode() => base.GetHashCode();
}
}

View File

@@ -62,6 +62,31 @@ namespace MPF.Frontend
}
}
/// <summary>
/// Get the string representation of the InterfaceLanguage enum values
/// </summary>
/// <param name="lang">InterfaceLanguage value to convert</param>
/// <returns>String representing the value, if possible</returns>
public static string LongName(this InterfaceLanguage lang)
=> ((InterfaceLanguage?)lang).LongName();
/// <summary>
/// Get the string representation of the InterfaceLanguage enum values
/// </summary>
/// <param name="lang">InterfaceLanguage value to convert</param>
/// <returns>String representing the value, if possible</returns>
public static string LongName(this InterfaceLanguage? lang)
{
return lang switch
{
InterfaceLanguage.AutoDetect => "Auto Detect",
InterfaceLanguage.English => "English",
InterfaceLanguage.Korean => "한국어",
_ => "Unknown",
};
}
/// <summary>
/// Get the string representation of the InternalProgram enum values
/// </summary>
@@ -188,6 +213,23 @@ namespace MPF.Frontend
#region Convert to Short Name
/// <summary>
/// Get the short string representation of the InterfaceLanguage enum values
/// </summary>
/// <param name="lang">InterfaceLanguage value to convert</param>
/// <returns>String representing the value, if possible</returns>
public static string ShortName(this InterfaceLanguage? lang)
{
return lang switch
{
InterfaceLanguage.AutoDetect => "_AUTO",
InterfaceLanguage.English => "eng",
InterfaceLanguage.Korean => "kor",
_ => "Unknown",
};
}
/// <summary>
/// Get the short string representation of the InternalProgram enum values
/// </summary>
@@ -223,6 +265,24 @@ namespace MPF.Frontend
#region Convert from String
/// <summary>
/// Get the InterfaceLanguage enum value for a given string
/// </summary>
/// <param name="internalLanguage">String value to convert</param>
/// <returns>InterfaceLanguage represented by the string, if possible</returns>
public static InterfaceLanguage ToInterfaceLanguage(this string? internalLanguage)
{
return (internalLanguage?.ToLowerInvariant()) switch
{
"_auto"
or "auto detect" => InterfaceLanguage.AutoDetect,
"eng" or "english" => InterfaceLanguage.English,
"kor" or "한국어" => InterfaceLanguage.Korean,
_ => InterfaceLanguage.AutoDetect,
};
}
/// <summary>
/// Get the InternalProgram enum value for a given string
/// </summary>

View File

@@ -1,5 +1,19 @@
namespace MPF.Frontend
{
/// <summary>
/// Interface language
/// </summary>
public enum InterfaceLanguage
{
/// <summary>
/// Default to auto-detecting language
/// </summary>
AutoDetect = 0,
English,
Korean,
}
/// <summary>
/// Drive type for dumping
/// </summary>
@@ -40,4 +54,4 @@ namespace MPF.Frontend
ERROR,
SECRET,
}
}
}

View File

@@ -144,12 +144,19 @@ namespace MPF.Frontend
/// <summary>
/// Default UI language to launch MPF into
/// null/empty = Detect locale
/// </summary>
public string? DefaultUILanguage
public InterfaceLanguage? DefaultUILanguage
{
get { return GetStringSetting(Settings, "DefaultUILanguage", "Auto Detect"); }
set { Settings["DefaultUILanguage"] = value; }
get
{
var valueString = GetStringSetting(Settings, "DefaultUILanguage", RedumpSystem.IBMPCcompatible.LongName());
var valueEnum = (valueString ?? string.Empty).ToInterfaceLanguage();
return valueEnum;
}
set
{
Settings["DefaultUILanguage"] = value.ShortName();
}
}
/// <summary>

View File

@@ -54,7 +54,7 @@ namespace MPF.Frontend.ViewModels
/// <summary>
/// List of available UI languages
/// </summary>
public static List<UILanguageComboBoxItem> UILanguages => UILanguageComboBoxItem.GenerateElements();
public static List<Element<InterfaceLanguage>> UILanguages => PopulateUILanguages();
/// <summary>
/// List of available log compression methods
@@ -110,6 +110,15 @@ namespace MPF.Frontend.ViewModels
return internalPrograms.ConvertAll(ip => new Element<InternalProgram>(ip));
}
/// <summary>
/// Get a complete list of supported interface languages
/// </summary>
private static List<Element<InterfaceLanguage>> PopulateUILanguages()
{
var languages = new List<InterfaceLanguage> { InterfaceLanguage.AutoDetect, InterfaceLanguage.English, InterfaceLanguage.Korean };
return languages.ConvertAll(ip => new Element<InterfaceLanguage>(ip));
}
/// <summary>
/// Get a complete list of supported log compression methods
/// </summary>

View File

@@ -97,20 +97,14 @@ namespace MPF.UI.Windows
// Set default language
var dictionary = new ResourceDictionary();
switch (MainViewModel.Options.DefaultUILanguage)
dictionary.Source = MainViewModel.Options.DefaultUILanguage switch
{
case "ENG":
// Change UI language to English
dictionary.Source = new Uri("../Resources/Strings.xaml", UriKind.Relative);
break;
case "한국어":
// Change UI language to Korean
dictionary.Source = new Uri("../Resources/Strings.ko.xaml", UriKind.Relative);
break;
default:
dictionary.Source = new Uri("../Resources/Strings.xaml", UriKind.Relative);
break;
}
InterfaceLanguage.English => new Uri("../Resources/Strings.xaml", UriKind.Relative),
InterfaceLanguage.Korean => new Uri("../Resources/Strings.ko.xaml", UriKind.Relative),
// Default to English
_ => new Uri("../Resources/Strings.xaml", UriKind.Relative),
};
Application.Current.Resources.MergedDictionaries.Add(dictionary);
}
@@ -135,7 +129,7 @@ namespace MPF.UI.Windows
DebugViewMenuItem!.Visibility = Visibility.Visible;
MainViewModel.Init(LogOutput!.EnqueueLog, DisplayUserMessage, ShowMediaInformationWindow);
// Pass translation strings to MainViewModel
var translationStrings = new Dictionary<string, string>();
translationStrings["StartDumpingButtonString"] = (string)Application.Current.FindResource("StartDumpingButtonString");

View File

@@ -95,17 +95,7 @@
<Label VerticalAlignment="Center" Content="Default UI Language:" HorizontalAlignment="Right" />
<ComboBox x:Name="DefaultUILanguageComboBox" Height="22" Width="200" HorizontalAlignment="Left"
ItemsSource="{Binding UILanguages}" SelectedItem="{Binding Options.DefaultUILanguage, Converter={StaticResource ElementConverter}, Mode=TwoWay}"
SelectedIndex="0" Style="{DynamicResource CustomComboBoxStyle}">
<ComboBox.ItemContainerStyle>
<Style TargetType="{x:Type ComboBoxItem}">
<Style.Triggers>
<DataTrigger Binding="{Binding IsHeader}" Value="True">
<Setter Property="IsEnabled" Value="False"/>
</DataTrigger>
</Style.Triggers>
</Style>
</ComboBox.ItemContainerStyle>
</ComboBox>
Style="{DynamicResource CustomComboBoxStyle}" />
</UniformGrid>
</GroupBox>