Skip to content

Commit be04e2d

Browse files
committed
Fix bugs of detecting window exposed
1 parent 1644c11 commit be04e2d

File tree

8 files changed

+95
-46
lines changed

8 files changed

+95
-46
lines changed

src/plugins/coreplugin/core/coreinterface.cpp

Lines changed: 20 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -222,20 +222,34 @@ namespace Core {
222222
Q_UNUSED(windowInterface);
223223
}
224224

225-
QQuickWindow *CoreInterface::newFile() {
225+
ProjectWindowInterface *CoreInterface::newFile() {
226226
qCInfo(lcCoreInterface) << "New file";
227227
Internal::ProjectStartupTimerAddOn::startTimer();
228228
// TODO: temporarily creates a project window for testing
229-
auto win = static_cast<QQuickWindow *>(ProjectWindowInterfaceRegistry::instance()->create()->window());
229+
auto windowInterface = ProjectWindowInterfaceRegistry::instance()->create();
230+
auto win = static_cast<QQuickWindow *>(windowInterface->window());
230231
win->show();
231232
if (HomeWindowInterface::instance() && (Internal::BehaviorPreference::startupBehavior() & Internal::BehaviorPreference::SB_CloseHomeWindowAfterOpeningProject)) {
232233
qCInfo(lcCoreInterface) << "Closing home window";
233234
HomeWindowInterface::instance()->quit();
234235
}
235-
connect(win, &QQuickWindow::sceneGraphInitialized, [] {
236-
Internal::CoreAchievementsModel::triggerAchievementCompleted(Internal::CoreAchievementsModel::Achievement_NewProject);
237-
});
238-
return win;
236+
class ExposedListener : public QObject {
237+
public:
238+
explicit ExposedListener(QObject *parent) : QObject(parent) {
239+
}
240+
241+
bool eventFilter(QObject *watched, QEvent *event) override {
242+
if (event->type() == QEvent::Expose && static_cast<QWindow *>(watched)->isExposed()) {
243+
Internal::CoreAchievementsModel::triggerAchievementCompleted(Internal::CoreAchievementsModel::Achievement_NewProject);
244+
deleteLater();
245+
}
246+
return QObject::eventFilter(watched, event);
247+
}
248+
249+
};
250+
auto listener = new ExposedListener(win);
251+
win->installEventFilter(listener);
252+
return windowInterface;
239253
}
240254

241255
bool CoreInterface::openFile(const QString &fileName, QWidget *parent) {

src/plugins/coreplugin/core/coreinterface.h

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,15 @@
1313

1414
class QQmlEngine;
1515
class QJSEngine;
16-
class QQuickWindow;
1716

1817
namespace Core {
1918

2019
namespace Internal {
2120
class CorePlugin;
2221
}
2322

23+
class ProjectWindowInterface;
24+
2425
class CoreInterfacePrivate;
2526

2627
class CORE_EXPORT CoreInterface : public CoreInterfaceBase {
@@ -42,7 +43,7 @@ namespace Core {
4243
Q_INVOKABLE static void showHome();
4344

4445
public:
45-
Q_INVOKABLE static QQuickWindow *newFile();
46+
Q_INVOKABLE static ProjectWindowInterface *newFile();
4647
static bool openFile(const QString &fileName, QWidget *parent = nullptr);
4748

4849
Q_SIGNALS:

src/plugins/coreplugin/internal/addon/projectstartuptimeraddon.cpp

Lines changed: 31 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -43,31 +43,8 @@ namespace Core::Internal {
4343

4444
void ProjectStartupTimerAddOn::extensionsInitialized() {
4545
auto windowInterface = windowHandle()->cast<ProjectWindowInterface>();
46-
auto window = qobject_cast<QQuickWindow *>(windowInterface->window());
47-
Q_ASSERT(window);
48-
connect(window, &QQuickWindow::sceneGraphInitialized, this, [=] {
49-
QTimer::singleShot(0, [=] {
50-
m_finishedMessage = new NotificationMessage(windowInterface->window());
51-
m_finishedMessage->setIcon(SVS::SVSCraft::Success);
52-
auto elapsedTime = stopTimerAndGetElapsedTime();
53-
if (elapsedTime != -1) {
54-
double second = elapsedTime / 1000.0;
55-
m_finishedMessage->setTitle(tr("Project window initialized in %1 seconds").arg(second, 0, 'f', 3));
56-
} else {
57-
m_finishedMessage->setTitle(tr("Project window initialized"));
58-
}
59-
m_finishedMessage->setAllowDoNotShowAgain(notificationVisible());
60-
connect(m_finishedMessage, &NotificationMessage::doNotShowAgainRequested, this, [=] {
61-
setNotificationVisible(false);
62-
m_finishedMessage->setAllowDoNotShowAgain(false);
63-
});
64-
windowInterface->sendNotification(m_finishedMessage, notificationVisible() ? ProjectWindowInterface::AutoHide : ProjectWindowInterface::DoNotShowBubble);
65-
m_initializingMessage->close();
66-
if (elapsedTime > 60000) {
67-
CoreAchievementsModel::triggerAchievementCompleted(CoreAchievementsModel::Achievement_KeepPatient);
68-
}
69-
});
70-
});
46+
auto window = windowInterface->window();
47+
window->installEventFilter(this);
7148
}
7249

7350
bool ProjectStartupTimerAddOn::delayedInitialize() {
@@ -105,4 +82,33 @@ namespace Core::Internal {
10582
settings->endGroup();
10683
return visible;
10784
}
85+
bool ProjectStartupTimerAddOn::eventFilter(QObject *watched, QEvent *event) {
86+
auto windowInterface = windowHandle()->cast<ProjectWindowInterface>();
87+
auto window = windowInterface->window();
88+
if (event->type() == QEvent::Expose && window->isExposed()) {
89+
QTimer::singleShot(0, [=] {
90+
m_finishedMessage = new NotificationMessage(windowInterface->window());
91+
m_finishedMessage->setIcon(SVS::SVSCraft::Success);
92+
auto elapsedTime = stopTimerAndGetElapsedTime();
93+
if (elapsedTime != -1) {
94+
double second = elapsedTime / 1000.0;
95+
m_finishedMessage->setTitle(tr("Project window initialized in %1 seconds").arg(second, 0, 'f', 3));
96+
} else {
97+
m_finishedMessage->setTitle(tr("Project window initialized"));
98+
}
99+
m_finishedMessage->setAllowDoNotShowAgain(notificationVisible());
100+
connect(m_finishedMessage, &NotificationMessage::doNotShowAgainRequested, this, [=] {
101+
setNotificationVisible(false);
102+
m_finishedMessage->setAllowDoNotShowAgain(false);
103+
});
104+
windowInterface->sendNotification(m_finishedMessage, notificationVisible() ? ProjectWindowInterface::AutoHide : ProjectWindowInterface::DoNotShowBubble);
105+
m_initializingMessage->close();
106+
if (elapsedTime > 60000) {
107+
CoreAchievementsModel::triggerAchievementCompleted(CoreAchievementsModel::Achievement_KeepPatient);
108+
}
109+
});
110+
window->removeEventFilter(this);
111+
}
112+
return WindowInterfaceAddOn::eventFilter(watched, event);
113+
}
108114
}

src/plugins/coreplugin/internal/addon/projectstartuptimeraddon.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,8 @@ namespace Core::Internal {
2525
static void setNotificationVisible(bool visible);
2626
static bool notificationVisible();
2727

28+
bool eventFilter(QObject *watched, QEvent *event) override;
29+
2830
private:
2931
NotificationMessage *m_initializingMessage{};
3032
NotificationMessage *m_finishedMessage{};

src/plugins/coreplugin/internal/addon/workspaceaddon.cpp

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,7 @@ namespace Core::Internal {
6262
}
6363
}
6464
void WorkspaceAddOn::extensionsInitialized() {
65+
windowHandle()->window()->installEventFilter(this);
6566
}
6667
bool WorkspaceAddOn::delayedInitialize() {
6768
emit panelEntriesChanged();
@@ -274,9 +275,7 @@ namespace Core::Internal {
274275
QVariantList WorkspaceAddOn::panelEntries() const {
275276
QVariantList ret;
276277
auto windowInterface = windowHandle()->cast<ProjectWindowInterface>();
277-
auto a = CoreInterface::actionRegistry()->catalog().children("core.workspacePanelWidgets") | std::views::filter([=](const QString &id) -> bool {
278-
return windowInterface->actionContext()->action(id);
279-
});
278+
auto a = CoreInterface::actionRegistry()->catalog().children("core.workspacePanelWidgets") | std::views::filter([=](const QString &id) -> bool { return windowInterface->actionContext()->action(id); });
280279
std::ranges::transform(a, std::back_inserter(ret), [](const QString &id) {
281280
auto info = CoreInterface::actionRegistry()->actionInfo(id);
282281
auto actionIcon = CoreInterface::actionRegistry()->actionIcon("", info.id());
@@ -290,6 +289,13 @@ namespace Core::Internal {
290289
});
291290
return ret;
292291
}
292+
bool WorkspaceAddOn::eventFilter(QObject *watched, QEvent *event) {
293+
if (event->type() == QEvent::Expose && windowHandle()->window()->isExposed()) {
294+
Q_EMIT windowExposed();
295+
windowHandle()->window()->removeEventFilter(this);
296+
}
297+
return WindowInterfaceAddOn::eventFilter(watched, event);
298+
}
293299
}
294300

295301
#include "moc_workspaceaddon.cpp"

src/plugins/coreplugin/internal/addon/workspaceaddon.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,8 +32,11 @@ namespace Core::Internal {
3232

3333
QVariantList panelEntries() const;
3434

35+
bool eventFilter(QObject *watched, QEvent *event) override;
36+
3537
Q_SIGNALS:
3638
void panelEntriesChanged();
39+
void windowExposed();
3740

3841
private:
3942
ProjectWindowWorkspaceManager *m_workspaceManager;

src/plugins/coreplugin/internal/coreplugin.cpp

Lines changed: 24 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -143,27 +143,28 @@ namespace Core::Internal {
143143
CoreAchievementsModel::triggerAchievementCompleted(CoreAchievementsModel::Achievement_UltimateSimplicity);
144144
}
145145

146-
static QQuickWindow *initializeGui(const QStringList &options, const QString &workingDirectory, const QStringList &args) {
146+
static ActionWindowInterfaceBase *initializeGui(const QStringList &options, const QString &workingDirectory, const QStringList &args) {
147147
if (options.contains(kOpenSettingsArg)) {
148148
qCInfo(lcCorePlugin) << "Open settings dialog with command line args";
149149
CoreInterface::execSettingsDialog("", nullptr);
150150
CoreAchievementsModel::triggerAchievementCompleted(CoreAchievementsModel::Achievement_CommandLineSettings);
151151
}
152-
QQuickWindow *win;
152+
ActionWindowInterfaceBase *windowInterface;
153153
if (options.contains(kNewProjectArg) || (BehaviorPreference::startupBehavior() & BehaviorPreference::SB_CreateNewProject)) {
154154
qCInfo(lcCorePlugin) << "Create new project on startup";
155-
win = CoreInterface::newFile();
155+
windowInterface = CoreInterface::newFile();
156156
} else {
157157
qCInfo(lcCorePlugin) << "Open home window on startup";
158158
CoreInterface::showHome();
159-
win = static_cast<QQuickWindow *>(HomeWindowInterface::instance()->window());
159+
windowInterface = HomeWindowInterface::instance();
160160
}
161+
auto win = windowInterface->window();
161162
if (win->visibility() == QWindow::Minimized) {
162163
win->showNormal();
163164
}
164165
win->raise();
165166
win->requestActivate();
166-
return win;
167+
return windowInterface;
167168
}
168169

169170
bool CorePlugin::initialize(const QStringList &arguments, QString *errorMessage) {
@@ -201,8 +202,24 @@ namespace Core::Internal {
201202
qCInfo(lcCorePlugin) << "Initializing GUI";
202203
// TODO plugin arguments
203204
auto args = QApplication::arguments();
204-
auto win = initializeGui(args, QDir::currentPath(), args);
205-
connect(win, &QQuickWindow::sceneGraphInitialized, RuntimeInterface::splash(), &QWidget::close);
205+
auto windowInterface = initializeGui(args, QDir::currentPath(), args);
206+
auto win = windowInterface->window();
207+
class ExposedListener : public QObject {
208+
public:
209+
explicit ExposedListener(QObject *parent) : QObject(parent) {
210+
}
211+
212+
bool eventFilter(QObject *watched, QEvent *event) override {
213+
if (event->type() == QEvent::Expose && static_cast<QWindow *>(watched)->isExposed()) {
214+
RuntimeInterface::splash()->close();
215+
deleteLater();
216+
}
217+
return QObject::eventFilter(watched, event);
218+
}
219+
220+
};
221+
auto listener = new ExposedListener(win);
222+
win->installEventFilter(listener);
206223
CoreAchievementsModel::triggerAchievementCompleted(CoreAchievementsModel::Achievement_DiffScope);
207224
checkUltimateSimplicityAchievement();
208225
QApplication::setQuitOnLastWindowClosed(true);

src/plugins/coreplugin/qml/windows/WorkspaceAddOnHelper.qml

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -255,9 +255,9 @@ QtObject {
255255
}
256256

257257
readonly property Connections windowHandleConnections: Connections {
258-
target: helper.window
259-
function onSceneGraphInitialized() {
260-
helper.initializeDockingViews()
258+
target: helper.addOn
259+
function onWindowExposed() {
260+
Qt.callLater(() => helper.initializeDockingViews())
261261
}
262262
}
263263

0 commit comments

Comments
 (0)