Warm tip: This article is reproduced from stackoverflow.com, please click
c# wpf

MouseDown Event for overlapping elements (Rectangle)

发布于 2020-04-07 10:10:57

I try to trigger both click events when I am clicking on the overlapping area (yellow marked). Currently when I am click on this area only the front element calls the function.

Rectangles

    <Rectangle Height="100" Width="100" MouseDown="Button_Click" StrokeThickness="1" Stroke="Black" Fill="Transparent" />
    <Rectangle Height="100" Width="100" Margin="396,209,297.6,111" MouseDown="Button_Click_1" StrokeThickness="1" Stroke="Black" Fill="Transparent"/>

    private void Button_Click(object sender, RoutedEventArgs e)
    {
        MessageBox.Show("Button_Click");
    }

    private void Button_Click_1(object sender, RoutedEventArgs e)
    {
        MessageBox.Show("Button_Click_1");
    }

Maybe someone can help. Thanks!

Questioner
user23623447
Viewed
60
Ribaz 2020-01-31 22:26

This may help you

<Canvas x:Name="canvas1" PreviewMouseDown="canvas1_PreviewMouseDown">
    <Rectangle Height="100" Tag="Rectangle1" Width="100"  StrokeThickness="1" Stroke="Black" Fill="Transparent" />
    <Rectangle Height="100" Tag="Rectangle2" Width="100" Margin="60,60,297.6,111"  StrokeThickness="1" Stroke="Black" Fill="Transparent"/>
</Canvas>

The back code:

        private List<HitTestResult> hitResultsList = new List<HitTestResult>();

        private void canvas1_PreviewMouseDown(object sender, MouseButtonEventArgs e)
        {
            if (canvas1.Children.Count > 0)
            {
                // Retrieve the coordinates of the mouse position.
                Point pt = e.GetPosition((UIElement)sender);

                // Clear the contents of the list used for hit test results.
                hitResultsList.Clear();

                // Set up a callback to receive the hit test result enumeration.
                VisualTreeHelper.HitTest(canvas1,
                                    new HitTestFilterCallback(MyHitTestFilter),
                                    new HitTestResultCallback(MyHitTestResult),
                                    new PointHitTestParameters(pt));

                // Perform actions on the hit test results list.
                if (hitResultsList.Count > 0)
                {
                    string msg = null;
                    foreach (HitTestResult htr in hitResultsList)
                    {
                        Rectangle r = (Rectangle)htr.VisualHit;
                        msg += r.Tag.ToString() + "\n";
                    }
                    //Message displaying the tag of all the rectangles 
                    //under the mouse when it was clicked.
                    MessageBox.Show(msg);
                }
            }
        }

        // Filter the hit test values for each object in the enumeration.
        private HitTestFilterBehavior MyHitTestFilter(DependencyObject o)
        {
            // Test for the object value you want to filter.
            if (o.GetType() == typeof(Label))
            {
                // Visual object and descendants are NOT part of hit test results enumeration.
                return HitTestFilterBehavior.ContinueSkipSelfAndChildren;
            }
            else
            {
                // Visual object is part of hit test results enumeration.
                return HitTestFilterBehavior.Continue;
            }
        }

        // Add the hit test result to the list of results.
        private HitTestResultBehavior MyHitTestResult(HitTestResult result)
        {
            //Filter out the canvas object.
            if (!result.VisualHit.ToString().Contains("Canvas"))
            {
                hitResultsList.Add(result);
            }
            // Set the behavior to return visuals at all z-order levels.
            return HitTestResultBehavior.Continue;
        }

Here is the result:

enter image description here