How to deal with XAML valueconverter class explosion
As I write my WPF and Silverlight apps, one thing that is 开发者_JAVA技巧starting to bother me is the sheer number of ValueConverters that I seem to have to write to do my binding. Many of the converters are handling things such OK button IsEnabled bindings, e.g.:
<Button x:Name="OKButton" Content="OK" IsEnabled="{Binding SelectedItem, ElementName=acbPassenger, Converter={StaticResource ValidPassengerConverter}}"/>
Its seems though that I am ending up with a dozen or so converters to handle each ever so slightly different conversion situation. Am I doing something wrong? Should I try to roll similar converters into one converter class? What do other people do? As the number of converters increases so does the temptation to throw the towel in and do some of the enabling/disabling etc. in a ye olde code behind event handler.
I have also written a fair number of IValueConverters, and it's definitely easy to overuse them. One technique is to move the logic and wrap it in a simpler property you can bind to.
For example, in the scenario you mentioned, you might consider moving the validation logic out of the converters and into the business objects, e.g. your Passenger class. Perhaps you could implement a boolean IsValid property on Passenger. Then you could either bind IsEnabled directly to it, or bind the button's Command property to an ICommand whose CanExecute property is connected to IsValid.
In general, another technique that can help cut down on the number of converters is by using ConverterParameter. For example, let's say you want a converter that can convert true to Visibility.Visible and false to Visibility.Collapsed, and you also want a converter that will do the opposite (true to Collapsed and false to Visible).
You could do this with two converters:
<TextBlock Visibility="{Binding MyBoolean, Converter={StaticResource BoolToVisibilityConverter}" />
<TextBlock Visibility="{Binding MyBoolean, Converter={StaticResource InvertedBoolToVisibilityConverter}" />
Or you could do it with one converter:
<TextBlock Visibility="{Binding MyBoolean, Converter={StaticResource BoolToVisibilityConverter}, ConverterParameter=true" />
<TextBlock Visibility="{Binding MyBoolean, Converter={StaticResource BoolToVisibilityConverter}, ConverterParameter=false" />
Then the converter would need to parse its parameter to a boolean and flip the result when it's false.
精彩评论