views:

44

answers:

1

There is a very similar question already posted. In fact, the result of the answer in that post is exactly what I'm after, but I have no codebehind to place that code in. All of our logic is encapsulated in a ViewModel. Since the ViewModel is not supposed to have direct references to specific visual elements, this code cannot exist there either. Is there a way to perform this same thing in XAML somehow, or have I finally ran into a reason to be forced to create codebehind files?

+1  A: 

You could try doing something with attached properties..it's a bit elaborate, but it does the same as the other answer, so i think it should work:

public class DependencyPropertyCollection : List<DependencyProperty>
{ }

public static class ValidationUtil
{
    public static readonly DependencyProperty ForceValidationProperty =
        DependencyProperty.RegisterAttached("ForceValidation", typeof(DependencyPropertyCollection), typeof(ValidationUtil), new PropertyMetadata(OnForceValidationChanged));
    private static void OnForceValidationChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
    {
        FrameworkElement element = (FrameworkElement)sender;
        element.Loaded += OnElementLoaded;
    }

    private static void OnElementLoaded(object sender, RoutedEventArgs e)
    {
        FrameworkElement element = (FrameworkElement)sender;
        element.Loaded -= OnElementLoaded;
        foreach (DependencyProperty property in GetForceValidation(element))
            element.GetBindingExpression(property).UpdateSource();
    }

    public static DependencyPropertyCollection GetForceValidation(DependencyObject obj)
    {
        return (DependencyPropertyCollection)obj.GetValue(ForceValidationProperty);
    }
    public static void SetForceValidation(DependencyObject obj, DependencyPropertyCollection value)
    {
        obj.SetValue(ForceValidationProperty, value);
    }
}

And you use it like this:

<TextBlock Text="{Binding Text}">
    <local:ValidationUtil.ForceValidation>
        <local:DependencyPropertyCollection>
            <x:StaticExtension Member="TextBlock.TextProperty"/>
        </local:DependencyPropertyCollection>
    </local:ValidationUtil.ForceValidation>
</TextBlock>

Inside the collection you specify each DependencyProperty which has a binding that you want to validate.

Bubblewrap