[autotests] New test case to verify cursor changes correctly in effects

The test case verifies that setting an override cursor during mouse
interception works and that it's also possible to change it. When
ending mouse interception the cursor image should be adjusted again.

The test shows that when mouse interception starts KWin should send
a pointer leave event to the current focused window and similar needs
to handle the stop of mouse interception.
This commit is contained in:
Martin Gräßlin 2016-02-25 09:04:29 +01:00
parent b6677ca04e
commit 6d495f1dc9

View file

@ -70,6 +70,7 @@ private Q_SLOTS:
void testMouseActionActiveWindow_data();
void testMouseActionActiveWindow();
void testCursorImage();
void testEffectOverrideCursorImage();
private:
void render(KWayland::Client::Surface *surface, const QSize &size = QSize(100, 50));
@ -856,6 +857,92 @@ void PointerInputTest::testCursorImage()
QVERIFY(!p->cursorImage().isNull());
}
class HelperEffect : public Effect
{
Q_OBJECT
public:
HelperEffect() {}
~HelperEffect() {}
};
void PointerInputTest::testEffectOverrideCursorImage()
{
// this test verifies the effect cursor override handling
using namespace KWayland::Client;
// we need a pointer to get the enter event and set a cursor
auto pointer = m_seat->createPointer(m_seat);
QVERIFY(pointer);
QVERIFY(pointer->isValid());
QSignalSpy enteredSpy(pointer, &Pointer::entered);
QVERIFY(enteredSpy.isValid());
QSignalSpy leftSpy(pointer, &Pointer::left);
QVERIFY(leftSpy.isValid());
// move cursor somewhere the new window won't open
Cursor::setPos(800, 800);
auto p = input()->pointer();
// here we should have the fallback cursor
const QImage fallback = p->cursorImage();
QVERIFY(!fallback.isNull());
// now let's create a window
QSignalSpy clientAddedSpy(waylandServer(), &WaylandServer::shellClientAdded);
QVERIFY(clientAddedSpy.isValid());
Surface *surface = m_compositor->createSurface(m_compositor);
QVERIFY(surface);
ShellSurface *shellSurface = m_shell->createSurface(surface, surface);
QVERIFY(shellSurface);
render(surface);
QVERIFY(clientAddedSpy.wait());
AbstractClient *window = workspace()->activeClient();
QVERIFY(window);
// and move cursor to the window
QVERIFY(!window->geometry().contains(QPoint(800, 800)));
Cursor::setPos(window->geometry().center());
QVERIFY(enteredSpy.wait());
// cursor image should be null
QVERIFY(p->cursorImage().isNull());
// now create an effect and set an override cursor
QScopedPointer<HelperEffect> effect(new HelperEffect);
effects->startMouseInterception(effect.data(), Qt::OpenHandCursor);
const QImage openHand = p->cursorImage();
QVERIFY(!openHand.isNull());
QVERIFY(openHand != fallback);
QEXPECT_FAIL("", "Fix me", Continue);
QVERIFY(leftSpy.wait());
// let's change to arrow cursor, this should be our fallback
effects->defineCursor(Qt::ArrowCursor);
QCOMPARE(p->cursorImage(), fallback);
// back to openhand
effects->defineCursor(Qt::OpenHandCursor);
QCOMPARE(p->cursorImage(), openHand);
// move cursor outside the window area
Cursor::setPos(800, 800);
// and end the override, which should switch to fallback
effects->stopMouseInterception(effect.data());
QEXPECT_FAIL("", "Fix me", Continue);
QCOMPARE(p->cursorImage(), fallback);
// start mouse interception again
effects->startMouseInterception(effect.data(), Qt::OpenHandCursor);
QCOMPARE(p->cursorImage(), openHand);
// move cursor to area of window
Cursor::setPos(window->geometry().center());
// this should not result in an enter event
QVERIFY(!enteredSpy.wait(100));
// after ending the interception we should get an enter event
effects->stopMouseInterception(effect.data());
QEXPECT_FAIL("", "Fix me", Continue);
QVERIFY(enteredSpy.wait());
QVERIFY(p->cursorImage().isNull());
}
}
WAYLANDTEST_MAIN(KWin::PointerInputTest)