ComboBox.Text does not respect ItemStringFormat property
I just noticed some strange behavior that looks like a bug. Consider the following XAML:
<Page
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:sys="clr-namespace:System;assembly=mscorlib">
<Page.Resources>
<x:Array x:Key="data" Type="{x:Type sys:String}">
<sys:String>Foo</sys:String>
<sys:String>Bar</sys:String>
<sys:String>Baz</sys:String>
</x:Array>
</Page.Resources>
<StackPanel Orientation="Vertical">
<Button>Boo</Button>
<ComboBox Name="combo" ItemsSource="{Binding Source={StaticResource data}}" ItemStringFormat="##{0}##" />
<TextBlock Text="{Binding Text, ElementName=combo}"/>
</StackPanel>
</Page>
ComboBox
displays values ββas "## Foo ##", "## Bar ##" and "## Baz ##". But it TextBlock
displays the selected values ββas "Foo", "Bar" and "Baz". So it ItemStringFormat
seems to be ignored for property Text
...
This is mistake? If so, is there a workaround?
Or am I just doing something wrong?
a source to share
This is not an error: ItemStringFormat
- it is just a shortcut to "data template where the text block is bound to a value with the specified string format set in the binding". Text
however, it is usually used when it IsEditable
is true and represents user input. If the list contains anything other than strings, it is preferable to use SelectedItem
than Text
. In any case, the following code will reapply the format to the text:
<TextBlock Text="{Binding ElementName=combo, Path=Text, StringFormat='##{0}##'}"/>
a source to share
I know it is probably too late to help the OP, but just in case someone stumbles over this ...
The solution I would use for the real problem that the OP mentioned in a comment to another answer is to use IValueConverter
.
Here's the code for the class FormatConverter
:
public class FormatConverter : System.Windows.Data.IValueConverter
{
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
string format = parameter.ToString();
return string.Format(format, value);
}
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
{
throw new NotImplementedException();
}
}
And this is how you use it (taken from the question with modification):
<Page
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:sys="clr-namespace:System;assembly=mscorlib"
xmlns:local="clr-namespace:YourNamespace">
<Page.Resources>
<x:Array x:Key="data" Type="{x:Type sys:String}">
<sys:String>Foo</sys:String>
<sys:String>Bar</sys:String>
<sys:String>Baz</sys:String>
</x:Array>
<local:FormatConverter x:Key="FormatConverter" />
</Page.Resources>
<StackPanel>
<ComboBox ItemsSource="{Binding Source={StaticResource data}}" ItemStringFormat="##{0}##"
Text="{Binding Path=VMProp, Mode=OneWayToSource, Converter={StaticResource FormatConverter}, ConverterParameter=##{0}##}" />
</StackPanel>
</Page>
This will cause items to appear ComboBox
as "## Foo ##", "## Bar ##" and "## Baz ##" thanks to the ItemStringFormat
"## {0} ##" setting . Also, the property VMProp
on the ViewModel will be assigned values ββin the same format when selected, thanks FormatConverter
when the parameter is ConverterParameter
set to "## {0} ##".
Note that even if I used the property ComboBox.Text
to stay consistent with the original question, I would assume that the property ComboBox.SelectedItem
would be more appropriate.;)
a source to share