Bezdepbonusu7Программирование: статьи и ответы

Вопрос

Отключить выбор WPF TreeView (или TreeViewItem)?

Автор вопроса: Shimmy WeitzhandlerОтветов: 8

Есть ли хороший способ (кроме повторного создания всего TreeViewItem.Template) отключить выделение в TreeView?

Я в основном ищу стиль ItemsControl для TreeView (ItemsControl - лучшее применение для "отключения" выбора на ListBox, прочтите this сообщение)

  • Вот еще один подход: stackoverflow.com/questions/1398559/ 26.04.2011

wpfxamlselectiontreeviewitemscontrol

Ответы

Ответ 1 · рейтинг 1 · Daniel Rose

Каждый раз, когда элемент выбран, вы можете "отменить выбор". Бывший. измените код из http://www.codeproject.com/KB/WPF/TreeView_SelectionWPF.aspx или используйте подход MVVM (см. http://www.codeproject.com/KB/WPF/TreeViewWithViewModel.aspx) и всегда возвращать IsSelected значение false.

Ответ 2 · рейтинг 21 · Morten Strand

Попробуй это:

<Trigger Property="HasItems" Value="true">
   <Setter Property="Focusable" Value="false" />
</Trigger>

Ответ 3 · рейтинг 4 · Balki

Основываясь на ссылках на принятый в настоящее время ответ, я реализовал это в своем проекте:

<ListView.ItemContainerStyle>
    <Style TargetType="{x:Type ListViewItem}">
        <Setter Property="IsSelected" Value="{Binding IsSelected, Mode=TwoWay}" />
    </Style>
</ListView.ItemContainerStyle>

Также работает для TreeViewItem. И в модели представления:

protected bool _DisableSelection;
private bool _IsSelected;
public bool IsSelected
{
    get { return _IsSelected; }
    set
    {
        if (value == _IsSelected) return;
        _IsSelected = _DisableSelection ? false : value;
        NotifyPropertyChanged();
    }
}

Теперь тебе не нужно идти на охоту!

Ответ 4 · рейтинг 3 · Shimmy Weitzhandler

Это помогло мне (на основе этого ответа, но не привязанного к элементу - выбор вообще отключен):

<TreeView>
  <TreeView.ItemContainerStyle>
    <Style TargetType="TreeViewItem">
      <Setter Property="Focusable" Value="False" />
    </Style>
  </TreeView.ItemContainerStyle>
</TreeView>

Ответ 5 · рейтинг 1 · Shimmy Weitzhandler

Я решил написать многоразовое поведение HTH:

Namespace Components
  Public NotInheritable Class TreeViewBehavior

    Public Shared Function GetIsTransparent(
      ByVal element As TreeViewItem) As Boolean
      If element Is Nothing Then Throw New ArgumentNullException("element")
      Return element.GetValue(IsTransparentProperty)
    End Function
    Public Shared Sub SetIsTransparent(ByVal element As TreeViewItem,
                                       ByVal value As Boolean)
      If element Is Nothing Then Throw New ArgumentNullException("element")
      element.SetValue(IsTransparentProperty, value)
    End Sub
    Public Shared ReadOnly IsTransparentProperty As DependencyProperty =
      DependencyProperty.RegisterAttached("IsTransparent", GetType(Boolean),
        GetType(TreeViewBehavior),
        New FrameworkPropertyMetadata(False,
          AddressOf IsTransparent_PropertyChanged))
    Private Shared Sub IsTransparent_PropertyChanged(
      ByVal sender As Object, ByVal e As DependencyPropertyChangedEventArgs)
      Dim tvi = DirectCast(sender, TreeViewItem)
      Dim isTransparent = CBool(e.NewValue)

      If isTransparent Then
        AddHandler tvi.Selected, AddressOf tvi_Selected
      Else
        RemoveHandler tvi.Selected, AddressOf tvi_Selected
      End If
    End Sub
    Private Shared Sub tvi_Selected(ByVal sender As Object,
                                    ByVal e As RoutedEventArgs)
      Dim treeViewItem = DirectCast(sender, TreeViewItem)
      If Not treeViewItem.IsSelected Then Exit Sub

      treeViewItem.Dispatcher.Invoke(
        Sub(tvi As TreeViewItem) tvi.IsSelected = False,
        System.Windows.Threading.DispatcherPriority.Send,
        treeViewItem)
    End Sub

  End Class
End Namespace

Использование:

<Window xmlns:components="clr-namespace:WpfApplication.Components">
  <TreeView>
    <TreeView.ItemContainerStyle>
      <Style TargetType="TreeViewItem">
        <Setter
          Property="components:TreeViewBehavior.IsTransparent"
          Value="True" />
      </Style>
    </TreeView.ItemContainerStyle>
  </TreeView>
</Window>

Ответ 6 · рейтинг 1 · CongoTM

Я пробовал это, и у меня это сработало. Потому что у меня простое, а не динамическое древовидное представление. Но я думаю, что это может сработать, если оформить его в стиле

<TreeViewItem ... Focusable="False" IsSelected="False"/>

Ответ 7 · рейтинг 1 · Henrik Bøgelund Lavstsen

Я просто снял выделение с TreeViewItems по мере их выбора. Я использую TreeView только один раз. Однако, если бы я добавил это в нескольких местах, я бы подумал о том, чтобы добавить это в Attached Behavior.

Xaml:

<TreeView SelectedItemChanged="TreeView_SelectionChanged">

Код позади:

private void TreeView_SelectionChanged(object sender, RoutedEventArgs e)
{
    if (!(sender is TreeView myTreeView)) return;
    var selectedItem = (TreeViewItem)myTreeView.SelectedItem;
    if (selectedItem == null) return;
    selectedItem.IsSelected = false;
}

Ответ 8 · Danield

Я сделал это иначе, чем принятый ответ:

Допустим, у вас есть свойство в вашей ViewModel (скажем, ShouldPreventSelection). Теперь, когда ShouldPreventSelection имеет значение true, вы хотите, чтобы выбор был отключен:

В вашем TreeView запустите событие PreviewSelected следующим образом:

<TreeView Name="TreeView1"
     ...
     PreviewSelected="TreeView1_PreviewSelected"
     ..
/>

Затем в выделенном коде вы можете следующее:

private void TreeView1_PreviewSelected(object sender, RoutedEventArgs e)
{
    MyViewModel myViewModel = TreeView1.DataContext as MyViewModel;
    if (myViewModel == null)
    {
        return;
    }
    if (myViewModel .ShouldPreventSelection)
    {
        e.Handled = true;
    }

}

Перевод вопроса и ответов сообщества Stack Overflow, лицензия CC BY-SA. Оригинал на Stack Overflow.

Похожие материалы