0

ダイアログ タイプのウィンドウの 2 つのコントロールに同じコマンドを使用したいと考えています。潜在的に興味深い背景として、私は Josh Smith の ViewModel / RelayCommand のアイデアを使用しています。これは、私が WPF を初めて使用し、全体像の観点から実際に理解できるのを初めて見たからです。

したがって、コマンドは ViewModel のプロパティであり、Button の組み込みサポートにより、XAML でコマンドにバインドするのは簡単で簡単です。

<Button ... Command="{Binding Path=PickCommand}"  Content="_Ok"></Button>

ListView では、ダブルクリックでトリガーするように接続された同じコマンドを使用する唯一の方法は、イベント ハンドラーを使用することです。

<ListView ...
              ItemsSource="{Binding Path=AvailableProjects}" 
              SelectedItem="{Binding Path=SelectedProject, Mode=TwoWay}"
              MouseDoubleClick="OnProjectListingMouseDoubleClick"
              >

private void OnProjectListingMouseDoubleClick(object sender, MouseButtonEventArgs e) {
        var vm = (ProjectSelectionViewModel) DataContext;
        vm.Pick(); // execute the pick command
    }

ボタンの方法をバインドすることでこれを行う方法はありますか?

乾杯、
ベリル

<------ 実装 - より良い方法はありますか? --->

あなたの SelectionBehavior クラスは適切でしたが、xaml コードで混乱しました。listViewItem に「スタイル」を設定することで、実行したいコマンドが存在する DataContext の子を取得していました。そのため、ListView 自体に動作を追加しました。

<ListView ...Style="{StaticResource _attachedPickCommand}" >

そして、スタイルをリソース ディクショナリに入れます。

<Style x:Key="_attachedPickCommand" TargetType="ListView">
    <Setter Property="behaviors:SelectionBehavior.DoubleClickCommand" Value="{Binding Path=PickCommand}" />
</Style>

できます!しかし、リストビューのスタイルプロパティを設定するのは「気まずい」です。これは、wpfで視覚的なもの以上のスタイルに慣れていないためですか、それともこれを行うためのより良い方法がありますか?

乾杯、そしてありがとう!
ベリル

4

1 に答える 1

1

はいあります!アタッチされた動作を使用して、コマンドをその動作にバインドできます。

  public class SelectionBehavior {
public static readonly DependencyProperty CommandParameterProperty=
  DependencyProperty.RegisterAttached("CommandParameter", typeof(object), typeof(SelectionBehavior));

public static readonly DependencyProperty DoubleClickCommandProperty=
  DependencyProperty.RegisterAttached("DoubleClickCommand", typeof(ICommand), typeof(SelectionBehavior),
                                      new PropertyMetadata(OnDoubleClickAttached));

private static void OnDoubleClickAttached(DependencyObject d, DependencyPropertyChangedEventArgs e) {
  var fe=(FrameworkElement)d;

  if(e.NewValue!=null && e.OldValue==null) {
    fe.PreviewMouseDown+=fe_MouseDown;
  } else if(e.NewValue==null && e.OldValue!=null) {
    fe.PreviewMouseDown-=fe_MouseDown;
  }
}

private static void fe_MouseDown(object sender, MouseButtonEventArgs e) {
  if(e.ClickCount==2) {
    var dep=(FrameworkElement)sender;

    var command=GetDoubleClickCommand(dep);

    if(command!=null) {
      var param=GetCommandParameter(dep);
      command.Execute(param);
    }
  }
}

public static ICommand GetDoubleClickCommand(FrameworkElement element) {
  return (ICommand)element.GetValue(DoubleClickCommandProperty);
}

public static void SetDoubleClickCommand(FrameworkElement element, ICommand value) {
  element.SetValue(DoubleClickCommandProperty, value);
}

public static object GetCommandParameter(DependencyObject element) {
  return element.GetValue(CommandParameterProperty);
}

public static void SetCommandParameter(DependencyObject element, object value) {
  element.SetValue(CommandParameterProperty, value);
}

}

xaml では、ListView 内のデータを表す ListViewItem のスタイルを設定する必要があります。例

        <ListView>
        <ListView.ItemContainerStyle>
            <Style TargetType="{x:Type ListViewItem}">
                <Setter Property="local:SelectionBehavior.DoubleClickCommand" Value="{Binding Path=DataContext.PickCommand}"/>
                <Setter Property="local:SelectionBehavior.CommandParameter" Value="{Binding Path=DataContext}"/>
            </Style>
        </ListView.ItemContainerStyle>
    </ListView>

添付動作パターンに関する詳細情報は次のとおりです。

于 2009-10-08T22:54:25.590 に答える