2010-12-29 6 views
5

Mam PreviewMouseDown wydarzenie na TreeView w celu ustalenia, czy użytkownik może wybrać inny element na podstawie niektórych logiki. Po zmianie danych bieżącego elementu pojawi się komunikat MessageBox, który zapyta użytkownika, czy chce odrzucić zmiany. jeśli użytkownik naciśnie klawisz YES, ustawię e.Handled = false;, aby włączyć nowy wybór. a jeśli użytkownik naciśnie klawisz NIE, ustawię e.Handled = true;, aby anulować nowy wybór.WPF zatrzymać routingu zdarzenia, gdy pojawi się MessageBox?

Problem polega na tym, że chociaż ustawiłem e.Handled = false, zatrzymanie zdarzenia i brak zdarzenia wyboru na TreeView. Ktoś ma na to rozwiązanie?

Z góry dziękuję!

Odpowiedz

3

Zmiana ostrości w oknie komunikatu anuluje zdarzenie polegające na przyciąganiu myszką, więc nie ma znaczenia, czy jest obsługiwane, czy nie. Ponieważ wiesz, który element użytkownik próbował wybrać przed wyświetleniem okna komunikatu, po prostu wybierz ten element programowo, jeśli użytkownik naciśnie klawisz YES.

+0

Ale nie wiem, który element użytkownik próbował wybrać. Mam tylko MouseEventArgs. Masz pomysł, jak zdobyć ten przedmiot lub zarejestrować się w SelectedItemChanged? – yossharel

+1

Użyj tej techniki, aby uzyskać DataContext: http://stackoverflow.com/questions/1092639/in-wpf-how-do-i-get-the-data-object-associated-to-tree-view-item -Poniżej, a następnie użyj SelectedItems.Add() –

+0

MouseEventArgs.Source powie ci obiekt, który został kliknięty. Robiłem coś podobnego z TabItems (wyświetlając okno dialogowe, gdy użytkownik wybrał inną kartę), a poprawka polegała na ustawieniu myTabControl.SelectedItem = e.Source. – TarkaDaal

1

Zdaję sobie sprawę, że jest to stare pytanie, ale pomyślałem, że dodam odpowiedź.

Właściwie, @yossharel, wiesz, który element użytkownik próbował wybrać, z MouseEventArgs. Musisz spojrzeć na e.OriginalSource (prawdopodobnie TextBlock), na co kliknął użytkownik. Jako taki ma DataContext.

Ustawia więc SelectedItem drzewa TreeView jako e.OriginalSource.DataContext.

W VB, można być wyraźna lub dorozumiana: myTreeView.SelectedItem = CType (e.OriginalSource, TextBlock) .DataContext() myTreeView.SelectedItem = e.OriginalSource.DataContext()

W języku C#, będziesz musiał określić typ e.OriginalSource. Zrób to, umieszczając punkt przerwania i zobacz, co Studio mówi, że jest. W tym przykładzie: myTreeView.SelectedItem = ((TextBlock) e.OriginalSource). DataContext()

Oto przykład z mojego własnego kodu. W moim przypadku jest to DataGrid zamiast TreeView, ale powinien działać tak samo. Używam tego kodu, aby zapytać użytkownika, czy są niezapisane zmiany na wybranym elemencie. Jeśli użytkownik odpowie "Tak" na "Kontynuuj bez zapisywania?" kod jest kontynuowany z nowym wyborem. W przeciwnym razie niech Message Box zablokuje RoutedEvent, zapobiegając uruchomieniu zdarzenia SelectionChanged.

Private Sub dgDataGrid_PreviewMouseLeftButtonDown(sender As Object, e As System.Windows.Input.MouseButtonEventArgs) Handles dgDataGrid.PreviewMouseLeftButtonDown 
    If dgDataGrid.SelectedItem IsNot Nothing Then 
     If MyDataContext.ExternalViewModel.ItemIsModified Then 
      Dim prompt As String = String.Format("Changes have not been saved.{0}{0}Continue without saving?", vbCrLf) 
      Dim title As String = "Changes Not Saved" 
      Dim result As MsgBoxResult = MsgBox(prompt, MsgBoxStyle.Exclamation Or MsgBoxStyle.YesNo, title) 
      If result = MsgBoxResult.Yes Then 
       dgDataGrid.SelectedItem = e.OriginalSource.DataContext() 
      End If 
     End If 
    End If 
End Sub 

Private Sub dgDataGrid_SelectionChanged(sender As System.Object, e As System.Windows.Controls.SelectionChangedEventArgs) Handles dgDataGrid.SelectionChanged 
    MyDataContext.SetSearchItem(dgDataGrid.SelectedItem) 
End Sub 
Powiązane problemy