Recently I was delving into Localization with .NET. Essentially, I learnt how to customize a form (using the Language and Localizable property) and then change the culture accordingly.
However, I found that when migrating my hard coded English strings into the auto-generated resource files, and use .GetString("Key") -- well, let's just say it wasn't happy :P.
I decided to make a separate set of resx files dedicated purely to the hard coded string translations. They followed the convention/requirement of [name].[culture-code].resx. I made of of these for each relevant language; e.g. appstrings.de.resx (For German) and appstrings.resx (as invariant baseline).
To utilise these new resources, I created an instance of ResourceManager and Resource Set
Dim resManager As New ResourceManager("LanguageTest.appstrings", Assembly.GetExecutingAssembly)
Dim resSet As ResourceSet = resManager.GetResourceSet(My.Application.UICulture, True, True)
The current UI culture was set (for example, to German) using
My.Application.ChangeUICulture("de")
Original issue
Unless the resSet.GetString("Key") is explicitly defined in the appstrings.de.resx, it will return a blank string. Is there anyway I can make it fallback to the appstrings.resx (where "Key" does exist), which I assumed would be the default baseline?
Update
Rhapsody made a suggestion below, while the actual tip itself didn't work, it did in-fact spark an interesting point, using resManager.GetString("Key") as opposed to resSet.GetString("Key"). This appears to work without flaw so far. That is, values present in the specialized language file are returned, while 'missing' values fall-back to the default culture when accessed by a single key.
Subsequent Issue
The only remaining issue would be whether the performance impact of using ResourceManger as opposed to a cached ResourceSet will be that detrimental?
You can try declaring a default Culture for the application as below
[assembly: NeutralResourcesLanguageAttribute("en-US", UltimateResourceFallbackLocation.Satellite)]
This code declares that your default culture is en-US. In your example if current culture is "de-DE" it looks for for resource in "de-DE", then looks for the parent "de" culture and so on and Ultimatly goes to the defined culture (en-US) resource file. see MSDN for fallback strategies by resourceManage. The above code normaly goes in the assenblyInfo.cs. The second parameter is telling the resource manager where are the resources located in Main assembly or satellite.
Unfortunatly in this solution you have to use a culture name, Not the resource file name. however you could extend RM to use a specific resource by file name, But its way simpler to pick a default culture and rename your resource file to that culture and you have the solution out of the box.
Try
Public Function GetString(ByVal Name As String) As String
Return My.Resources.Strings.ResourceManager.GetString(Name)
End Function
Where Strings
is the name of the resx files in your project.
This will automatically return the baseline value when it's not available for the current culture.
It's an easy example, you might want to make it more fool proof.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With