ScrollViewer im gesamten Fenster per Mausrad bedienen

  • WPF

Es gibt 3 Antworten in diesem Thema. Der letzte Beitrag () ist von eichseinet.

    ScrollViewer im gesamten Fenster per Mausrad bedienen

    Hallo zusammen!

    In dem Projekt befindet sich ein Scrollviewer, darin ein Stackpanel und darin Listboxen. Soweit funktioniert auch alles. Leider lässt sich mit der Maus aber nur scrollen, wenn der Cursor über dem Scrollbalken steht. Was muss man ändern, um bei beliebiger Cursorposition im Stackpanel per Mausrad zu scrollen?
    Weil's ja nicht um die DataTemplates geht, hier ein vereinfachtes Beispiel, wie es aufgebaut ist.

    XML-Quellcode

    1. <ScrollViewer HorizontalScrollBarVisibility="Auto" VerticalScrollBarVisibility="Auto" Grid.Row="1" Grid.ColumnSpan="12">
    2. <StackPanel Grid.ColumnSpan="12">
    3. <ListBox x:Name="IC_01" ItemsSource="{Binding Coll_normPC}" Grid.ColumnSpan="12"/>
    4. <ListBox x:Name="IC_02" ItemsSource="{Binding Coll_vidpc}" Grid.ColumnSpan="12"/>
    5. <ListBox x:Name="IC_03" ItemsSource="{Binding Coll_TVPC}" Grid.ColumnSpan="12"/>
    6. </StackPanel>
    7. </ScrollViewer>


    Gruß
    eddi

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „eichseinet“ ()

    eichseinet schrieb:

    um bei beliebiger Cursorposition im Stackpanel


    Damit wärst du dann über einer ListBox und jede hat einen eigenen ScrollViewer welcher dann benutzt wird. Entweder Scrollst du die ListBox oder den ScrollViewer.
    Überdenke vielleicht das Design. 3 ListBoxen in einem Stackpanel erscheint mir nicht sinnvoll.
    Rechtschreibfehler betonen den künstlerischen Charakter des Autors.
    Ich weiss schon, dass es an den Listboxen liegt. (wusste auch, dass es nicht lange dauert, bis jemand drauf kommt, dass man es so nicht macht :) )
    Es sollen Daten aus 3 Listen von 3 Rechnern auf einer Seite anzeigt werden. Mit 3 Itemscontrols ginge es, aber dann lässt sich nix markieren. Ich hatte gehofft man könne irgendwie auch über den Listboxen mit dem Mausrad auf den Scrollviewer gugreifen; vielleicht über einen Mouseover-Trigger? Aber was tun im Trigger?
    Der Scrollviewer in den Listboxen wurde schon testweise auf deaktiviert gestellt; leider ohne Erfolg.

    Gruß
    eddi
    Lösung endlich gefunden;

    XAML

    XML-Quellcode

    1. <ListBox PreviewMouseWheel="ScrollViewer_PreviewMouseWheel">


    im Codebehind

    VB.NET-Quellcode

    1. Private Sub ScrollViewer_PreviewMouseWheel(ByVal sender As Object, ByVal e As MouseWheelEventArgs)
    2. If TypeOf sender Is ListBox AndAlso Not e.Handled Then
    3. e.Handled = True
    4. Dim eventArg = New MouseWheelEventArgs(e.MouseDevice, e.Timestamp, e.Delta)
    5. eventArg.RoutedEvent = UIElement.MouseWheelEvent
    6. eventArg.Source = sender
    7. Dim parent = TryCast((CType(sender, Control)).Parent, UIElement)
    8. parent.[RaiseEvent](eventArg)
    9. End If
    10. End Sub


    Nachdem ich mich heute morgen mehr auf die Deaktivierung der Scrollfunktion in der Listbox konzentriert habe, statt auf die Aktivierung des Scrollviewers fürs gesamte Fenster kam das dann zum Vorschein. Das Event vom Mausrad wird abgefangen und an das Parent-Element der Listbox weitergeleitet. (wenn ich alles richtig verstehe, lasse mich da gern korrigieren) Und dann klappt's auch mit dem Scrollen. :)
    Lässt sich bestimmt auch über ein AttachedProperty lösen, statt wie beschrieben über den CodeBehind. Das überleg ich mir noch.

    Nachtrag: Für alle die es auch lieber als AttachedProperty einbinden möchten:

    Spoiler anzeigen

    XML-Quellcode

    1. <ListBox ItemsSource="{Binding Coll_vidpc}" local:AP_Mausrad.Mausrad=""/>


    Spoiler anzeigen

    VB.NET-Quellcode

    1. Public Class AP_Mausrad
    2. Public Shared Function GetMausrad(ByVal element As ListBox) As Object
    3. If element Is Nothing Then
    4. Throw New ArgumentNullException("element")
    5. End If
    6. Return element.GetValue(MausradProperty)
    7. End Function
    8. Public Shared Sub SetMausrad(ByVal element As ListBox, ByVal value As Object)
    9. If element Is Nothing Then
    10. Throw New ArgumentNullException("element")
    11. End If
    12. element.SetValue(MausradProperty, value)
    13. End Sub
    14. Public Shared ReadOnly MausradProperty As _
    15. DependencyProperty = DependencyProperty.RegisterAttached("Mausrad",
    16. GetType(Object), GetType(AP_Mausrad),
    17. New PropertyMetadata(Nothing, AddressOf Mausrad_weiterleiten))
    18. Private Shared Sub Mausrad_weiterleiten(d As DependencyObject, e As DependencyPropertyChangedEventArgs)
    19. Dim MyListbox = DirectCast(d, ListBox)
    20. AddHandler MyListbox.PreviewMouseWheel, Sub(sender As Object, ev As MouseWheelEventArgs)
    21. If TypeOf sender Is ListBox AndAlso Not ev.Handled Then
    22. ev.Handled = True
    23. Dim eventArg = New MouseWheelEventArgs(ev.MouseDevice, ev.Timestamp, ev.Delta)
    24. eventArg.RoutedEvent = UIElement.MouseWheelEvent
    25. eventArg.Source = sender
    26. Dim parent = TryCast(CType(sender, Control).Parent, UIElement)
    27. parent.[RaiseEvent](eventArg)
    28. End If
    29. End Sub
    30. End Sub
    31. End Class


    Die bösen (deutschen) Wörter könnt ihr bei Bedarf ja selbst austauschen. :)

    Gruß
    eddi

    Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von „eichseinet“ ()