File indexing completed on 2024-04-28 16:44:32
0001 /* 0002 * SPDX-FileCopyrightText: 2014 Martin Gräßlin <mgraesslin@kde.org> 0003 * 0004 * SPDX-License-Identifier: LGPL-2.1-only OR LGPL-3.0-only OR LicenseRef-KDE-Accepted-LGPL 0005 */ 0006 #include "../src/decoratedclient.h" 0007 #include "../src/decorationsettings.h" 0008 #include "mockbridge.h" 0009 #include "mockbutton.h" 0010 #include "mockclient.h" 0011 #include "mockdecoration.h" 0012 #include "mocksettings.h" 0013 #include <QSignalSpy> 0014 #include <QStyleHints> 0015 #include <QTest> 0016 0017 Q_DECLARE_METATYPE(Qt::MouseButton) 0018 0019 class DecorationButtonTest : public QObject 0020 { 0021 Q_OBJECT 0022 private Q_SLOTS: 0023 void testButton(); 0024 void testChecked(); 0025 void testEnabled(); 0026 void testPressIgnore_data(); 0027 void testPressIgnore(); 0028 void testReleaseIgnore_data(); 0029 void testReleaseIgnore(); 0030 void testHoverEnterIgnore_data(); 0031 void testHoverEnterIgnore(); 0032 void testHoverLeaveIgnore_data(); 0033 void testHoverLeaveIgnore(); 0034 void testHover(); 0035 void testMouseMove_data(); 0036 void testMouseMove(); 0037 void testClose(); 0038 void testMinimize(); 0039 void testQuickHelp(); 0040 void testKeepAbove(); 0041 void testKeepBelow(); 0042 void testShade(); 0043 void testMaximize(); 0044 void testOnAllDesktops(); 0045 void testMenu(); 0046 void testMenuDoubleClick(); 0047 void testMenuPressAndHold(); 0048 void testApplicationMenu(); 0049 void testContains_data(); 0050 void testContains(); 0051 }; 0052 0053 void DecorationButtonTest::testButton() 0054 { 0055 MockBridge bridge; 0056 MockDecoration mockDecoration(&bridge); 0057 // create a custom button and verify the base settings 0058 MockButton button(KDecoration2::DecorationButtonType::Custom, &mockDecoration); 0059 QCOMPARE(button.decoration().data(), &mockDecoration); 0060 const MockButton &constRef(button); 0061 QCOMPARE(constRef.decoration().data(), &mockDecoration); 0062 QCOMPARE(button.type(), KDecoration2::DecorationButtonType::Custom); 0063 QCOMPARE(button.acceptedButtons(), Qt::MouseButtons(Qt::LeftButton)); 0064 QCOMPARE(button.isCheckable(), false); 0065 QCOMPARE(button.isChecked(), false); 0066 QCOMPARE(button.isEnabled(), true); 0067 QCOMPARE(button.isHovered(), false); 0068 QCOMPARE(button.isPressed(), false); 0069 QCOMPARE(button.isVisible(), true); 0070 QCOMPARE(button.size(), QSizeF(0, 0)); 0071 QCOMPARE(button.geometry(), QRectF()); 0072 0073 // test setting the geometry 0074 QSignalSpy geometryChangedSpy(&button, &KDecoration2::DecorationButton::geometryChanged); 0075 QVERIFY(geometryChangedSpy.isValid()); 0076 // setting to default geometry shouldn't change 0077 button.setGeometry(QRectF()); 0078 QCOMPARE(button.geometry(), QRectF()); 0079 QCOMPARE(geometryChangedSpy.count(), 0); 0080 // setting to a proper geometry should change 0081 const QRectF testGeometry = QRectF(0, 0, 10, 20); 0082 button.setGeometry(testGeometry); 0083 QCOMPARE(button.geometry(), testGeometry); 0084 QCOMPARE(button.size(), testGeometry.size()); 0085 QCOMPARE(geometryChangedSpy.count(), 1); 0086 QCOMPARE(geometryChangedSpy.first().first().toRectF(), testGeometry); 0087 0088 // test changing visibility 0089 QSignalSpy visibilityChangedSpy(&button, &KDecoration2::DecorationButton::visibilityChanged); 0090 QVERIFY(visibilityChangedSpy.isValid()); 0091 button.setVisible(true); 0092 QCOMPARE(visibilityChangedSpy.count(), 0); 0093 button.setVisible(false); 0094 QCOMPARE(button.isVisible(), false); 0095 QCOMPARE(visibilityChangedSpy.count(), 1); 0096 QCOMPARE(visibilityChangedSpy.first().first().toBool(), false); 0097 } 0098 0099 void DecorationButtonTest::testChecked() 0100 { 0101 MockBridge bridge; 0102 MockDecoration mockDecoration(&bridge); 0103 // create a custom button and verify the base settings 0104 MockButton button(KDecoration2::DecorationButtonType::Custom, &mockDecoration); 0105 button.setGeometry(QRect(0, 0, 10, 10)); 0106 0107 // without being checkable it should not get checked 0108 QSignalSpy checkedChangedSpy(&button, &KDecoration2::DecorationButton::checkedChanged); 0109 QVERIFY(checkedChangedSpy.isValid()); 0110 button.setChecked(true); 0111 QCOMPARE(button.isChecked(), false); 0112 QCOMPARE(checkedChangedSpy.count(), 0); 0113 0114 // now let's set the checkable state 0115 QSignalSpy checkableChangedSpy(&button, &KDecoration2::DecorationButton::checkableChanged); 0116 QVERIFY(checkableChangedSpy.isValid()); 0117 // setting to same should not emit 0118 button.setCheckable(false); 0119 QCOMPARE(checkableChangedSpy.count(), 0); 0120 button.setCheckable(true); 0121 QCOMPARE(button.isCheckable(), true); 0122 QCOMPARE(checkableChangedSpy.count(), 1); 0123 QCOMPARE(checkableChangedSpy.first().first().toBool(), true); 0124 0125 // now it should be possible to check the button 0126 button.setChecked(true); 0127 QCOMPARE(button.isChecked(), true); 0128 QCOMPARE(checkedChangedSpy.count(), 1); 0129 // setting again should not change 0130 button.setChecked(true); 0131 QCOMPARE(button.isChecked(), true); 0132 QCOMPARE(checkedChangedSpy.count(), 1); 0133 // and disable 0134 button.setChecked(false); 0135 QCOMPARE(button.isChecked(), false); 0136 QCOMPARE(checkedChangedSpy.count(), 2); 0137 QCOMPARE(checkedChangedSpy.first().first().toBool(), true); 0138 QCOMPARE(checkedChangedSpy.last().first().toBool(), false); 0139 0140 // last but not least let's disable the checkable again, this should disable a checked button 0141 button.setChecked(true); 0142 QCOMPARE(button.isChecked(), true); 0143 checkedChangedSpy.clear(); 0144 QCOMPARE(checkedChangedSpy.count(), 0); 0145 button.setCheckable(false); 0146 QCOMPARE(button.isCheckable(), false); 0147 QCOMPARE(checkableChangedSpy.count(), 2); 0148 QCOMPARE(checkableChangedSpy.last().first().toBool(), false); 0149 QCOMPARE(button.isChecked(), false); 0150 QCOMPARE(checkedChangedSpy.count(), 1); 0151 } 0152 0153 void DecorationButtonTest::testEnabled() 0154 { 0155 MockBridge bridge; 0156 MockDecoration mockDecoration(&bridge); 0157 // create a custom button and verify the base settings 0158 MockButton button(KDecoration2::DecorationButtonType::Custom, &mockDecoration); 0159 button.setGeometry(QRect(0, 0, 10, 10)); 0160 0161 // enabling has influence on whether the button accepts events, so we need to fake events 0162 QSignalSpy enabledChangedSpy(&button, &KDecoration2::DecorationButton::enabledChanged); 0163 QVERIFY(enabledChangedSpy.isValid()); 0164 // setting to same shouldn't change 0165 button.setEnabled(true); 0166 QCOMPARE(enabledChangedSpy.count(), 0); 0167 button.setEnabled(false); 0168 QCOMPARE(button.isEnabled(), false); 0169 QCOMPARE(enabledChangedSpy.count(), 1); 0170 QCOMPARE(enabledChangedSpy.first().first().toBool(), false); 0171 0172 // now let's send it a hover entered event 0173 QSignalSpy hoveredChangedSpy(&button, &KDecoration2::DecorationButton::hoveredChanged); 0174 QVERIFY(hoveredChangedSpy.isValid()); 0175 QHoverEvent event(QEvent::HoverEnter, QPointF(1, 1), QPointF(-1, -1)); 0176 event.setAccepted(false); 0177 button.event(&event); 0178 QCOMPARE(event.isAccepted(), false); 0179 QCOMPARE(hoveredChangedSpy.count(), 0); 0180 0181 // if we enable the button again we should get a hovered changed signal 0182 button.setEnabled(true); 0183 QCOMPARE(enabledChangedSpy.count(), 2); 0184 QCOMPARE(enabledChangedSpy.last().first().toBool(), true); 0185 button.event(&event); 0186 QCOMPARE(event.isAccepted(), true); 0187 QCOMPARE(hoveredChangedSpy.count(), 1); 0188 QCOMPARE(hoveredChangedSpy.first().first().toBool(), true); 0189 0190 // if we disable the button now we get a hovered disabled signal 0191 button.setEnabled(false); 0192 QCOMPARE(hoveredChangedSpy.count(), 2); 0193 QCOMPARE(hoveredChangedSpy.last().first().toBool(), false); 0194 } 0195 0196 void DecorationButtonTest::testPressIgnore_data() 0197 { 0198 QTest::addColumn<bool>("enabled"); 0199 QTest::addColumn<bool>("visible"); 0200 QTest::addColumn<QPoint>("clickPos"); 0201 QTest::addColumn<Qt::MouseButton>("mouseButton"); 0202 QTest::addColumn<bool>("expectedAccepted"); 0203 0204 QTest::newRow("all-disabled") << false << false << QPoint(0, 0) << Qt::LeftButton << false; 0205 QTest::newRow("enabled") << true << false << QPoint(0, 0) << Qt::LeftButton << false; 0206 QTest::newRow("visible") << false << true << QPoint(0, 0) << Qt::LeftButton << false; 0207 QTest::newRow("outside") << true << true << QPoint(20, 20) << Qt::LeftButton << false; 0208 QTest::newRow("wrong-button") << true << true << QPoint(0, 0) << Qt::RightButton << false; 0209 } 0210 0211 void DecorationButtonTest::testPressIgnore() 0212 { 0213 MockBridge bridge; 0214 MockDecoration mockDecoration(&bridge); 0215 // create a custom button and verify the base settings 0216 MockButton button(KDecoration2::DecorationButtonType::Custom, &mockDecoration); 0217 button.setGeometry(QRect(0, 0, 10, 10)); 0218 button.setAcceptedButtons(Qt::LeftButton); 0219 QSignalSpy pressedSpy(&button, &KDecoration2::DecorationButton::pressed); 0220 QVERIFY(pressedSpy.isValid()); 0221 QSignalSpy pressedChangedSpy(&button, &KDecoration2::DecorationButton::pressedChanged); 0222 QVERIFY(pressedChangedSpy.isValid()); 0223 0224 QFETCH(bool, enabled); 0225 QFETCH(bool, visible); 0226 button.setEnabled(enabled); 0227 button.setVisible(visible); 0228 0229 QFETCH(QPoint, clickPos); 0230 QFETCH(Qt::MouseButton, mouseButton); 0231 QMouseEvent pressEvent(QEvent::MouseButtonPress, clickPos, mouseButton, mouseButton, Qt::NoModifier); 0232 pressEvent.setAccepted(false); 0233 button.event(&pressEvent); 0234 QTEST(pressEvent.isAccepted(), "expectedAccepted"); 0235 QCOMPARE(button.isPressed(), false); 0236 QVERIFY(pressedSpy.isEmpty()); 0237 QVERIFY(pressedChangedSpy.isEmpty()); 0238 } 0239 0240 void DecorationButtonTest::testReleaseIgnore_data() 0241 { 0242 QTest::addColumn<bool>("enabled"); 0243 QTest::addColumn<bool>("visible"); 0244 QTest::addColumn<QPoint>("clickPos"); 0245 QTest::addColumn<Qt::MouseButton>("mouseButton"); 0246 QTest::addColumn<bool>("expectedAccepted"); 0247 QTest::addColumn<bool>("expectedPressed"); 0248 QTest::addColumn<int>("expectedPressedChanged"); 0249 0250 QTest::newRow("all-disabled") << false << false << QPoint(0, 0) << Qt::LeftButton << false << false << 2; 0251 QTest::newRow("enabled") << true << false << QPoint(0, 0) << Qt::LeftButton << false << false << 2; 0252 QTest::newRow("visible") << false << true << QPoint(0, 0) << Qt::LeftButton << false << false << 2; 0253 QTest::newRow("outside") << true << true << QPoint(20, 20) << Qt::LeftButton << true << false << 2; 0254 QTest::newRow("wrong-button") << true << true << QPoint(0, 0) << Qt::RightButton << false << true << 1; 0255 } 0256 0257 void DecorationButtonTest::testReleaseIgnore() 0258 { 0259 MockBridge bridge; 0260 MockDecoration mockDecoration(&bridge); 0261 // create a custom button and verify the base settings 0262 MockButton button(KDecoration2::DecorationButtonType::Custom, &mockDecoration); 0263 button.setGeometry(QRect(0, 0, 10, 10)); 0264 button.setAcceptedButtons(Qt::LeftButton); 0265 button.setEnabled(true); 0266 button.setVisible(true); 0267 QSignalSpy pressedSpy(&button, &KDecoration2::DecorationButton::pressed); 0268 QVERIFY(pressedSpy.isValid()); 0269 QSignalSpy pressedChangedSpy(&button, &KDecoration2::DecorationButton::pressedChanged); 0270 QVERIFY(pressedChangedSpy.isValid()); 0271 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 0272 QVERIFY(clickedSpy.isValid()); 0273 0274 QMouseEvent pressEvent(QEvent::MouseButtonPress, QPoint(0, 0), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 0275 pressEvent.setAccepted(false); 0276 button.event(&pressEvent); 0277 QCOMPARE(pressEvent.isAccepted(), true); 0278 QCOMPARE(button.isPressed(), true); 0279 QCOMPARE(pressedSpy.count(), 1); 0280 QCOMPARE(pressedChangedSpy.count(), 1); 0281 QCOMPARE(pressedChangedSpy.last().first().toBool(), true); 0282 0283 QFETCH(bool, enabled); 0284 QFETCH(bool, visible); 0285 button.setEnabled(enabled); 0286 button.setVisible(visible); 0287 0288 QFETCH(QPoint, clickPos); 0289 QFETCH(Qt::MouseButton, mouseButton); 0290 QMouseEvent releaseEvent(QEvent::MouseButtonRelease, clickPos, mouseButton, Qt::NoButton, Qt::NoModifier); 0291 releaseEvent.setAccepted(false); 0292 button.event(&releaseEvent); 0293 QTEST(releaseEvent.isAccepted(), "expectedAccepted"); 0294 QTEST(button.isPressed(), "expectedPressed"); 0295 QCOMPARE(pressedSpy.count(), 1); 0296 QFETCH(int, expectedPressedChanged); 0297 QCOMPARE(pressedChangedSpy.count(), expectedPressedChanged); 0298 QCOMPARE(pressedChangedSpy.last().first().toBool(), button.isPressed()); 0299 QCOMPARE(clickedSpy.count(), 0); 0300 } 0301 0302 void DecorationButtonTest::testHoverEnterIgnore_data() 0303 { 0304 QTest::addColumn<bool>("enabled"); 0305 QTest::addColumn<bool>("visible"); 0306 QTest::addColumn<QPoint>("enterPos"); 0307 0308 QTest::newRow("all-disabled") << false << false << QPoint(0, 0); 0309 QTest::newRow("enabled") << true << false << QPoint(0, 0); 0310 QTest::newRow("visible") << false << true << QPoint(0, 0); 0311 QTest::newRow("outside") << true << true << QPoint(20, 20); 0312 } 0313 0314 void DecorationButtonTest::testHoverEnterIgnore() 0315 { 0316 MockBridge bridge; 0317 MockDecoration mockDecoration(&bridge); 0318 // create a custom button and verify the base settings 0319 MockButton button(KDecoration2::DecorationButtonType::Custom, &mockDecoration); 0320 button.setGeometry(QRect(0, 0, 10, 10)); 0321 QSignalSpy pointerEnteredSpy(&button, &KDecoration2::DecorationButton::pointerEntered); 0322 QVERIFY(pointerEnteredSpy.isValid()); 0323 QSignalSpy hoveredChangedSpy(&button, &KDecoration2::DecorationButton::hoveredChanged); 0324 QVERIFY(hoveredChangedSpy.isValid()); 0325 0326 QFETCH(bool, enabled); 0327 QFETCH(bool, visible); 0328 button.setEnabled(enabled); 0329 button.setVisible(visible); 0330 0331 QFETCH(QPoint, enterPos); 0332 QHoverEvent enterEvent(QEvent::HoverEnter, enterPos, QPoint()); 0333 enterEvent.setAccepted(false); 0334 button.event(&enterEvent); 0335 QCOMPARE(enterEvent.isAccepted(), false); 0336 QCOMPARE(button.isHovered(), false); 0337 QCOMPARE(pointerEnteredSpy.count(), 0); 0338 QCOMPARE(hoveredChangedSpy.count(), 0); 0339 0340 // send a HoverLeft event should not be processed 0341 button.setEnabled(true); 0342 button.setVisible(true); 0343 QHoverEvent leftEvent(QEvent::HoverLeave, QPoint(20, 20), enterPos); 0344 leftEvent.setAccepted(false); 0345 button.event(&leftEvent); 0346 QCOMPARE(leftEvent.isAccepted(), false); 0347 } 0348 0349 void DecorationButtonTest::testHoverLeaveIgnore_data() 0350 { 0351 QTest::addColumn<bool>("enabled"); 0352 QTest::addColumn<bool>("visible"); 0353 QTest::addColumn<QPoint>("leavePos"); 0354 QTest::addColumn<int>("expectedLeaveCount"); 0355 QTest::addColumn<int>("expectedHoverChangedCount"); 0356 0357 QTest::newRow("all-disabled") << false << false << QPoint(20, 20) << 1 << 2; 0358 QTest::newRow("enabled") << true << false << QPoint(20, 20) << 1 << 2; 0359 QTest::newRow("visible") << false << true << QPoint(20, 20) << 1 << 2; 0360 QTest::newRow("inside") << true << true << QPoint(5, 5) << 0 << 1; 0361 } 0362 0363 void DecorationButtonTest::testHoverLeaveIgnore() 0364 { 0365 MockBridge bridge; 0366 MockDecoration mockDecoration(&bridge); 0367 // create a custom button and verify the base settings 0368 MockButton button(KDecoration2::DecorationButtonType::Custom, &mockDecoration); 0369 button.setGeometry(QRect(0, 0, 10, 10)); 0370 button.setEnabled(true); 0371 button.setVisible(true); 0372 QSignalSpy pointerEnteredSpy(&button, &KDecoration2::DecorationButton::pointerEntered); 0373 QVERIFY(pointerEnteredSpy.isValid()); 0374 QSignalSpy hoveredChangedSpy(&button, &KDecoration2::DecorationButton::hoveredChanged); 0375 QVERIFY(hoveredChangedSpy.isValid()); 0376 QSignalSpy pointerLeavedSpy(&button, &KDecoration2::DecorationButton::pointerLeft); 0377 QVERIFY(pointerLeavedSpy.isValid()); 0378 0379 QHoverEvent enterEvent(QEvent::HoverEnter, QPoint(0, 0), QPoint()); 0380 enterEvent.setAccepted(false); 0381 button.event(&enterEvent); 0382 QCOMPARE(enterEvent.isAccepted(), true); 0383 QCOMPARE(button.isHovered(), true); 0384 QCOMPARE(pointerEnteredSpy.count(), 1); 0385 QCOMPARE(hoveredChangedSpy.count(), 1); 0386 QCOMPARE(hoveredChangedSpy.last().first().toBool(), true); 0387 0388 QFETCH(bool, enabled); 0389 QFETCH(bool, visible); 0390 button.setEnabled(enabled); 0391 button.setVisible(visible); 0392 0393 QFETCH(QPoint, leavePos); 0394 QHoverEvent leftEvent(QEvent::HoverLeave, leavePos, QPoint(0, 0)); 0395 leftEvent.setAccepted(false); 0396 button.event(&leftEvent); 0397 QCOMPARE(leftEvent.isAccepted(), false); 0398 QCOMPARE(pointerEnteredSpy.count(), 1); 0399 QFETCH(int, expectedLeaveCount); 0400 QFETCH(int, expectedHoverChangedCount); 0401 QCOMPARE(pointerLeavedSpy.count(), expectedLeaveCount); 0402 QCOMPARE(hoveredChangedSpy.count(), expectedHoverChangedCount); 0403 QCOMPARE(hoveredChangedSpy.last().first().toBool(), button.isHovered()); 0404 } 0405 0406 void DecorationButtonTest::testHover() 0407 { 0408 MockBridge bridge; 0409 MockDecoration mockDecoration(&bridge); 0410 // create a custom button and verify the base settings 0411 MockButton button(KDecoration2::DecorationButtonType::Custom, &mockDecoration); 0412 button.setGeometry(QRectF(0, 0, 10, 10)); 0413 button.setEnabled(true); 0414 button.setVisible(true); 0415 QSignalSpy pointerEnteredSpy(&button, &KDecoration2::DecorationButton::pointerEntered); 0416 QVERIFY(pointerEnteredSpy.isValid()); 0417 QSignalSpy hoveredChangedSpy(&button, &KDecoration2::DecorationButton::hoveredChanged); 0418 QVERIFY(hoveredChangedSpy.isValid()); 0419 QSignalSpy pointerLeavedSpy(&button, &KDecoration2::DecorationButton::pointerLeft); 0420 QVERIFY(pointerLeavedSpy.isValid()); 0421 0422 QHoverEvent enterEvent(QEvent::HoverEnter, QPoint(0, 0), QPoint()); 0423 enterEvent.setAccepted(false); 0424 button.event(&enterEvent); 0425 QCOMPARE(enterEvent.isAccepted(), true); 0426 QCOMPARE(button.isHovered(), true); 0427 QCOMPARE(pointerEnteredSpy.count(), 1); 0428 QCOMPARE(hoveredChangedSpy.count(), 1); 0429 QCOMPARE(hoveredChangedSpy.last().first().toBool(), true); 0430 0431 // send in a hovermove event - it's passed through, but not used 0432 QHoverEvent moveEvent(QEvent::HoverMove, QPoint(5, 0), QPoint(0, 0)); 0433 moveEvent.setAccepted(false); 0434 button.event(&moveEvent); 0435 QCOMPARE(moveEvent.isAccepted(), false); 0436 0437 QHoverEvent leftEvent(QEvent::HoverLeave, QPointF(10.1, 0.0), QPointF(0, 0)); 0438 leftEvent.setAccepted(false); 0439 button.event(&leftEvent); 0440 QCOMPARE(leftEvent.isAccepted(), true); 0441 QCOMPARE(pointerEnteredSpy.count(), 1); 0442 QCOMPARE(pointerLeavedSpy.count(), 1); 0443 QCOMPARE(hoveredChangedSpy.count(), 2); 0444 QCOMPARE(hoveredChangedSpy.last().first().toBool(), false); 0445 } 0446 0447 void DecorationButtonTest::testMouseMove_data() 0448 { 0449 QTest::addColumn<bool>("enabled"); 0450 QTest::addColumn<bool>("visible"); 0451 QTest::addColumn<QPointF>("movePos"); 0452 QTest::addColumn<bool>("expectedAccepted"); 0453 QTest::addColumn<bool>("expectedHovered"); 0454 QTest::addColumn<int>("expectedChangedCount"); 0455 0456 QTest::newRow("outside") << true << true << QPointF(10.1, 10) << true << false << 2; 0457 QTest::newRow("inside") << true << true << QPointF(5, 5) << false << true << 1; 0458 QTest::newRow("disabled") << false << true << QPointF(10, 10) << false << false << 2; 0459 QTest::newRow("invisible") << true << false << QPointF(10, 10) << false << false << 2; 0460 } 0461 0462 void DecorationButtonTest::testMouseMove() 0463 { 0464 MockBridge bridge; 0465 MockDecoration mockDecoration(&bridge); 0466 // create a custom button and verify the base settings 0467 MockButton button(KDecoration2::DecorationButtonType::Custom, &mockDecoration); 0468 button.setGeometry(QRectF(0, 0, 10, 10)); 0469 button.setEnabled(true); 0470 button.setVisible(true); 0471 QSignalSpy hoveredChangedSpy(&button, &KDecoration2::DecorationButton::hoveredChanged); 0472 QVERIFY(hoveredChangedSpy.isValid()); 0473 QSignalSpy pointerLeavedSpy(&button, &KDecoration2::DecorationButton::pointerLeft); 0474 QVERIFY(pointerLeavedSpy.isValid()); 0475 0476 QHoverEvent enterEvent(QEvent::HoverEnter, QPoint(0, 0), QPoint()); 0477 enterEvent.setAccepted(false); 0478 button.event(&enterEvent); 0479 QCOMPARE(enterEvent.isAccepted(), true); 0480 QCOMPARE(button.isHovered(), true); 0481 QCOMPARE(hoveredChangedSpy.count(), 1); 0482 QCOMPARE(hoveredChangedSpy.last().first().toBool(), true); 0483 0484 QFETCH(bool, enabled); 0485 button.setEnabled(enabled); 0486 QFETCH(bool, visible); 0487 button.setVisible(visible); 0488 0489 QFETCH(QPointF, movePos); 0490 QMouseEvent mouseMoveEvent(QEvent::MouseMove, movePos, Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 0491 mouseMoveEvent.setAccepted(false); 0492 button.event(&mouseMoveEvent); 0493 QTEST(mouseMoveEvent.isAccepted(), "expectedAccepted"); 0494 QTEST(button.isHovered(), "expectedHovered"); 0495 QFETCH(int, expectedChangedCount); 0496 QCOMPARE(hoveredChangedSpy.count(), expectedChangedCount); 0497 QCOMPARE(hoveredChangedSpy.last().first().toBool(), button.isHovered()); 0498 0499 // explicit further move event outside of button 0500 QMouseEvent mouseMoveEvent2(QEvent::MouseMove, QPoint(50, 50), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 0501 mouseMoveEvent2.setAccepted(false); 0502 button.event(&mouseMoveEvent2); 0503 QTEST(mouseMoveEvent2.isAccepted(), "expectedHovered"); 0504 QCOMPARE(button.isHovered(), false); 0505 } 0506 0507 void DecorationButtonTest::testClose() 0508 { 0509 MockBridge bridge; 0510 MockDecoration mockDecoration(&bridge); 0511 MockClient *client = bridge.lastCreatedClient(); 0512 MockButton button(KDecoration2::DecorationButtonType::Close, &mockDecoration); 0513 button.setGeometry(QRect(0, 0, 10, 10)); 0514 0515 QCOMPARE(button.isEnabled(), false); 0516 QCOMPARE(button.isCheckable(), false); 0517 QCOMPARE(button.isChecked(), false); 0518 QCOMPARE(button.isVisible(), true); 0519 QCOMPARE(button.acceptedButtons(), Qt::LeftButton); 0520 0521 // if the client is closeable the button should get enabled 0522 QSignalSpy closeableChangedSpy(mockDecoration.client().toStrongRef().data(), &KDecoration2::DecoratedClient::closeableChanged); 0523 QVERIFY(closeableChangedSpy.isValid()); 0524 client->setCloseable(true); 0525 QCOMPARE(button.isEnabled(), true); 0526 QCOMPARE(closeableChangedSpy.count(), 1); 0527 QCOMPARE(closeableChangedSpy.first().first().toBool(), true); 0528 0529 // clicking the button should trigger a request for close 0530 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 0531 QVERIFY(clickedSpy.isValid()); 0532 QSignalSpy pressedSpy(&button, &KDecoration2::DecorationButton::pressed); 0533 QVERIFY(pressedSpy.isValid()); 0534 QSignalSpy releasedSpy(&button, &KDecoration2::DecorationButton::released); 0535 QVERIFY(releasedSpy.isValid()); 0536 QSignalSpy closeRequestedSpy(client, &MockClient::closeRequested); 0537 QVERIFY(closeRequestedSpy.isValid()); 0538 QSignalSpy pressedChangedSpy(&button, &KDecoration2::DecorationButton::pressedChanged); 0539 QVERIFY(pressedChangedSpy.isValid()); 0540 0541 QMouseEvent pressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 0542 pressEvent.setAccepted(false); 0543 button.event(&pressEvent); 0544 QCOMPARE(pressEvent.isAccepted(), true); 0545 QCOMPARE(button.isPressed(), true); 0546 QCOMPARE(clickedSpy.count(), 0); 0547 QCOMPARE(pressedSpy.count(), 1); 0548 QCOMPARE(releasedSpy.count(), 0); 0549 QCOMPARE(closeRequestedSpy.count(), 0); 0550 QCOMPARE(pressedChangedSpy.count(), 1); 0551 QCOMPARE(pressedChangedSpy.first().first().toBool(), true); 0552 0553 QMouseEvent releaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::LeftButton, Qt::NoButton, Qt::NoModifier); 0554 releaseEvent.setAccepted(false); 0555 button.event(&releaseEvent); 0556 QCOMPARE(releaseEvent.isAccepted(), true); 0557 QCOMPARE(button.isPressed(), false); 0558 QCOMPARE(clickedSpy.count(), 1); 0559 QCOMPARE(clickedSpy.first().first().value<Qt::MouseButton>(), Qt::LeftButton); 0560 QCOMPARE(pressedSpy.count(), 1); 0561 QCOMPARE(releasedSpy.count(), 1); 0562 QVERIFY(closeRequestedSpy.wait()); 0563 QCOMPARE(closeRequestedSpy.count(), 1); 0564 QCOMPARE(pressedChangedSpy.count(), 2); 0565 QCOMPARE(pressedChangedSpy.last().first().toBool(), false); 0566 } 0567 0568 void DecorationButtonTest::testMinimize() 0569 { 0570 MockBridge bridge; 0571 MockDecoration mockDecoration(&bridge); 0572 MockClient *client = bridge.lastCreatedClient(); 0573 MockButton button(KDecoration2::DecorationButtonType::Minimize, &mockDecoration); 0574 button.setGeometry(QRect(0, 0, 10, 10)); 0575 0576 QCOMPARE(button.isEnabled(), false); 0577 QCOMPARE(button.isCheckable(), false); 0578 QCOMPARE(button.isChecked(), false); 0579 QCOMPARE(button.isVisible(), true); 0580 QCOMPARE(button.acceptedButtons(), Qt::LeftButton); 0581 0582 // if the client is minimizeable the button should get enabled 0583 QSignalSpy minimizableChangedSpy(mockDecoration.client().toStrongRef().data(), &KDecoration2::DecoratedClient::minimizeableChanged); 0584 QVERIFY(minimizableChangedSpy.isValid()); 0585 client->setMinimizable(true); 0586 QCOMPARE(button.isEnabled(), true); 0587 QCOMPARE(minimizableChangedSpy.count(), 1); 0588 QCOMPARE(minimizableChangedSpy.first().first().toBool(), true); 0589 0590 // clicking the button should trigger a request for minimize 0591 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 0592 QVERIFY(clickedSpy.isValid()); 0593 QSignalSpy pressedSpy(&button, &KDecoration2::DecorationButton::pressed); 0594 QVERIFY(pressedSpy.isValid()); 0595 QSignalSpy releasedSpy(&button, &KDecoration2::DecorationButton::released); 0596 QVERIFY(releasedSpy.isValid()); 0597 QSignalSpy minimizeRequestedSpy(client, &MockClient::minimizeRequested); 0598 QVERIFY(minimizeRequestedSpy.isValid()); 0599 QSignalSpy pressedChangedSpy(&button, &KDecoration2::DecorationButton::pressedChanged); 0600 QVERIFY(pressedChangedSpy.isValid()); 0601 0602 QMouseEvent pressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 0603 pressEvent.setAccepted(false); 0604 button.event(&pressEvent); 0605 QCOMPARE(pressEvent.isAccepted(), true); 0606 QCOMPARE(button.isPressed(), true); 0607 QCOMPARE(clickedSpy.count(), 0); 0608 QCOMPARE(pressedSpy.count(), 1); 0609 QCOMPARE(releasedSpy.count(), 0); 0610 QCOMPARE(minimizeRequestedSpy.count(), 0); 0611 QCOMPARE(pressedChangedSpy.count(), 1); 0612 QCOMPARE(pressedChangedSpy.first().first().toBool(), true); 0613 0614 QMouseEvent releaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::LeftButton, Qt::NoButton, Qt::NoModifier); 0615 releaseEvent.setAccepted(false); 0616 button.event(&releaseEvent); 0617 QCOMPARE(releaseEvent.isAccepted(), true); 0618 QCOMPARE(button.isPressed(), false); 0619 QCOMPARE(clickedSpy.count(), 1); 0620 QCOMPARE(clickedSpy.first().first().value<Qt::MouseButton>(), Qt::LeftButton); 0621 QCOMPARE(pressedSpy.count(), 1); 0622 QCOMPARE(releasedSpy.count(), 1); 0623 QVERIFY(minimizeRequestedSpy.wait()); 0624 QCOMPARE(minimizeRequestedSpy.count(), 1); 0625 QCOMPARE(pressedChangedSpy.count(), 2); 0626 QCOMPARE(pressedChangedSpy.last().first().toBool(), false); 0627 } 0628 0629 void DecorationButtonTest::testQuickHelp() 0630 { 0631 MockBridge bridge; 0632 MockDecoration mockDecoration(&bridge); 0633 MockClient *client = bridge.lastCreatedClient(); 0634 MockButton button(KDecoration2::DecorationButtonType::ContextHelp, &mockDecoration); 0635 button.setGeometry(QRect(0, 0, 10, 10)); 0636 0637 QCOMPARE(button.isEnabled(), true); 0638 QCOMPARE(button.isCheckable(), false); 0639 QCOMPARE(button.isChecked(), false); 0640 QCOMPARE(button.isVisible(), false); 0641 QCOMPARE(button.acceptedButtons(), Qt::LeftButton); 0642 0643 // if the client provides quickhelp the button should get enabled 0644 QSignalSpy providesContextHelpChangedSpy(mockDecoration.client().toStrongRef().data(), &KDecoration2::DecoratedClient::providesContextHelpChanged); 0645 QVERIFY(providesContextHelpChangedSpy.isValid()); 0646 client->setProvidesContextHelp(true); 0647 QCOMPARE(button.isVisible(), true); 0648 QCOMPARE(providesContextHelpChangedSpy.count(), 1); 0649 QCOMPARE(providesContextHelpChangedSpy.first().first().toBool(), true); 0650 0651 // clicking the button should trigger a request for minimize 0652 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 0653 QVERIFY(clickedSpy.isValid()); 0654 QSignalSpy pressedSpy(&button, &KDecoration2::DecorationButton::pressed); 0655 QVERIFY(pressedSpy.isValid()); 0656 QSignalSpy releasedSpy(&button, &KDecoration2::DecorationButton::released); 0657 QVERIFY(releasedSpy.isValid()); 0658 QSignalSpy quickhelpRequestedSpy(client, &MockClient::quickHelpRequested); 0659 QVERIFY(quickhelpRequestedSpy.isValid()); 0660 QSignalSpy pressedChangedSpy(&button, &KDecoration2::DecorationButton::pressedChanged); 0661 QVERIFY(pressedChangedSpy.isValid()); 0662 0663 QMouseEvent pressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 0664 pressEvent.setAccepted(false); 0665 button.event(&pressEvent); 0666 QCOMPARE(pressEvent.isAccepted(), true); 0667 QCOMPARE(button.isPressed(), true); 0668 QCOMPARE(clickedSpy.count(), 0); 0669 QCOMPARE(pressedSpy.count(), 1); 0670 QCOMPARE(releasedSpy.count(), 0); 0671 QCOMPARE(quickhelpRequestedSpy.count(), 0); 0672 QCOMPARE(pressedChangedSpy.count(), 1); 0673 QCOMPARE(pressedChangedSpy.first().first().toBool(), true); 0674 0675 QMouseEvent releaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::LeftButton, Qt::NoButton, Qt::NoModifier); 0676 releaseEvent.setAccepted(false); 0677 button.event(&releaseEvent); 0678 QCOMPARE(releaseEvent.isAccepted(), true); 0679 QCOMPARE(button.isPressed(), false); 0680 QCOMPARE(clickedSpy.count(), 1); 0681 QCOMPARE(clickedSpy.first().first().value<Qt::MouseButton>(), Qt::LeftButton); 0682 QCOMPARE(pressedSpy.count(), 1); 0683 QCOMPARE(releasedSpy.count(), 1); 0684 QVERIFY(quickhelpRequestedSpy.wait()); 0685 QCOMPARE(quickhelpRequestedSpy.count(), 1); 0686 QCOMPARE(pressedChangedSpy.count(), 2); 0687 QCOMPARE(pressedChangedSpy.last().first().toBool(), false); 0688 } 0689 0690 void DecorationButtonTest::testKeepAbove() 0691 { 0692 MockBridge bridge; 0693 MockDecoration mockDecoration(&bridge); 0694 MockButton button(KDecoration2::DecorationButtonType::KeepAbove, &mockDecoration); 0695 button.setGeometry(QRect(0, 0, 10, 10)); 0696 0697 QCOMPARE(button.isEnabled(), true); 0698 QCOMPARE(button.isCheckable(), true); 0699 QCOMPARE(button.isChecked(), false); 0700 QCOMPARE(button.isVisible(), true); 0701 QCOMPARE(button.acceptedButtons(), Qt::LeftButton); 0702 0703 // clicking the button should trigger a request for keep above changed 0704 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 0705 QVERIFY(clickedSpy.isValid()); 0706 QSignalSpy pressedSpy(&button, &KDecoration2::DecorationButton::pressed); 0707 QVERIFY(pressedSpy.isValid()); 0708 QSignalSpy releasedSpy(&button, &KDecoration2::DecorationButton::released); 0709 QVERIFY(releasedSpy.isValid()); 0710 QSignalSpy keepAboveChangedSpy(mockDecoration.client().toStrongRef().data(), &KDecoration2::DecoratedClient::keepAboveChanged); 0711 QVERIFY(keepAboveChangedSpy.isValid()); 0712 QSignalSpy pressedChangedSpy(&button, &KDecoration2::DecorationButton::pressedChanged); 0713 QVERIFY(pressedChangedSpy.isValid()); 0714 0715 QMouseEvent pressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 0716 pressEvent.setAccepted(false); 0717 button.event(&pressEvent); 0718 QCOMPARE(pressEvent.isAccepted(), true); 0719 QCOMPARE(button.isPressed(), true); 0720 QCOMPARE(clickedSpy.count(), 0); 0721 QCOMPARE(pressedSpy.count(), 1); 0722 QCOMPARE(releasedSpy.count(), 0); 0723 QCOMPARE(keepAboveChangedSpy.count(), 0); 0724 QCOMPARE(pressedChangedSpy.count(), 1); 0725 QCOMPARE(pressedChangedSpy.first().first().toBool(), true); 0726 0727 QMouseEvent releaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::LeftButton, Qt::NoButton, Qt::NoModifier); 0728 releaseEvent.setAccepted(false); 0729 button.event(&releaseEvent); 0730 QCOMPARE(releaseEvent.isAccepted(), true); 0731 QCOMPARE(button.isPressed(), false); 0732 QCOMPARE(clickedSpy.count(), 1); 0733 QCOMPARE(clickedSpy.first().first().value<Qt::MouseButton>(), Qt::LeftButton); 0734 QCOMPARE(pressedSpy.count(), 1); 0735 QCOMPARE(releasedSpy.count(), 1); 0736 QVERIFY(keepAboveChangedSpy.wait()); 0737 QCOMPARE(keepAboveChangedSpy.count(), 1); 0738 QCOMPARE(keepAboveChangedSpy.first().first().toBool(), true); 0739 QCOMPARE(pressedChangedSpy.count(), 2); 0740 QCOMPARE(pressedChangedSpy.last().first().toBool(), false); 0741 QCOMPARE(button.isChecked(), true); 0742 0743 // click once more should change again 0744 button.event(&pressEvent); 0745 button.event(&releaseEvent); 0746 QVERIFY(keepAboveChangedSpy.wait()); 0747 QCOMPARE(keepAboveChangedSpy.count(), 2); 0748 QCOMPARE(keepAboveChangedSpy.first().first().toBool(), true); 0749 QCOMPARE(keepAboveChangedSpy.last().first().toBool(), false); 0750 QCOMPARE(button.isChecked(), false); 0751 } 0752 0753 void DecorationButtonTest::testKeepBelow() 0754 { 0755 MockBridge bridge; 0756 MockDecoration mockDecoration(&bridge); 0757 MockButton button(KDecoration2::DecorationButtonType::KeepBelow, &mockDecoration); 0758 button.setGeometry(QRect(0, 0, 10, 10)); 0759 0760 QCOMPARE(button.isEnabled(), true); 0761 QCOMPARE(button.isCheckable(), true); 0762 QCOMPARE(button.isChecked(), false); 0763 QCOMPARE(button.isVisible(), true); 0764 QCOMPARE(button.acceptedButtons(), Qt::LeftButton); 0765 0766 // clicking the button should trigger a request for keep above changed 0767 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 0768 QVERIFY(clickedSpy.isValid()); 0769 QSignalSpy pressedSpy(&button, &KDecoration2::DecorationButton::pressed); 0770 QVERIFY(pressedSpy.isValid()); 0771 QSignalSpy releasedSpy(&button, &KDecoration2::DecorationButton::released); 0772 QVERIFY(releasedSpy.isValid()); 0773 QSignalSpy keepBelowChangedSpy(mockDecoration.client().toStrongRef().data(), &KDecoration2::DecoratedClient::keepBelowChanged); 0774 QVERIFY(keepBelowChangedSpy.isValid()); 0775 QSignalSpy pressedChangedSpy(&button, &KDecoration2::DecorationButton::pressedChanged); 0776 QVERIFY(pressedChangedSpy.isValid()); 0777 0778 QMouseEvent pressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 0779 pressEvent.setAccepted(false); 0780 button.event(&pressEvent); 0781 QCOMPARE(pressEvent.isAccepted(), true); 0782 QCOMPARE(button.isPressed(), true); 0783 QCOMPARE(clickedSpy.count(), 0); 0784 QCOMPARE(pressedSpy.count(), 1); 0785 QCOMPARE(releasedSpy.count(), 0); 0786 QCOMPARE(keepBelowChangedSpy.count(), 0); 0787 QCOMPARE(pressedChangedSpy.count(), 1); 0788 QCOMPARE(pressedChangedSpy.first().first().toBool(), true); 0789 0790 QMouseEvent releaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::LeftButton, Qt::NoButton, Qt::NoModifier); 0791 releaseEvent.setAccepted(false); 0792 button.event(&releaseEvent); 0793 QCOMPARE(releaseEvent.isAccepted(), true); 0794 QCOMPARE(button.isPressed(), false); 0795 QCOMPARE(clickedSpy.count(), 1); 0796 QCOMPARE(clickedSpy.first().first().value<Qt::MouseButton>(), Qt::LeftButton); 0797 QCOMPARE(pressedSpy.count(), 1); 0798 QCOMPARE(releasedSpy.count(), 1); 0799 QVERIFY(keepBelowChangedSpy.wait()); 0800 QCOMPARE(keepBelowChangedSpy.count(), 1); 0801 QCOMPARE(keepBelowChangedSpy.first().first().toBool(), true); 0802 QCOMPARE(pressedChangedSpy.count(), 2); 0803 QCOMPARE(pressedChangedSpy.last().first().toBool(), false); 0804 QCOMPARE(button.isChecked(), true); 0805 0806 // click once more should change again 0807 button.event(&pressEvent); 0808 button.event(&releaseEvent); 0809 QVERIFY(keepBelowChangedSpy.wait()); 0810 QCOMPARE(keepBelowChangedSpy.count(), 2); 0811 QCOMPARE(keepBelowChangedSpy.first().first().toBool(), true); 0812 QCOMPARE(keepBelowChangedSpy.last().first().toBool(), false); 0813 QCOMPARE(button.isChecked(), false); 0814 } 0815 0816 void DecorationButtonTest::testShade() 0817 { 0818 MockBridge bridge; 0819 MockDecoration mockDecoration(&bridge); 0820 MockClient *client = bridge.lastCreatedClient(); 0821 MockButton button(KDecoration2::DecorationButtonType::Shade, &mockDecoration); 0822 button.setGeometry(QRect(0, 0, 10, 10)); 0823 0824 QCOMPARE(button.isEnabled(), false); 0825 QCOMPARE(button.isCheckable(), true); 0826 QCOMPARE(button.isChecked(), false); 0827 QCOMPARE(button.isVisible(), true); 0828 QCOMPARE(button.acceptedButtons(), Qt::LeftButton); 0829 0830 // if the client is shadeable the button should get enabled 0831 const auto decoClient = mockDecoration.client(); 0832 QSignalSpy shadeableChangedSpy(decoClient.toStrongRef().data(), &KDecoration2::DecoratedClient::shadeableChanged); 0833 QVERIFY(shadeableChangedSpy.isValid()); 0834 client->setShadeable(true); 0835 QCOMPARE(button.isEnabled(), true); 0836 QCOMPARE(shadeableChangedSpy.count(), 1); 0837 QCOMPARE(shadeableChangedSpy.first().first().toBool(), true); 0838 0839 // clicking the button should trigger a request for keep above changed 0840 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 0841 QVERIFY(clickedSpy.isValid()); 0842 QSignalSpy pressedSpy(&button, &KDecoration2::DecorationButton::pressed); 0843 QVERIFY(pressedSpy.isValid()); 0844 QSignalSpy releasedSpy(&button, &KDecoration2::DecorationButton::released); 0845 QVERIFY(releasedSpy.isValid()); 0846 QSignalSpy shadedChangedSpy(decoClient.toStrongRef().data(), &KDecoration2::DecoratedClient::shadedChanged); 0847 QVERIFY(shadedChangedSpy.isValid()); 0848 QSignalSpy pressedChangedSpy(&button, &KDecoration2::DecorationButton::pressedChanged); 0849 QVERIFY(pressedChangedSpy.isValid()); 0850 0851 QMouseEvent pressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 0852 pressEvent.setAccepted(false); 0853 button.event(&pressEvent); 0854 QCOMPARE(pressEvent.isAccepted(), true); 0855 QCOMPARE(button.isPressed(), true); 0856 QCOMPARE(clickedSpy.count(), 0); 0857 QCOMPARE(pressedSpy.count(), 1); 0858 QCOMPARE(releasedSpy.count(), 0); 0859 QCOMPARE(shadedChangedSpy.count(), 0); 0860 QCOMPARE(pressedChangedSpy.count(), 1); 0861 QCOMPARE(pressedChangedSpy.first().first().toBool(), true); 0862 0863 QMouseEvent releaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::LeftButton, Qt::NoButton, Qt::NoModifier); 0864 releaseEvent.setAccepted(false); 0865 button.event(&releaseEvent); 0866 QCOMPARE(releaseEvent.isAccepted(), true); 0867 QCOMPARE(button.isPressed(), false); 0868 QCOMPARE(clickedSpy.count(), 1); 0869 QCOMPARE(clickedSpy.first().first().value<Qt::MouseButton>(), Qt::LeftButton); 0870 QCOMPARE(pressedSpy.count(), 1); 0871 QCOMPARE(releasedSpy.count(), 1); 0872 QVERIFY(shadedChangedSpy.wait()); 0873 QCOMPARE(shadedChangedSpy.count(), 1); 0874 QCOMPARE(shadedChangedSpy.first().first().toBool(), true); 0875 QCOMPARE(pressedChangedSpy.count(), 2); 0876 QCOMPARE(pressedChangedSpy.last().first().toBool(), false); 0877 QCOMPARE(button.isChecked(), true); 0878 0879 // click once more should change again 0880 button.event(&pressEvent); 0881 button.event(&releaseEvent); 0882 QVERIFY(shadedChangedSpy.wait()); 0883 QCOMPARE(shadedChangedSpy.count(), 2); 0884 QCOMPARE(shadedChangedSpy.first().first().toBool(), true); 0885 QCOMPARE(shadedChangedSpy.last().first().toBool(), false); 0886 QCOMPARE(button.isChecked(), false); 0887 } 0888 0889 void DecorationButtonTest::testMaximize() 0890 { 0891 MockBridge bridge; 0892 MockDecoration mockDecoration(&bridge); 0893 MockClient *client = bridge.lastCreatedClient(); 0894 MockButton button(KDecoration2::DecorationButtonType::Maximize, &mockDecoration); 0895 button.setGeometry(QRect(0, 0, 10, 10)); 0896 0897 QCOMPARE(button.isEnabled(), false); 0898 QCOMPARE(button.isCheckable(), true); 0899 QCOMPARE(button.isChecked(), false); 0900 QCOMPARE(button.isVisible(), true); 0901 QCOMPARE(button.acceptedButtons(), Qt::LeftButton | Qt::MiddleButton | Qt::RightButton); 0902 0903 // if the client is maximizable the button should get enabled 0904 const auto decoClient = mockDecoration.client().toStrongRef(); 0905 QSignalSpy maximizableChangedSpy(decoClient.data(), &KDecoration2::DecoratedClient::maximizeableChanged); 0906 QVERIFY(maximizableChangedSpy.isValid()); 0907 client->setMaximizable(true); 0908 QCOMPARE(button.isEnabled(), true); 0909 QCOMPARE(maximizableChangedSpy.count(), 1); 0910 QCOMPARE(maximizableChangedSpy.first().first().toBool(), true); 0911 0912 // clicking the button should trigger a request for keep above changed 0913 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 0914 QVERIFY(clickedSpy.isValid()); 0915 QSignalSpy pressedSpy(&button, &KDecoration2::DecorationButton::pressed); 0916 QVERIFY(pressedSpy.isValid()); 0917 QSignalSpy releasedSpy(&button, &KDecoration2::DecorationButton::released); 0918 QVERIFY(releasedSpy.isValid()); 0919 QSignalSpy maximizedChangedSpy(decoClient.data(), &KDecoration2::DecoratedClient::maximizedChanged); 0920 QVERIFY(maximizedChangedSpy.isValid()); 0921 QSignalSpy maximizedVerticallyChangedSpy(decoClient.data(), &KDecoration2::DecoratedClient::maximizedVerticallyChanged); 0922 QVERIFY(maximizedVerticallyChangedSpy.isValid()); 0923 QSignalSpy maximizedHorizontallyChangedSpy(decoClient.data(), &KDecoration2::DecoratedClient::maximizedHorizontallyChanged); 0924 QVERIFY(maximizedHorizontallyChangedSpy.isValid()); 0925 QSignalSpy pressedChangedSpy(&button, &KDecoration2::DecorationButton::pressedChanged); 0926 QVERIFY(pressedChangedSpy.isValid()); 0927 0928 QMouseEvent leftPressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 0929 leftPressEvent.setAccepted(false); 0930 button.event(&leftPressEvent); 0931 QCOMPARE(leftPressEvent.isAccepted(), true); 0932 QCOMPARE(button.isPressed(), true); 0933 QCOMPARE(clickedSpy.count(), 0); 0934 QCOMPARE(pressedSpy.count(), 1); 0935 QCOMPARE(releasedSpy.count(), 0); 0936 QCOMPARE(maximizedChangedSpy.count(), 0); 0937 QCOMPARE(pressedChangedSpy.count(), 1); 0938 QCOMPARE(pressedChangedSpy.first().first().toBool(), true); 0939 0940 QMouseEvent leftReleaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::LeftButton, Qt::NoButton, Qt::NoModifier); 0941 leftReleaseEvent.setAccepted(false); 0942 button.event(&leftReleaseEvent); 0943 QCOMPARE(leftReleaseEvent.isAccepted(), true); 0944 QCOMPARE(button.isPressed(), false); 0945 QCOMPARE(clickedSpy.count(), 1); 0946 QCOMPARE(clickedSpy.first().first().value<Qt::MouseButton>(), Qt::LeftButton); 0947 QCOMPARE(pressedSpy.count(), 1); 0948 QCOMPARE(releasedSpy.count(), 1); 0949 QVERIFY(maximizedChangedSpy.wait()); 0950 QCOMPARE(maximizedChangedSpy.count(), 1); 0951 QCOMPARE(maximizedChangedSpy.first().first().toBool(), true); 0952 QCOMPARE(pressedChangedSpy.count(), 2); 0953 QCOMPARE(pressedChangedSpy.last().first().toBool(), false); 0954 QCOMPARE(button.isChecked(), true); 0955 0956 // clicking again should set to restored 0957 button.event(&leftPressEvent); 0958 button.event(&leftReleaseEvent); 0959 QVERIFY(maximizedChangedSpy.wait()); 0960 QCOMPARE(maximizedChangedSpy.count(), 2); 0961 QCOMPARE(maximizedChangedSpy.first().first().toBool(), true); 0962 QCOMPARE(maximizedChangedSpy.last().first().toBool(), false); 0963 QCOMPARE(button.isChecked(), false); 0964 0965 // test the other buttons 0966 QMouseEvent rightPressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::RightButton, Qt::RightButton, Qt::NoModifier); 0967 rightPressEvent.setAccepted(false); 0968 button.event(&rightPressEvent); 0969 QCOMPARE(rightPressEvent.isAccepted(), true); 0970 QCOMPARE(button.isPressed(), true); 0971 0972 QMouseEvent middlePressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::MiddleButton, Qt::MiddleButton, Qt::NoModifier); 0973 middlePressEvent.setAccepted(false); 0974 button.event(&middlePressEvent); 0975 QCOMPARE(middlePressEvent.isAccepted(), true); 0976 QCOMPARE(button.isPressed(), true); 0977 0978 QMouseEvent middleReleaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::MiddleButton, Qt::NoButton, Qt::NoModifier); 0979 middleReleaseEvent.setAccepted(false); 0980 button.event(&middleReleaseEvent); 0981 QCOMPARE(middleReleaseEvent.isAccepted(), true); 0982 QVERIFY(maximizedHorizontallyChangedSpy.wait()); 0983 QCOMPARE(button.isPressed(), true); 0984 QCOMPARE(clickedSpy.count(), 3); 0985 QCOMPARE(button.isChecked(), false); 0986 QCOMPARE(client->isMaximizedHorizontally(), true); 0987 QCOMPARE(client->isMaximizedVertically(), false); 0988 0989 QMouseEvent rightReleaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::RightButton, Qt::NoButton, Qt::NoModifier); 0990 rightReleaseEvent.setAccepted(false); 0991 button.event(&rightReleaseEvent); 0992 QCOMPARE(rightReleaseEvent.isAccepted(), true); 0993 QVERIFY(maximizedVerticallyChangedSpy.wait()); 0994 QCOMPARE(button.isPressed(), false); 0995 QCOMPARE(clickedSpy.count(), 4); 0996 QCOMPARE(client->isMaximizedHorizontally(), true); 0997 QCOMPARE(client->isMaximizedVertically(), true); 0998 QCOMPARE(button.isChecked(), true); 0999 } 1000 1001 void DecorationButtonTest::testOnAllDesktops() 1002 { 1003 MockBridge bridge; 1004 auto decoSettings = QSharedPointer<KDecoration2::DecorationSettings>::create(&bridge); 1005 MockDecoration mockDecoration(&bridge); 1006 mockDecoration.setSettings(decoSettings); 1007 MockButton button(KDecoration2::DecorationButtonType::OnAllDesktops, &mockDecoration); 1008 button.setGeometry(QRect(0, 0, 10, 10)); 1009 1010 QCOMPARE(button.isEnabled(), true); 1011 QCOMPARE(button.isCheckable(), true); 1012 QCOMPARE(button.isChecked(), false); 1013 QCOMPARE(button.isVisible(), false); 1014 QCOMPARE(button.acceptedButtons(), Qt::LeftButton); 1015 const auto decoClient = mockDecoration.client().toStrongRef(); 1016 QCOMPARE(decoClient.data()->isOnAllDesktops(), false); 1017 1018 MockSettings *settings = bridge.lastCreatedSettings(); 1019 QVERIFY(settings); 1020 1021 QSignalSpy onAllDesktopsAvailableChangedSpy(decoSettings.data(), &KDecoration2::DecorationSettings::onAllDesktopsAvailableChanged); 1022 QVERIFY(onAllDesktopsAvailableChangedSpy.isValid()); 1023 QSignalSpy visibleChangedSpy(&button, &KDecoration2::DecorationButton::visibilityChanged); 1024 QVERIFY(visibleChangedSpy.isValid()); 1025 1026 settings->setOnAllDesktopsAvailabe(true); 1027 QCOMPARE(onAllDesktopsAvailableChangedSpy.count(), 1); 1028 QCOMPARE(onAllDesktopsAvailableChangedSpy.last().first().toBool(), true); 1029 QCOMPARE(visibleChangedSpy.count(), 1); 1030 QCOMPARE(visibleChangedSpy.last().first().toBool(), true); 1031 1032 // clicking the button should trigger a request for on all desktops 1033 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 1034 QVERIFY(clickedSpy.isValid()); 1035 QSignalSpy pressedSpy(&button, &KDecoration2::DecorationButton::pressed); 1036 QVERIFY(pressedSpy.isValid()); 1037 QSignalSpy releasedSpy(&button, &KDecoration2::DecorationButton::released); 1038 QVERIFY(releasedSpy.isValid()); 1039 QSignalSpy onAllDesktopsChangedSpy(decoClient.data(), &KDecoration2::DecoratedClient::onAllDesktopsChanged); 1040 QVERIFY(onAllDesktopsChangedSpy.isValid()); 1041 QSignalSpy pressedChangedSpy(&button, &KDecoration2::DecorationButton::pressedChanged); 1042 QVERIFY(pressedChangedSpy.isValid()); 1043 1044 QMouseEvent pressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 1045 pressEvent.setAccepted(false); 1046 button.event(&pressEvent); 1047 QCOMPARE(pressEvent.isAccepted(), true); 1048 QCOMPARE(button.isPressed(), true); 1049 QCOMPARE(clickedSpy.count(), 0); 1050 QCOMPARE(pressedSpy.count(), 1); 1051 QCOMPARE(releasedSpy.count(), 0); 1052 QCOMPARE(onAllDesktopsChangedSpy.count(), 0); 1053 QCOMPARE(pressedChangedSpy.count(), 1); 1054 QCOMPARE(pressedChangedSpy.first().first().toBool(), true); 1055 1056 QMouseEvent releaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::LeftButton, Qt::NoButton, Qt::NoModifier); 1057 releaseEvent.setAccepted(false); 1058 button.event(&releaseEvent); 1059 QCOMPARE(releaseEvent.isAccepted(), true); 1060 QCOMPARE(button.isPressed(), false); 1061 QCOMPARE(clickedSpy.count(), 1); 1062 QCOMPARE(clickedSpy.first().first().value<Qt::MouseButton>(), Qt::LeftButton); 1063 QCOMPARE(pressedSpy.count(), 1); 1064 QCOMPARE(releasedSpy.count(), 1); 1065 QVERIFY(onAllDesktopsChangedSpy.wait()); 1066 QCOMPARE(onAllDesktopsChangedSpy.count(), 1); 1067 QCOMPARE(onAllDesktopsChangedSpy.first().first().toBool(), true); 1068 QCOMPARE(pressedChangedSpy.count(), 2); 1069 QCOMPARE(pressedChangedSpy.last().first().toBool(), false); 1070 QCOMPARE(button.isChecked(), true); 1071 } 1072 1073 void DecorationButtonTest::testMenu() 1074 { 1075 MockBridge bridge; 1076 auto decoSettings = QSharedPointer<KDecoration2::DecorationSettings>::create(&bridge); 1077 MockDecoration mockDecoration(&bridge); 1078 mockDecoration.setSettings(decoSettings); 1079 MockClient *client = bridge.lastCreatedClient(); 1080 MockButton button(KDecoration2::DecorationButtonType::Menu, &mockDecoration); 1081 button.setGeometry(QRect(0, 0, 10, 10)); 1082 1083 QCOMPARE(button.isEnabled(), true); 1084 QCOMPARE(button.isCheckable(), false); 1085 QCOMPARE(button.isChecked(), false); 1086 QCOMPARE(button.isVisible(), true); 1087 QCOMPARE(button.acceptedButtons(), Qt::LeftButton | Qt::RightButton); 1088 1089 // clicking the button should trigger a request for menu button 1090 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 1091 QVERIFY(clickedSpy.isValid()); 1092 QSignalSpy pressedSpy(&button, &KDecoration2::DecorationButton::pressed); 1093 QVERIFY(pressedSpy.isValid()); 1094 QSignalSpy releasedSpy(&button, &KDecoration2::DecorationButton::released); 1095 QVERIFY(releasedSpy.isValid()); 1096 QSignalSpy pressedChangedSpy(&button, &KDecoration2::DecorationButton::pressedChanged); 1097 QVERIFY(pressedChangedSpy.isValid()); 1098 QSignalSpy menuRequestedSpy(client, &MockClient::menuRequested); 1099 QVERIFY(menuRequestedSpy.isValid()); 1100 1101 QMouseEvent pressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 1102 pressEvent.setAccepted(false); 1103 button.event(&pressEvent); 1104 QCOMPARE(pressEvent.isAccepted(), true); 1105 QCOMPARE(button.isPressed(), true); 1106 QCOMPARE(clickedSpy.count(), 0); 1107 QCOMPARE(pressedSpy.count(), 1); 1108 QCOMPARE(releasedSpy.count(), 0); 1109 QCOMPARE(menuRequestedSpy.count(), 0); 1110 QCOMPARE(pressedChangedSpy.count(), 1); 1111 QCOMPARE(pressedChangedSpy.first().first().toBool(), true); 1112 1113 QMouseEvent releaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::LeftButton, Qt::NoButton, Qt::NoModifier); 1114 releaseEvent.setAccepted(false); 1115 button.event(&releaseEvent); 1116 QCOMPARE(releaseEvent.isAccepted(), true); 1117 QCOMPARE(button.isPressed(), false); 1118 QCOMPARE(clickedSpy.count(), 1); 1119 QCOMPARE(clickedSpy.first().first().value<Qt::MouseButton>(), Qt::LeftButton); 1120 QCOMPARE(pressedSpy.count(), 1); 1121 QCOMPARE(releasedSpy.count(), 1); 1122 QVERIFY(menuRequestedSpy.wait()); 1123 QCOMPARE(menuRequestedSpy.count(), 1); 1124 QCOMPARE(pressedChangedSpy.count(), 2); 1125 QCOMPARE(pressedChangedSpy.last().first().toBool(), false); 1126 } 1127 1128 void DecorationButtonTest::testMenuDoubleClick() 1129 { 1130 MockBridge bridge; 1131 auto decoSettings = QSharedPointer<KDecoration2::DecorationSettings>::create(&bridge); 1132 MockDecoration mockDecoration(&bridge); 1133 mockDecoration.setSettings(decoSettings); 1134 MockClient *client = bridge.lastCreatedClient(); 1135 MockButton button(KDecoration2::DecorationButtonType::Menu, &mockDecoration); 1136 button.setGeometry(QRect(0, 0, 10, 10)); 1137 1138 MockSettings *settings = bridge.lastCreatedSettings(); 1139 QVERIFY(settings); 1140 QSignalSpy closeOnDoubleClickOnMenuChangedSpy(decoSettings.data(), &KDecoration2::DecorationSettings::closeOnDoubleClickOnMenuChanged); 1141 QVERIFY(closeOnDoubleClickOnMenuChangedSpy.isValid()); 1142 settings->setCloseOnDoubleClickOnMenu(true); 1143 QCOMPARE(closeOnDoubleClickOnMenuChangedSpy.count(), 1); 1144 QCOMPARE(closeOnDoubleClickOnMenuChangedSpy.last().first().toBool(), true); 1145 1146 // button used a queued connection, so we need to run event loop 1147 QCoreApplication::processEvents(); 1148 1149 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 1150 QVERIFY(clickedSpy.isValid()); 1151 QSignalSpy doubleClickedSpy(&button, &KDecoration2::DecorationButton::doubleClicked); 1152 QVERIFY(doubleClickedSpy.isValid()); 1153 QSignalSpy closeRequestedSpy(client, &MockClient::closeRequested); 1154 QVERIFY(closeRequestedSpy.isValid()); 1155 QSignalSpy menuRequestedSpy(client, &MockClient::menuRequested); 1156 QVERIFY(menuRequestedSpy.isValid()); 1157 1158 QMouseEvent pressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 1159 pressEvent.setAccepted(false); 1160 button.event(&pressEvent); 1161 QCOMPARE(pressEvent.isAccepted(), true); 1162 QMouseEvent releaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::LeftButton, Qt::NoButton, Qt::NoModifier); 1163 releaseEvent.setAccepted(false); 1164 button.event(&releaseEvent); 1165 QCOMPARE(releaseEvent.isAccepted(), true); 1166 // should not have emitted a clicked 1167 QCOMPARE(clickedSpy.count(), 0); 1168 QCOMPARE(doubleClickedSpy.count(), 0); 1169 1170 // another press should trigger the double click event 1171 pressEvent.setAccepted(false); 1172 button.event(&pressEvent); 1173 QCOMPARE(pressEvent.isAccepted(), true); 1174 QVERIFY(closeRequestedSpy.wait()); 1175 QCOMPARE(doubleClickedSpy.count(), 1); 1176 QCOMPARE(closeRequestedSpy.count(), 1); 1177 QCOMPARE(menuRequestedSpy.count(), 0); 1178 1179 releaseEvent.setAccepted(false); 1180 button.event(&releaseEvent); 1181 QCOMPARE(releaseEvent.isAccepted(), true); 1182 QCOMPARE(clickedSpy.count(), 0); 1183 // run events 1184 QCoreApplication::processEvents(); 1185 QCOMPARE(closeRequestedSpy.count(), 1); 1186 QCOMPARE(menuRequestedSpy.count(), 0); 1187 1188 // a double click of right button shouldn't trigger the double click event 1189 QMouseEvent rightPressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::RightButton, Qt::RightButton, Qt::NoModifier); 1190 rightPressEvent.setAccepted(false); 1191 button.event(&rightPressEvent); 1192 QCOMPARE(rightPressEvent.isAccepted(), true); 1193 QMouseEvent rightReleaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::RightButton, Qt::NoButton, Qt::NoModifier); 1194 rightReleaseEvent.setAccepted(false); 1195 button.event(&rightReleaseEvent); 1196 QCOMPARE(rightReleaseEvent.isAccepted(), true); 1197 QCOMPARE(clickedSpy.count(), 1); 1198 QVERIFY(menuRequestedSpy.wait()); 1199 QCOMPARE(menuRequestedSpy.count(), 1); 1200 // second click 1201 rightPressEvent.setAccepted(false); 1202 button.event(&rightPressEvent); 1203 QCOMPARE(rightPressEvent.isAccepted(), true); 1204 rightReleaseEvent.setAccepted(false); 1205 button.event(&rightReleaseEvent); 1206 QCOMPARE(rightReleaseEvent.isAccepted(), true); 1207 QCOMPARE(clickedSpy.count(), 2); 1208 QVERIFY(menuRequestedSpy.wait()); 1209 QCOMPARE(menuRequestedSpy.count(), 2); 1210 } 1211 1212 void DecorationButtonTest::testMenuPressAndHold() 1213 { 1214 MockBridge bridge; 1215 auto decoSettings = QSharedPointer<KDecoration2::DecorationSettings>::create(&bridge); 1216 MockDecoration mockDecoration(&bridge); 1217 mockDecoration.setSettings(decoSettings); 1218 MockClient *client = bridge.lastCreatedClient(); 1219 MockButton button(KDecoration2::DecorationButtonType::Menu, &mockDecoration); 1220 button.setGeometry(QRect(0, 0, 10, 10)); 1221 1222 MockSettings *settings = bridge.lastCreatedSettings(); 1223 QVERIFY(settings); 1224 QSignalSpy closeOnDoubleClickOnMenuChangedSpy(decoSettings.data(), &KDecoration2::DecorationSettings::closeOnDoubleClickOnMenuChanged); 1225 QVERIFY(closeOnDoubleClickOnMenuChangedSpy.isValid()); 1226 settings->setCloseOnDoubleClickOnMenu(true); 1227 QCOMPARE(closeOnDoubleClickOnMenuChangedSpy.count(), 1); 1228 QCOMPARE(closeOnDoubleClickOnMenuChangedSpy.last().first().toBool(), true); 1229 1230 // button used a queued connection, so we need to run event loop 1231 QCoreApplication::processEvents(); 1232 1233 QSignalSpy menuRequestedSpy(client, &MockClient::menuRequested); 1234 QVERIFY(menuRequestedSpy.isValid()); 1235 QSignalSpy doubleClickedSpy(&button, &KDecoration2::DecorationButton::doubleClicked); 1236 QVERIFY(doubleClickedSpy.isValid()); 1237 QSignalSpy closeRequestedSpy(client, &MockClient::closeRequested); 1238 QVERIFY(closeRequestedSpy.isValid()); 1239 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 1240 QVERIFY(clickedSpy.isValid()); 1241 1242 // send a press event 1243 QMouseEvent pressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 1244 pressEvent.setAccepted(false); 1245 button.event(&pressEvent); 1246 QCOMPARE(pressEvent.isAccepted(), true); 1247 QCOMPARE(clickedSpy.count(), 0); 1248 1249 // and wait 1250 QVERIFY(menuRequestedSpy.wait()); 1251 QCOMPARE(menuRequestedSpy.count(), 1); 1252 QCOMPARE(clickedSpy.count(), 1); 1253 1254 // send release event 1255 QMouseEvent releaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::LeftButton, Qt::NoButton, Qt::NoModifier); 1256 releaseEvent.setAccepted(false); 1257 button.event(&releaseEvent); 1258 QCOMPARE(releaseEvent.isAccepted(), true); 1259 QCOMPARE(clickedSpy.count(), 1); 1260 1261 QTest::qWait(QGuiApplication::styleHints()->mouseDoubleClickInterval() + 5); 1262 1263 // and it shouldn't be a double click 1264 pressEvent.setAccepted(false); 1265 button.event(&pressEvent); 1266 QCOMPARE(pressEvent.isAccepted(), true); 1267 1268 // while waiting we disable click and hold 1269 settings->setCloseOnDoubleClickOnMenu(false); 1270 QCOMPARE(closeOnDoubleClickOnMenuChangedSpy.count(), 2); 1271 QCOMPARE(closeOnDoubleClickOnMenuChangedSpy.last().first().toBool(), false); 1272 // button used a queued connection, so we need to run event loop 1273 QCoreApplication::processEvents(); 1274 // and releasing should emit the menu signal 1275 releaseEvent.setAccepted(false); 1276 button.event(&releaseEvent); 1277 QCOMPARE(releaseEvent.isAccepted(), true); 1278 QCOMPARE(clickedSpy.count(), 2); 1279 QVERIFY(menuRequestedSpy.wait()); 1280 QCOMPARE(menuRequestedSpy.count(), 2); 1281 // never got a dobule click 1282 QCOMPARE(closeRequestedSpy.count(), 0); 1283 } 1284 1285 void DecorationButtonTest::testApplicationMenu() 1286 { 1287 MockBridge bridge; 1288 auto decoSettings = QSharedPointer<KDecoration2::DecorationSettings>::create(&bridge); 1289 MockDecoration mockDecoration(&bridge); 1290 mockDecoration.setSettings(decoSettings); 1291 MockClient *client = bridge.lastCreatedClient(); 1292 MockButton button(KDecoration2::DecorationButtonType::ApplicationMenu, &mockDecoration); 1293 button.setGeometry(QRect(0, 0, 10, 10)); 1294 1295 QCOMPARE(button.isEnabled(), true); 1296 QCOMPARE(button.isCheckable(), true); 1297 QCOMPARE(button.isChecked(), false); 1298 QCOMPARE(button.isVisible(), true); 1299 QCOMPARE(button.acceptedButtons(), Qt::LeftButton); 1300 1301 // clicking the button should trigger a request for application menu 1302 QSignalSpy clickedSpy(&button, &KDecoration2::DecorationButton::clicked); 1303 QVERIFY(clickedSpy.isValid()); 1304 QSignalSpy pressedSpy(&button, &KDecoration2::DecorationButton::pressed); 1305 QVERIFY(pressedSpy.isValid()); 1306 QSignalSpy releasedSpy(&button, &KDecoration2::DecorationButton::released); 1307 QVERIFY(releasedSpy.isValid()); 1308 QSignalSpy pressedChangedSpy(&button, &KDecoration2::DecorationButton::pressedChanged); 1309 QVERIFY(pressedChangedSpy.isValid()); 1310 QSignalSpy applicationMenuRequestedSpy(client, &MockClient::applicationMenuRequested); 1311 QVERIFY(applicationMenuRequestedSpy.isValid()); 1312 1313 QMouseEvent pressEvent(QEvent::MouseButtonPress, QPointF(5, 5), Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); 1314 pressEvent.setAccepted(false); 1315 button.event(&pressEvent); 1316 QCOMPARE(pressEvent.isAccepted(), true); 1317 QCOMPARE(button.isPressed(), true); 1318 QCOMPARE(clickedSpy.count(), 0); 1319 QCOMPARE(pressedSpy.count(), 1); 1320 QCOMPARE(releasedSpy.count(), 0); 1321 QCOMPARE(applicationMenuRequestedSpy.count(), 0); 1322 QCOMPARE(pressedChangedSpy.count(), 1); 1323 QCOMPARE(pressedChangedSpy.first().first().toBool(), true); 1324 1325 QMouseEvent releaseEvent(QEvent::MouseButtonRelease, QPointF(5, 5), Qt::LeftButton, Qt::NoButton, Qt::NoModifier); 1326 releaseEvent.setAccepted(false); 1327 button.event(&releaseEvent); 1328 QCOMPARE(releaseEvent.isAccepted(), true); 1329 QCOMPARE(button.isPressed(), false); 1330 QCOMPARE(clickedSpy.count(), 1); 1331 QCOMPARE(clickedSpy.first().first().value<Qt::MouseButton>(), Qt::LeftButton); 1332 QCOMPARE(pressedSpy.count(), 1); 1333 QCOMPARE(releasedSpy.count(), 1); 1334 QVERIFY(applicationMenuRequestedSpy.wait()); 1335 QCOMPARE(applicationMenuRequestedSpy.count(), 1); 1336 QCOMPARE(pressedChangedSpy.count(), 2); 1337 QCOMPARE(pressedChangedSpy.last().first().toBool(), false); 1338 } 1339 1340 void DecorationButtonTest::testContains_data() 1341 { 1342 QTest::addColumn<QPointF>("pos"); 1343 QTest::addColumn<bool>("contains"); 1344 1345 // Button geometry: QRectF(0, 0, 10, 10). 1346 QTest::newRow("on left edge") << QPointF(0, 5) << true; 1347 QTest::newRow("on top edge") << QPointF(5, 0) << true; 1348 QTest::newRow("on right edge") << QPointF(9, 5) << true; 1349 QTest::newRow("on bottom edge") << QPointF(5, 9) << true; 1350 QTest::newRow("inside") << QPointF(5, 5) << true; 1351 QTest::newRow("outside 1") << QPointF(-1, 5) << false; 1352 QTest::newRow("outside 2") << QPointF(5, -1) << false; 1353 QTest::newRow("outside 3") << QPointF(10, 5) << false; 1354 QTest::newRow("outside 4") << QPointF(5, 10) << false; 1355 } 1356 1357 void DecorationButtonTest::testContains() 1358 { 1359 MockBridge bridge; 1360 MockDecoration mockDecoration(&bridge); 1361 1362 MockButton button(KDecoration2::DecorationButtonType::Custom, &mockDecoration); 1363 button.setGeometry(QRectF(0, 0, 10, 10)); 1364 button.setEnabled(true); 1365 button.setVisible(true); 1366 1367 QFETCH(QPointF, pos); 1368 QTEST(button.contains(pos), "contains"); 1369 } 1370 1371 QTEST_MAIN(DecorationButtonTest) 1372 #include "decorationbuttontest.moc"