Line data Source code
1 : /*
2 : * SPDX-License-Identifier: GPL-3.0-only
3 : * MuseScore-CLA-applies
4 : *
5 : * MuseScore Studio
6 : * Music Composition & Notation
7 : *
8 : * Copyright (C) 2021 MuseScore Limited and others
9 : *
10 : * This program is free software: you can redistribute it and/or modify
11 : * it under the terms of the GNU General Public License version 3 as
12 : * published by the Free Software Foundation.
13 : *
14 : * This program is distributed in the hope that it will be useful,
15 : * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 : * GNU General Public License for more details.
18 : *
19 : * You should have received a copy of the GNU General Public License
20 : * along with this program. If not, see <https://www.gnu.org/licenses/>.
21 : */
22 : #pragma once
23 :
24 : #include <qqmlintegration.h>
25 :
26 : #include <QPointer>
27 : #include <QQmlParserStatus>
28 : #include <QQuickItem>
29 : #include <QQuickView>
30 : #include <QQmlEngine>
31 :
32 : #include "async/asyncable.h"
33 :
34 : #include "modularity/ioc.h"
35 : #include "interactive/iinteractive.h"
36 : #include "ui/imainwindow.h"
37 : #include "ui/inavigationcontroller.h"
38 : #include "ui/iuiconfiguration.h"
39 :
40 : Q_MOC_INCLUDE(< QWindow >)
41 :
42 : class QQuickCloseEvent;
43 : class QQuickView;
44 :
45 : namespace muse::ui {
46 : class INavigationControl;
47 : }
48 :
49 : namespace muse::uicomponents {
50 : class WindowView : public QObject, public QQmlParserStatus, public Contextable, public async::Asyncable
51 : {
52 : Q_OBJECT
53 : Q_INTERFACES(QQmlParserStatus)
54 :
55 : QML_ELEMENT;
56 : QML_UNCREATABLE("Not creatable as it is abstract base class")
57 :
58 : Q_PROPERTY(QQuickItem * parent READ parentItem WRITE setParentItem NOTIFY parentItemChanged)
59 :
60 : Q_PROPERTY(QQuickItem * contentItem READ contentItem WRITE setContentItem NOTIFY contentItemChanged)
61 : Q_PROPERTY(int contentWidth READ contentWidth WRITE setContentWidth NOTIFY contentWidthChanged)
62 : Q_PROPERTY(int contentHeight READ contentHeight WRITE setContentHeight NOTIFY contentHeightChanged)
63 :
64 : Q_PROPERTY(QWindow * window READ window NOTIFY windowChanged)
65 : Q_PROPERTY(QWindow * parentWindow READ parentWindow WRITE setParentWindow NOTIFY parentWindowChanged FINAL)
66 :
67 : Q_PROPERTY(bool isOpened READ isOpened NOTIFY isOpenedChanged)
68 : Q_PROPERTY(OpenPolicies openPolicies READ openPolicies WRITE setOpenPolicies NOTIFY openPoliciesChanged)
69 :
70 : Q_PROPERTY(bool isContentReady READ isContentReady WRITE setIsContentReady NOTIFY isContentReadyChanged)
71 :
72 : Q_PROPERTY(
73 : bool activateParentOnClose READ activateParentOnClose WRITE setActivateParentOnClose NOTIFY activateParentOnCloseChanged)
74 :
75 : Q_PROPERTY(FocusPolicies focusPolicies READ focusPolicies WRITE setFocusPolicies NOTIFY focusPoliciesChanged)
76 :
77 : protected:
78 : GlobalInject<ui::IUiConfiguration> uiConfiguration;
79 : ContextInject<IInteractive> interactive = { this };
80 : ContextInject<ui::IMainWindow> mainWindow = { this };
81 : ContextInject<ui::INavigationController> navigationController = { this };
82 :
83 : public:
84 : explicit WindowView(QQuickItem* parent = nullptr);
85 :
86 : enum class OpenPolicy {
87 : Default = 0x00000000,
88 : NoActivateFocus = 0x00000001,
89 : OpenOnContentReady = 0x00000002
90 : };
91 : Q_DECLARE_FLAGS(OpenPolicies, OpenPolicy)
92 0 : Q_FLAG(OpenPolicies)
93 :
94 : enum class FocusPolicy {
95 : TabFocus = 0x00000001,
96 : ClickFocus = 0x00000002,
97 : DefaultFocus = FocusPolicy::TabFocus | FocusPolicy::ClickFocus,
98 : NoFocus = 0
99 : };
100 : Q_DECLARE_FLAGS(FocusPolicies, FocusPolicy)
101 0 : Q_FLAG(FocusPolicies)
102 :
103 : QQuickItem* parentItem() const;
104 :
105 : QQuickItem* contentItem() const;
106 : int contentWidth() const;
107 : int contentHeight() const;
108 :
109 : QWindow* window() const;
110 :
111 : QRect geometry() const;
112 :
113 : bool hasActiveFocus();
114 : Q_INVOKABLE void forceActiveFocus();
115 :
116 : void init();
117 :
118 : Q_INVOKABLE void open();
119 : Q_INVOKABLE virtual void close(bool force = false);
120 : Q_INVOKABLE void toggleOpened();
121 :
122 : OpenPolicies openPolicies() const;
123 :
124 : bool activateParentOnClose() const;
125 : FocusPolicies focusPolicies() const;
126 :
127 : ui::INavigationControl* navigationParentControl() const;
128 :
129 : bool isOpened() const;
130 :
131 : bool isContentReady() const;
132 : void setIsContentReady(bool ready);
133 :
134 0 : virtual void repositionWindowIfNeed() {}
135 :
136 : public slots:
137 : void setEngine(QQmlEngine* engine);
138 : virtual void setParentItem(QQuickItem* parent);
139 : void setContentItem(QQuickItem* content);
140 : void setContentWidth(int contentWidth);
141 : void setContentHeight(int contentHeight);
142 : void setOpenPolicies(muse::uicomponents::WindowView::OpenPolicies openPolicies);
143 : void setNavigationParentControl(muse::ui::INavigationControl* parentNavigationControl);
144 :
145 : void setActivateParentOnClose(bool activateParentOnClose);
146 : void setFocusPolicies(const muse::uicomponents::WindowView::FocusPolicies& policies);
147 :
148 : signals:
149 : void parentItemChanged();
150 : void contentItemChanged();
151 : void contentWidthChanged();
152 : void contentHeightChanged();
153 : void windowChanged();
154 : void openPoliciesChanged(muse::uicomponents::WindowView::OpenPolicies openPolicies);
155 : void navigationParentControlChanged(muse::ui::INavigationControl* navigationParentControl);
156 :
157 : void isOpenedChanged();
158 : void opened();
159 : void aboutToClose(/*QQuickCloseEvent*/ QObject* closeEvent);
160 : void closed(bool force);
161 :
162 : void activateParentOnCloseChanged(bool activateParentOnClose);
163 : void focusPoliciesChanged();
164 :
165 : void isContentReadyChanged();
166 :
167 : void parentWindowChanged();
168 :
169 : protected:
170 0 : void classBegin() override {}
171 : void componentComplete() override;
172 :
173 : virtual void initView();
174 : void setViewContent(QQuickItem* item);
175 :
176 : virtual void beforeOpen();
177 0 : virtual void afterShow() {}
178 : void doOpen();
179 : void showView();
180 :
181 : virtual void onHidden();
182 :
183 : bool eventFilter(QObject* watched, QEvent* event) override;
184 :
185 : QQmlEngine* engine() const;
186 :
187 : QWindow* parentWindow() const;
188 : void setParentWindow(QWindow* window);
189 : void resolveParentWindow();
190 :
191 : QScreen* resolveScreen() const;
192 : QRect currentScreenGeometry() const;
193 : virtual void updateGeometry() = 0;
194 : virtual QRect viewGeometry() const;
195 : void updateSize(const QSize& newSize);
196 :
197 : void resolveNavigationParentControl();
198 : void activateNavigationParentControl();
199 :
200 : QQmlEngine* m_engine = nullptr;
201 : QPointer<QWindow> m_parentWindow;
202 : QQuickView* m_view = nullptr;
203 :
204 : QQuickItem* m_contentItem = nullptr;
205 : int m_contentWidth = 0;
206 : int m_contentHeight = 0;
207 : bool m_resizable = false;
208 :
209 : QPointF m_globalPos;
210 :
211 : OpenPolicies m_openPolicies = { OpenPolicy::Default };
212 : bool m_shouldOpenOnReady = false;
213 : bool m_isContentReady = false;
214 :
215 : FocusPolicies m_focusPolicies = { FocusPolicy::DefaultFocus };
216 :
217 : bool m_activateParentOnClose = true;
218 : ui::INavigationControl* m_navigationParentControl = nullptr;
219 :
220 : bool m_forceClosed = false;
221 : };
222 : }
|