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
qquicktableviewdelegate.cpp
Go to the documentation of this file.
1// Copyright (C) 2024 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
7
8#include <QtQuickTemplates2/private/qquickitemdelegate_p_p.h>
9#include <QtQuick/private/qquicktaphandler_p.h>
10#include <QtQuick/private/qquicktableview_p.h>
11
12#include <QtCore/qpointer.h>
13
15
16/*!
17 \qmltype TableViewDelegate
18 \inherits ItemDelegate
19 \inqmlmodule QtQuick.Controls
20 \since 6.9
21 \ingroup qtquickcontrols-delegates
22 \brief A delegate that can be assigned to a TableView.
23
24 \image qtquickcontrols-tableviewdelegate.png
25
26 A TableViewDelegate is a delegate that can be assigned to the
27 \l {TableView::delegate} {delegate property} of a \l TableView.
28 It renders each cell of the table in the view using the application style.
29
30 \code
31 TableView {
32 anchors.fill: parent
33 delegate: TableViewDelegate {}
34 // model: yourModel
35 }
36 \endcode
37
38 TableViewDelegate inherits \l ItemDelegate, which means that it's composed of
39 two items: a \l[QML]{Control::}{background} and a \l [QML]{Control::}{contentItem}.
40
41 The position of the contentItem is controlled with \l [QML]{Control::}{padding}.
42
43 \section2 Interacting with pointers
44 TableViewDelegate inherits \l ItemDelegate. This means that it will emit signals such as
45 \l {AbstractButton::clicked()}{clicked} when the user clicks on the delegate.
46 You can connect to this signal to implement application-specific functionality.
47
48 However, the ItemDelegate API does not give you information about the position of the
49 click, or which modifiers are being held. If this is needed, a better approach would
50 be to use pointer handlers, for example:
51
52 \code
53 TableView {
54 id: tableView
55 delegate: TableViewDelegate {
56 TapHandler {
57 acceptedButtons: Qt.RightButton
58 onTapped: someContextMenu.open()
59 }
60
61 TapHandler {
62 acceptedModifiers: Qt.ControlModifier
63 onTapped: tableView.doSomethingToCell(row, column)
64 }
65 }
66 }
67 \endcode
68
69 \note If you want to disable the default behavior that occurs when the
70 user clicks on the delegate (like changing the current index), you can set
71 \l {TableView::pointerNavigationEnabled}{pointerNavigationEnabled} to \c false.
72
73 \section2 Editing cells in the table
74 TableViewDelegate has a default \l {TableView::editDelegate}{edit delegate} assigned.
75 If \l TableView has \l {TableView::editTriggers}{edit triggers} set, and
76 the \l {TableView::model}{model} has support for \l {Editing cells} {editing model items},
77 then the user can activate any of the edit triggers to edit the text of
78 the \l {TableViewDelegate::current}{current} table cell.
79
80 The default edit delegate will use the \c {Qt.EditRole} to read and write data to the
81 \l {TableView::model}{model}. If you need to use another role, or otherwise have needs
82 outside what the default edit delegate offers, you can always assign your own delegate
83 to \l {TableView::editDelegate}{TableView.editDelegate}.
84
85 \sa {Customizing TableViewDelegate}, {TableView}
86*/
87
88/*!
89 \qmlproperty TableView QtQuick.Controls::TableViewDelegate::tableView
90
91 This property points to the \l TableView that contains the delegate item.
92*/
93
94/*!
95 \qmlproperty bool QtQuick.Controls::TableViewDelegate::current
96
97 This property holds whether or not the delegate represents the
98 \l {QItemSelectionModel::currentIndex()}{current index}
99 in the \l {TableView::selectionModel}{selection model}.
100*/
101
102/*!
103 \qmlproperty bool QtQuick.Controls::TableViewDelegate::selected
104
105 This property holds whether or not the delegate represents a
106 \l {QItemSelectionModel::selection()}{selected index}
107 in the \l {TableView::selectionModel}{selection model}.
108*/
109
110/*!
111 \qmlproperty bool QtQuick.Controls::TableViewDelegate::editing
112
113 This property holds whether or not the delegate is being \l {Editing cells}{edited}.
114*/
115
116using namespace Qt::Literals::StringLiterals;
117
118QQuickTableViewDelegate::QQuickTableViewDelegate(QQuickItem *parent)
119 : QQuickItemDelegate(*(new QQuickTableViewDelegatePrivate), parent)
120{
121 Q_D(QQuickTableViewDelegate);
122
123 auto tapHandler = new QQuickTapHandler(this);
124 tapHandler->setAcceptedModifiers(Qt::NoModifier);
125
126 // Since we override mousePressEvent to avoid QQuickAbstractButton from blocking
127 // pointer handlers, we inform the button about its pressed state from the tap
128 // handler instead. This will ensure that we emit button signals like
129 // pressed, clicked, and doubleClicked.
130 connect(tapHandler, &QQuickTapHandler::pressedChanged, this, [this, d, tapHandler] {
131 auto view = tableView();
132 if (!view || !view->pointerNavigationEnabled())
133 return;
134
135 const QQuickHandlerPoint p = tapHandler->point();
136 if (tapHandler->isPressed())
137 d->handlePress(p.position(), 0);
138 else if (tapHandler->tapCount() > 0)
139 d->handleRelease(p.position(), 0);
140 else
141 d->handleUngrab();
142
143 if (tapHandler->tapCount() > 1 && !tapHandler->isPressed())
144 emit doubleClicked();
145 }, Qt::DirectConnection);
146}
147
148QQuickTableViewDelegate::QQuickTableViewDelegate(QQuickTableViewDelegatePrivate &dd, QQuickItem *parent)
149 : QQuickItemDelegate(dd, parent)
150{
151}
152
153void QQuickTableViewDelegate::mousePressEvent(QMouseEvent *event)
154{
155 Q_D(QQuickTableViewDelegate);
156
157 const auto view = d->m_tableView;
158 if (view && view->pointerNavigationEnabled()) {
159 // Ignore mouse events so that we don't block our own pointer handlers, or
160 // pointer handlers in e.g TreeView, TableView, or SelectionRectangle. Instead
161 // we call out to the needed mouse handling functions in QQuickAbstractButton directly
162 // from our pointer handlers, to ensure that we continue to work as a button.
163 event->ignore();
164 return;
165 }
166
167 QQuickItemDelegate::mousePressEvent(event);
168}
169
170QPalette QQuickTableViewDelegatePrivate::defaultPalette() const
171{
172 return QQuickTheme::palette(QQuickTheme::ItemView);
173}
174
175QFont QQuickTableViewDelegate::defaultFont() const
176{
177 return QQuickTheme::font(QQuickTheme::ItemView);
178}
179
180bool QQuickTableViewDelegate::current() const
181{
182 return d_func()->current;
183}
184
185void QQuickTableViewDelegate::setCurrent(bool current)
186{
187 Q_D(QQuickTableViewDelegate);
188 if (d->current == current)
189 return;
190
191 d->current = current;
192 emit currentChanged();
193}
194
195bool QQuickTableViewDelegate::selected() const
196{
197 return d_func()->selected;
198}
199
200void QQuickTableViewDelegate::setSelected(bool selected)
201{
202 Q_D(QQuickTableViewDelegate);
203 if (d->selected == selected)
204 return;
205
206 d->selected = selected;
207 emit selectedChanged();
208}
209
210bool QQuickTableViewDelegate::editing() const
211{
212 return d_func()->editing;
213}
214
215void QQuickTableViewDelegate::setEditing(bool editing)
216{
217 Q_D(QQuickTableViewDelegate);
218 if (d->editing == editing)
219 return;
220
221 d->editing = editing;
222 emit editingChanged();
223}
224
225QQuickTableView *QQuickTableViewDelegate::tableView() const
226{
227 return d_func()->m_tableView;
228}
229
230void QQuickTableViewDelegate::setTableView(QQuickTableView *tableView)
231{
232 Q_D(QQuickTableViewDelegate);
233 if (d->m_tableView == tableView)
234 return;
235
236 d->m_tableView = tableView;
237 emit tableViewChanged();
238}
239
240QT_END_NAMESPACE
241
242#include "moc_qquicktableviewdelegate_p.cpp"