0

私はこの質問に対するいくつかの答えを見つけましたが、どういうわけかそれを理解できません。失礼します。

MVVMパターンに従ったWPFアプリケーションがあります。これには、ビューモデルのコマンドにバインドされているボタンが含まれています。

<button Content="Login" Command="{Binding ProjectLoginCommand}"/>

コマンドはを使用してRelayCommandいます。今、私は次のことをしたいと思います:

  • ユーザーがボタンをクリックすると、対応するコマンドが実行されます。これは機能します。
  • このコマンド内で、別のボタンが非アクティブ化されます。つまり、クリックできなくなります。

私はこれが使用して可能であるはずであるCanExecuteが、正直であることに気づきました:私は単にそれを理解していません。ボタンを有効/無効に設定できますか?

これはRelayCommand.cs

namespace MyApp.Helpers {
    class RelayCommand : ICommand {

    readonly Action<object> execute;
    readonly Predicate<object> canExecute;

    public RelayCommand(Action<object> execute) : this(execute, null) {
    }

    public RelayCommand(Action<object> execute, Predicate<object> canExecute)
    {
      if (execute == null)
          throw new ArgumentNullException("execute");

      this.execute = execute;
      this.canExecute = canExecute;           
    }

    public bool CanExecute(object parameter)
    {
      return canExecute == null ? true : canExecute(parameter);
    }

  public event EventHandler CanExecuteChanged
  {
      add { CommandManager.RequerySuggested += value; }
      remove { CommandManager.RequerySuggested -= value; }
  }

  public void Execute(object parameter)
  {
      execute(parameter);
  }
 }
}

これが私がコマンドを呼び出す方法です:

RelayCommand getProjectListCommand;

public ICommand GetProjectListCommand {
    get {
        if (getProjectListCommand == null) {
            getProjectListCommand = new RelayCommand(param => this.ProjectLogin());
        }
        return getProjectListCommand;
    }
}
4

3 に答える 3

3

RelayCommandオブジェクトを作成するときは、can Predicateを渡す必要があります。これは、(とりわけ)次のシグネチャを持つメソッドである可能性があります。

bool MethodName(オブジェクトパラメータ)。

パラメーターが必要ない場合は、たとえばbool MethodName()を使用しますが、次のように、RelayCommandコンストラクターに渡します:(o)=> MethodName()。

このメソッドでは、ロジックを実行し、コマンドを実行できるかどうかを示す値を返す必要があります。残りは、WPFコマンドインフラストラクチャで処理する必要があります。

于 2012-11-21T17:12:36.483 に答える
1

canExecuteコールバックの操作に問題がある場合は、RelayCommandのより単純なバージョンを使用する方が簡単な場合があります。

class RelayCommand : ICommand 
{
    readonly Action execute;
    private bool canExecute;

    public RelayCommand(Action execute) 
    {
        this.execute = execute;
        this.canExecute = true;
    }

    public bool CanExecute(object parameter)
    {
        return canExecute;
    }

    public void SetCanExecute(bool canExecute)
    {
        this.canExecute = canExecute;
        var handler = CanExecuteChanged;
        if (handler != null) handler(this, EventArgs.Empty);
    }

    public event EventHandler CanExecuteChanged;

    public void Execute(object parameter)
    {
        execute();
    }
}

このアプローチでは、作成したRelayCommandオブジェクトへの参照を保存し、次のようなコマンドを無効にできるようにします。

getProjectListCommand.SetCanExecute(false);
于 2012-11-21T17:30:15.853 に答える
1

RelayCommandを使用する場合、2つの方法を指定できます。最初のメソッドは、コマンドが呼び出されたときに実行するメインメソッドです。検証などのチェックを追加するために使用する2番目のメソッド。これにより、ブール値が返されます。falseが返された場合、mainメソッドは実行されません。

コマンドがバインドされているボタンにどのように影響するか、ブールメソッドを継続的に実行し、falseが返される間、コマンドがバインドされているボタンは無効になります。

したがって、コマンドプロパティでは次のようになります。

public ICommand GetProjectListCommand {
get {
    if (getProjectListCommand == null) {
        getProjectListCommand = new RelayCommand(param => this.ProjectLogin(), CanProjectLogin());
    }
    return getProjectListCommand;
}

新しいメソッドを追加します。

public bool CanProjectLogin()
{
    //here check some properties to make sure everything is set that you'd want to use in your ProjectLogin() method
}

boolメソッドにブレークポイントを設定すると、CanExecuteがどのように機能するかを確認できます。

于 2012-11-21T17:14:56.597 に答える