Provides a table view of items to display data from a model. 更多...
import 语句: | import QtQuick 2.2 |
Since: | Qt 5.12 |
继承: | Flickable |
A TableView has a model that defines the data to be displayed, and a delegate that defines how the data should be displayed.
TableView inherits Flickable . This means that while the model can have any number of rows and columns, only a subsection of the table is usually visible inside the viewport. As soon as you flick, new rows and columns enter the viewport, while old ones exit and are removed from the viewport. The rows and columns that move out are reused for building the rows and columns that move into the viewport. As such, the TableView support models of any size without affecting performance.
A TableView displays data from models created from built-in QML types such as ListModel and XmlListModel , which populates the first column only in a TableView. To create models with multiple columns, either use TableModel or a C++ model that inherits QAbstractItemModel .
The following example shows how to create a model from C++ with multiple columns:
#include <qqml.h> #include <QAbstractTableModel> class TableModel : public QAbstractTableModel { Q_OBJECT QML_ELEMENT QML_ADDED_IN_MINOR_VERSION(1) public: int rowCount(const QModelIndex & = QModelIndex()) const override { return 200; } int columnCount(const QModelIndex & = QModelIndex()) const override { return 200; } QVariant data(const QModelIndex &index, int role) const override { switch (role) { case Qt::DisplayRole: return QString("%1, %2").arg(index.column()).arg(index.row()); default: break; } return QVariant(); } QHash<int, QByteArray> roleNames() const override { return { {Qt::DisplayRole, "display"} }; } };
And then how to use it from QML:
import QtQuick 2.12 import TableModel 0.1 TableView { anchors.fill: parent columnSpacing: 1 rowSpacing: 1 clip: true model: TableModel {} delegate: Rectangle { implicitWidth: 100 implicitHeight: 50 Text { text: display } } }
For prototyping and displaying very simple data (from a web API, for example), TableModel 可以被使用:
import QtQuick 2.14 import Qt.labs.qmlmodels 1.0 TableView { anchors.fill: parent columnSpacing: 1 rowSpacing: 1 clip: true model: TableModel { TableModelColumn { display: "name" } TableModelColumn { display: "color" } rows: [ { "name": "cat", "color": "black" }, { "name": "dog", "color": "brown" }, { "name": "bird", "color": "white" } ] } delegate: Rectangle { implicitWidth: 100 implicitHeight: 50 border.width: 1 Text { text: display anchors.centerIn: parent } } }
TableView recycles delegate items by default, instead of instantiating from the delegate whenever new rows and columns are flicked into view. This approach gives a huge performance boost, depending on the complexity of the delegate.
When an item is flicked out, it moves to the reuse pool , which is an internal cache of unused items. When this happens, the TableView::pooled signal is emitted to inform the item about it. Likewise, when the item is moved back from the pool, the TableView::reused 信号被发射。
Any item properties that come from the model are updated when the item is reused. This includes
index
,
row
,和
column
, but also any model roles.
注意: Avoid storing any state inside a delegate. If you do, reset it manually on receiving the TableView::reused 信号。
If an item has timers or animations, consider pausing them on receiving the TableView::pooled signal. That way you avoid using the CPU resources for items that are not visible. Likewise, if an item has resources that cannot be reused, they could be freed up.
If you don't want to reuse items or if the
delegate
cannot support it, you can set the
reuseItems
特性到
false
.
注意: While an item is in the pool, it might still be alive and respond to connected signals and bindings.
The following example shows a delegate that animates a spinning rectangle. When it is pooled, the animation is temporarily paused:
Component { id: tableViewDelegate Rectangle { implicitWidth: 100 implicitHeight: 50 TableView.onPooled: rotationAnimation.pause() TableView.onReused: rotationAnimation.resume() Rectangle { id: rect anchors.centerIn: parent width: 40 height: 5 color: "green" RotationAnimation { id: rotationAnimation target: rect duration: (Math.random() * 2000) + 200 from: 0 to: 359 running: true loops: Animation.Infinite } } } }
When a new column is flicked into view, TableView will determine its width by calling the columnWidthProvider function. TableView does not store row height or column width, as it's designed to support large models containing any number of rows and columns. Instead, it will ask the application whenever it needs to know.
TableView uses the largest
implicitWidth
among the items as the column width, unless the
columnWidthProvider
property is explicitly set. Once the column width is found, all other items in the same column are resized to this width, even if new items that are flicked in later have larger
implicitWidth
. Setting an explicit
width
on an item is ignored and overwritten.
注意:
The calculated width of a column is discarded when it is flicked out of the viewport, and is recalculated if the column is flicked back in. The calculation is always based on the items that are visible when the column is flicked in. This means that column width can be different each time, depending on which row you're at when the column enters. You should therefore have the same
implicitWidth
for all items in a column, or set
columnWidthProvider
. The same logic applies for the row height calculation.
If you change the values that a rowHeightProvider 或 columnWidthProvider return for rows and columns inside the viewport, you must call forceLayout . This informs TableView that it needs to use the provider functions again to recalculate and update the layout.
Since Qt 5.13, if you want to hide a specific column, you can return
0
从
columnWidthProvider
for that column. Likewise, you can return 0 from the
rowHeightProvider
to hide a row. If you return a negative number, TableView will fall back to calculate the size based on the delegate items.
注意: The size of a row or column should be a whole number to avoid sub-pixel alignment of items.
The following example shows how to set a simple
columnWidthProvider
together with a timer that modifies the values the function returns. When the array is modified,
forceLayout
is called to let the changes take effect:
TableView { id: tableView property var columnWidths: [100, 50, 80, 150] columnWidthProvider: function (column) { return columnWidths[column] } Timer { running: true interval: 2000 onTriggered: { tableView.columnWidths[2] = 150 tableView.forceLayout(); } } }
All new items that are instantiated from the delegate are parented to the
contentItem
采用
z
值,
1
. You can add your own items inside the Tableview, as child items of the Flickable. By controlling their
z
value, you can make them be on top of or underneath the table items.
Here is an example that shows how to add some text on top of the table, that moves together with the table as you flick:
TableView { id: tableView topMargin: header.implicitHeight Text { id: header text: "A table header" } }
You can add selection support to TableView by assigning an ItemSelectionModel 到 selectionModel property. It will then use this model to control which delegate items should be shown as selected. For a delegate item to be shown as selected, it needs to contain the following property:
required property bool selected
注意:
It's important for the
selected
property to be defined as
required
. This will inform TableView that it should take responsibility for the property's value. If it's not defined as required, it will simply be ignored. See also
Required Properties
.
The following snippet shows how an application can render the delegate differently depending on the
selected
特性:
TableView { id: tableView anchors.fill: parent clip: true model: TableModel { TableModelColumn { display: "name" } rows: [ { "name": "Harry" }, { "name": "Hedwig" } ] } selectionModel: ItemSelectionModel { model: tableView.model } delegate: Rectangle { implicitWidth: 100 implicitHeight: 30 color: selected ? "blue" : "lightgray" required property bool selected Text { text: display } } }
注意: Qt Quick Controls offers a SelectionRectangle that can be used to let the user select cells.
bottomRow : int |
This property holds the bottom-most row that is currently visible inside the view.
另请参阅 leftColumn , rightColumn ,和 topRow .
columnSpacing : real |
This property holds the spacing between the columns.
默认值为
0
.
columnWidthProvider : var |
This property can hold a function that returns the column width for each column in the model. It is called whenever
TableView
needs to know the width of a specific column. The function takes one argument,
column
, for which the
TableView
needs to know the width.
Since Qt 5.13, if you want to hide a specific column, you can return
0
width for that column. If you return a negative number,
TableView
calculates the width based on the delegate items.
注意: The columnWidthProvider will usually be called two times when a column is about to load (or when doing layout). First, to know if the column is visible and should be loaded. And second, to determine the width of the column after all items have been loaded. If you need to calculate the column width based on the size of the delegate items, you need to wait for the second call, when all the items have been loaded. You can check for this by calling isColumnLoaded(column) , and simply return -1 if that is not yet the case.
另请参阅 rowHeightProvider , isColumnLoaded() ,和 Row heights and column widths .
[read-only] columns : int |
This property holds the number of columns in the table.
注意: columns is usually equal to the number of columns in the model, but can temporarily differ until all pending model changes have been processed.
If the model is a list, columns will be
1
.
This property is read only.
contentHeight : real |
This property holds the table height required to accommodate the number of rows in the data model. This is usually not the same as the
height
的
view
, which means that the table's height could be larger or smaller than the viewport height. As a
TableView
cannot always know the exact height of the table without loading all rows in the model, the
contentHeight
is usually an estimate based on the initially loaded table.
If you know what the height of the table will be, assign a value to
contentHeight
, to avoid unnecessary calculations and updates to the
TableView
.
另请参阅 contentWidth and rowHeightProvider .
contentWidth : real |
This property holds the table width required to accommodate the number of columns in the model. This is usually not the same as the
width
的
view
, which means that the table's width could be larger or smaller than the viewport width. As a
TableView
cannot always know the exact width of the table without loading all columns in the model, the
contentWidth
is usually an estimate based on the initially loaded table.
If you know what the width of the table will be, assign a value to
contentWidth
, to avoid unnecessary calculations and updates to the
TableView
.
另请参阅 contentHeight and columnWidthProvider .
delegate : 组件 |
The delegate provides a template defining each cell item instantiated by the view. The model index is exposed as an accessible
index
property. The same applies to
row
and
column
. Properties of the model are also available depending upon the type of
Data Model
.
A delegate should specify its size using implicitWidth and implicitHeight 。 TableView lays out the items based on that information. Explicit width or height settings are ignored and overwritten.
注意:
Delegates are instantiated as needed and may be destroyed at any time. They are also reused if the
reuseItems
property is set to
true
. You should therefore avoid storing state information in the delegates.
另请参阅 Row heights and column widths and Reusing items .
leftColumn : int |
This property holds the leftmost column that is currently visible inside the view.
另请参阅 rightColumn , topRow ,和 bottomRow .
model : model |
This property holds the model that provides data for the table.
The model provides the set of data that is used to create the items in the view. Models can be created directly in QML using TableModel , ListModel , ObjectModel , or provided by a custom C++ model class. The C++ model must be a subclass of QAbstractItemModel or a simple list.
另请参阅 数据模型 .
reuseItems : bool |
This property holds whether or not items instantiated from the
delegate
should be reused. If set to
false
, any currently pooled items are destroyed.
另请参阅 Reusing items , TableView::pooled ,和 TableView::reused .
rightColumn : int |
This property holds the rightmost column that is currently visible inside the view.
另请参阅 leftColumn , topRow ,和 bottomRow .
rowHeightProvider : var |
This property can hold a function that returns the row height for each row in the model. It is called whenever
TableView
needs to know the height of a specific row. The function takes one argument,
row
, for which the
TableView
needs to know the height.
Since Qt 5.13, if you want to hide a specific row, you can return
0
height for that row. If you return a negative number,
TableView
calculates the height based on the delegate items.
注意: The rowHeightProvider will usually be called two times when a row is about to load (or when doing layout). First, to know if the row is visible and should be loaded. And second, to determine the height of the row after all items have been loaded. If you need to calculate the row height based on the size of the delegate items, you need to wait for the second call, when all the items have been loaded. You can check for this by calling isRowLoaded(row) , and simply return -1 if that is not yet the case.
另请参阅 rowHeightProvider, isRowLoaded() ,和 Row heights and column widths .
rowSpacing : real |
This property holds the spacing between the rows.
默认值为
0
.
[read-only] rows : int |
This property holds the number of rows in the table.
注意: rows is usually equal to the number of rows in the model, but can temporarily differ until all pending model changes have been processed.
This property is read only.
selectionModel : ItemSelectionModel |
This property can be set to control which delegate items should be shown as selected. If the delegate has a
required property bool selected
defined,
TableView
will keep it in sync with the selection state of the corresponding model item in the selection model.
另请参阅 选择项 and SelectionRectangle .
syncDirection : Qt::Orientations |
若
syncView
被设置在
TableView
, this property controls synchronization of flicking direction(s) for both tables. The default is
Qt.Horizontal | Qt.Vertical
, which means that if you flick either table in either direction, the other table is flicked the same amount in the same direction.
This property and syncView can be used to make two tableViews synchronize with each other smoothly in flicking regardless of the different overshoot/undershoot, velocity, acceleration/deceleration or rebound animation, and so on.
A typical use case is to make several headers flick along with the table.
另请参阅 syncView .
syncView : TableView |
If this property of a TableView is set to another TableView , both the tables will synchronize with regard to flicking, column widths/row heights, and spacing according to syncDirection .
若 syncDirection 包含 Qt.Horizontal , current tableView's column widths, column spacing, and horizontal flicking movement synchronizes with syncView's.
若 syncDirection 包含 Qt.Vertical , current tableView's row heights, row spacing, and vertical flicking movement synchronizes with syncView's.
另请参阅 syncDirection .
topRow : int |
This property holds the topmost row that is currently visible inside the view.
另请参阅 leftColumn , rightColumn ,和 bottomRow .
TableView.view : TableView |
This attached property holds the view that manages the delegate instance. It is attached to each instance of the delegate.
pooled () |
This signal is emitted after an item has been added to the reuse pool. You can use it to pause ongoing timers or animations inside the item, or free up resources that cannot be reused.
This signal is emitted only if the
reuseItems
特性为
true
.
注意:
相应处理程序是
onPooled
.
另请参阅 Reusing items , reuseItems ,和 reused .
reused () |
This signal is emitted after an item has been reused. At this point, the item has been taken out of the pool and placed inside the content view, and the model properties such as index, row, and column have been updated.
Other properties that are not provided by the model does not change when an item is reused. You should avoid storing any state inside a delegate, but if you do, manually reset that state on receiving this signal.
This signal is emitted when the item is reused, and not the first time the item is created.
This signal is emitted only if the
reuseItems
特性为
true
.
注意:
相应处理程序是
onReused
.
另请参阅 Reusing items , reuseItems ,和 pooled .
点 cellAtPos ( real x , real y , bool includeSpacing ) |
Convenience for calling
cellAtPos(Qt.point(x, y), includeSpacing)
.
点 cellAtPos ( point position , bool includeSpacing ) |
Returns the cell at the given
position
in the view. If no cell intersects with
position
, the return value will be
point(-1, -1)
.
若
includeSpacing
被设为
true
, a cell's bounding box will be considered to include half the adjacent
rowSpacing
and
columnSpacing
on each side. The default value is
false
.
另请参阅 columnSpacing and rowSpacing .
[since 6.2]
real
columnWidth
(
int
column
)
|
返回宽度为给定
column
. If the column is not loaded (and therefore not visible), the return value will be
-1
.
注意: It's the applications responsibility to store what the column widths are, by using a columnWidthProvider . Hence, there is no setter function. This getter function is mostly useful if the TableView doesn't have a columnWidthProvider set, since otherwise you can call that function instead (which will work, even for columns that are not currently visible. If no columnWidthProvider is set, the height of a row will be equal to its implicitColumnWidth() .
This method was introduced in Qt 6.2.
另请参阅 columnWidthProvider , implicitColumnWidth() , isColumnLoaded() ,和 Row heights and column widths .
forceLayout () |
Responding to changes in the model are batched so that they are handled only once per frame. This means the TableView delays showing any changes while a script is being run. The same is also true when changing properties, such as rowSpacing or leftMargin .
This method forces the TableView to immediately update the layout so that any recent changes take effect.
Calling this function re-evaluates the size and position of each visible row and column. This is needed if the functions assigned to rowHeightProvider or columnWidthProvider return different values than what is already assigned.
[since 6.2]
real
implicitColumnWidth
(
int
column
)
|
Returns the implicit width of the given
column
. If the column is not loaded (and therefore not visible), the return value will be
-1
.
The implicit width of a column is the largest implicitWidth found among the currently loaded delegate items inside that column. Widths returned by the columnWidthProvider will not be taken into account.
This method was introduced in Qt 6.2.
另请参阅 columnWidthProvider , columnWidth() , isColumnLoaded() ,和 Row heights and column widths .
[since 6.2]
real
implicitRowHeight
(
int
row
)
|
Returns the implicit height of the given
row
. If the row is not loaded (and therefore not visible), the return value will be
-1
.
The implicit height of a row is the largest implicitHeight found among the currently loaded delegate items inside that row. Heights returned by the rowHeightProvider will not be taken into account.
This method was introduced in Qt 6.2.
另请参阅 rowHeightProvider , rowHeight() , isRowLoaded() ,和 Row heights and column widths .
[since 6.2]
bool
isColumnLoaded
(
int
column
)
|
返回
true
若给定
column
is loaded.
A column is loaded when TableView has loaded the delegate items needed to show the column inside the view. This also usually means that the column is visible for the user, but not always.
This function can be used whenever you need to iterate over the delegate items for a column, e.g from a columnWidthProvider , to be sure that the delegate items are available for iteration.
This method was introduced in Qt 6.2.
[since 6.2]
bool
isRowLoaded
(
int
row
)
|
返回
true
若给定
row
is loaded.
A row is loaded when TableView has loaded the delegate items needed to show the row inside the view. This also usually means that the row is visible for the user, but not always.
This function can be used whenever you need to iterate over the delegate items for a row, e.g from a rowHeightProvider , to be sure that the delegate items are available for iteration.
This method was introduced in Qt 6.2.
Item itemAtCell ( int column , int row ) |
Convenience for calling
itemAtCell(Qt.point(column, row))
.
Item itemAtCell ( point cell ) |
Returns the delegate item at
cell
if loaded, otherwise
null
.
注意: only the items that are visible in the view are normally loaded. As soon as a cell is flicked out of the view, the item inside will either be unloaded or placed in the recycle pool. As such, the return value should never be stored.
positionViewAtCell ( int column , int row , Qt . Alignment alignment , point offset ) |
Convenience for calling
positionViewAtCell(Qt.point(column, row), alignment, offset)
positionViewAtCell ( point cell , Qt . Alignment alignment , point offset ) |
Positions contentX and contentY such that cell is at the position specified by alignment . alignment can be an or-ed combination of the following:
常量 | 描述 |
---|---|
Qt.AlignLeft
|
Position the cell at the left of the view. |
Qt.AlignHCenter
|
Position the cell at the horizontal center of the view. |
Qt.AlignRight
|
Position the cell at the right of the view. |
Qt.AlignTop
|
Position the cell at the top of the view. |
Qt.AlignVCenter
|
Position the cell at the vertical center of the view. |
Qt.AlignBottom
|
Position the cell at the bottom of the view. |
Qt.AlignCenter
|
The same as (Qt.AlignHCenter | Qt.AlignVCenter) |
If no vertical alignment is specified, vertical positioning will be ignored. The same is true for horizontal alignment.
Optionally, you can specify offset to move contentX and contentY an extra number of pixels beyond the target alignment. E.g if you want to position the view so that cell [10, 10] ends up at the top-left corner with a 5px margin, you could do:
positionViewAtCell(Qt.point(10, 10), Qt.AlignLeft | Qt.AlignTop, Qt.point(-5, -5))
注意: It is not recommended to use contentX or contentY to position the view at a particular cell. This is unreliable since removing items from the start of the table does not cause all other items to be repositioned. TableView can also sometimes place rows and columns at approximate positions to optimize for speed. The only exception is if the cell is already visible in the view, which can be checked upfront by calling itemAtCell() .
Methods should only be called after the Component has completed. To position the view at startup, this method should be called by Component.onCompleted. For example, to position the view at the end:
Component.onCompleted: positionViewAtCell(Qt.point(columns - 1, rows - 1), Qt.AlignRight | Qt.AlignBottom)
positionViewAtColumn ( int column , Qt . Alignment alignment , real offset ) |
Convenience method for calling
positionViewAtCell(Qt.point(
column
, 0),
alignment
& Qt.AlignHorizontal_Mask, Qt.point(
offset
, 0))
positionViewAtRow ( int row , Qt . Alignment alignment , real offset ) |
Convenience method for calling
positionViewAtCell(Qt.point(0,
row
),
alignment
& Qt.AlignVertical_Mask, Qt.point(0,
offset
))
[since 6.2]
real
rowHeight
(
int
row
)
|
返回高度为给定
row
. If the row is not loaded (and therefore not visible), the return value will be
-1
.
注意: It's the applications responsibility to store what the row heights are, by using a rowHeightProvider . Hence, there is no setter function. This getter function is mostly useful if the TableView doesn't have a rowHeightProvider set, since otherwise you can call that function instead (which will work, even for rows that are not currently visible. If no rowHeightProvider is set, the height of a row will be equal to its implicitRowHeight() .
This method was introduced in Qt 6.2.
另请参阅 rowHeightProvider , implicitRowHeight() , isRowLoaded() ,和 Row heights and column widths .