首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >WPF ItemsControl ItemTemplate验证

WPF ItemsControl ItemTemplate验证
EN

Stack Overflow用户
提问于 2011-07-13 08:23:02
回答 2查看 1.2K关注 0票数 1

有没有一种方法可以确定ItemsControl是否有任何带有验证错误的子控件?我想把这个值(布尔值)绑定到一个按钮上的IsEnabled属性。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2011-07-13 09:00:32

我最近使用了前面的代码,因此请回答以获得更好的效果。

我有一个包含DataGrid的用户控件。用户控件公开了一个包含getter的IsValid属性,该属性只是调用静态IsValid函数,将DataGrid作为DependencyObject传入:

代码语言:javascript
复制
public class MyControl : UserControl
{
    public bool IsValid
    {
        get { return Validator.IsValid(MyDataGrid); }
    }
}

然后,可以通过绑定到要启用/禁用的按钮的命令的CanExecute函数来检查控件的IsValid属性。

我链接到的代码的唯一问题是它实际上评估了绑定上的验证,这意味着一旦你运行它,任何在技术上无效但尚未失效的字段(即用户可能还没有在该字段中输入任何数据,因为他们还没有访问它)现在将处于无效状态-我还没有考虑到避免或减轻这种情况的方法。

编辑:

这是一个更新的版本,不会像我之前提到的那样使控件失效。我简单地注释掉/稍微更改了一些行,但保留了所有内容,以便您可以看到不同之处。请注意,这也应该执行得更快,因为您将在发现第一个无效绑定时退出。

代码语言:javascript
复制
public static bool IsValid(DependencyObject parent)
{
    // Validate all the bindings on the parent
    bool valid = true;
    LocalValueEnumerator localValues = parent.GetLocalValueEnumerator();
    while (localValues.MoveNext())
    {
        LocalValueEntry entry = localValues.Current;
        if (BindingOperations.IsDataBound(parent, entry.Property))
        {
            Binding binding = BindingOperations.GetBinding(parent, entry.Property);
            foreach (ValidationRule rule in binding.ValidationRules)
            {
                ValidationResult result = rule.Validate(parent.GetValue(entry.Property), null);
                if (!result.IsValid)
                {
                    //BindingExpression expression = BindingOperations.GetBindingExpression(parent, entry.Property);
                    //System.Windows.Controls.Validation.MarkInvalid(expression, new ValidationError(rule, expression, result.ErrorContent, null));
                    //valid = false;
                    return false;
                }
            }
        }
    }

    // Validate all the bindings on the children
    for (int i = 0; i != VisualTreeHelper.GetChildrenCount(parent); ++i)
    {
        DependencyObject child = VisualTreeHelper.GetChild(parent, i);
        if (!IsValid(child))
        {
            //valid = false;
            return false;
        }
    }

    //return valid;
    return true;
}
票数 0
EN

Stack Overflow用户

发布于 2012-06-25 23:00:45

我不知道为什么,slugter的答案对我不起作用(LocalValueEnumerator返回了一些属性,但从来没有像Text那样返回绑定的属性)。

我设法让它使用下面的代码(从this answer派生):

代码语言:javascript
复制
public static bool IsValid(DependencyObject obj)
{
    // The dependency object is valid if it has no errors, 
    //and all of its children (that are dependency objects) are error-free.
    return !Validation.GetHasError(obj) &&
        GetVisualTreeChildren(obj)
        .OfType<DependencyObject>()
        .All(child => IsValid(child));
}

//VisualTreeHelper don't have a method to get all the children of a visual object
private static IEnumerable GetVisualTreeChildren(DependencyObject parent)
{
    for (int i = 0; i < VisualTreeHelper.GetChildrenCount(parent); i++)
        yield return VisualTreeHelper.GetChild(parent, i);
}
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/6672781

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档