File indexing completed on 2024-11-10 04:56:25
0001 /* 0002 KWin - the KDE window manager 0003 This file is part of the KDE project. 0004 0005 SPDX-FileCopyrightText: 2013 Martin Gräßlin <mgraesslin@kde.org> 0006 0007 SPDX-License-Identifier: GPL-2.0-or-later 0008 */ 0009 #include "testutils.h" 0010 // KWin 0011 #include "utils/xcbutils.h" 0012 // Qt 0013 #include <QApplication> 0014 #include <QTest> 0015 #include <private/qtx11extras_p.h> 0016 // xcb 0017 #include <xcb/xcb.h> 0018 0019 using namespace KWin; 0020 0021 class TestXcbWindow : public QObject 0022 { 0023 Q_OBJECT 0024 private Q_SLOTS: 0025 void initTestCase(); 0026 void defaultCtor(); 0027 void ctor(); 0028 void classCtor(); 0029 void create(); 0030 void mapUnmap(); 0031 void geometry(); 0032 void destroy(); 0033 void destroyNotManaged(); 0034 }; 0035 0036 void TestXcbWindow::initTestCase() 0037 { 0038 qApp->setProperty("x11RootWindow", QVariant::fromValue<quint32>(QX11Info::appRootWindow())); 0039 qApp->setProperty("x11Connection", QVariant::fromValue<void *>(QX11Info::connection())); 0040 } 0041 0042 void TestXcbWindow::defaultCtor() 0043 { 0044 Xcb::Window window; 0045 QCOMPARE(window.isValid(), false); 0046 xcb_window_t wId = window; 0047 QCOMPARE(wId, noneWindow()); 0048 0049 xcb_window_t nativeWindow = createWindow(); 0050 Xcb::Window window2(nativeWindow); 0051 QCOMPARE(window2.isValid(), true); 0052 wId = window2; 0053 QCOMPARE(wId, nativeWindow); 0054 } 0055 0056 void TestXcbWindow::ctor() 0057 { 0058 const QRect geometry(0, 0, 10, 10); 0059 const uint32_t values[] = {true}; 0060 Xcb::Window window(geometry, XCB_CW_OVERRIDE_REDIRECT, values); 0061 QCOMPARE(window.isValid(), true); 0062 QVERIFY(window != XCB_WINDOW_NONE); 0063 Xcb::WindowGeometry windowGeometry(window); 0064 QCOMPARE(windowGeometry.isNull(), false); 0065 QCOMPARE(windowGeometry.rect(), geometry); 0066 } 0067 0068 void TestXcbWindow::classCtor() 0069 { 0070 const QRect geometry(0, 0, 10, 10); 0071 const uint32_t values[] = {true}; 0072 Xcb::Window window(geometry, XCB_WINDOW_CLASS_INPUT_ONLY, XCB_CW_OVERRIDE_REDIRECT, values); 0073 QCOMPARE(window.isValid(), true); 0074 QVERIFY(window != XCB_WINDOW_NONE); 0075 Xcb::WindowGeometry windowGeometry(window); 0076 QCOMPARE(windowGeometry.isNull(), false); 0077 QCOMPARE(windowGeometry.rect(), geometry); 0078 0079 Xcb::WindowAttributes attribs(window); 0080 QCOMPARE(attribs.isNull(), false); 0081 QVERIFY(attribs->_class == XCB_WINDOW_CLASS_INPUT_ONLY); 0082 } 0083 0084 void TestXcbWindow::create() 0085 { 0086 Xcb::Window window; 0087 QCOMPARE(window.isValid(), false); 0088 xcb_window_t wId = window; 0089 QCOMPARE(wId, noneWindow()); 0090 0091 const QRect geometry(0, 0, 10, 10); 0092 const uint32_t values[] = {true}; 0093 window.create(geometry, XCB_CW_OVERRIDE_REDIRECT, values); 0094 QCOMPARE(window.isValid(), true); 0095 QVERIFY(window != XCB_WINDOW_NONE); 0096 // and reset again 0097 window.reset(); 0098 QCOMPARE(window.isValid(), false); 0099 QVERIFY(window == XCB_WINDOW_NONE); 0100 } 0101 0102 void TestXcbWindow::mapUnmap() 0103 { 0104 const QRect geometry(0, 0, 10, 10); 0105 const uint32_t values[] = {true}; 0106 Xcb::Window window(geometry, XCB_WINDOW_CLASS_INPUT_ONLY, XCB_CW_OVERRIDE_REDIRECT, values); 0107 Xcb::WindowAttributes attribs(window); 0108 QCOMPARE(attribs.isNull(), false); 0109 QVERIFY(attribs->map_state == XCB_MAP_STATE_UNMAPPED); 0110 0111 window.map(); 0112 Xcb::WindowAttributes attribs2(window); 0113 QCOMPARE(attribs2.isNull(), false); 0114 QVERIFY(attribs2->map_state != XCB_MAP_STATE_UNMAPPED); 0115 0116 window.unmap(); 0117 Xcb::WindowAttributes attribs3(window); 0118 QCOMPARE(attribs3.isNull(), false); 0119 QVERIFY(attribs3->map_state == XCB_MAP_STATE_UNMAPPED); 0120 0121 // map, unmap shouldn't fail for an invalid window, it's just ignored 0122 window.reset(); 0123 window.map(); 0124 window.unmap(); 0125 } 0126 0127 void TestXcbWindow::geometry() 0128 { 0129 const QRect geometry(0, 0, 10, 10); 0130 const uint32_t values[] = {true}; 0131 Xcb::Window window(geometry, XCB_WINDOW_CLASS_INPUT_ONLY, XCB_CW_OVERRIDE_REDIRECT, values); 0132 Xcb::WindowGeometry windowGeometry(window); 0133 QCOMPARE(windowGeometry.isNull(), false); 0134 QCOMPARE(windowGeometry.rect(), geometry); 0135 0136 const QRect geometry2(10, 20, 100, 200); 0137 window.setGeometry(geometry2); 0138 Xcb::WindowGeometry windowGeometry2(window); 0139 QCOMPARE(windowGeometry2.isNull(), false); 0140 QCOMPARE(windowGeometry2.rect(), geometry2); 0141 0142 // setting a geometry on an invalid window should be ignored 0143 window.reset(); 0144 window.setGeometry(geometry2); 0145 Xcb::WindowGeometry windowGeometry3(window); 0146 QCOMPARE(windowGeometry3.isNull(), true); 0147 } 0148 0149 void TestXcbWindow::destroy() 0150 { 0151 const QRect geometry(0, 0, 10, 10); 0152 const uint32_t values[] = {true}; 0153 Xcb::Window window(geometry, XCB_CW_OVERRIDE_REDIRECT, values); 0154 QCOMPARE(window.isValid(), true); 0155 xcb_window_t wId = window; 0156 0157 window.create(geometry, XCB_CW_OVERRIDE_REDIRECT, values); 0158 // wId should now be invalid 0159 xcb_generic_error_t *error = nullptr; 0160 UniqueCPtr<xcb_get_window_attributes_reply_t> attribs(xcb_get_window_attributes_reply( 0161 connection(), 0162 xcb_get_window_attributes(connection(), wId), 0163 &error)); 0164 QVERIFY(!attribs); 0165 QCOMPARE(error->error_code, uint8_t(3)); 0166 QCOMPARE(error->resource_id, wId); 0167 free(error); 0168 0169 // test the same for the dtor 0170 { 0171 Xcb::Window scopedWindow(geometry, XCB_CW_OVERRIDE_REDIRECT, values); 0172 QVERIFY(scopedWindow.isValid()); 0173 wId = scopedWindow; 0174 } 0175 error = nullptr; 0176 UniqueCPtr<xcb_get_window_attributes_reply_t> attribs2(xcb_get_window_attributes_reply( 0177 connection(), 0178 xcb_get_window_attributes(connection(), wId), 0179 &error)); 0180 QVERIFY(!attribs2); 0181 QCOMPARE(error->error_code, uint8_t(3)); 0182 QCOMPARE(error->resource_id, wId); 0183 free(error); 0184 } 0185 0186 void TestXcbWindow::destroyNotManaged() 0187 { 0188 Xcb::Window window; 0189 // just destroy the non-existing window 0190 window.reset(); 0191 0192 // now let's add a window 0193 window.reset(createWindow(), false); 0194 xcb_window_t w = window; 0195 window.reset(); 0196 Xcb::WindowAttributes attribs(w); 0197 QVERIFY(attribs); 0198 } 0199 0200 Q_CONSTRUCTOR_FUNCTION(forceXcb) 0201 QTEST_MAIN(TestXcbWindow) 0202 #include "test_xcb_window.moc"