4#include <qohosapplicationstatetracker.h>
6#include <QtCore/private/qohoslogger_p.h>
7#include <QtGui/private/qguiapplication_p.h>
8#include <QtGui/qwindow.h>
10#include <qohosplatformwindow.h>
11#include <qohosutils.h>
12#include <qpa/qwindowsysteminterface_p.h>
13#include <render/qohosview.h>
22using WindowSystemEventType = QWindowSystemInterfacePrivate::EventType;
23using WindowSystemEvent = QWindowSystemInterfacePrivate::WindowSystemEvent;
24using WindowStateChangedEvent = QWindowSystemInterfacePrivate::WindowStateChangedEvent;
25using FocusWindowEvent = QWindowSystemInterfacePrivate::FocusWindowEvent;
26using ExposeEvent = QWindowSystemInterfacePrivate::ExposeEvent;
27using ApplicationStateChangedEvent = QWindowSystemInterfacePrivate::ApplicationStateChangedEvent;
35class ApplicationStateTracker
final :
public QWindowSystemEventHandler
43 ProcessEventResult processApplicationStateChangedEvent(ApplicationStateChangedEvent *event);
45 void startTrackingViewIfNeeded(
QOhosView *view);
46 void tryUpdateApplicationState();
48 std::set<QOhosView *> m_trackedViews;
49 std::set<QOhosView *> m_visibleViews;
50 std::set<QOhosView *> m_activeViews;
52 QOhosOptional<Qt::ApplicationState> m_lastReceivedApplicationState;
53 QOhosOptional<Qt::ApplicationState> m_lastSentApplicationState;
54 QObject m_signalReceiver;
59 auto *platformWindow = QOhosPlatformWindow::fromQWindowOrNull(window);
60 return platformWindow !=
nullptr
61 ? platformWindow->ownedViewOrNull()
65ProcessEventResult ApplicationStateTracker::processWindowStateChangedEvent(WindowStateChangedEvent *evt)
67 auto *view = evt->window !=
nullptr
68 ? mapQWindowToViewOrNull(evt->window)
74 startTrackingViewIfNeeded(view);
76 if (evt->newState.testFlag(Qt::WindowState::WindowActive))
77 std::ignore = m_activeViews.insert(view);
79 std::ignore = m_activeViews.erase(view);
86 auto *view = evt->window !=
nullptr
87 ? mapQWindowToViewOrNull(evt->window)
93 startTrackingViewIfNeeded(view);
96 std::ignore = m_visibleViews.insert(view);
98 std::ignore = m_visibleViews.erase(view);
103ProcessEventResult ApplicationStateTracker::processApplicationStateChangedEvent(ApplicationStateChangedEvent *evt)
105 auto state = evt->newState;
106 m_lastReceivedApplicationState = state;
110bool ApplicationStateTracker::
sendEvent(WindowSystemEvent *event)
113 switch (event->type) {
114 case WindowSystemEventType::WindowStateChanged:
115 processEventResult = processWindowStateChangedEvent(
static_cast<WindowStateChangedEvent *>(event));
117 case WindowSystemEventType::Expose:
118 processEventResult = processExposeEvent(
static_cast<ExposeEvent *>(event));
120 case WindowSystemEventType::ApplicationStateChanged:
121 processEventResult = processApplicationStateChangedEvent(
static_cast<ApplicationStateChangedEvent *>(event));
129 QGuiApplicationPrivate::processWindowSystemEvent(event);
131 bool hasPendingEvents = QWindowSystemInterfacePrivate::windowSystemEventsQueued();
132 if (!hasPendingEvents)
133 tryUpdateApplicationState();
138void ApplicationStateTracker::tryUpdateApplicationState()
140 bool allWindowsInactive = m_activeViews.empty();
141 bool allWindowsHidden = m_visibleViews.empty();
143 auto updatedApplicationState =
144 m_lastReceivedApplicationState == Qt::ApplicationSuspended
145 ? Qt::ApplicationSuspended
147 ? Qt::ApplicationHidden
149 ? Qt::ApplicationInactive
150 : Qt::ApplicationActive;
152 if (m_lastSentApplicationState == updatedApplicationState)
155 m_lastSentApplicationState = updatedApplicationState;
156 ApplicationStateChangedEvent eventToSend{updatedApplicationState};
157 QGuiApplicationPrivate::processWindowSystemEvent(&eventToSend);
160void ApplicationStateTracker::startTrackingViewIfNeeded(
QOhosView *viewToTrack)
163 std::tie(std::ignore, added) = m_trackedViews.insert(viewToTrack);
166 viewToTrack, &QOhosView::destroyed,
167 &m_signalReceiver, [
this, viewToTrack](QObject *) {
168 std::ignore = m_trackedViews.erase(viewToTrack);
169 std::ignore = m_visibleViews.erase(viewToTrack);
170 std::ignore = m_activeViews.erase(viewToTrack);
179 return std::make_shared<ApplicationStateTracker>();
std::enable_if_t< qohosplugincore_h_detail::isQOhosOptional< QOhosInvokeResult< Func, T > >, QOhosInvokeResult< Func, T > > andThen(Func &&func) const
bool sendEvent(WindowSystemEvent *event) override
Combined button and popup list for selecting options.
@ ForwardToGuiApplication
QOhosView * mapQWindowToViewOrNull(QWindow *window)
std::shared_ptr< QWindowSystemEventHandler > makeApplicationStateTracker()