带有MVVM的PasswordBox

Ran*_*gel 19 wpf mvvm passwordbox

嗨人stackoverflow.我正在使用MVVM,我让ViewModel使用Property Password调用UserViewModel.在View中有一个控件PasswordBox.

<PasswordBox x:Name="txtPassword" Password="{Binding Password}" />
Run Code Online (Sandbox Code Playgroud)

但是这个xaml不起作用.你怎么做绑定?请帮忙!!

Mar*_*ris 13

出于安全原因,Password属性不是依赖项属性,因此您无法绑定它.不幸的是,您需要在旧式方式后面的代码中执行绑定(注册OnPropertyChanged事件并通过代码更新值...)


我快速搜索带我到这个博客文章,其中显示如何编写附加属性来回避问题.这是否值得做,但实际上取决于你对代码隐藏的厌恶.


Nir*_*Nir 5

您始终可以编写一个包装密码的控件,并为Password属性添加依赖项属性.

我只会使用代码,但如果你必须你可以做以下事情:

public class BindablePasswordBox : Decorator
{
    public static readonly DependencyProperty PasswordProperty =
        DependencyProperty.Register("Password", typeof(string), typeof(BindablePasswordBox));

    public string Password
    {
        get { return (string)GetValue(PasswordProperty); }
        set { SetValue(PasswordProperty, value); }
    }

    public BindablePasswordBox()
    {
        Child = new PasswordBox();
        ((PasswordBox)Child).PasswordChanged += BindablePasswordBox_PasswordChanged;
    }

    void BindablePasswordBox_PasswordChanged(object sender, RoutedEventArgs e)
    {
        Password = ((PasswordBox)Child).Password;
    }

}
Run Code Online (Sandbox Code Playgroud)


J.H*_*.H. 5

BindablePasswordBox存在问题。它只能在一个方向上工作,从PasswordBox到PasswordProperty。下面是它的修改版本,可双向使用。它注册一个PropertyChangedCallback并在调用时更新PasswordBox的密码。我希望有人觉得这有用。

public class BindablePasswordBox : Decorator
{
    public static readonly DependencyProperty PasswordProperty = DependencyProperty.Register("Password", typeof(string), typeof(BindablePasswordBox), new PropertyMetadata(string.Empty, OnDependencyPropertyChanged));
    public string Password
    {
        get { return (string)GetValue(PasswordProperty); }
        set { SetValue(PasswordProperty, value); }
    }

    private static void OnDependencyPropertyChanged(DependencyObject source, DependencyPropertyChangedEventArgs e)
    {
        BindablePasswordBox p = source as BindablePasswordBox;
        if (p != null)
        {
            if (e.Property == PasswordProperty)
            {
                var pb = p.Child as PasswordBox;
                if (pb != null)
                {
                    if (pb.Password != p.Password)
                        pb.Password = p.Password;
                }
            }
        }
    }

    public BindablePasswordBox()
    {
        Child = new PasswordBox();
        ((PasswordBox)Child).PasswordChanged += BindablePasswordBox_PasswordChanged;
    }

    void BindablePasswordBox_PasswordChanged(object sender, RoutedEventArgs e)
    {
        Password = ((PasswordBox)Child).Password;
    }
}
Run Code Online (Sandbox Code Playgroud)