How to capture mousemove events beneath child controls

后端 未结 5 998
粉色の甜心
粉色の甜心 2021-01-18 09:42

I am trying to handle a mouseclick event on a particular form that should fire if the mouse cursor falls between a set of coordinates - lets say a square.

I understa

5条回答
  •  长情又很酷
    2021-01-18 10:10

    I know I'm a bit late to the punch, but I was having troubles with this earlier today when using a Panel as a title bar. I had a label to display some text, a picturebox and a few buttons all nested within the Panel, but I needed to trap the MouseMove event regardless.

    What I decided to do was implement a recursive method handler to do this, as I only had 1 level of nested controls, this may not scale overly well when you start approaching ridiculous levels of nesting.

    Here's how I did it:

        protected virtual void NestedControl_Mousemove(object sender, MouseEventArgs e)
        {
            Control current = sender as Control;
            //you will need to edit this to identify the true parent of your top-level control. As I was writing a custom UserControl, "this" was my title-bar's parent.
            if (current.Parent != this) 
            {
                // Reconstruct the args to get a correct X/Y value.
                // you can ignore this if you never need to get e.X/e.Y accurately.
                MouseEventArgs newArgs = new MouseEventArgs
                (
                    e.Button, 
                    e.Clicks, 
                    e.X + current.Location.X, 
                    e.Y + current.Location.Y, 
                    e.Delta
                );
                NestedControl_Mousemove(current.Parent, newArgs);
            }
            else
            {
                // My "true" MouseMove handler, called at last.
                TitlebarMouseMove(current, e);
            }
        }
    
        //helper method to basically just ensure all the child controls subscribe to the NestedControl_MouseMove event.
        protected virtual void AddNestedMouseHandler(Control root, MouseEventHandler nestedHandler)
        {
            root.MouseMove += new MouseEventHandler(nestedHandler);
            if (root.Controls.Count > 0)
                foreach (Control c in root.Controls)
                    AddNestedMouseHandler(c, nestedHandler);
        }
    

    And then to set it up is relatively simple:

    Define your "true" handler:

        protected virtual void TitlebarMouseMove(object sender, MouseEventArgs e)
        {
            if (e.Button == MouseButtons.Left)
            {
                this.Text = string.Format("({0}, {1})", e.X, e.Y);
            }
        }
    

    And then set up the controls event subscribers:

    //pnlDisplay is my title bar panel.
    AddNestedMouseHandler(pnlDisplay, NestedControl_Mousemove);
    

    Relatively simple to use, and I can vouch for the fact it works :)

提交回复
热议问题