Qt
Internal/Contributor docs for the Qt SDK. <b>Note:</b> These are NOT official API docs; those are found <a href='https://doc.qt.io/'>here</a>.
Loading...
Searching...
No Matches
qcombobox_p.h
Go to the documentation of this file.
1// Copyright (C) 2016 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
4#ifndef QCOMBOBOX_P_H
5#define QCOMBOBOX_P_H
6
7//
8// W A R N I N G
9// -------------
10//
11// This file is not part of the Qt API. It exists purely as an
12// implementation detail. This header file may change from version to
13// version without notice, or even be removed.
14//
15// We mean it.
16//
17
18#include <QtWidgets/private/qtwidgetsglobal_p.h>
19#include "QtWidgets/qcombobox.h"
20
21#include "QtWidgets/qabstractslider.h"
22#include "QtWidgets/qapplication.h"
23#include "QtWidgets/qstyleditemdelegate.h"
24#include "QtGui/qstandarditemmodel.h"
25#include "QtWidgets/qlineedit.h"
26#include "QtWidgets/qlistview.h"
27#include "QtGui/qpainter.h"
28#include "QtWidgets/qstyle.h"
29#include "QtWidgets/qstyleoption.h"
30#include "QtCore/qtimer.h"
31#include "private/qwidget_p.h"
32#include "QtCore/qpointer.h"
33#if QT_CONFIG(completer)
34#include "QtWidgets/qcompleter.h"
35#endif
36#include "QtGui/qevent.h"
37#include "QtCore/qdebug.h"
38
39#include <limits.h>
40
42
44
45class QPlatformMenu;
46
48{
50public:
51 QComboBoxListView(QComboBox *cmb = nullptr) : combo(cmb)
52 {
53 if (cmb)
54 setScreen(cmb->screen());
55 }
56
57protected:
63
64 void initViewItemOption(QStyleOptionViewItem *option) const override
65 {
67 option->showDecorationSelected = true;
68 if (combo)
69 option->font = combo->font();
70 }
71
72 void paintEvent(QPaintEvent *e) override
73 {
74 if (combo) {
76 opt.initFrom(combo);
77 opt.editable = combo->isEditable();
78 if (combo->style()->styleHint(QStyle::SH_ComboBox_Popup, &opt, combo)) {
79 //we paint the empty menu area to avoid having blank space that can happen when scrolling
81 menuOpt.initFrom(this);
82 menuOpt.palette = palette();
83 menuOpt.state = QStyle::State_None;
84 menuOpt.checkType = QStyleOptionMenuItem::NotCheckable;
85 menuOpt.menuRect = e->rect();
86 menuOpt.maxIconWidth = 0;
87 menuOpt.reservedShortcutWidth = 0;
89 combo->style()->drawControl(QStyle::CE_MenuEmptyArea, &menuOpt, &p, this);
90 }
91 }
93 }
94
95private:
96 QComboBox *combo;
97};
98
100{
102
103public:
110 QSize sizeHint() const override {
111 return QSize(20, style()->pixelMetric(QStyle::PM_MenuScrollerHeight, nullptr, this));
112 }
113
114protected:
115 inline void stopTimer() {
116 timer.stop();
117 }
118
119 inline void startTimer() {
120 timer.start(100, this);
121 fast = false;
122 }
123
124 void enterEvent(QEnterEvent *) override {
125 startTimer();
126 }
127
128 void leaveEvent(QEvent *) override {
129 stopTimer();
130 }
131 void timerEvent(QTimerEvent *e) override {
132 if (e->timerId() == timer.timerId()) {
133 emit doScroll(sliderAction);
134 if (fast) {
135 emit doScroll(sliderAction);
136 emit doScroll(sliderAction);
137 }
138 }
139 }
140 void hideEvent(QHideEvent *) override {
141 stopTimer();
142 }
143
144 void mouseMoveEvent(QMouseEvent *e) override
145 {
146 // Enable fast scrolling if the cursor is directly above or below the popup.
147 const int mouseX = e->position().toPoint().x();
148 const int mouseY = e->position().toPoint().y();
149 const bool horizontallyInside = pos().x() < mouseX && mouseX < rect().right() + 1;
150 const bool verticallyOutside = (sliderAction == QAbstractSlider::SliderSingleStepAdd) ?
151 rect().bottom() + 1 < mouseY : mouseY < pos().y();
152
153 fast = horizontallyInside && verticallyOutside;
154 }
155
156 void paintEvent(QPaintEvent *) override {
157 QPainter p(this);
158 QStyleOptionMenuItem menuOpt;
159 menuOpt.initFrom(this);
160 menuOpt.checkType = QStyleOptionMenuItem::NotCheckable;
161 menuOpt.menuRect = rect();
162 menuOpt.maxIconWidth = 0;
163 menuOpt.reservedShortcutWidth = 0;
164 menuOpt.menuItemType = QStyleOptionMenuItem::Scroller;
165 if (sliderAction == QAbstractSlider::SliderSingleStepAdd)
166 menuOpt.state |= QStyle::State_DownArrow;
167 p.eraseRect(rect());
169 }
170
172 void doScroll(int action);
173
174private:
177 bool fast = false;
178};
179
180class Q_WIDGETS_EXPORT QComboBoxPrivateContainer : public QFrame
181{
183
184public:
187 QAbstractItemView *itemView() const;
188 void setItemView(QAbstractItemView *itemView);
189 int spacing() const;
190 int topMargin() const;
191 int bottomMargin() const { return topMargin(); }
192 void updateTopBottomMargin();
193 void updateStyleSettings();
194
198
199public Q_SLOTS:
200 void scrollItemView(int action);
201 void hideScrollers();
202 void updateScrollers();
203 void viewDestroyed();
204
205protected:
206 void changeEvent(QEvent *e) override;
207 bool eventFilter(QObject *o, QEvent *e) override;
208 void mousePressEvent(QMouseEvent *e) override;
209 void mouseReleaseEvent(QMouseEvent *e) override;
210 void showEvent(QShowEvent *e) override;
211 void hideEvent(QHideEvent *e) override;
212 void timerEvent(QTimerEvent *timerEvent) override;
213 void resizeEvent(QResizeEvent *e) override;
214 void paintEvent(QPaintEvent *e) override;
215 QStyleOptionComboBox comboStyleOption() const;
216
220
221private:
222 QComboBox *combo;
223 QAbstractItemView *view = nullptr;
224 QComboBoxPrivateScroller *top = nullptr;
226 QElapsedTimer popupTimer;
227 bool maybeIgnoreMouseButtonRelease = false;
228
229 friend class QComboBox;
230 friend class QComboBoxPrivate;
231};
232
234{
236public:
238 : QAbstractItemDelegate(parent), mCombo(cmb), pressedIndex(-1)
239 {}
240
241protected:
243 const QStyleOptionViewItem &option,
244 const QModelIndex &index) const override {
245 QStyleOptionMenuItem opt = getStyleOption(option, index);
247 mCombo->style()->drawControl(QStyle::CE_MenuItem, &opt, painter, mCombo);
248 }
249 QSize sizeHint(const QStyleOptionViewItem &option,
250 const QModelIndex &index) const override {
251 QStyleOptionMenuItem opt = getStyleOption(option, index);
252 return mCombo->style()->sizeFromContents(
253 QStyle::CT_MenuItem, &opt, option.rect.size(), mCombo);
254 }
255 bool editorEvent(QEvent *event, QAbstractItemModel *model,
256 const QStyleOptionViewItem &option, const QModelIndex &index) override;
257
258private:
259 QStyleOptionMenuItem getStyleOption(const QStyleOptionViewItem &option,
260 const QModelIndex &index) const;
261 QComboBox *mCombo;
262 int pressedIndex;
263};
264
266{
268public:
270 : QStyledItemDelegate(parent), mCombo(cmb)
271 {}
272
273 static bool isSeparator(const QModelIndex &index) {
274 return index.data(Qt::AccessibleDescriptionRole).toString()
275 == QLatin1StringView("separator");
276 }
279 if (QStandardItemModel *m = qobject_cast<QStandardItemModel*>(model))
280 if (QStandardItem *item = m->itemFromIndex(index))
282 }
283
284protected:
286 const QStyleOptionViewItem &option,
287 const QModelIndex &index) const override {
288 if (isSeparator(index)) {
289 QRect rect = option.rect;
290 if (const QAbstractItemView *view = qobject_cast<const QAbstractItemView*>(option.widget))
291 rect.setWidth(view->viewport()->width());
293 opt.rect = rect;
294 mCombo->style()->drawPrimitive(QStyle::PE_IndicatorToolBarSeparator, &opt, painter, mCombo);
295 } else {
297 }
298 }
299
300 QSize sizeHint(const QStyleOptionViewItem &option,
301 const QModelIndex &index) const override {
302 if (isSeparator(index)) {
303 int pm = mCombo->style()->pixelMetric(QStyle::PM_DefaultFrameWidth, nullptr, mCombo);
304 return QSize(pm, pm);
305 }
307 }
308private:
309 QComboBox *mCombo;
310};
311
313{
314 Q_DECLARE_PUBLIC(QComboBox)
315public:
318 void init();
319 QComboBoxPrivateContainer* viewContainer();
320 void updateLineEditGeometry();
321 Qt::MatchFlags matchFlags() const;
322 void editingFinished();
323 void returnPressed();
324 void complete();
325 void itemSelected(const QModelIndex &item);
326 bool contains(const QString &text, int role);
327 void emitActivated(const QModelIndex &index);
328 void emitHighlighted(const QModelIndex &index);
329 void emitCurrentIndexChanged(const QModelIndex &index);
330 void modelDestroyed();
331 void modelReset();
332 void updateMicroFocus() { q_func()->updateMicroFocus(); } // PMF connect doesn't handle default args
333#if QT_CONFIG(completer)
334 void completerActivated(const QModelIndex &index);
335#endif
336 void resetButton();
337 void dataChanged(const QModelIndex &topLeft, const QModelIndex &bottomRight);
338 void updateIndexBeforeChange();
339 void rowsInserted(const QModelIndex &parent, int start, int end);
340 void rowsRemoved(const QModelIndex &parent, int start, int end);
341 void updateArrow(QStyle::StateFlag state);
342 bool updateHoverControl(const QPoint &pos);
343 void trySetValidIndex();
344 QRect popupGeometry(const QPoint &globalPos) const;
345 QStyle::SubControl newHoverControl(const QPoint &pos);
346 int computeWidthHint() const;
347 QSize recomputeSizeHint(QSize &sh) const;
348 void adjustComboBoxSize();
349 QString itemText(const QModelIndex &index) const;
350 QIcon itemIcon(const QModelIndex &index) const;
351 int itemRole() const;
352 void updateLayoutDirection();
353 void setCurrentIndex(const QModelIndex &index);
354 void updateDelegate(bool force = false);
355 void keyboardSearchString(const QString &text);
356 void modelChanged();
357 void updateViewContainerPaletteAndOpacity();
358 void updateFocusPolicy();
359 void showPopupFromMouseEvent(QMouseEvent *e);
360 void doHidePopup();
361 void updateCurrentText(const QString &text);
362 void connectModel();
363 void disconnectModel();
364
365#ifdef Q_OS_MAC
366 void cleanupNativePopup();
367 bool showNativePopup();
368 struct IndexSetter {
369 int index;
370 QComboBox *cb;
371
372 void operator()(void)
373 {
374 cb->setCurrentIndex(index);
375 cb->d_func()->emitActivated(cb->d_func()->currentIndex);
376 }
377 };
378#endif
379
380 std::array<QMetaObject::Connection, 8> modelConnections;
382 QLineEdit *lineEdit = nullptr;
383 QPointer<QComboBoxPrivateContainer> container;
384#ifdef Q_OS_MAC
385 QPlatformMenu *m_platformMenu = nullptr;
386#endif
399 int minimumContentsLength = 0;
400 int indexBeforeChange = -1;
401 int maxVisibleItems = 10;
402 int maxCount = (std::numeric_limits<int>::max)();
403 int modelColumn = 0;
404 int placeholderIndex = -1;
405 bool shownOnce : 1;
407 bool frame : 1;
408 bool inserting : 1;
409 bool hidingPopup : 1;
410};
411
413
414#endif // QCOMBOBOX_P_H
The QAbstractItemDelegate class is used to display and edit data items from a model.
virtual Q_INVOKABLE bool setData(const QModelIndex &index, const QVariant &value, int role=Qt::EditRole)
Sets the role data for the item at index to value.
The QAbstractItemView class provides the basic functionality for item view classes.
SliderAction
\value SliderNoAction \value SliderSingleStepAdd \value SliderSingleStepSub \value SliderPageStepAdd ...
\inmodule QtCore
Definition qbasictimer.h:18
void paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const override
This pure abstract function must be reimplemented if you want to provide custom rendering.
static bool isSeparator(const QModelIndex &index)
QComboBoxDelegate(QObject *parent, QComboBox *cmb)
QSize sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const override
This pure abstract function must be reimplemented if you want to provide custom rendering.
static void setSeparator(QAbstractItemModel *model, const QModelIndex &index)
void resizeEvent(QResizeEvent *event) override
Definition qcombobox_p.h:58
QComboBoxListView(QComboBox *cmb=nullptr)
Definition qcombobox_p.h:51
void initViewItemOption(QStyleOptionViewItem *option) const override
Definition qcombobox_p.h:64
void paintEvent(QPaintEvent *e) override
Definition qcombobox_p.h:72
void itemSelected(const QModelIndex &)
void mouseMoveEvent(QMouseEvent *e) override
This event handler, for event event, can be reimplemented in a subclass to receive mouse move events ...
void enterEvent(QEnterEvent *) override
This event handler can be reimplemented in a subclass to receive widget enter events which are passed...
void doScroll(int action)
void timerEvent(QTimerEvent *e) override
This event handler can be reimplemented in a subclass to receive timer events for the object.
void leaveEvent(QEvent *) override
This event handler can be reimplemented in a subclass to receive widget leave events which are passed...
QComboBoxPrivateScroller(QAbstractSlider::SliderAction action, QWidget *parent)
void hideEvent(QHideEvent *) override
This event handler can be reimplemented in a subclass to receive widget hide events.
QSize sizeHint() const override
void paintEvent(QPaintEvent *) override
This event handler can be reimplemented in a subclass to receive paint events passed in event.
QPointer< QComboBoxPrivateContainer > container
QPersistentModelIndex currentIndex
QPersistentModelIndex root
std::array< QMetaObject::Connection, 8 > modelConnections
QString placeholderText
bool contains(const QString &text, int role)
void updateMicroFocus()
The QComboBox widget combines a button with a dropdown list.
Definition qcombobox.h:24
InsertPolicy
This enum specifies what the QComboBox should do when a new string is entered by the user.
Definition qcombobox.h:67
@ InsertAtBottom
Definition qcombobox.h:71
SizeAdjustPolicy
This enum specifies how the size hint of the QComboBox should adjust when new content is added or con...
Definition qcombobox.h:81
@ AdjustToContentsOnFirstShow
Definition qcombobox.h:83
bool isEditable() const
QSize sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const override
This pure abstract function must be reimplemented if you want to provide custom rendering.
void paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const override
This pure abstract function must be reimplemented if you want to provide custom rendering.
QComboMenuDelegate(QObject *parent, QComboBox *cmb)
\inmodule QtCore
\inmodule QtGui
Definition qevent.h:165
\inmodule QtCore
Definition qcoreevent.h:45
The QFrame class is the base class of widgets that can have a frame.
Definition qframe.h:17
void setFlags(GraphicsItemFlags flags)
Sets the item flags to flags.
GraphicsItemFlags flags() const
Returns this item's flags.
The QHideEvent class provides an event which is sent after a widget is hidden.
Definition qevent.h:586
The QIcon class provides scalable icons in different modes and states.
Definition qicon.h:20
The QLineEdit widget is a one-line text editor.
Definition qlineedit.h:28
The QListView class provides a list or icon view onto a model.
Definition qlistview.h:17
void resizeEvent(QResizeEvent *e) override
\reimp
void initViewItemOption(QStyleOptionViewItem *option) const override
\reimp
QSize contentsSize() const
void resizeContents(int width, int height)
void paintEvent(QPaintEvent *e) override
\reimp
\inmodule QtCore
\inmodule QtGui
Definition qevent.h:196
\inmodule QtCore
Definition qobject.h:103
int startTimer(int interval, Qt::TimerType timerType=Qt::CoarseTimer)
This is an overloaded function that will start a timer of type timerType and a timeout of interval mi...
Definition qobject.cpp:1817
The QPaintEvent class contains event parameters for paint events.
Definition qevent.h:486
const QRect & rect() const
Returns the rectangle that needs to be updated.
Definition qevent.h:492
The QPainter class performs low-level painting on widgets and other paint devices.
Definition qpainter.h:46
void fillRect(const QRectF &, const QBrush &)
Fills the given rectangle with the brush specified.
const QBrush & window() const
Returns the window (general background) brush of the current color group.
Definition qpalette.h:93
constexpr QPoint toPoint() const
Rounds the coordinates of this point to the nearest integer, and returns a QPoint object with the rou...
Definition qpoint.h:404
\inmodule QtCore\reentrant
Definition qpoint.h:25
constexpr int x() const noexcept
Returns the x coordinate of this point.
Definition qpoint.h:130
constexpr int y() const noexcept
Returns the y coordinate of this point.
Definition qpoint.h:135
\inmodule QtCore\reentrant
Definition qrect.h:30
constexpr int bottom() const noexcept
Returns the y-coordinate of the rectangle's bottom edge.
Definition qrect.h:182
constexpr void setWidth(int w) noexcept
Sets the width of the rectangle to the given width.
Definition qrect.h:381
constexpr QSize size() const noexcept
Returns the size of the rectangle.
Definition qrect.h:242
constexpr int right() const noexcept
Returns the x-coordinate of the rectangle's right edge.
Definition qrect.h:179
The QResizeEvent class contains event parameters for resize events.
Definition qevent.h:548
The QShowEvent class provides an event that is sent when a widget is shown.
Definition qevent.h:578
QPointF position() const
Returns the position of the point in this event, relative to the widget or item that received the eve...
Definition qevent.h:119
\inmodule QtCore
Definition qsize.h:25
The QStandardItemModel class provides a generic model for storing custom data.
The QStandardItem class provides an item for use with the QStandardItemModel class.
\macro QT_RESTRICTED_CAST_FROM_ASCII
Definition qstring.h:129
static QString fromLatin1(QByteArrayView ba)
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition qstring.cpp:5871
\variable QStyleOptionToolButton::features
\variable QStyleOptionProgressBar::minimum
The QStyleOption class stores the parameters used by QStyle functions.
QPalette palette
void initFrom(const QWidget *w)
StateFlag
This enum describes flags that are used when drawing primitive elements.
Definition qstyle.h:65
@ State_DownArrow
Definition qstyle.h:73
@ State_None
Definition qstyle.h:66
@ CT_MenuItem
Definition qstyle.h:554
@ SH_ComboBox_Popup
Definition qstyle.h:610
virtual int styleHint(StyleHint stylehint, const QStyleOption *opt=nullptr, const QWidget *widget=nullptr, QStyleHintReturn *returnData=nullptr) const =0
Returns an integer representing the specified style hint for the given widget described by the provid...
@ CE_MenuItem
Definition qstyle.h:190
@ CE_MenuEmptyArea
Definition qstyle.h:195
@ CE_MenuScroller
Definition qstyle.h:191
@ PM_DefaultFrameWidth
Definition qstyle.h:420
@ PM_MenuScrollerHeight
Definition qstyle.h:450
@ PE_IndicatorToolBarSeparator
Definition qstyle.h:142
virtual void drawControl(ControlElement element, const QStyleOption *opt, QPainter *p, const QWidget *w=nullptr) const =0
Draws the given element with the provided painter with the style options specified by option.
SubControl
This enum describes the available sub controls.
Definition qstyle.h:347
@ SC_None
Definition qstyle.h:348
The QStyledItemDelegate class provides display and editing facilities for data items from a model.
QSize sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const override
Returns the size needed by the delegate to display the item specified by index, taking into account t...
void paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const override
Renders the delegate using the given painter and style option for the item specified by index.
\inmodule QtCore
Definition qcoreevent.h:366
int timerId() const
Returns the unique timer identifier, which is the same identifier as returned from QObject::startTime...
Definition qcoreevent.h:370
\inmodule QtCore
Definition qtimer.h:20
void start(int msec)
Starts or restarts the timer with a timeout interval of msec milliseconds.
Definition qtimer.cpp:241
int timerId() const
Returns the ID of the timer if the timer is running; otherwise returns -1.
Definition qtimer.cpp:183
void stop()
Stops the timer.
Definition qtimer.cpp:267
The QWidget class is the base class of all user interface objects.
Definition qwidget.h:99
void setAttribute(Qt::WidgetAttribute, bool on=true)
Sets the attribute attribute on this widget if on is true; otherwise clears the attribute.
void setSizePolicy(QSizePolicy)
QPoint pos
the position of the widget within its parent widget
Definition qwidget.h:111
QRect rect
the internal geometry of the widget excluding any window frame
Definition qwidget.h:116
QStyle * style() const
Definition qwidget.cpp:2600
QFont font
the font currently set for the widget
Definition qwidget.h:133
int width
the width of the window's geometry
Definition qwindow.h:82
QString text
qreal spacing
rect
[4]
QStyleOptionButton opt
else opt state
[0]
Combined button and popup list for selecting options.
@ WA_NoMousePropagation
Definition qnamespace.h:339
@ AccessibleDescriptionRole
@ ItemIsSelectable
@ ItemIsEnabled
static bool isSeparator(char c)
Definition qhsts.cpp:280
const GLfloat * m
GLint GLsizei GLsizei height
GLuint index
[2]
GLuint GLuint end
GLdouble GLdouble GLdouble GLdouble top
GLint GLsizei width
GLint GLint bottom
GLuint start
struct _cl_event * event
GLsizei maxCount
Definition qopenglext.h:677
GLfloat GLfloat p
[1]
GLuint GLenum option
SSL_CTX int(* cb)(SSL *ssl, unsigned char **out, unsigned char *outlen, const unsigned char *in, unsigned int inlen, void *arg)
#define Q_AUTOTEST_EXPORT
#define QT_REQUIRE_CONFIG(feature)
static QT_BEGIN_NAMESPACE void init(QTextBoundaryFinder::BoundaryType type, QStringView str, QCharAttributes *attributes)
#define Q_OBJECT
#define Q_SLOTS
#define Q_SIGNALS
#define emit
QSqlQueryModel * model
[16]
QLineEdit * lineEdit
QTimer * timer
[3]
QGraphicsItem * item
view viewport() -> scroll(dx, dy, deviceRect)
QPainter painter(this)
[7]
QQuickView * view
[0]