22//
33// SPDX-License-Identifier: GPL-3.0-or-later
44
5- #include < QDebug >
5+ #include < QLoggingCategory >
66
77#include " util.h"
8- #include " xcbthread.h"
98
109#include < QSize>
1110#include < QPixmap>
1211#include < QBitmap>
1312#include < QFileInfo>
1413#include < QtGlobal>
14+ #include < QSocketNotifier>
15+ #include < QCoreApplication>
16+ #include < QAbstractEventDispatcher>
1517
1618#include < X11/Xlib.h>
1719
1820#include < mutex>
1921#include < xcb/res.h>
2022#include < xcb/xcb.h>
23+ #include < xcb/xcb_atom.h>
2124#include < xcb/xtest.h>
2225#include < xcb/xproto.h>
2326#include < xcb/composite.h>
2427
28+ Q_LOGGING_CATEGORY (TRAYUTIL , " org.deepin.dde.trayloader.util" )
29+
2530namespace tray {
2631void clean_xcb_image (void *data)
2732{
@@ -36,7 +41,29 @@ Util* Util::instance()
3641 return _instance;
3742}
3843
44+ void Util::dispatchEvents (DispatchEventsMode mode)
45+ {
46+ xcb_connection_t *connection = m_x11connection;
47+ if (!connection) {
48+ qCWarning (TRAYUTIL , " Attempting to dispatch X11 events with no connection" );
49+ return ;
50+ }
51+
52+ auto pollEventFunc = mode == DispatchEventsMode::Poll ? xcb_poll_for_event : xcb_poll_for_queued_event;
53+
54+ while (xcb_generic_event_t *event = pollEventFunc (connection)) {
55+ qintptr result = 0 ;
56+
57+ QAbstractEventDispatcher *dispatcher = QCoreApplication::eventDispatcher ();
58+ dispatcher->filterNativeEvent (QByteArrayLiteral (" xcb_generic_event_t" ), event, &result);
59+ free (event);
60+ }
61+
62+ xcb_flush (connection);
63+ }
64+
3965Util::Util ()
66+ : QObject()
4067{
4168 m_x11connection = xcb_connect (nullptr , nullptr );
4269 m_display = XOpenDisplay (" " );
@@ -50,8 +77,20 @@ Util::Util()
5077 m_rootWindow = screen->root ;
5178
5279 xcb_ewmh_init_atoms_replies (&m_ewmh, xcb_ewmh_init_atoms (m_x11connection, &m_ewmh), nullptr );
53- m_xcbThread = new XcbThread (m_x11connection);
54- m_xcbThread->start ();
80+
81+ const int fd = xcb_get_file_descriptor (m_x11connection);
82+ QSocketNotifier * qfd = new QSocketNotifier (fd, QSocketNotifier::Read, this );
83+ connect (qfd, &QSocketNotifier::activated, this , [this ](){
84+ dispatchEvents (DispatchEventsMode::Poll);
85+ });
86+
87+ QAbstractEventDispatcher *dispatcher = QCoreApplication::eventDispatcher ();
88+ connect (dispatcher, &QAbstractEventDispatcher::aboutToBlock, this , [this ]() {
89+ dispatchEvents (DispatchEventsMode::EventQueue);
90+ });
91+ connect (dispatcher, &QAbstractEventDispatcher::awake, this , [this ]() {
92+ dispatchEvents (DispatchEventsMode::EventQueue);
93+ });
5594}
5695
5796Util::~Util ()
@@ -143,6 +182,11 @@ QString Util::getNameByAtom(const xcb_atom_t& atom)
143182 return name;
144183}
145184
185+ xcb_atom_t Util::getAtomFromDisplay (const char * name)
186+ {
187+ return getAtomByName (xcb_atom_name_by_screen (name, DefaultScreen (getDisplay ())));
188+ }
189+
146190void Util::moveX11Window (const xcb_window_t & window, const uint32_t & x, const uint32_t & y)
147191{
148192 const uint32_t windowMoveConfigVals[2 ] = {x, y};
0 commit comments