2016-08-15 22 views
0

以下はDelegateCommandの非常に単純なPrism.Wpfの例です。ExecuteCanExecuteの両方の代理人があります。プリズム:RaiseCanExecuteChanged()を明示的に呼び出す必要があります

CanExecuteがいくつかのプロパティに依存するとします。 PrismのDelegateCommandは、他のMVVMフレームワークでRelayCommandと同じように、このプロパティが変更されたときに自動的にCanExecuteの状態を再評価しないようです。代わりに、プロパティセッターでRaiseCanExecuteChanged()を明示的に呼び出す必要があります。これにより、些細なビューモデルでも繰り返しコードが多く発生します。

良い方法がありますか?

のViewModel

using System; 
using Prism.Commands; 
using Prism.Mvvm; 

namespace PrismCanExecute.ViewModels 
{ 
public class MainWindowViewModel : BindableBase 
{ 
    private string _title = "Prism Unity Application"; 
    public string Title 
    { 
     get { return _title; } 
     set { SetProperty(ref _title, value); } 
    } 
    private string _name; 
    public string Name 
    { 
     get { return _name; } 
     set 
     { 
      SetProperty(ref _name, value); 

      // Prism doesn't track CanExecute condition changes? 
      // Have to call it explicitly to re-evaluate CanSubmit() 
      // Is there a better way? 
      SubmitCommand.RaiseCanExecuteChanged(); 
     } 
    } 
    public MainWindowViewModel() 
    { 
     SubmitCommand = new DelegateCommand(Submit, CanSubmit); 
    } 

    public DelegateCommand SubmitCommand { get; private set; } 
    private bool CanSubmit() 
    { 
     return (!String.IsNullOrEmpty(Name)); 
    } 
    private void Submit() 
    { 
     System.Windows.MessageBox.Show(Name); 
    } 

} 
} 

ビューは:

<Window x:Class="PrismCanExecute.Views.MainWindow" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    xmlns:prism="http://prismlibrary.com/" 
    Title="{Binding Title}" 
    Width="525" 
    Height="350" 
    prism:ViewModelLocator.AutoWireViewModel="True"> 
<Grid> 
    <!--<ContentControl prism:RegionManager.RegionName="ContentRegion" />--> 
    <StackPanel> 
     <StackPanel Orientation="Horizontal"> 
      <TextBlock Text="Name: " /> 
      <TextBox Width="150" 
        Margin="5" 
        Text="{Binding Name, UpdateSourceTrigger=PropertyChanged}"/> 
     </StackPanel> 
     <StackPanel Orientation="Horizontal" HorizontalAlignment="Center"> 
      <Button Width="50" 
        Command="{Binding SubmitCommand}" 
        Content="Submit" Margin="10"/> 
      <!--<Button Width="50" 
        Content="Cancel" 
        IsCancel="True" Margin="10"/>--> 
     </StackPanel> 
    </StackPanel> 
</Grid> 
</Window> 

答えて

4

@ 103tは説明されていますが、これは署名によるものです。 DelegateCommandに変更のVMプロパティを自動的に監視させたい場合は、delegateCommandのObservesPropertyメソッドをオフにしてください。

var command = new DelegateCommand(Execute).ObservesProperty(()=> Name); 
1

これは仕様によるものです。パフォーマンス関連です。

は、Prism DelegateCommandの代わりに、カスタムメイドのコマンドを使用します。例えば。 this実装はそのトリックを行うようです。しかし、私はそれを使用することをお勧めしません。たくさんのコマンドがあれば、パフォーマンスの問題に遭遇する可能性が非常に高いでしょう。

また、answerを参照してください。

+0

ありがとうございました。私はまた、以下のリンクが非常に有用であることを発見しました:(http://stackoverflow.com/questions/33459183/how-to-make-the-canexecute-trigger-properly-using-prism-6?rq=1) ://stackoverflow.com/questions/33313190/observesproperty-method-isnt-observing-models-properties-at-prism-6) – mechanic

関連する問題