WPF and Localization in the XAML with String.Format()

I had a localization issue today.

I was trying to get our product running in Spanish to show decimals as a comma (,) instead of a period (.).

Here is the XAML snippet I have.

        <StackPanel Orientation="Horizontal" Margin="0,0,0,5" >
            <Image Source="{Binding Image}" Width="24" Height="24" />
            <Label>
                <TextBlock>
                  <TextBlock.Text>
                         <MultiBinding StringFormat="{}{0} ({1}:) - {2} {3:F} GB, {4} {5:F} GB, {6} {7:F} GB">
                            <Binding Path="Drive.VolumeLabel" />
                            <Binding Path="Drive.DriveLetter" />
                            <Binding Source="{x:Static p:Resources.Required}" />
                            <Binding Path="Drive.TotalRequiredSpace.Gigabyte" />
                            <Binding Source="{x:Static p:Resources.Recommended}" />
                            <Binding Path="Drive.TotalRecommendedSpace.Gigabyte" />
                            <Binding Source="{x:Static p:Resources.Available}" />
                            <Binding Path="Drive.AvailableSpace.Gigabyte" />
                         </MultiBinding>
                  </TextBlock.Text>
                </TextBlock>
            </Label>
            <Image Source="{Binding DriveSpaceStatusImage}" Width="24" Height="24" Margin="15,0" />
        </StackPanel>

The Drive.TotalRequiredSpace object is a DataMeasurement object (which I have posted code for in a previous post).

The Gigabyte parameter is a Double.  These Double’s displayed the decimal separator using a period (.) character even though I was testing on a Spanish version of Windows Server 2008 R2.

I located the answer on another blog.
WPF Data Binding Cheat Sheet Update – The Internationalization Fix

He was using Date’s which like Double’s require decimals, and was seeing the same issue.  The solution is the same though.

Add the following code somewhere before your first WPF window opens.

System.Windows.FrameworkElement.LanguageProperty.OverrideMetadata
(
    typeof(System.Windows.FrameworkElement),
    new System.Windows.FrameworkPropertyMetadata(
        System.Windows.Markup.XmlLanguage.GetLanguage(CultureInfo.CurrentCulture.IetfLanguageTag)
    )
);

I am pretty sure this is a poor oversight and a bug in my opinion. Even though there is a one line fix, it was a costly fix, as I had to spend time troubleshooting and researching to find this one line solution which should be the default behavior.

Leave a Reply