ContextMenu в ListView / GridView - PullRequest
       24

ContextMenu в ListView / GridView

0 голосов
/ 07 марта 2012

Внутри ListView у меня есть GridView, и я пытаюсь настроить его так, чтобы, когда пользователь щелкает правой кнопкой мыши «строку» в ListView, я мог получить доступ к исходному объекту данных.Я думаю, что это часть сетки ViewView ListView, которая делает это немного сложнее.

Я создал образец, который демонстрирует, где у меня возникают трудности.Когда пользователь щелкает правой кнопкой мыши по строке, например Person1, я хотел бы получить доступ к объекту данных PersonClass в обработчике MenuItem_Click.Я пытался играть с PlacementTarget, но все, что я получаю, это нулевые объекты или объекты типа MenuItem.

<Window x:Class="MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="MainWindow" Height="350" Width="525">

    <Window.Resources>        
        <ContextMenu Name="cm" x:Key="TestContextMenu">
            <MenuItem Header="Context1" Click="MenuItem_Click"/>
            <MenuItem Header="Context2"/>
            <MenuItem Header="Context3"/>
        </ContextMenu>
    </Window.Resources>

    <Grid>
        <ListView Margin="20" Name="TestListView" SelectionMode="Multiple">

            <ListView.ItemContainerStyle>
                <Style TargetType="ListViewItem">
                    <Setter Property="ContextMenu" Value="{StaticResource TestContextMenu}" />
                </Style>
            </ListView.ItemContainerStyle>

            <ListView.View>
                <GridView>
                    <GridViewColumn Header="FirstName" Width="200" DisplayMemberBinding="{Binding Path=FirstName}"/>
                    <GridViewColumn Header="Surname" Width="200" DisplayMemberBinding="{Binding Path=Surname}"/>
                </GridView>
            </ListView.View>

        </ListView>
    </Grid>

</Window>

Код:

Class MainWindow 

    Private Sub Window_Loaded(sender As System.Object, e As System.Windows.RoutedEventArgs) Handles MyBase.Loaded

        Dim Person1 As New PersonClass("John", "Fletcher")
        Dim Person2 As New PersonClass("Bob", "Smith")

        Dim ListOfPersons As New List(Of PersonClass)
        ListOfPersons.Add(Person1)
        ListOfPersons.Add(Person2)

        TestListView.ItemsSource = ListOfPersons

    End Sub

    Private Sub MenuItem_Click(sender As System.Object, e As System.Windows.RoutedEventArgs)

        MsgBox(e.OriginalSource.ToString)
        MsgBox(sender.ToString)
        MsgBox(e.Source.ToString)


    End Sub

End Class


Public Class PersonClass

    Private _firstName As String
    Private _surname As String

    Public Property FirstName() As String
        Get
            Return _firstName
        End Get
        Set(ByVal Value As String)
            _firstName = Value
        End Set
    End Property

    Public Property Surname() As String
        Get
            Return _surname
        End Get
        Set(ByVal Value As String)
            _surname = Value
        End Set
    End Property

    Public Sub New()
    End Sub

    Public Sub New(FirstName As String, Surname As String)
        Me.FirstName = FirstName
        Me.Surname = Surname
    End Sub

End Class

Ответы [ 2 ]

0 голосов
/ 08 марта 2012

Я наконец получил PlacementTarget для работы, вот код ниже. Причина, по которой выбранный элемент оказался бесполезным, состоит в том, что если элемент уже выбран, и при щелчке по нему правой кнопкой мыши строка становится невыбранной.

Измените Window.Resources из исходного поста на:

<Window.Resources>
    <ContextMenu Name="cm" x:Key="TestContextMenu" >
        <MenuItem Header="Context1" Click="MenuItem_Click" >
            <MenuItem.DataContext>
                <Binding RelativeSource="{RelativeSource AncestorType={x:Type ContextMenu}}" Path="PlacementTarget.DataContext"/>
            </MenuItem.DataContext>
        </MenuItem>
        <MenuItem Header="Context2"/>
        <MenuItem Header="Context3"/>
    </ContextMenu>
</Window.Resources>

и

Private Sub MenuItem_Click(sender As System.Object, e As System.Windows.RoutedEventArgs)

    Dim MenuI As New MenuItem
    MenuI = TryCast(sender, MenuItem)

    Dim APerson As New PersonClass
    APerson = MenuI.DataContext

    MsgBox(APerson.FirstName)

End Sub
0 голосов
/ 07 марта 2012

Если я правильно вас понял, этот простой код должен сработать (в случае MenuItem_Click).Также обратите внимание, что явного приведения не требуется, поскольку каждый элемент уже представляет экземпляр PersonClass:

If TestListView.SelectedItem IsNot Nothing Then
    Dim person As PersonClass = TestListView.SelectedItem
    //Do something with "person"
Else
    MsgBox("No item selected!")
End If

Обратите внимание, что вы установили режим выбора на несколько, с этим кодом в коде будет использоваться только первый элемент,Для нескольких предметов используйте этот код:

If TestListView.SelectedItems.Count > 0 Then
    For Each person As PersonClass In TestListView.SelectedItems
        //Do something with "person"
    Next
End If

Надеюсь, это поможет!

...