如何处理底层 Form 中的 MouseMoveEvent 而不是其中的 Panels?

How to handle the MouseMoveEvent in the underlying Form instead of the Panels inside it?

我有一个用 C# 编写的应用程序,它是一个以幻灯片方式显示信息的目录系统。

在我的 Form 中,我停靠了一个 Panel 来填充表单的内容。在该面板内有 9 个面板,每个面板显示特定对象的信息。

现在我想要的是,每当我移动鼠标时,我都想触发托管面板 的表单的 MouseMoveEvent ,而不是大面板的那些或里面的面板。

这是我处理表单 MouseMoveEvent:

的代码
protected override void OnMouseMove(MouseEventArgs e)
{
    MessageBox.Show("Moved!");
}

我知道这不会触发,因为鼠标光标在面板内,但无论如何如何触发表单上的事件?

这样做的目的是当鼠标光标在窗体中移动时,隐藏当前窗体并显示另一个窗体。有可能吗?

尝试面板上的 "MouseMove" 事件。如果禁用停靠面板,将触发表单的 "MouseMove" 事件。

这个例子对我来说是正确的,程序只在我移动鼠标时调用 TheMouseMoved() 方法。

public partial class Form1 : Form
{
    int counter = 0;
    public Form1()
    {
        GlobalMouseHandler gmh = new GlobalMouseHandler();
        gmh.TheMouseMoved += new MouseMovedEvent(gmh_TheMouseMoved);
        Application.AddMessageFilter(gmh);

        InitializeComponent();
    }

    void gmh_TheMouseMoved()
    {
        Point cur_pos = System.Windows.Forms.Cursor.Position;
        //System.Console.WriteLine(cur_pos);
        System.Console.WriteLine("{0}. [ {1},{2} ]", counter++, (cur_pos.X - this.Location.X), (cur_pos.Y - this.Location.Y));
    }
}

public delegate void MouseMovedEvent();

public class GlobalMouseHandler : IMessageFilter
{
    private const int WM_MOUSEMOVE = 0x0200;

    public event MouseMovedEvent TheMouseMoved;

    #region IMessageFilter Members

    public bool PreFilterMessage(ref Message m)
    {
        if (m.Msg == WM_MOUSEMOVE)
        {
            if (TheMouseMoved != null)
            {
                TheMouseMoved();
            }
        }
        // Always allow message to continue to the next filter control
        return false;
    }

    #endregion
}

我通过修改 How do I capture the mouse move event 的答案解决了这个问题,因为根据@Randy Gamage 的评论,即使鼠标没有移动,接受的答案也在不断触发。

我用这段代码解决了。

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;

namespace GlobalMouseEvents
{
   public partial class Form1 : Form
   {
      public Form1()
      {
         GlobalMouseHandler gmh = new GlobalMouseHandler();
         gmh.TheMouseMoved += new MouseMovedEvent(gmh_TheMouseMoved);
         Application.AddMessageFilter(gmh);

         InitializeComponent();
      }

      void gmh_TheMouseMoved()
      {
         Point cur_pos = System.Windows.Forms.Cursor.Position;
         System.Console.WriteLine(cur_pos);
      }
   }

   public delegate void MouseMovedEvent();

   public class GlobalMouseHandler : IMessageFilter
   {
        private const int WM_MOUSEMOVE = 0x0200;
        private System.Drawing.Point previousMousePosition = new System.Drawing.Point();
        public static event EventHandler<MouseEventArgs> MouseMovedEvent = delegate { };

        #region IMessageFilter Members

        public bool PreFilterMessage(ref System.Windows.Forms.Message m)
        {
            if (m.Msg == WM_MOUSEMOVE)
            {
                System.Drawing.Point currentMousePoint = Control.MousePosition;

                // Prevent event from firing twice.
                if (previousMousePosition == new System.Drawing.Point(0, 0))
                { return; }

                if (previousMousePosition != currentMousePoint)
                {
                    previousMousePosition = currentMousePoint;
                    MouseMovedEvent(this, new MouseEventArgs(MouseButtons.None, 0, currentMousePoint.X, currentMousePoint.Y, 0));
                }
            }
            // Always allow message to continue to the next filter control
            return false;
        }

        #endregion
    }
}