Qt
Internal/Contributor docs for the Qt SDK. Note: These are NOT official API docs; those are found at https://doc.qt.io/
Loading...
Searching...
No Matches
qquickpopupitem.cpp
Go to the documentation of this file.
1// Copyright (C) 2017 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3// Qt-Security score:significant reason:default
4
11
12#if QT_CONFIG(accessibility)
13#include <QtQuick/private/qquickaccessibleattached_p.h>
14#endif
15
17
18Q_STATIC_LOGGING_CATEGORY(lcPopupItem, "qt.quick.controls.popupitem")
19
20QQuickPopupItemPrivate::QQuickPopupItemPrivate(QQuickPopup *popup)
21 : popup(popup)
22{
23 isTabFence = true;
24}
25
26QQuickPopupItemPrivate *QQuickPopupItemPrivate::get(QQuickPopupItem *popupItem)
27{
28 return popupItem->d_func();
29}
30
31void QQuickPopupItemPrivate::implicitWidthChanged()
32{
33 qCDebug(lcPopupItem).nospace() << "implicitWidthChanged called on " << q_func() << "; new implicitWidth is " << implicitWidth;
34 QQuickPagePrivate::implicitWidthChanged();
35 emit popup->implicitWidthChanged();
36}
37
38void QQuickPopupItemPrivate::implicitHeightChanged()
39{
40 qCDebug(lcPopupItem).nospace() << "implicitHeightChanged called on " << q_func() << "; new implicitHeight is " << implicitHeight;
41 QQuickPagePrivate::implicitHeightChanged();
42 emit popup->implicitHeightChanged();
43}
44
45void QQuickPopupItemPrivate::resolveFont()
46{
47 if (QQuickApplicationWindow *window = qobject_cast<QQuickApplicationWindow *>(popup->window()))
48 inheritFont(window->font());
49 else
50 inheritFont(QQuickTheme::font(QQuickTheme::System));
51}
52
53QQuickItem *QQuickPopupItemPrivate::getContentItem()
54{
55 Q_Q(QQuickPopupItem);
56 if (QQuickItem *item = QQuickPagePrivate::getContentItem())
57 return item;
58
59 return new QQuickContentItem(popup, q);
60}
61
62static inline QString contentItemName() { return QStringLiteral("contentItem"); }
63
64void QQuickPopupItemPrivate::cancelContentItem()
65{
66 quickCancelDeferred(popup, contentItemName());
67}
68
69void QQuickPopupItemPrivate::executeContentItem(bool complete)
70{
71 if (contentItem.wasExecuted())
72 return;
73
74 if (!contentItem || complete)
75 quickBeginDeferred(popup, contentItemName(), contentItem);
76 if (complete)
77 quickCompleteDeferred(popup, contentItemName(), contentItem);
78}
79
80void QQuickPopupItemPrivate::cancelBackground()
81{
82 quickCancelDeferred(popup, backgroundName());
83}
84
85void QQuickPopupItemPrivate::executeBackground(bool complete)
86{
87 if (background.wasExecuted())
88 return;
89
90 if (!background || complete)
91 quickBeginDeferred(popup, backgroundName(), background);
92 if (complete)
93 quickCompleteDeferred(popup, backgroundName(), background);
94}
95
96QQuickPopupItem::QQuickPopupItem(QQuickPopup *popup)
97 : QQuickPage(*(new QQuickPopupItemPrivate(popup)), nullptr)
98{
99 setParent(popup);
100 setFlag(ItemIsFocusScope);
101 setAcceptedMouseButtons(Qt::AllButtons);
102#if QT_CONFIG(quicktemplates2_multitouch)
103 setAcceptTouchEvents(true);
104#endif
105#if QT_CONFIG(cursor)
106 setCursor(Qt::ArrowCursor);
107#endif
108
109 connect(popup, &QQuickPopup::paletteChanged, this, &QQuickItem::paletteChanged);
110 connect(popup, &QQuickPopup::paletteCreated, this, &QQuickItem::paletteCreated);
111
112#if QT_CONFIG(quicktemplates2_hover)
113 // TODO: switch to QStyleHints::useHoverEffects in Qt 5.8
114 setHoverEnabled(true);
115 // setAcceptHoverEvents(QGuiApplication::styleHints()->useHoverEffects());
116 // connect(QGuiApplication::styleHints(), &QStyleHints::useHoverEffectsChanged, this, &QQuickItem::setAcceptHoverEvents);
117#endif
118}
119
120QQuickPalette *QQuickPopupItemPrivate::palette() const
121{
122 return QQuickPopupPrivate::get(popup)->palette();
123}
124
125void QQuickPopupItemPrivate::setPalette(QQuickPalette *p)
126{
127 QQuickPopupPrivate::get(popup)->setPalette(p);
128}
129
130void QQuickPopupItemPrivate::resetPalette()
131{
132 QQuickPopupPrivate::get(popup)->resetPalette();
133}
134
135QPalette QQuickPopupItemPrivate::defaultPalette() const
136{
137 return QQuickPopupPrivate::get(popup)->defaultPalette();
138}
139
140bool QQuickPopupItemPrivate::providesPalette() const
141{
142 return QQuickPopupPrivate::get(popup)->providesPalette();
143}
144
145QPalette QQuickPopupItemPrivate::parentPalette(const QPalette &fallbackPalette) const
146{
147 return QQuickPopupPrivate::get(popup)->parentPalette(fallbackPalette);
148}
149
150void QQuickPopupItem::updatePolish()
151{
152 Q_D(QQuickPopupItem);
153 return QQuickPopupPrivate::get(d->popup)->reposition();
154}
155
156bool QQuickPopupItem::childMouseEventFilter(QQuickItem *child, QEvent *event)
157{
158 Q_D(QQuickPopupItem);
159 return d->popup->childMouseEventFilter(child, event);
160}
161
162void QQuickPopupItem::focusInEvent(QFocusEvent *event)
163{
164 Q_D(QQuickPopupItem);
165 d->popup->focusInEvent(event);
166}
167
168void QQuickPopupItem::focusOutEvent(QFocusEvent *event)
169{
170 Q_D(QQuickPopupItem);
171 d->popup->focusOutEvent(event);
172}
173
174void QQuickPopupItem::keyPressEvent(QKeyEvent *event)
175{
176 Q_D(QQuickPopupItem);
177 d->popup->keyPressEvent(event);
178}
179
180void QQuickPopupItem::keyReleaseEvent(QKeyEvent *event)
181{
182 Q_D(QQuickPopupItem);
183 d->popup->keyReleaseEvent(event);
184}
185
186void QQuickPopupItem::mousePressEvent(QMouseEvent *event)
187{
188 Q_D(QQuickPopupItem);
189 d->popup->mousePressEvent(event);
190}
191
192void QQuickPopupItem::mouseMoveEvent(QMouseEvent *event)
193{
194 Q_D(QQuickPopupItem);
195 d->popup->mouseMoveEvent(event);
196}
197
198void QQuickPopupItem::mouseReleaseEvent(QMouseEvent *event)
199{
200 Q_D(QQuickPopupItem);
201 d->popup->mouseReleaseEvent(event);
202}
203
204void QQuickPopupItem::mouseDoubleClickEvent(QMouseEvent *event)
205{
206 Q_D(QQuickPopupItem);
207 d->popup->mouseDoubleClickEvent(event);
208}
209
210void QQuickPopupItem::mouseUngrabEvent()
211{
212 Q_D(QQuickPopupItem);
213 d->popup->mouseUngrabEvent();
214}
215
216#if QT_CONFIG(quicktemplates2_multitouch)
217void QQuickPopupItem::touchEvent(QTouchEvent *event)
218{
219 Q_D(QQuickPopupItem);
220 d->popup->touchEvent(event);
221}
222
223void QQuickPopupItem::touchUngrabEvent()
224{
225 Q_D(QQuickPopupItem);
226 d->popup->touchUngrabEvent();
227}
228#endif
229
230#if QT_CONFIG(wheelevent)
231void QQuickPopupItem::wheelEvent(QWheelEvent *event)
232{
233 Q_D(QQuickPopupItem);
234 d->popup->wheelEvent(event);
235}
236#endif
237
238void QQuickPopupItem::contentItemChange(QQuickItem *newItem, QQuickItem *oldItem)
239{
240 Q_D(QQuickPopupItem);
241 QQuickPage::contentItemChange(newItem, oldItem);
242 d->popup->contentItemChange(newItem, oldItem);
243}
244
245void QQuickPopupItem::contentSizeChange(const QSizeF &newSize, const QSizeF &oldSize)
246{
247 Q_D(QQuickPopupItem);
248 qCDebug(lcPopupItem) << "contentSizeChange called on" << this << "newSize" << newSize << "oldSize" << oldSize;
249 QQuickPage::contentSizeChange(newSize, oldSize);
250 d->popup->contentSizeChange(newSize, oldSize);
251}
252
253void QQuickPopupItem::fontChange(const QFont &newFont, const QFont &oldFont)
254{
255 Q_D(QQuickPopupItem);
256 QQuickPage::fontChange(newFont, oldFont);
257 d->popup->fontChange(newFont, oldFont);
258}
259
260void QQuickPopupItem::geometryChange(const QRectF &newGeometry, const QRectF &oldGeometry)
261{
262 Q_D(QQuickPopupItem);
263 qCDebug(lcPopupItem) << "geometryChange called on" << this << "newGeometry" << newGeometry << "oldGeometry" << oldGeometry;
264 QQuickPage::geometryChange(newGeometry, oldGeometry);
265 d->popup->geometryChange(newGeometry, oldGeometry);
266}
267
268void QQuickPopupItem::localeChange(const QLocale &newLocale, const QLocale &oldLocale)
269{
270 Q_D(QQuickPopupItem);
271 QQuickPage::localeChange(newLocale, oldLocale);
272 d->popup->localeChange(newLocale, oldLocale);
273}
274
275void QQuickPopupItem::mirrorChange()
276{
277 Q_D(QQuickPopupItem);
278 emit d->popup->mirroredChanged();
279}
280
281void QQuickPopupItem::itemChange(ItemChange change, const ItemChangeData &data)
282{
283 Q_D(QQuickPopupItem);
284 QQuickPage::itemChange(change, data);
285 d->popup->itemChange(change, data);
286}
287
288void QQuickPopupItem::paddingChange(const QMarginsF &newPadding, const QMarginsF &oldPadding)
289{
290 Q_D(QQuickPopupItem);
291 QQuickPage::paddingChange(newPadding, oldPadding);
292 d->popup->paddingChange(newPadding, oldPadding);
293}
294
295void QQuickPopupItem::enabledChange()
296{
297 Q_D(QQuickPopupItem);
298 // Just having QQuickPopup connect our QQuickItem::enabledChanged() signal
299 // to its enabledChanged() signal is enough for the enabled property to work,
300 // but we must also ensure that its paletteChanged() signal is emitted
301 // so that bindings to palette are re-evaluated, because QQuickControl::palette()
302 // returns a different palette depending on whether or not the control is enabled.
303 // To save a connection, we also emit enabledChanged here.
304 emit d->popup->enabledChanged();
305}
306
307QFont QQuickPopupItem::defaultFont() const
308{
309 Q_D(const QQuickPopupItem);
310 return d->popup->defaultFont();
311}
312
313#if QT_CONFIG(accessibility)
314QAccessible::Role QQuickPopupItem::accessibleRole() const
315{
316 Q_D(const QQuickPopupItem);
317 return d->popup->effectiveAccessibleRole();
318}
319
320void QQuickPopupItem::accessibilityActiveChanged(bool active)
321{
322 Q_D(const QQuickPopupItem);
323 // Can't just use d->popup->accessibleName() here, because that refers to the accessible
324 // name of us, the popup item, which is not what we want.
325 const QQuickAccessibleAttached *popupAccessibleAttached = QQuickControlPrivate::accessibleAttached(d->popup);
326 const QString oldPopupName = popupAccessibleAttached ? popupAccessibleAttached->name() : QString();
327 const bool wasNameExplicitlySetOnPopup = popupAccessibleAttached && popupAccessibleAttached->wasNameExplicitlySet();
328
329 QQuickPage::accessibilityActiveChanged(active);
330
331 QQuickAccessibleAttached *accessibleAttached = QQuickControlPrivate::accessibleAttached(this);
332 const QString ourName = accessibleAttached ? accessibleAttached->name() : QString();
333 if (wasNameExplicitlySetOnPopup && accessibleAttached && ourName != oldPopupName) {
334 // The user set Accessible.name on the Popup. Since the Popup and its popup item
335 // have different accessible attached properties, the popup item doesn't know that
336 // a name was set on the Popup by the user, and that it should use that, rather than
337 // whatever QQuickPage sets. That's why we need to do it here.
338 // To avoid it being overridden by the call to accessibilityActiveChanged() below,
339 // we set it explicitly. It's safe to do this as the popup item is an internal implementation detail.
340 accessibleAttached->setName(oldPopupName);
341 }
342
343 // This allows the different popup types to set a name on their popup item accordingly.
344 // For example: Dialog uses its title and ToolTip uses its text.
345 d->popup->accessibilityActiveChanged(active);
346}
347#endif
348
349QT_END_NAMESPACE
350
351#include "moc_qquickpopupitem_p_p.cpp"
static QString contentItemName()