0
votes

How to change ListBox and ListView selection rule as same way as WinForms?

In WPF, if already an item is selected in ListBox/ListView, even an empty area of the List is clicked, the selection is still remained. In WinForm/MFC, the selection is unselected when an empty area is clicked.

That is very useful especially for implementation-wise.

For example, when user double-clicked an item in ListBox, one of preferable behaviors is followings: -If user double-clicked an item, it is shortcut to modify the item, so configuration dialog will be opened. -If user double-clicked an empty are, it is shortcut to add an new item, so file selection dialog will be opened.

To implement this behavior, using hit-test to find clicked item would be preferable. But, since hit-test in WPF is not so easy to use comparing with WinForm, the easiest way is just checking selected item whenever user double-clicked the List.

It worked the application is made by WinForm/MFC, but not WPF because of the behavior difference of list item selection.

Is there any way to change list item selection to same way as WinForm/MFC? Or, should I choose different way to implement above behavior?

1

1 Answers

1
votes

The following listbox sample distinguishes between double clicks on item and listbox.

XAML:

<Window x:Class="ListBoxTest.Window1"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="Window1" Height="300" Width="300">

    <ListBox 
        ItemsSource="{Binding Path=Data}" 
        MouseDoubleClick="OnListBoxMouseDoubleClick">
        <ListBox.Resources>
            <Style x:Key="{x:Type ListBoxItem}" TargetType="{x:Type ListBoxItem}">
                <EventSetter Event="PreviewMouseDoubleClick" Handler="OnItemPreviewMouseDoubleClick" />
            </Style>
        </ListBox.Resources>
    </ListBox>

</Window>

Code behind:

using System;
using System.Collections.Generic;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Input;

namespace ListBoxTest
{
    public partial class Window1 : Window
    {
        public Window1()
        {
            InitializeComponent();

            Data = new List<string>() { "AAA", "BBB", "CCC" };
            DataContext = this;
        }

        public List<string> Data { get; private set; }

        private void OnListBoxMouseDoubleClick(object sender, MouseButtonEventArgs e)
        {
            MessageBox.Show("Add new item");
        }

        private void OnItemPreviewMouseDoubleClick(object sender, MouseButtonEventArgs e)
        {
            string content = (sender as ListBoxItem).Content as string;
            MessageBox.Show("Edit " + content);
        }
    }
}