看起来Qt Quick测试要求测试窗口具有焦点,以便发送自己的鼠标和键盘事件。没关系,我只运行一次测试。但是当我尝试运行Qt Quick测试的多个实例时,他们争取窗口焦点,这会导致测试失败。
如何在不关注测试窗口的情况下执行Qt Quick测试?有没有选择强制Qt Quick使用假的鼠标和键盘事件而不是使用真正的窗口系统?如何在没有焦点问题的情况下运行多个Qt Quick测试实例?
答案 0 :(得分:3)
好的,我会咬人。
您可以使用一些C ++事件发布将单个事件重定向到多个QML窗口:
class Dispatcher : public QObject {
Q_OBJECT
public slots:
void click(qreal x, qreal y) {
foreach (QObject * o, objects) {
QMouseEvent * e1 = new QMouseEvent(QEvent::MouseButtonPress, QPointF(x, y), Qt::MouseButton::LeftButton, Qt::MouseButton::LeftButton, Qt::KeyboardModifier::NoModifier);
QCoreApplication::postEvent(o, e1);
QMouseEvent * e2 = new QMouseEvent(QEvent::MouseButtonRelease, QPointF(x, y), Qt::MouseButton::LeftButton, Qt::MouseButton::LeftButton, Qt::KeyboardModifier::NoModifier);
QCoreApplication::postEvent(o, e2);
}
}
void addTarget(QObject * obj) {
objects.append(obj);
}
private:
QObjectList objects;
};
然后创建一个调度程序并将其注册为上下文属性,或者将其注册为QML类型,并在QML中实例化它,并使用它来注册应该接收事件的所有对象。
以下是我编写的快速QML测试,以测试它是否有效:
主窗口包含MouseArea
,它只是将click事件重定向到调度程序。每个额外窗口都包含一个鼠标区域和输出点击坐标的文本,并在调度程序中注册自己。当单击主窗口中的鼠标区域时,调度程序将为两个窗口模拟单击事件,结果其中的文本确认事件确实已分派到窗口并由基础鼠标区域处理。
Window {
id: main
visible: true
width: 300
height: 300
x: 100
y: 100
MouseArea {
anchors.fill: parent
onClicked: Dispatcher.click(mouseX, mouseY)
}
Component {
id: comp
Item {
anchors.fill: parent
Text {
id: txt
}
MouseArea {
id: ma
anchors.fill: parent
onClicked: txt.text = "clicked at " + mouseX + ", " + mouseY
}
}
}
Window {
id: w1
visible: true
width: 300
height: 300
x: 420
y: 100
Loader {
anchors.fill: parent
sourceComponent: comp
}
Component.onCompleted: Dispatcher.addTarget(w1)
}
Window {
id: w2
visible: true
width: 300
height: 300
x: 740
y: 100
Loader {
anchors.fill: parent
sourceComponent: comp
}
Component.onCompleted: Dispatcher.addTarget(w2)
}
}
您可以使用类似的方法将事件从一个窗口重定向到多个窗口,或者为每个窗口生成完全独立的事件序列,您还可以编写事件记录器,然后保存手动触发的事件并在变速项目。你几乎可以做任何事情。同样的方法也适用于键盘事件。此外,您可以在发布事件时从C ++端一次为每个窗口启用焦点。