Caliburn.Micro,MVVM模式:CanExecute命令不起作用

时间:2016-12-10 22:55:47

标签: c# wpf mvvm caliburn.micro

这是我的观点:

private Customer customer;
public Customer Customer
{
    get { return customer; }
    set { customer = value; NotifyOfPropertyChange(() => Customer); }
}

public bool CanUpdateClick 
{ 
    get 
    {
        if (string.IsNullOrEmpty(customer.Name))
        {
            return false;
        }
        return true; 
    } 
}

public void UpdateClick()
{
    //...
}

这是我的ViewModel:

private string name;
public string Name
{
    get { return name; }
    set { name = value; NotifyOfPropertyChange(() => Name); }
}

这是我的模特:

{{1}}

所以我有UpdateClick方法,它完美无缺。我也有CanUpdateClick属性,但它不起作用,我不知道为什么?当文本框为空时,应禁用UI上的按钮。请帮忙!

1 个答案:

答案 0 :(得分:3)

您可以订阅PropertyChanged类的Customer事件(因为您似乎是PropertyChangedBase的子类)并在NotifyOfPropertyChanged(() => CanUpdateClick)属性时调用Name改变了:

// in your view model
// i'm assuming here that Customer is set before your view model is activated
protected override void OnActivate()
{
    base.OnActivate();
    Customer.PropertyChanged += CustomerPropertyChangedHandler;
}

protected override void OnDeactivate(bool close)
{
    base.OnDeactivate(close);
    // unregister handler
    Customer.PropertyChanged -= CustomerPropertyChangedHandler;
}

// event handler
protected void CustomerPropertyChangedHandler(object sender, PropertyChangedEventArgs e)
{
    if (e.PropertyName == nameof(Customer.Name))
    {
        NotifyOfPropertyChange(() => CanUpdateClick);
    }
}

或者,您只需在视图模型中创建NameCustomerName属性即可绑定到a)使用Customer.Name作为后备字段或b)使用普通支持字段然后在更新时设置Customer.Name

在您看来:

<TextBox Text="{Binding CustomerName, UpdateSourceTrigger=PropertyChanged}" Width="136"/>

以下是在视图模型中实现选项a的方法:

public string CustomerName
{
    get { return Customer.Name; }
    set
    {
        Customer.Name = value;
        NotifyOfPropertyChange(); // CallerMemberName goodness
        NotifyOfPropertyChange(() => CanUpdateClick);
    }
}