C Sharp WPF - Luke31/i18n-cs GitHub Wiki

Intro

This Tutorial is NOT based on Microsofts MSDN Tutorial WPF Globalization and Localization Overview

Why not use the Microsoft way with LocBaml?

  • The localization process is not integrated into the standard Visual Studio build mechanism (as it is for Windows Forms applications).
  • There is no way to view or edit the localized XAML within the Visual Studio designer.
  • Locbaml uses CSV files and has issues when the translated text includes commas. The use of CSV files forces translators to work with two separate mechanisms since they still have to work with standard .NET RESX files for programmatically translated strings.
  • The Locbaml approach results in the complete binary XAML for the window being replicated in the satellite assemblies for each localized language. This results in much larger footprint for localized applications compared to the Windows Forms approach where only those resources that differ from the invariant culture are compiled into the satellite assemblies.
  • There is no way to dynamically change the language of the application at runtime without closing and recreating windows.

Sources for reasons: WPF Localization Using RESX Files and Globalizing and Localizing a WPF application

Comparison of WPF Localization with Advantages and Disadvantages: WPF LOCALIZATION

WPF with only resources

Example Project: WPFSimpleResources

If the WPFLocalizationExtension library is too large and not all features are needed, one may use the simpler resources-only approach, as described in this tutorial: WPF - Localization Resources or Tutorial – Binding to Resources.resx for strings in a WPF Application: A technique to prepare for localization

Hint: In this part, we don't use the Properties Resources as described in the tutorial. Instead we use custom resources which has the benefit of splitting the translation-strings in various resources.

Perform the following steps:

  1. Create a resource .resx file, add your texts and set the Access Modifier to Public

    In our example the resource file is located here: WPFSimpleResources.Loc.LocResources.resx and WPFSimpleResources.Loc.LocResources.ja.resx

  2. In your XAML set following lines to use the resource for e.g. in a Textbox:

     <Window
     	xmlns:loc="clr-namespace:WPFSimpleResources.Loc">
     	<Grid ...>
     		<TextBlock x:Uid="TextBlock_1" 
     			   VerticalAlignment="Top"
     			   HorizontalAlignment="Left"
     			   Text="{x:Static loc:LocResources.helloWorld}" 
     			   />
     	</Grid>
     </Window>
    

Images:

Images don't work out of the box from resource-files. You need to add a Converter for Bitmap to an Image source:

  1. Add a Bitmap extension Method, see in project: WPFSimpleResources.Extensions.BitmapExtension

  2. Add a converter, see in project: WPFSimpleResources.Converters.BitmapImageConverter

  3. In your XAML set following lines to use the converter in your Image Source:

     <Window>
     	<Window.Resources>
     		<converters:BitmapImageConverter x:Key="ImageConverter" />
     	</Window.Resources>
     	<Grid ...>
     		<Image x:Uid="Image_1" Source="{Binding Source={x:Static loc:LocResources.img}, 
     		Converter={StaticResource ImageConverter}}" 
     			   VerticalAlignment="Top" 
     			   HorizontalAlignment="Right" 
     			   Stretch="None"></Image>
     	</Grid>
     </Window>
    

WPF with WPFLocalizationExtension

Example Project: WPFLocalizationExtension

Instead we will use the free WPFLocalizationExtension (https://github.com/SeriousM/WPFLocalizationExtension) under the Ms-PL license in combination with Resources .resx files.

Advantages: (Source: Globalizing and Localizing a WPF application)

  • Design time support (See result without running)
  • Change language at runtime

Disadvantages:

  • Large library

Follow the very simple Tutorial WPF: Localization using Resources and Localization Extension and mind the hints below:

  • You can install the WPFLocalizationExtension using NuGet:

      Install-Package WpfLocalizeExtension
    
  • For created Resource .resx files, set the Access Modifier to Public

  • Specify the current language to the System langauge in starting your application:

      LocalizeDictionary.Instance.SetCurrentThreadCulture = true;
      
      //Set Extension Culture to System culture:
      LocalizeDictionary.Instance.Culture = new CultureInfo(CultureInfo.CurrentUICulture.Name);
    
  • How to prepare your XAML, you may see here Usage - Preparing the XAML code

      <Window xmlns:lex="http://wpflocalizeextension.codeplex.com"
      	lex:LocalizeDictionary.DesignCulture="en"
      	lex:ResxLocalizationProvider.DefaultAssembly="WPFLocalizationExtension"
      	lex:ResxLocalizationProvider.DefaultDictionary="Loc.LocResources">
      	<!-- Some controls -->
      </Window>
    
  • How to access the resources in the XAML you may find here: Usage - Keys

  • If you would like to access Resources from different assemblies in the XAML, look here: Usage - Multiple assemblies and dictionaries

  • Look at the WPFLocalizationExtension Wiki for further questions

WPF with custom MarkupExtension

No Example Project

If you'd like to have runtime translations, but WPFLocalizationExtensionLibrary is too heavy, you may write your own MarkupExtension: WPF Localization at runtime with ResX files. Part II.

Additional helpful features

  • SizeToContent - Make window size automatic depending on content

      <Window SizeToContent="WidthAndHeight">
    
  • SharedSizeGroup - The elements have the same size from the biggest element

      <Grid.ColumnDefinitions>
        <ColumnDefinition x:Uid="ColumnDefinition_1" />
        <ColumnDefinition x:Uid="ColumnDefinition_2" />
        <ColumnDefinition x:Uid="ColumnDefinition_3" **SharedSizeGroup="Buttons"** />
        <ColumnDefinition x:Uid="ColumnDefinition_4" **SharedSizeGroup="Buttons"** />
        <ColumnDefinition x:Uid="ColumnDefinition_5" **SharedSizeGroup="Buttons"** />
      </Grid.ColumnDefinitions>
    
⚠️ **GitHub.com Fallback** ⚠️