C++ 在Qt5中的多个弹出窗口小部件上接收鼠标EnterEvent和LeaveEvent

C++ 在Qt5中的多个弹出窗口小部件上接收鼠标EnterEvent和LeaveEvent,c++,qt,qt5,C++,Qt,Qt5,从Qt4.8移植到5.4之后,我遇到了下一个问题。。。 当我显示设置了Qt::Popup标志的多个小部件时,只有第一个小部件可以接收鼠标enterEvent或leaveEvent 在4.8.0版本中,所有弹出窗口小部件在鼠标进入或离开时都会做出反应 这是Qt5的正常现象还是一些错误 在下面的代码中,只有第一个弹出窗口小部件w1在鼠标移动时报告enterEvent和leaveEvent。如果未设置Qt::Popup标志,则所有窗口小部件报告 class PopupWidget : public Q

从Qt4.8移植到5.4之后,我遇到了下一个问题。。。 当我显示设置了
Qt::Popup
标志的多个小部件时,只有第一个小部件可以接收鼠标
enterEvent
leaveEvent

在4.8.0版本中,所有弹出窗口小部件在鼠标进入或离开时都会做出反应

这是Qt5的正常现象还是一些错误

在下面的代码中,只有第一个弹出窗口小部件w1在鼠标移动时报告
enterEvent
leaveEvent
。如果未设置
Qt::Popup
标志,则所有窗口小部件报告

class PopupWidget : public QWidget
{
Q_OBJECT
public:
    explicit PopupWidget( QWidget *parent = 0):QWidget(parent)
    {
    setWindowFlags( windowFlags() | Qt::Popup );
    setAutoFillBackground( true );
    setFixedSize( 100, 100 );
    }

protected:
    void    enterEvent(QEvent * event)
    { qDebug() << "enterEvent"; }

    void    leaveEvent(QEvent * event)
    { qDebug() << "leaveEvent"; }
};

void main()
{
    PopupWidget w1, w2, w3;

    w1.move( mapToGlobal(QPoint(0,0)) );
    w1.show();

    w2.move( mapToGlobal(QPoint(110,0)) );
    w2.show();

    w3.move( mapToGlobal(QPoint(220,0)) );
    w3.show();
}
classpopuwidget:publicqwidget
{
Q_对象
公众:
显式PopuWidget(QWidget*parent=0):QWidget(parent)
{
setWindowFlags(windowFlags()| Qt::Popup);
setAutoFillBackground(真);
设置固定大小(100100);
}
受保护的:
无效事件(QEvent*事件)

{qDebug()同样的问题。在Qt5中,似乎不能同时使用多个弹出窗口。如果在弹出窗口中打开弹出窗口,即使按钮的标准悬停效果也会停止工作。我开始使用
Qt::Tool
而不是
Qt::popup
,以避免此问题

在窗口构造函数中(我使用
QFrame
作为基类):

打开窗口:

QFrame::show();
QApplication::setActiveWindow (this);
处理聚焦事件:

bool event (QEvent * e)
{ if(e->type() == QEvent::WindowDeactivate) hide();
  return QFrame::event (e);
}
全局事件过滤器,用于捕获由控制盘引起的聚焦事件(将其安装在主窗口上):

bool事件过滤器(QObject*obj,QEvent*e)
{如果(e->type()==QEvent::Wheel)
{QWidget*w=qobject_cast(obj);
QWidget*aw=QApplication::activeWindow();
如果(w&&!w->isActiveWindow()&&aw!=m_主窗口)aw->hide();
}
返回QObject::eventFilter(obj,e);
}

我使用了类似的方法,并且效果很好,但是在Windows 10上出现了一个奇怪的错误,当你:-显示小部件-隐藏它-转到平板电脑模式-返回正常模式-小部件再次显示(但没有收到showEvent()或任何东西).我正试图找到一种方法,通过使用Qt::Popup仍然可以获取其他小部件上的事件,而且似乎我需要使用我自己的鼠标低级钩子来知道鼠标何时在小部件上…不过这似乎有点过火了。
bool event (QEvent * e)
{ if(e->type() == QEvent::WindowDeactivate) hide();
  return QFrame::event (e);
}
bool eventFilter (QObject * obj, QEvent * e)
{ if(e->type() == QEvent::Wheel)
  { QWidget * w = qobject_cast <QWidget*> (obj);
    QWidget * aw = QApplication::activeWindow();
    if(w && !w->isActiveWindow() && aw != m_MainWindow) aw->hide();
  }
  return QObject::eventFilter (obj, e);
}