1

Here is the working code i have: The text and background color property do change when I click the button (but for a micro second) and are then set back to the default text/color. Seems like RaisePropertyChanged is being triggered again and again. Can somebody help point what I am doing wrong?

MainWindow.xaml code

 <Window x:Class="BuiltIn_Custom_Commands_Eg.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="MainWindow" Height="350" Width="525">
<Grid>
    <StackPanel HorizontalAlignment="Center">
        <TextBlock Text="{Binding txtblck_text, StringFormat=Default: {0}}" Padding="10" FontStyle="Italic" Background="{Binding txtblck_color}"/>
        <Button Content="Change Color" Width="100" Height="30" Margin="20" Command="{Binding OkCommand}" />
    </StackPanel>
</Grid>

ViewModel Code:

class Example_ViewModel : ViewModelBase
{
    #region Properties
    private string _txtblck_text;
    private Brush _txtblck_color;
    public ICommand OkCommand {get; set;}

    public string txtblck_text
    {
        get { return _txtblck_text; }
        set 
        { 
            _txtblck_text = value;
            RaisePropertyChanged("txtblck_text");
        }
    }

    public Brush txtblck_color
    {
        get { return _txtblck_color; }
        set
        {
            _txtblck_color = value;
            RaisePropertyChanged("txtblck_color");
        }
    }
    #endregion

    #region Constructor
    public Example_ViewModel()
    {
        OkCommand = new myCommand(myOkExecute, myCanOkExecute);
    }
    #endregion

    private void myOkExecute(object parameter)
    {
        txtblck_color = Brushes.CadetBlue;
        //RaisePropertyChanged("txtblck_color");

        txtblck_text = "You Clicked me!!!";
        //RaisePropertyChanged("txtblck_text");
    }

    private bool myCanOkExecute(object parameter)
    {
        txtblck_color = Brushes.Yellow;
        txtblck_text = "You havent clicked me!!!";
        return true;
    }
}
4

2 回答 2

2

每当绑定发生变化时,都会并且应该调用 CanExecute 方法。因此,更改 Execute 方法中的绑定(颜色)将导致 CanExecute 再次被调用。

相反,为什么不在构造函数中初始化颜色私有成员一次,如下所示。

public Example_ViewModel()
{
    OkCommand = new myCommand(myOkExecute, myCanOkExecute);
    _txtblck_color =  = Brushes.Yellow;
}

请注意,对于 text 属性也是如此。通常,所有属性私有成员都应在初始化(构造函数)时设置默认值,因为这样可以避免对 INotifyPropertyChanged 的​​不必要调用。

此外,为了测试代码的行为方式并确认这一点,只需在 CanExecute 方法中设置一些断点以查看程序流的行为方式。

于 2012-08-17T20:02:26.663 回答
1

您的问题是您不应该在 myCanOkExecute 中对您的属性进行任何设置......因为它正在被调用并将您的属性更改回黄色等。

Commands 的 CanExecute 方法可能会被多次调用,有时在您不期望的情况下......例如,当焦点更改为不同的控件时,当某些控件正在编辑/发送按键时,在执行命令后,当有人调用 CommandManager.InvalidateRequerySuggested 等。

因此,在您单击并执行按钮后不久,您的 myCanOkExecute 就会被调用。

于 2012-08-17T21:04:40.440 回答