17#include <private/qscrollbar_p.h>
18#if QT_CONFIG(accessibility)
22#include <private/qapplication_p.h>
23#include <private/qtreeview_p.h>
24#include <private/qheaderview_p.h>
173 d->clearConnections();
189 if (
d->selectionModel) {
192 d->viewItems.clear();
193 d->expandedIndexes.clear();
194 d->hiddenIndexes.clear();
195 d->geometryRecursionBlock =
true;
196 d->header->setModel(
model);
197 d->geometryRecursionBlock =
false;
208 d->modelConnections = {
216 if (
d->sortingEnabled)
217 d->sortIndicatorChanged(
header()->sortIndicatorSection(),
header()->sortIndicatorOrder());
226 d->header->setRootIndex(
index);
237 if (
d->selectionModel) {
245 if (
d->selectionModel) {
247 d->selectionmodelConnection =
277 if (
d->header &&
d->header->parent() ==
this)
280 d->header->setParent(
this);
283 if (!
d->header->model()) {
284 d->header->setModel(
d->model);
285 if (
d->selectionModel)
286 d->header->setSelectionModel(
d->selectionModel);
289 d->headerConnections = {
320 return d->autoExpandDelay;
326 d->autoExpandDelay = delay;
351 if (!
d->customIndent || (
i !=
d->indent)) {
353 d->customIndent =
true;
354 d->viewport->update();
361 if (
d->customIndent) {
362 d->updateIndentationFromStyle();
363 d->customIndent =
false;
381 return d->rootDecoration;
387 if (
show !=
d->rootDecoration) {
388 d->rootDecoration =
show;
389 d->viewport->update();
412 return d->uniformRowHeights;
418 d->uniformRowHeights = uniform;
434 return d->itemsExpandable;
456 return d->expandsOnDoubleClick;
462 d->expandsOnDoubleClick =
enable;
471 return d->header->sectionViewportPosition(
column);
482 return d->header->sectionSize(
column);
505 return d->header->logicalIndexAt(
x);
516 return d->header->isSectionHidden(
column);
527 if (column < 0 || column >=
d->header->count())
545 return d->header->isHidden();
551 d->header->setHidden(
hide);
565 return d->isRowHidden(
d->model->index(
row, 0, parent));
579 if (!
index.isValid())
583 d->hiddenIndexes.insert(
index);
584 }
else if (
d->isPersistent(
index)) {
585 d->hiddenIndexes.remove(
index);
588 d->doDelayedItemsLayout();
602 if (
d->spanningIndexes.isEmpty() || !
d->model)
605 return d->spanningIndexes.contains(
index);
623 if (!
index.isValid())
627 d->spanningIndexes.insert(
index);
629 d->spanningIndexes.remove(
index);
631 d->executePostedLayout();
634 d->viewItems[
i].spanning =
span;
636 d->viewport->update();
643 const QList<int> &roles)
648 if (
d->delayedPendingLayout)
654 bool sizeChanged =
false;
655 int topViewIndex =
d->viewIndex(topLeft);
656 if (topViewIndex == 0) {
658 sizeChanged =
d->defaultItemHeight != newDefaultItemHeight;
659 d->defaultItemHeight = newDefaultItemHeight;
662 if (topViewIndex != -1) {
663 if (topLeft.
row() == bottomRight.
row()) {
664 int oldHeight =
d->itemHeight(topViewIndex);
665 d->invalidateHeightCache(topViewIndex);
666 sizeChanged |= (oldHeight !=
d->itemHeight(topViewIndex));
667 if (topLeft.
column() == 0)
668 d->viewItems[topViewIndex].hasChildren =
d->hasVisibleChildren(topLeft);
670 int bottomViewIndex =
d->viewIndex(bottomRight);
671 for (
int i = topViewIndex;
i <= bottomViewIndex; ++
i) {
672 int oldHeight =
d->itemHeight(
i);
673 d->invalidateHeightCache(
i);
674 sizeChanged |= (oldHeight !=
d->itemHeight(
i));
675 if (topLeft.
column() == 0)
676 d->viewItems[
i].hasChildren =
d->hasVisibleChildren(
d->viewItems.at(
i).index);
682 d->updateScrollBars();
683 d->viewport->update();
700 if (
d->header->isSectionHidden(
column))
702 d->header->hideSection(
column);
714 if (!
d->header->isSectionHidden(
column))
716 d->header->showSection(
column);
730 if (!
d->isIndexValid(
index))
734 if (
d->isIndexExpanded(
index))
736 if (
d->delayedPendingLayout) {
738 if (
d->storeExpanded(
index))
746 if (!
d->isAnimating()) {
748 d->viewport->update();
750 }
else if (
d->storeExpanded(
index)) {
765 if (!
d->isIndexValid(
index))
767 if (!
d->isIndexExpanded(
index))
770 d->delayedAutoScroll.stop();
772 if (
d->delayedPendingLayout) {
774 if (
d->isPersistent(
index) &&
d->expandedIndexes.remove(
index))
780 d->collapse(
i,
true);
781 if (!
d->isAnimating()) {
786 if (
d->isPersistent(
index) &&
d->expandedIndexes.remove(
index))
802 return d->isIndexExpanded(
index);
844 d->sortHeaderConnection =
857 return d->sortingEnabled;
876 d->animationsEnabled = animate;
882 return d->animationsEnabled;
899 if (
d->allColumnsShowFocus ==
enable)
901 d->allColumnsShowFocus =
enable;
902 d->viewport->update();
908 return d->allColumnsShowFocus;
927 if (
d->wrapItemText == on)
929 d->wrapItemText = on;
930 d->doDelayedItemsLayout();
936 return d->wrapItemText;
952 d->viewport->update();
967 return d->treePosition;
976 if (!
d->model->rowCount(
d->root) || !
d->model->columnCount(
d->root))
980 d->executePostedLayout();
981 if (
d->viewItems.isEmpty())
988 start =
d->viewItems.at(0).index;
990 bool skipRow =
false;
991 bool keyboardTimeWasValid =
d->keyboardInputTime.isValid();
992 qint64 keyboardInputTimeElapsed;
993 if (keyboardTimeWasValid)
994 keyboardInputTimeElapsed =
d->keyboardInputTime.restart();
996 d->keyboardInputTime.start();
997 if (search.
isEmpty() || !keyboardTimeWasValid
999 d->keyboardInput = search;
1002 d->keyboardInput += search;
1006 bool sameKey =
false;
1007 if (
d->keyboardInput.size() > 1) {
1008 int c =
d->keyboardInput.
count(
d->keyboardInput.at(
d->keyboardInput.size() - 1));
1009 sameKey = (
c ==
d->keyboardInput.size());
1019 const int origCol =
start.column();
1020 start =
d->viewItems.at(0).index;
1021 if (origCol !=
start.column())
1026 int startIndex =
d->viewIndex(
start);
1027 if (startIndex <= -1)
1030 int previousLevel = -1;
1033 QString searchString = sameKey ?
QString(
d->keyboardInput.at(0)) :
d->keyboardInput;
1034 for (
int i = 0;
i <
d->viewItems.size(); ++
i) {
1035 if ((
int)
d->viewItems.at(
i).level > previousLevel) {
1037 if (
start.column() > 0)
1038 searchFrom = searchFrom.
sibling(searchFrom.row(),
start.column());
1039 if (searchFrom.parent() ==
start.parent())
1043 int hitIndex =
d->viewIndex(
match.at(0));
1044 if (hitIndex >= 0 && hitIndex < startIndex)
1045 bestAbove = bestAbove == -1 ? hitIndex :
qMin(hitIndex, bestAbove);
1046 else if (hitIndex >= startIndex)
1047 bestBelow = bestBelow == -1 ? hitIndex :
qMin(hitIndex, bestBelow);
1050 previousLevel =
d->viewItems.at(
i).level;
1055 index =
d->viewItems.at(bestBelow).index;
1056 else if (bestAbove > -1)
1057 index =
d->viewItems.at(bestAbove).index;
1059 if (
start.column() > 0)
1062 if (
index.isValid())
1118 width =
q->viewport()->width();
1119 }
else if (addIndentation) {
1122 width -= indentation;
1123 if (!
q->isRightToLeft())
1145 if (!
d->isIndexValid(
index))
1148 d->executePostedLayout();
1149 d->updateScrollBars();
1156 parent =
d->
model->parent(parent);
1167 int top = verticalScrollBar()->value();
1168 int bottom =
top + verticalScrollBar()->pageStep();
1172 verticalScrollBar()->setValue(
item);
1174 const int currentItemHeight =
d->itemHeight(
item);
1177 ?
area.height() / 2 + currentItemHeight - 1
1180 if (
y > currentItemHeight) {
1182 y -=
d->itemHeight(
item);
1190 verticalScrollBar()->setValue(
item);
1194 d->coordinateForItem(
item),
1196 d->itemHeight(
item));
1198 if (
rect.isEmpty()) {
1201 d->viewport->update(
rect);
1206 ||
area.height() <
rect.height()));
1211 int verticalValue = verticalScrollBar()->value();
1213 verticalValue +=
rect.top();
1215 verticalValue +=
rect.bottom() -
area.height();
1217 verticalValue +=
rect.top() - ((
area.height() -
rect.height()) / 2);
1218 verticalScrollBar()->setValue(verticalValue);
1222 int viewportWidth =
d->viewport->width();
1224 int horizontalPosition =
d->header->sectionPosition(
index.column());
1225 int cellWidth =
d->header->sectionSize(
index.column());
1228 horizontalScrollBar()->setValue(horizontalPosition - ((viewportWidth - cellWidth) / 2));
1230 if (horizontalPosition - horizontalOffset < 0 || cellWidth > viewportWidth)
1231 horizontalScrollBar()->setValue(horizontalPosition);
1232 else if (horizontalPosition -
horizontalOffset + cellWidth > viewportWidth)
1233 horizontalScrollBar()->setValue(horizontalPosition - viewportWidth + cellWidth);
1244 if (!
d->customIndent) {
1247 d->updateIndentationFromStyle();
1250 QAbstractItemView::changeEvent(
event);
1259 if (
event->timerId() ==
d->columnResizeTimerID) {
1261 killTimer(
d->columnResizeTimerID);
1262 d->columnResizeTimerID = 0;
1264 int viewportHeight =
d->viewport->
height();
1265 int viewportWidth =
d->viewport->width();
1266 for (
int i =
d->columnsToUpdate.size() - 1;
i >= 0; --
i) {
1267 int column =
d->columnsToUpdate.at(
i);
1269 if (isRightToLeft())
1272 rect |=
QRect(
x, 0, viewportWidth -
x, viewportHeight);
1274 d->viewport->update(
rect.normalized());
1275 d->columnsToUpdate.clear();
1276 }
else if (
event->timerId() ==
d->openTimer.timerId()) {
1279 &&
d->viewport->rect().contains(
pos)) {
1283 d->openTimer.stop();
1292#if QT_CONFIG(draganddrop)
1293void QTreeView::dragMoveEvent(QDragMoveEvent *
event)
1296 if (
d->autoExpandDelay >= 0)
1297 d->openTimer.start(
d->autoExpandDelay,
this);
1298 QAbstractItemView::dragMoveEvent(
event);
1308 switch (
event->type()) {
1313 const int oldBranch =
d->hoverBranch;
1314 d->hoverBranch =
d->itemDecorationAt(he->position().toPoint());
1316 if (
d->hover != newIndex ||
d->hoverBranch != oldBranch) {
1334 d->executePostedLayout();
1336#if QT_CONFIG(animation)
1337 if (
d->isAnimating()) {
1339 d->drawAnimatedOperation(&
painter);
1344#if QT_CONFIG(draganddrop)
1364 if (rowHeight <= 0) {
1371 option->features.setFlag(QStyleOptionViewItem::Alternate,
current & 1);
1394 q->updateGeometries();
1412 const auto parentIdx = topLeft.
parent();
1415 int left = std::numeric_limits<int>::max();
1416 int right = std::numeric_limits<int>::min();
1422 if (
left != std::numeric_limits<int>::max()) {
1425 if (!rowRect.intersects(
rect))
1432 if (!rowRect.intersects(
rect))
1435 for (
int col = topLeft.
column(); col <= bottomRight.
column(); ++col) {
1440 if (idxRect.isNull())
1443 if (idxRect.top() >
rect.bottom() && idxRect.bottom() <
rect.top())
1445 if (!idxRect.intersects(
rect))
1447 rowRect = rowRect.united(idxRect);
1448 if (rowRect.left() <
rect.left() && rowRect.right() >
rect.right())
1451 left = std::min(
left, rowRect.left());
1454 updateRect = updateRect.
united(rowRect);
1474 if (idx.column() > 0 &&
q->isFirstColumnSpanned(idx.row(), idx.parent()))
1489 ||
option->showDecorationSelected;
1493 QList<QStyleOptionViewItem::ViewItemPosition>
1501 const int visualIndex = logicalIndices.indexOf(
current.column());
1502 option->viewItemPosition = viewItemPosList.at(visualIndex);
1517 const QList<QTreeViewItem> &viewItems =
d->viewItems;
1519 QStyleOptionViewItem
option;
1524 if (viewItems.size() == 0 ||
d->header->count() == 0 || !
d->itemDelegate) {
1529 int firstVisibleItemOffset = 0;
1530 const int firstVisibleItem =
d->firstVisibleItem(&firstVisibleItemOffset);
1531 if (firstVisibleItem < 0) {
1536 const int viewportWidth =
d->viewport->width();
1539 d->hoverBranch =
d->itemDecorationAt(hoverPos);
1542 bool multipleRects = (region.
rectCount() > 1);
1543 for (
const QRect &
a : region) {
1545 ?
QRect(0,
a.y(), viewportWidth,
a.height())
1547 d->leftAndRight =
d->startAndEndColumns(
area);
1549 int i = firstVisibleItem;
1550 int y = firstVisibleItemOffset;
1553 for (;
i < viewItems.size(); ++
i) {
1554 const int itemHeight =
d->itemHeight(
i);
1555 if (
y + itemHeight >
area.top())
1561 for (;
i < viewItems.size() &&
y <=
area.bottom(); ++
i) {
1563 const int itemHeight =
d->itemHeight(
i);
1569 d->spanning = viewItems.at(
i).spanning;
1570 if (!multipleRects || !drawn.contains(
i)) {
1578 if (
y <=
area.bottom()) {
1588 for (
QObject *parent =
other; parent !=
nullptr; parent = parent->parent()) {
1596 QList<int> *logicalIndices, QList<QStyleOptionViewItem::ViewItemPosition> *itemPositions,
1603 int logicalIndexBeforeLeft = -1, logicalIndexAfterRight = -1;
1604 for (
int visualIndex =
left - 1; visualIndex >= 0; --visualIndex) {
1607 logicalIndexBeforeLeft = logicalIndex;
1612 for (
int visualIndex =
left; visualIndex < columnCount; ++visualIndex) {
1615 if (visualIndex >
right) {
1616 logicalIndexAfterRight = logicalIndex;
1619 logicalIndices->append(logicalIndex);
1623 itemPositions->resize(logicalIndices->size());
1624 for (
int currentLogicalSection = 0; currentLogicalSection < logicalIndices->size(); ++currentLogicalSection) {
1625 const int headerSection = logicalIndices->at(currentLogicalSection);
1627 int nextLogicalSection = currentLogicalSection + 1 >= logicalIndices->size()
1628 ? logicalIndexAfterRight
1629 : logicalIndices->at(currentLogicalSection + 1);
1630 int prevLogicalSection = currentLogicalSection - 1 < 0
1631 ? logicalIndexBeforeLeft
1632 : logicalIndices->at(currentLogicalSection - 1);
1633 QStyleOptionViewItem::ViewItemPosition
pos;
1634 if (columnCount == 1 || (nextLogicalSection == 0 && prevLogicalSection == -1)
1635 || (headerSection == 0 && nextLogicalSection == -1) ||
spanning)
1636 pos = QStyleOptionViewItem::OnlyOne;
1637 else if (
isTreePosition(headerSection) || (nextLogicalSection != 0 && prevLogicalSection == -1))
1638 pos = QStyleOptionViewItem::Beginning;
1639 else if (nextLogicalSection == 0 || nextLogicalSection == -1)
1640 pos = QStyleOptionViewItem::End;
1642 pos = QStyleOptionViewItem::Middle;
1643 (*itemPositions)[currentLogicalSection] =
pos;
1684 const bool reverse = isRightToLeft();
1686 const bool spanning =
d->spanning;
1689 const bool alternate =
d->alternatingColors;
1696 bool indexWidgetHasFocus =
false;
1697 if ((current.
row() ==
index.row()) && !
d->editorIndexHash.isEmpty()) {
1698 const int r =
index.row();
1704 indexWidgetHasFocus =
true;
1711 const bool widgetHasFocus = hasFocus();
1712 bool currentRowHasFocus =
false;
1715 const int r =
index.row();
1716 for (
int c = 0;
c <
left && !currentRowHasFocus; ++
c) {
1718 currentRowHasFocus = (idx == current);
1722 currentRowHasFocus = (
d->model->index(
r,
c, parent) == current);
1732 ||
option.showDecorationSelected;
1741 QList<int> logicalIndices;
1742 QList<QStyleOptionViewItem::ViewItemPosition>
1744 d->calcLogicalIndices(&logicalIndices, &viewItemPosList,
left,
right);
1746 for (
int currentLogicalSection = 0; currentLogicalSection < logicalIndices.size(); ++currentLogicalSection) {
1747 int headerSection = logicalIndices.at(currentLogicalSection);
1761 modelIndex =
d->
model->index(
index.row(), headerSection, parent);
1766 opt.viewItemPosition = viewItemPosList.at(currentLogicalSection);
1769 if (indexWidgetHasFocus)
1772 if (
d->selectionModel->isSelected(modelIndex))
1774 if (widgetHasFocus && (current == modelIndex)) {
1776 currentRowHasFocus =
true;
1781 (hoverRow || modelIndex == hover)
1782 && (
option.showDecorationSelected ||
d->hoverBranch == -1));
1798 opt.
features.setFlag(QStyleOptionViewItem::Alternate,
d->current & 1);
1805 if (
d->isTreePosition(headerSection)) {
1806 const int i =
d->indentationForItem(
d->current);
1808 const bool setClipRect = branches.
width() >
width;
1821 const bool oldShowDecorationSelected =
opt.showDecorationSelected;
1824 opt.
features |= QStyleOptionViewItem::HasDecoration;
1827 opt.
features &= ~QStyleOptionViewItem::HasDecoration;
1831 QStyle::State oldState =
opt.
state;
1836 opt.showDecorationSelected = oldShowDecorationSelected;
1843 QStyle::State oldState =
opt.
state;
1853 if (currentRowHasFocus) {
1855 o.QStyleOption::operator=(
option);
1859 o.backgroundColor =
option.palette.color(cg,
d->selectionModel->isSelected(
index)
1862 if (!
option.showDecorationSelected)
1865 o.rect = style()->visualRect(layoutDirection(),
d->viewport->rect(), focusRect);
1872 o.rect = style()->visualRect(layoutDirection(),
d->viewport->rect(), sectionRect);
1887 const bool reverse = isRightToLeft();
1888 const int indent =
d->indent;
1889 const int outer =
d->rootDecoration ? 0 : 1;
1890 const int item =
d->current;
1899 QStyleOptionViewItem
opt;
1910 if (
d->alternatingColors) {
1911 opt.
features.setFlag(QStyleOptionViewItem::Alternate,
d->current & 1);
1917 &&
opt.showDecorationSelected
1918 &&
index.parent() ==
d->hover.parent()
1919 &&
index.row() ==
d->hover.row();
1921 if (
d->selectionModel->isSelected(
index))
1924 if (
level >= outer) {
1926 primitive.moveLeft(reverse ? primitive.left() : primitive.left() - indent);
1929 const bool expanded = viewItem.expanded;
1930 const bool children = viewItem.hasChildren;
1931 bool moreSiblings = viewItem.hasMoreSiblings;
1943 primitive.moveLeft(reverse ? primitive.left() + indent : primitive.left() - indent);
1946 bool moreSiblings =
false;
1947 if (
d->hiddenIndexes.isEmpty()) {
1948 moreSiblings = (
d->model->rowCount(ancestor) - 1 > current.
row());
1950 int successor =
item + viewItem.total + 1;
1951 while (successor < d->viewItems.size()
1952 &&
d->viewItems.at(successor).level >=
uint(
level)) {
1954 if (successorItem.level ==
uint(
level)) {
1955 moreSiblings =
true;
1958 successor += successorItem.
total + 1;
1967 ancestor = current.
parent();
1978 bool handled =
false;
1980 handled =
d->expandOrCollapseItemAtPos(
event->position().toPoint());
1981 if (!handled &&
d->itemDecorationAt(
event->position().toPoint()) == -1)
1993 if (
d->itemDecorationAt(
event->position().toPoint()) == -1) {
1999 d->expandOrCollapseItemAtPos(
event->position().toPoint());
2009 if (
state() !=
NoState || !
d->viewport->rect().contains(
event->position().toPoint()))
2012 int i =
d->itemDecorationAt(
event->position().toPoint());
2014 i =
d->itemAtCoordinate(
event->position().toPoint().y());
2021 if (
d->pressedIndex != persistent) {
2038 d->releaseFromDoubleClick =
true;
2039 d->executePostedLayout();
2040 if (
d->itemsExpandable
2041 &&
d->expandsOnDoubleClick
2042 &&
d->hasVisibleChildren(persistent)) {
2043 if (!((i < d->viewItems.size()) && (
d->viewItems.at(
i).index == firstColumnIndex))) {
2045 for (
i = 0;
i <
d->viewItems.size(); ++
i) {
2046 if (
d->viewItems.at(
i).index == firstColumnIndex)
2049 if (
i ==
d->viewItems.size())
2052 if (
d->viewItems.at(
i).expanded)
2053 d->collapse(
i,
true);
2068 if (
d->itemDecorationAt(
event->position().toPoint()) == -1)
2080 if (
d->isIndexValid(current) &&
d->model &&
d->itemsExpandable) {
2081 switch (
event->key()) {
2103 d->executePostedLayout();
2105 int visualIndex =
d->itemAtCoordinate(point.
y());
2110 if (
d->viewItems.at(visualIndex).spanning)
2113 int column =
d->columnAt(point.
x());
2127 if (!
d->isIndexValid(
index))
2129 d->executePostedLayout();
2133 const QModelIndex firstColumnIndex =
d->viewItems.at(
i).index;
2134 return firstColumnIndex.
sibling(firstColumnIndex.row(),
index.column());
2143 if (!
d->isIndexValid(
index))
2145 d->executePostedLayout();
2147 if (++
i >=
d->viewItems.size())
2149 const QModelIndex firstColumnIndex =
d->viewItems.at(
i).index;
2150 return firstColumnIndex.
sibling(firstColumnIndex.row(),
index.column());
2161 if (
d->hasRemovedItems) {
2163 d->hasRemovedItems =
false;
2165 while (
it !=
d->expandedIndexes.
end()) {
2172 while (
it !=
d->hiddenIndexes.
end()) {
2181 if (
d->model->hasChildren(parent)) {
2185 d->header->doItemsLayout();
2186 d->updateAccessibility();
2195 d->expandedIndexes.clear();
2196 d->hiddenIndexes.clear();
2197 d->spanningIndexes.clear();
2198 d->viewItems.clear();
2213 return d->header->offset();
2225 if (
d->uniformRowHeights)
2226 return verticalScrollBar()->value() *
d->defaultItemHeight;
2230 d->executePostedLayout();
2232 const int cnt =
qMin(
d->viewItems.size(), verticalScrollBar()->
value());
2233 for (
int i = 0;
i < cnt; ++
i)
2238 return verticalScrollBar()->value();
2250 d->executePostedLayout();
2254 int i =
d->below(-1);
2256 while (c < d->
header->
count() &&
d->header->isSectionHidden(
d->header->logicalIndex(
c)))
2258 if (i < d->viewItems.size() && c < d->
header->
count()) {
2259 return d->modelIndex(
i,
d->header->logicalIndex(
c));
2264 const int vi =
qMax(0,
d->viewIndex(current));
2266 if (isRightToLeft()) {
2272 switch (cursorAction) {
2275#ifdef QT_KEYPAD_NAVIGATION
2276 if (vi ==
d->viewItems.count()-1 && QApplicationPrivate::keypadNavigationEnabled())
2277 return d->model->index(0, current.
column(),
d->root);
2279 return d->modelIndex(
d->below(vi), current.
column());
2282#ifdef QT_KEYPAD_NAVIGATION
2283 if (vi == 0 && QApplicationPrivate::keypadNavigationEnabled())
2284 return d->modelIndex(
d->viewItems.count() - 1, current.
column());
2286 return d->modelIndex(
d->above(vi), current.
column());
2289 if (vi < d->viewItems.size() &&
d->viewItems.at(vi).expanded &&
d->itemsExpandable && sb->value() == sb->minimum()) {
2290 d->collapse(vi,
true);
2291 d->moveCursorUpdatedView =
true;
2303 int visualColumn =
d->header->visualIndex(current.
column()) - 1;
2304 while (visualColumn >= 0 &&
isColumnHidden(
d->header->logicalIndex(visualColumn)))
2306 int newColumn =
d->header->logicalIndex(visualColumn);
2312 int oldValue = sb->value();
2313 sb->setValue(sb->value() - sb->singleStep());
2314 if (oldValue != sb->value())
2315 d->moveCursorUpdatedView =
true;
2324 if (vi < d->viewItems.size() && !
d->viewItems.at(vi).expanded &&
d->itemsExpandable
2325 &&
d->hasVisibleChildren(
d->viewItems.at(vi).index)) {
2326 d->expand(vi,
true);
2327 d->moveCursorUpdatedView =
true;
2332 if (idx.
parent() == current)
2339 int visualColumn =
d->header->visualIndex(current.
column()) + 1;
2342 const int newColumn =
d->header->logicalIndex(visualColumn);
2350 int oldValue = sb->value();
2351 sb->setValue(sb->value() + sb->singleStep());
2352 if (oldValue != sb->value())
2353 d->moveCursorUpdatedView =
true;
2360 return d->modelIndex(
d->pageUp(vi), current.
column());
2362 return d->modelIndex(
d->pageDown(vi), current.
column());
2364 return d->modelIndex(
d->itemForKeyHome(), current.
column());
2366 return d->modelIndex(
d->itemForKeyEnd(), current.
column());
2383 d->executePostedLayout();
2390 if (!topLeft.isValid() && !bottomRight.
isValid()) {
2395 if (!topLeft.isValid() && !
d->viewItems.isEmpty())
2396 topLeft =
d->viewItems.constFirst().index;
2397 if (!bottomRight.
isValid() && !
d->viewItems.isEmpty()) {
2398 const int column =
d->header->logicalIndex(
d->header->count() - 1);
2403 if (!
d->isIndexEnabled(topLeft) || !
d->isIndexEnabled(bottomRight))
2406 d->select(topLeft, bottomRight, command);
2423 const QRect &viewportRect =
d->viewport->rect();
2425 if (!
range.isValid())
2429 int columnCount =
d->
model->columnCount(parent);
2431 if (leftIndex.column() + 1 < columnCount)
2432 leftIndex =
d->model->index(leftIndex.row(), leftIndex.column() + 1, parent);
2436 if (!leftIndex.isValid())
2439 int top = leftRect.
top();
2442 if (rightIndex.column() - 1 >= 0)
2443 rightIndex =
d->
model->index(rightIndex.row(), rightIndex.column() - 1, parent);
2447 if (!rightIndex.isValid())
2454 if (
d->header->sectionsMoved()) {
2458 selectionRegion += rangeRect;
2461 QRect combined = leftRect|rightRect;
2464 selectionRegion += combined;
2467 return selectionRegion;
2479 for (
int i = 0;
i < modelSelected.size(); ++
i) {
2484 if (
index.isValid())
2486 viewSelected.append(modelSelected.at(
i));
2488 return viewSelected;
2498 d->delayedAutoScroll.stop();
2500 dx = isRightToLeft() ? -dx : dx;
2502 int oldOffset =
d->header->offset();
2505 int newOffset =
d->header->offset();
2506 dx = isRightToLeft() ? newOffset - oldOffset : oldOffset - newOffset;
2510 const int itemHeight =
d->defaultItemHeight <= 0 ?
sizeHintForRow(0) :
d->defaultItemHeight;
2511 if (
d->viewItems.isEmpty() || itemHeight == 0)
2515 int viewCount =
d->viewport->height() / itemHeight;
2516 int maxDeltaY =
qMin(
d->viewItems.size(), viewCount);
2518 if (
qAbs(dy) >
qAbs(maxDeltaY) &&
d->editorIndexHash.isEmpty()) {
2519 verticalScrollBar()->update();
2520 d->viewport->update();
2525 int currentScrollbarValue = verticalScrollBar()->value();
2526 int previousScrollbarValue = currentScrollbarValue + dy;
2527 int currentViewIndex = currentScrollbarValue;
2528 int previousViewIndex = previousScrollbarValue;
2530 if (previousViewIndex < currentViewIndex) {
2531 for (
int i = previousViewIndex;
i < currentViewIndex; ++
i) {
2532 if (i < d->viewItems.size())
2533 dy -=
d->itemHeight(
i);
2535 }
else if (previousViewIndex > currentViewIndex) {
2536 for (
int i = previousViewIndex - 1;
i >= currentViewIndex; --
i) {
2537 if (i < d->viewItems.size())
2538 dy +=
d->itemHeight(
i);
2543 d->scrollContentsBy(dx, dy);
2553 d->viewport->update();
2572 if (
d->delayedPendingLayout) {
2583 const int parentRowCount =
d->model->rowCount(parent);
2585 if (parent !=
d->root && !
d->isIndexExpanded(parent) && parentRowCount > delta) {
2590 const int parentItem =
d->viewIndex(parent);
2591 if (((parentItem != -1) &&
d->viewItems.at(parentItem).expanded)
2592 || (parent ==
d->root)) {
2593 d->doDelayedItemsLayout();
2594 }
else if (parentItem != -1 && parentRowCount == delta) {
2596 d->viewItems[parentItem].hasChildren =
true;
2610 d->viewItems.clear();
2622 d->viewItems.clear();
2623 d->doDelayedItemsLayout();
2624 d->hasRemovedItems =
true;
2635 if (oldCount == 0 && newCount > 0) {
2637 d->doDelayedItemsLayout();
2653 d->executePostedLayout();
2654 if (column < 0 || column >=
d->header->count())
2680 if (!
d->sortingEnabled ||
2681 (
d->header->sortIndicatorSection() ==
column &&
d->header->sortIndicatorOrder() ==
order))
2694 d->executePostedLayout();
2696 const QModelIndex &idx =
d->viewItems.constLast().index;
2698 d->select(
d->viewItems.constFirst().index, lastItemIndex,
2710 d->executePostedLayout();
2712 if (
d->viewItems.size() == 0)
2716 const QRect deepestRect =
d->visualRect(
d->viewItems.last().index,
2719 if (!deepestRect.isValid())
2725 result +=
QSize(0,
d->header->isHidden() ? 0 :
d->header->height());
2745 d->viewItems.clear();
2746 d->interruptDelayedItemsLayout();
2747 d->layout(-1,
true);
2749 d->viewport->update();
2750 d->updateAccessibility();
2775 d->doDelayedItemsLayout();
2779 QStack<QPair<QModelIndex, int>> parents;
2780 parents.push({
index, 0});
2781 while (!parents.isEmpty()) {
2782 const QPair<QModelIndex, int> elem = parents.pop();
2784 const int curDepth = elem.second;
2785 const int rowCount =
d->
model->rowCount(parent);
2786 for (
int row = 0;
row < rowCount; ++
row) {
2788 if (!
d->isIndexValid(
child))
2791 parents.push({
child, curDepth + 1});
2792 if (
d->isIndexExpanded(
child))
2794 if (
d->storeExpanded(
child))
2810 QSet<QPersistentModelIndex> old_expandedIndexes;
2811 old_expandedIndexes =
d->expandedIndexes;
2812 d->expandedIndexes.clear();
2815 for (;
i != old_expandedIndexes.constEnd(); ++
i) {
2836 d->viewItems.clear();
2837 QSet<QPersistentModelIndex> old_expandedIndexes;
2838 old_expandedIndexes =
d->expandedIndexes;
2839 d->expandedIndexes.clear();
2840 d->interruptDelayedItemsLayout();
2842 for (
int i = 0;
i <
d->viewItems.size(); ++
i) {
2844 d->viewItems[
i].expanded =
true;
2846 d->storeExpanded(
d->viewItems.at(
i).index);
2853 if (!signalsBlocked() && someSignalEnabled) {
2855 QSet<QPersistentModelIndex> collapsedIndexes = old_expandedIndexes -
d->expandedIndexes;
2857 for (;
i != collapsedIndexes.constEnd(); ++
i) {
2863 QSet<QPersistentModelIndex> expandedIndexs =
d->expandedIndexes - old_expandedIndexes;
2864 i = expandedIndexs.constBegin();
2865 for (;
i != expandedIndexs.constEnd(); ++
i) {
2873 d->viewport->update();
2874 d->updateAccessibility();
2887 d->columnsToUpdate.append(
column);
2888 if (
d->columnResizeTimerID == 0)
2889 d->columnResizeTimerID = startTimer(0);
2899 if (
d->geometryRecursionBlock)
2901 d->geometryRecursionBlock =
true;
2903 if (!
d->header->isHidden()) {
2904 height =
qMax(
d->header->minimumHeight(),
d->header->sizeHint().height());
2907 setViewportMargins(0,
height, 0, 0);
2908 QRect vg =
d->viewport->geometry();
2910 d->header->setGeometry(geometryRect);
2912 d->updateScrollBars();
2913 d->geometryRecursionBlock =
false;
2935 d->executePostedLayout();
2936 if (
d->viewItems.isEmpty())
2940 QStyleOptionViewItem
option;
2942 const QList<QTreeViewItem> viewItems =
d->viewItems;
2944 const int maximumProcessRows =
d->header->resizeContentsPrecision();
2949 if (
start < 0 ||
end < 0 ||
end == viewItems.size() - 1) {
2950 end = viewItems.size() - 1;
2951 if (maximumProcessRows < 0) {
2953 }
else if (maximumProcessRows == 0) {
2955 int remainingHeight =
viewport()->height();
2956 while (
start > 0 && remainingHeight > 0) {
2957 remainingHeight -=
d->itemHeight(
start);
2965 int rowsProcessed = 0;
2968 if (viewItems.at(
i).spanning)
2974 if (rowsProcessed == maximumProcessRows)
2979 int actualBottom = viewItems.size() - 1;
2981 if (maximumProcessRows == 0)
2984 while (rowsProcessed != maximumProcessRows && (
start > 0 ||
end < actualBottom)) {
2987 if ((rowsProcessed % 2 &&
start > 0) ||
end == actualBottom) {
2990 if (viewItems.at(
start).spanning)
2996 while (
end < actualBottom) {
2998 if (viewItems.at(
end).spanning)
3023 if (!
d->isIndexValid(
index) || !
d->itemDelegate)
3028 int indexRow =
index.row();
3029 int count =
d->header->count();
3030 bool emptyHeader = (
count == 0);
3035 start =
d->header->visualIndexAt(0);
3041 if (isRightToLeft()) {
3053 QStyleOptionViewItem
option;
3060 option.rect.setWidth(-1);
3063 int logicalColumn = emptyHeader ?
column :
d->header->logicalIndex(
column);
3064 if (
d->header->isSectionHidden(logicalColumn))
3068 QWidget *editor =
d->editorForIndex(idx).widget.data();
3069 if (editor &&
d->persistent.contains(editor)) {
3071 int min = editor->minimumSize().height();
3072 int max = editor->maximumSize().height();
3091 d->executePostedLayout();
3095 return d->itemHeight(
i);
3122 updateStyledFrameWidths();
3133#if QT_CONFIG(animation)
3137 this, &QTreeViewPrivate::endAnimatedOperation);
3149#if QT_CONFIG(animation)
3164#if QT_CONFIG(animation)
3181#if QT_CONFIG(animation)
3183 beginAnimatedOperation();
3208bool QTreeViewPrivate::checkViewItems()
const
3240#if QT_CONFIG(animation)
3252 while (
index > -1) {
3261#if QT_CONFIG(animation)
3263 beginAnimatedOperation();
3268#if QT_CONFIG(animation)
3271 animatedOperation.item =
item;
3272 animatedOperation.viewport =
viewport;
3273 animatedOperation.setDirection(
direction);
3285 animatedOperation.setEndValue(
top +
h);
3287 animatedOperation.setStartValue(
top);
3288 animatedOperation.before = renderTreeToPixmapForAnimation(
rect);
3291void QTreeViewPrivate::beginAnimatedOperation()
3300 int c = animatedOperation.item +
viewItems.
at(animatedOperation.item).
total + 1;
3301 for (
int i = animatedOperation.item + 1;
i <
c &&
h <
limit; ++
i)
3304 animatedOperation.setEndValue(animatedOperation.top() +
h);
3307 if (!
rect.isEmpty()) {
3308 animatedOperation.after = renderTreeToPixmapForAnimation(
rect);
3311 animatedOperation.start();
3317 const int start = animatedOperation.startValue().toInt(),
3318 end = animatedOperation.endValue().toInt(),
3319 current = animatedOperation.currentValue().toInt();
3321 const QPixmap top = collapsing ? animatedOperation.before : animatedOperation.after;
3323 const QPixmap bottom = collapsing ? animatedOperation.after : animatedOperation.before;
3327QPixmap QTreeViewPrivate::renderTreeToPixmapForAnimation(
const QRect &
rect)
const
3331 pixmap.setDevicePixelRatio(
q->devicePixelRatio());
3332 if (
rect.size().isEmpty())
3342 QStyleOptionViewItem
option;
3343 q->initViewItemOption(&
option);
3348 if (
option.rect.isValid()) {
3367void QTreeViewPrivate::endAnimatedOperation()
3371 q->updateGeometries();
3397#if QT_CONFIG(accessibility)
3399 if (pendingAccessibilityUpdate) {
3400 pendingAccessibilityUpdate =
false;
3401 if (QAccessible::isActive()) {
3402 QAccessibleTableModelChangeEvent
event(
q, QAccessibleTableModelChangeEvent::ModelReset);
3403 QAccessible::updateAccessibility(&
event);
3430#if QT_CONFIG(accessibility)
3435 pendingAccessibilityUpdate |= oldViewItemsSize != viewItems.size();
3458 bool expanding =
true;
3465 afterIsUninitialized =
true;
3467 if (!afterIsUninitialized)
3485 last =
j - hidden + children;
3487 last =
j - hidden + children;
3489 item->hasMoreSiblings =
true;
3495 item->spanning =
q->isFirstColumnSpanned(
current.row(), parent);
3496 item->expanded =
false;
3498 item->hasMoreSiblings =
false;
3502 item->expanded =
true;
3503 layout(last, recursiveExpanding, afterIsUninitialized);
3505 children +=
item->total;
3506 item->hasChildren =
item->total > 0;
3507 last =
j - hidden + children;
3516 if (!afterIsUninitialized)
3589 if (!
index.isValid())
3613 return y - vbar->value();
3617 int topViewItemIndex = vbar->value();
3620 if (
item >= topViewItemIndex) {
3623 int viewItemCoordinate = 0;
3624 int viewItemIndex = topViewItemIndex;
3626 if (viewItemIndex ==
item)
3627 return viewItemCoordinate;
3628 viewItemCoordinate +=
itemHeight(viewItemIndex);
3633 return viewItemCoordinate;
3636 int viewItemCoordinate = 0;
3637 for (
int viewItemIndex = topViewItemIndex; viewItemIndex > 0; --viewItemIndex) {
3638 if (viewItemIndex ==
item)
3639 return viewItemCoordinate;
3640 viewItemCoordinate -=
itemHeight(viewItemIndex - 1);
3642 return viewItemCoordinate;
3665 return ((viewItemIndex >= itemCount || viewItemIndex < 0) ? -1 : viewItemIndex);
3668 int viewItemCoordinate = 0;
3669 const int contentsCoordinate = coordinate + vbar->value();
3670 for (
int viewItemIndex = 0; viewItemIndex <
viewItems.
size(); ++viewItemIndex) {
3671 viewItemCoordinate +=
itemHeight(viewItemIndex);
3672 if (viewItemCoordinate > contentsCoordinate)
3673 return (viewItemIndex >= itemCount ? -1 : viewItemIndex);
3676 int topViewItemIndex = vbar->value();
3681 return ((viewItemIndex >= itemCount || viewItemIndex < 0) ? -1 : viewItemIndex);
3683 if (coordinate >= 0) {
3685 int viewItemCoordinate = 0;
3686 for (
int viewItemIndex = topViewItemIndex; viewItemIndex <
viewItems.
size(); ++viewItemIndex) {
3687 viewItemCoordinate +=
itemHeight(viewItemIndex);
3688 if (viewItemCoordinate > coordinate)
3689 return (viewItemIndex >= itemCount ? -1 : viewItemIndex);
3693 int viewItemCoordinate = 0;
3694 for (
int viewItemIndex = topViewItemIndex; viewItemIndex >= 0; --viewItemIndex) {
3695 if (viewItemCoordinate <= coordinate)
3696 return (viewItemIndex >= itemCount ? -1 : viewItemIndex);
3697 viewItemCoordinate -=
itemHeight(viewItemIndex);
3716 for (
int i = 0;
i < localCount; ++
i) {
3718 if (idx1.row() ==
row && idx1.internalId() == internalId) {
3723 if (idx2.row() ==
row && idx2.internalId() == internalId) {
3761 const int value = vbar->value();
3790 if (firstVisual < 0 ||
offset < 0) {
3792 if (firstVisual < 0)
3816 viewportSize =
QSize(0, 0);
3823 int itemsInViewport = 0;
3831 const int viewportHeight = viewportSize.
height();
3834 if (
height > viewportHeight)
3841 itemsInViewport =
qMax(1, itemsInViewport);
3843 vbar->setPageStep(itemsInViewport);
3844 vbar->setSingleStep(1);
3846 int contentsHeight = 0;
3853 vbar->setRange(0, contentsHeight - viewportSize.
height());
3854 vbar->setPageStep(viewportSize.
height());
3855 vbar->d_func()->itemviewChangeSingleStep(
qMax(viewportSize.
height() / (itemsInViewport + 1), 2));
3859 const int viewportWidth = viewportSize.
width();
3860 int columnsInViewport = 0;
3864 if (
width > viewportWidth)
3866 ++columnsInViewport;
3868 if (columnCount > 0)
3869 columnsInViewport =
qMax(1, columnsInViewport);
3871 hbar->setRange(0, columnCount - columnsInViewport);
3872 hbar->setPageStep(columnsInViewport);
3873 hbar->setSingleStep(1);
3876 const QSize maxSize =
q->maximumViewportSize();
3877 if (maxSize.
width() >= horizontalLength && vbar->maximum() <= 0)
3878 viewportSize = maxSize;
3879 hbar->setPageStep(viewportSize.
width());
3880 hbar->setRange(0,
qMax(horizontalLength - viewportSize.
width(), 0));
3881 hbar->d_func()->itemviewChangeSingleStep(
qMax(viewportSize.
width() / (columnsInViewport + 1), 2));
3889 bool spanned =
false;
3892 if (
index.isValid())
3893 spanned =
q->isFirstColumnSpanned(
index.row(),
index.parent());
3901 if (!returning.contains(
pos))
3904 return viewItemIndex;
3922 if (
q->isRightToLeft())
3940 const int start =
qMin(topVisual, bottomVisual);
3941 const int end =
qMax(topVisual, bottomVisual);
3943 QList<int> logicalIndexes;
3949 logicalIndexes << logical;
3953 std::sort(logicalIndexes.begin(), logicalIndexes.end());
3955 QList<QPair<int, int>>
ret;
3959 for(
int i = 0;
i < logicalIndexes.size(); ++
i) {
3960 const int logicalColumn = logicalIndexes.at(
i);
3961 if (
current.second + 1 != logicalColumn) {
3982 QItemSelectionModel::SelectionFlags command)
3989 const QList<QPair<int, int>> colRanges =
columnRanges(topIndex, bottomIndex);
3990 QList<QPair<int, int>>::const_iterator
it;
3992 const int left = (*it).first,
3993 right = (*it).second;
3997 QStack<QItemSelectionRange> rangeStack;
4002 if (previous.
isValid() && parent == previousParent) {
4006 if (currentRange.isValid()) {
4013 currentRange.parent());
4018 rangeStack.push(currentRange);
4021 if (currentRange.isValid())
4023 if (rangeStack.isEmpty()) {
4026 currentRange = rangeStack.pop();
4027 index = currentRange.bottomRight();
4033 if (currentRange.isValid())
4035 for (
int i = 0;
i < rangeStack.size(); ++
i)
4038 q->selectionModel()->select(
selection, command);
4046 if (
q->isRightToLeft()) {
4064 if (
q->isIndexHidden(parent))
4067 for (
int i = 0;
i < rowCount; ++
i) {
4068 if (!
q->isRowHidden(
i, parent))
4087 return (
q->visualIndex(
index) + (
q->header() ? 1 : 0)) *
index.model()->columnCount() +
index.column();
4110#if QT_CONFIG(accessibility)
4111 if (QAccessible::isActive() && current.
isValid() && hasFocus()) {
4114 QAccessibleEvent
event(
this, QAccessible::Focus);
4115 event.setChild(
d->accessibleTree2Index(current));
4116 QAccessible::updateAccessibility(&
event);
4128#if QT_CONFIG(accessibility)
4129 if (QAccessible::isActive()) {
4134 if (sel.isValid()) {
4135 int entry =
d->accessibleTree2Index(sel);
4137 QAccessibleEvent
event(
this, QAccessible::SelectionAdd);
4138 event.setChild(
entry);
4139 QAccessible::updateAccessibility(&
event);
4141 QModelIndex desel = deselected.indexes().value(0);
4142 if (desel.isValid()) {
4143 int entry =
d->accessibleTree2Index(desel);
4145 QAccessibleEvent
event(
this, QAccessible::SelectionRemove);
4146 event.setChild(
entry);
4147 QAccessible::updateAccessibility(&
event);
4156 d->executePostedLayout();
4157 return d->viewIndex(
index);
4167 if (!
d->viewItems.isEmpty() &&
value == verticalScrollBar()->maximum()) {
4170 while (
ret.isValid()) {
4183#include "moc_qtreeview.cpp"
Direction
This enum describes the direction of the animation when in \l Running state.
void finished()
QAbstractAnimation emits this signal after the animation has stopped and has reached the end.
The QAbstractItemDelegate class is used to display and edit data items from a model.
virtual QSize sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const =0
This pure abstract function must be reimplemented if you want to provide custom rendering.
static QAbstractItemModel * staticEmptyModel()
void modelAboutToBeReset(QPrivateSignal)
virtual Q_INVOKABLE bool hasChildren(const QModelIndex &parent=QModelIndex()) const
Returns {true} if parent has any children; otherwise returns {false}.
virtual Q_INVOKABLE int rowCount(const QModelIndex &parent=QModelIndex()) const =0
Returns the number of rows under the given parent.
virtual Q_INVOKABLE void fetchMore(const QModelIndex &parent)
Fetches any available data for the items with the parent specified by the parent index.
void layoutChanged(const QList< QPersistentModelIndex > &parents=QList< QPersistentModelIndex >(), QAbstractItemModel::LayoutChangeHint hint=QAbstractItemModel::NoLayoutChangeHint)
virtual Q_INVOKABLE bool canFetchMore(const QModelIndex &parent) const
Returns {true} if there is more data available for parent; otherwise returns {false}.
virtual Q_INVOKABLE int columnCount(const QModelIndex &parent=QModelIndex()) const =0
Returns the number of columns for the children of the given parent.
virtual Q_INVOKABLE QModelIndex index(int row, int column, const QModelIndex &parent=QModelIndex()) const =0
Returns the index of the item in the model specified by the given row, column and parent index.
void rowsRemoved(const QModelIndex &parent, int first, int last, QPrivateSignal)
This signal is emitted after rows have been removed from the model.
virtual bool submit()
Lets the model know that it should submit cached information to permanent storage.
virtual void layoutChanged()
const QEditorInfo & editorForIndex(const QModelIndex &index) const
virtual QItemViewPaintPairs draggablePaintPairs(const QModelIndexList &indexes, QRect *r) const
void doDelayedItemsLayout(int delay=0)
QBasicTimer delayedAutoScroll
virtual void rowsRemoved(const QModelIndex &parent, int start, int end)
QSet< QWidget * > persistent
QPointer< QAbstractItemDelegate > itemDelegate
QAbstractItemView::ScrollMode horizontalScrollMode
QAbstractItemView::State state
bool isPersistent(const QModelIndex &index) const
QAbstractItemView::State stateBeforeAnimation
QPersistentModelIndex root
QAbstractItemModel * model
virtual void columnsRemoved(const QModelIndex &parent, int start, int end)
virtual void modelDestroyed()
virtual void columnsAboutToBeRemoved(const QModelIndex &parent, int start, int end)
bool isIndexValid(const QModelIndex &index) const
void executePostedLayout() const
QWidget * editor(const QModelIndex &index, const QStyleOptionViewItem &options)
QEditorIndexHash editorIndexHash
QAbstractItemView::SelectionBehavior selectionBehavior
QAbstractItemView::ScrollMode verticalScrollMode
The QAbstractItemView class provides the basic functionality for item view classes.
SelectionMode
This enum indicates how the view responds to user selections:
QWidget * indexWidget(const QModelIndex &index) const
void activated(const QModelIndex &index)
This signal is emitted when the item specified by index is activated by the user.
QAbstractItemModel * model() const
Returns the model that this view is presenting.
void setCurrentIndex(const QModelIndex &index)
Sets the current item to be the item at index.
void doubleClicked(const QModelIndex &index)
This signal is emitted when a mouse button is double-clicked.
virtual void setSelectionModel(QItemSelectionModel *selectionModel)
Sets the current selection model to the given selectionModel.
void timerEvent(QTimerEvent *event) override
This function is called with the given event when a timer event is sent to the widget.
ScrollMode verticalScrollMode
how the view scrolls its contents in the vertical direction
virtual void selectionChanged(const QItemSelection &selected, const QItemSelection &deselected)
This slot is called when the selection is changed.
State state() const
Returns the item view's state.
virtual void reset()
Reset the internal state of the view.
void mouseReleaseEvent(QMouseEvent *event) override
This function is called with the given event when a mouse button is released, after a mouse press eve...
virtual QAbstractItemDelegate * itemDelegateForIndex(const QModelIndex &index) const
virtual void dataChanged(const QModelIndex &topLeft, const QModelIndex &bottomRight, const QList< int > &roles=QList< int >())
This slot is called when items with the given roles are changed in the model.
QModelIndex currentIndex() const
Returns the model index of the current item.
bool viewportEvent(QEvent *event) override
This function is used to handle tool tips, and What's This? mode, if the given event is a QEvent::Too...
virtual void rowsAboutToBeRemoved(const QModelIndex &parent, int start, int end)
This slot is called when rows are about to be removed.
virtual void setModel(QAbstractItemModel *model)
Sets the model for the view to present.
ScrollMode horizontalScrollMode
how the view scrolls its contents in the horizontal direction
virtual void setRootIndex(const QModelIndex &index)
Sets the root item to the item at the given index.
virtual void initViewItemOption(QStyleOptionViewItem *option) const
virtual void doItemsLayout()
void keyPressEvent(QKeyEvent *event) override
This function is called with the given event when a key event is sent to the widget.
QModelIndex rootIndex() const
Returns the model index of the model's root item.
CursorAction
This enum describes the different ways to navigate between items,.
virtual void currentChanged(const QModelIndex ¤t, const QModelIndex &previous)
This slot is called when a new item becomes the current item.
ScrollHint
\value EnsureVisible Scroll to ensure that the item is visible.
void mousePressEvent(QMouseEvent *event) override
This function is called with the given event when a mouse button is pressed while the cursor is insid...
virtual void rowsInserted(const QModelIndex &parent, int start, int end)
This slot is called when rows are inserted.
virtual void updateEditorGeometries()
void setState(State state)
Sets the item view's state to the given state.
void mouseMoveEvent(QMouseEvent *event) override
This function is called with the given event when a mouse move event is sent to the widget.
QItemSelectionModel * selectionModel() const
Returns the current selection model.
virtual void verticalScrollbarValueChanged(int value)
virtual void updateGeometries()
SelectionBehavior selectionBehavior
which selection behavior the view uses
QSize viewportSizeHint() const override
virtual void horizontalScrollbarAction(int action)
virtual int sizeHintForRow(int row) const
Returns the height size hint for the specified row or -1 if there is no model.
static QWidget * focusWidget()
Returns the application widget that has the keyboard input focus, or \nullptr if no widget in this ap...
int keyboardInputInterval
the time limit in milliseconds that distinguishes a key press from two consecutive key presses
void stop()
Stops the timer.
static QPoint pos()
Returns the position of the cursor (hot spot) of the primary screen in global screen coordinates.
QGraphicsItem * parentItem() const
Returns a pointer to this item's parent item.
const_iterator constEnd() const noexcept
Returns a const \l{STL-style iterators}{STL-style iterator} pointing to the imaginary item after the ...
const_iterator constBegin() const noexcept
Returns a const \l{STL-style iterators}{STL-style iterator} pointing to the first item in the hash.
friend class const_iterator
QModelIndexList selectedIndexes
virtual void clear()
Clears the selection model.
void currentRowChanged(const QModelIndex ¤t, const QModelIndex &previous)
This signal is emitted if the current item changes and its row is different to the row of the previou...
Q_CORE_EXPORT QModelIndexList indexes() const
Returns a list of model indexes that correspond to the selected items.
The QKeyEvent class describes a key event.
qsizetype size() const noexcept
bool isEmpty() const noexcept
iterator insert(qsizetype i, parameter_type t)
const_reference at(qsizetype i) const noexcept
void remove(qsizetype i, qsizetype n=1)
qsizetype count() const noexcept
void resize(qsizetype size)
void append(parameter_type t)
constexpr int row() const noexcept
Returns the row this model index refers to.
QModelIndex parent() const
Returns the parent of the model index, or QModelIndex() if it has no parent.
constexpr const QAbstractItemModel * model() const noexcept
Returns a pointer to the model containing the item that this index refers to.
Qt::ItemFlags flags() const
constexpr int column() const noexcept
Returns the column this model index refers to.
constexpr bool isValid() const noexcept
Returns {true} if this model index is valid; otherwise returns {false}.
QModelIndex sibling(int row, int column) const
Returns the sibling at row and column.
constexpr quintptr internalId() const noexcept
Returns a {quintptr} used by the model to associate the index with the internal data structure.
static QMetaObject::Connection connect(const typename QtPrivate::FunctionPointer< Func1 >::Object *sender, Func1 signal, const typename QtPrivate::FunctionPointer< Func2 >::Object *receiverPrivate, Func2 slot, Qt::ConnectionType type=Qt::AutoConnection)
static bool disconnect(const typename QtPrivate::FunctionPointer< Func1 >::Object *sender, Func1 signal, const typename QtPrivate::FunctionPointer< Func2 >::Object *receiverPrivate, Func2 slot)
static QMetaObject::Connection connect(const QObject *sender, const char *signal, const QObject *receiver, const char *member, Qt::ConnectionType=Qt::AutoConnection)
\threadsafe
static bool disconnect(const QObject *sender, const char *signal, const QObject *receiver, const char *member)
\threadsafe
The QPaintEvent class contains event parameters for paint events.
The QPainter class performs low-level painting on widgets and other paint devices.
void setClipRect(const QRectF &, Qt::ClipOperation op=Qt::ReplaceClip)
Enables clipping, and sets the clip region to the given rectangle using the given clip operation.
void setBrushOrigin(int x, int y)
This is an overloaded member function, provided for convenience. It differs from the above function o...
void restore()
Restores the current painter state (pops a saved state off the stack).
void save()
Saves the current painter state (pushes the state onto a stack).
void drawPixmap(const QRectF &targetRect, const QPixmap &pixmap, const QRectF &sourceRect)
Draws the rectangular portion source of the given pixmap into the given target in the paint device.
QPoint brushOrigin() const
Returns the currently set brush origin.
void translate(const QPointF &offset)
Translates the coordinate system by the given offset; i.e.
void fillRect(const QRectF &, const QBrush &)
Fills the given rectangle with the brush specified.
void setCurrentColorGroup(ColorGroup cg)
Set the palette's current color group to cg.
ColorGroup
\value Disabled \value Active \value Inactive \value Normal synonym for Active
bool isValid() const
Returns {true} if this persistent model index is valid; otherwise returns {false}.
Returns a copy of the pixmap that is transformed using the given transformation transform and transfo...
\inmodule QtCore\reentrant
constexpr int x() const noexcept
Returns the x coordinate of this point.
constexpr int y() const noexcept
Returns the y coordinate of this point.
T * data() const noexcept
\inmodule QtCore\reentrant
bool intersects(const QRect &r) const noexcept
Returns true if this rectangle intersects with the given rectangle (i.e., there is at least one pixel...
constexpr int height() const noexcept
Returns the height of the rectangle.
QRect intersected(const QRect &other) const noexcept
constexpr int bottom() const noexcept
Returns the y-coordinate of the rectangle's bottom edge.
constexpr int top() const noexcept
Returns the y-coordinate of the rectangle's top edge.
bool contains(const QRect &r, bool proper=false) const noexcept
This is an overloaded member function, provided for convenience. It differs from the above function o...
constexpr int left() const noexcept
Returns the x-coordinate of the rectangle's left edge.
constexpr void setRect(int x, int y, int w, int h) noexcept
Sets the coordinates of the rectangle's top-left corner to ({x}, {y}), and its size to the given widt...
constexpr void setX(int x) noexcept
Sets the left edge of the rectangle to the given x coordinate.
constexpr int width() const noexcept
Returns the width of the rectangle.
QRect united(const QRect &other) const noexcept
constexpr void setTop(int pos) noexcept
Sets the top edge of the rectangle to the given y coordinate.
The QRegion class specifies a clip region for a painter.
QRect boundingRect() const noexcept
Returns the bounding rectangle of this region.
int rectCount() const noexcept
iterator erase(const_iterator i)
iterator find(const T &value)
bool contains(const T &value) const
constexpr int height() const noexcept
Returns the height.
constexpr int width() const noexcept
Returns the width.
constexpr bool isValid() const noexcept
Returns true if both the width and height is equal to or greater than 0; otherwise returns false.
\macro QT_RESTRICTED_CAST_FROM_ASCII
bool isEmpty() const noexcept
Returns true if the string has no characters; otherwise returns false.
qsizetype count(QChar c, Qt::CaseSensitivity cs=Qt::CaseSensitive) const
\variable QStyleOption::palette
The QStyleOption class stores the parameters used by QStyle functions.
void initFrom(const QWidget *w)
The QStyle class is an abstract base class that encapsulates the look and feel of a GUI.
@ State_KeyboardFocusChange
@ SH_ItemView_PaintAlternatingRowColorsForEmptyArea
@ SH_ItemView_ArrowKeysNavigateIntoChildren
@ SH_Widget_Animation_Duration
@ SH_ListViewExpand_SelectMouseType
@ SH_ItemView_ActivateItemOnSingleClick
@ SH_ItemView_ShowDecorationSelected
@ SE_TreeViewDisclosureItem
void sortIndicatorChanged(int column, Qt::SortOrder order)
int itemForKeyEnd() const
int widthHintForIndex(const QModelIndex &index, int hint, const QStyleOptionViewItem &option, int i) const
int accessibleTree2Index(const QModelIndex &index) const
bool isRowHidden(const QModelIndex &idx) const
int logicalIndexForTree() const
bool isItemHiddenOrDisabled(int i) const
QMetaObject::Connection animationConnection
int itemHeight(int item) const
void collapse(int item, bool emitSignal)
void calcLogicalIndices(QList< int > *logicalIndices, QList< QStyleOptionViewItem::ViewItemPosition > *itemPositions, int left, int right) const
void layout(int item, bool recusiveExpanding=false, bool afterIsUninitialized=false)
QMetaObject::Connection selectionmodelConnection
bool isIndexExpanded(const QModelIndex &idx) const
QModelIndex modelIndex(int i, int column=0) const
bool storeExpanded(const QPersistentModelIndex &idx)
QList< QPair< int, int > > columnRanges(const QModelIndex &topIndex, const QModelIndex &bottomIndex) const
void removeViewItems(int pos, int count)
bool isTreePosition(int logicalIndex) const
QRect intersectedRect(const QRect rect, const QModelIndex &topLeft, const QModelIndex &bottomRight) const override
int firstVisibleItem(int *offset=nullptr) const
QRect itemDecorationRect(const QModelIndex &index) const
void insertViewItems(int pos, int count, const QTreeViewItem &viewItem)
QItemViewPaintPairs draggablePaintPairs(const QModelIndexList &indexes, QRect *r) const override
\reimp
void columnsRemoved(const QModelIndex &, int, int) override
void select(const QModelIndex &start, const QModelIndex &stop, QItemSelectionModel::SelectionFlags command)
std::array< QMetaObject::Connection, 5 > headerConnections
void paintAlternatingRowColors(QPainter *painter, QStyleOptionViewItem *option, int y, int bottom) const
QList< QTreeViewItem > viewItems
QRect visualRect(const QModelIndex &index) const override
int pageUp(int item) const
void columnsAboutToBeRemoved(const QModelIndex &, int, int) override
int viewIndex(const QModelIndex &index) const
int itemDecorationAt(const QPoint &pos) const
QMetaObject::Connection sortHeaderConnection
int pageDown(int item) const
QSet< QPersistentModelIndex > hiddenIndexes
int lastVisibleItem(int firstVisual=-1, int offset=-1) const
int columnAt(int x) const
int itemAtCoordinate(int coordinate) const
QSet< QPersistentModelIndex > spanningIndexes
void updateAccessibility()
std::array< QMetaObject::Connection, 2 > modelConnections
int itemForKeyHome() const
int indentationForItem(int item) const
void updateIndentationFromStyle()
QSet< QPersistentModelIndex > expandedIndexes
bool expandOrCollapseItemAtPos(const QPoint &pos)
void adjustViewOptionsForIndex(QStyleOptionViewItem *option, const QModelIndex ¤t) const override
void modelDestroyed() override
int coordinateForItem(int item) const
void expand(int item, bool emitSignal)
QPair< int, int > startAndEndColumns(const QRect &rect) const
bool hasVisibleChildren(const QModelIndex &parent) const
void modelAboutToBeReset()
The QTreeView class provides a default model/view implementation of a tree view.
void setItemsExpandable(bool enable)
void dataChanged(const QModelIndex &topLeft, const QModelIndex &bottomRight, const QList< int > &roles=QList< int >()) override
\reimp
bool isSortingEnabled() const
bool isIndexHidden(const QModelIndex &index) const override
\reimp
void expand(const QModelIndex &index)
Expands the model item specified by the index.
bool itemsExpandable
whether the items are expandable by the user.
QRegion visualRegionForSelection(const QItemSelection &selection) const override
Returns the rectangle from the viewport of the items in the given selection.
void setWordWrap(bool on)
void setSelectionModel(QItemSelectionModel *selectionModel) override
\reimp
bool isHeaderHidden() const
virtual void drawBranches(QPainter *painter, const QRect &rect, const QModelIndex &index) const
Draws the branches in the tree view on the same row as the model item index, using the painter given.
void collapse(const QModelIndex &index)
Collapses the model item specified by the index.
void setRootIndex(const QModelIndex &index) override
\reimp
void setModel(QAbstractItemModel *model) override
\reimp
QModelIndex indexBelow(const QModelIndex &index) const
Returns the model index of the item below index.
int indexRowSizeHint(const QModelIndex &index) const
Returns the size hint for the row indicated by index.
void reset() override
\reimp
void doItemsLayout() override
int rowHeight(const QModelIndex &index) const
bool isExpanded(const QModelIndex &index) const
Returns true if the model item index is expanded; otherwise returns false.
void changeEvent(QEvent *event) override
\reimp
QSize viewportSizeHint() const override
\reimp
int columnViewportPosition(int column) const
Returns the horizontal position of the column in the viewport.
void columnCountChanged(int oldCount, int newCount)
Informs the tree view that the number of columns in the tree view has changed from oldCount to newCou...
void setColumnHidden(int column, bool hide)
If hide is true the column is hidden, otherwise the column is shown.
QHeaderView * header() const
Returns the header for the tree view.
void setColumnWidth(int column, int width)
void keyPressEvent(QKeyEvent *event) override
\reimp
void setTreePosition(int logicalIndex)
void rowsAboutToBeRemoved(const QModelIndex &parent, int start, int end) override
Informs the view that the rows from the start row to the end row inclusive are about to removed from ...
void setExpandsOnDoubleClick(bool enable)
QModelIndex moveCursor(CursorAction cursorAction, Qt::KeyboardModifiers modifiers) override
Move the cursor in the way described by cursorAction, using the information provided by the button mo...
void verticalScrollbarValueChanged(int value) override
bool wordWrap
the item text word-wrapping policy
int columnAt(int x) const
Returns the column in the tree view whose header covers the x coordinate given.
virtual void drawRow(QPainter *painter, const QStyleOptionViewItem &options, const QModelIndex &index) const
Draws the row in the tree view that contains the model item index, using the painter given.
void selectAll() override
\reimp
void setExpanded(const QModelIndex &index, bool expand)
Sets the item referred to by index to either collapse or expanded, depending on the value of expanded...
void updateGeometries() override
\reimp
void mousePressEvent(QMouseEvent *event) override
\reimp
void timerEvent(QTimerEvent *event) override
\reimp
~QTreeView()
Destroys the tree view.
QModelIndex indexAt(const QPoint &p) const override
\reimp
int sizeHintForColumn(int column) const override
Returns the size hint for the column's width or -1 if there is no model.
void setHeaderHidden(bool hide)
void currentChanged(const QModelIndex ¤t, const QModelIndex &previous) override
\reimp
QModelIndex indexAbove(const QModelIndex &index) const
Returns the model index of the item above index.
bool viewportEvent(QEvent *event) override
\reimp
void drawTree(QPainter *painter, const QRegion ®ion) const
void columnMoved()
This slot is called whenever a column has been moved.
bool uniformRowHeights
whether all items in the treeview have the same height
void expandToDepth(int depth)
void setUniformRowHeights(bool uniform)
void showColumn(int column)
Shows the given column in the tree view.
void setHeader(QHeaderView *header)
Sets the header for the tree view, to the given header.
QTreeView(QWidget *parent=nullptr)
Constructs a tree view with a parent to represent a model's data.
void setRootIsDecorated(bool show)
void setIndentation(int i)
int indentation
indentation of the items in the tree view.
void setAllColumnsShowFocus(bool enable)
void columnResized(int column, int oldSize, int newSize)
This function is called whenever {column}'s size is changed in the header.
void mouseReleaseEvent(QMouseEvent *event) override
\reimp
void setSelection(const QRect &rect, QItemSelectionModel::SelectionFlags command) override
Applies the selection command to the items in or touched by the rectangle, rect.
bool allColumnsShowFocus
whether items should show keyboard focus using all columns
void paintEvent(QPaintEvent *event) override
\reimp
void resizeColumnToContents(int column)
Resizes the column given to the size of its contents.
void selectionChanged(const QItemSelection &selected, const QItemSelection &deselected) override
\reimp
void setFirstColumnSpanned(int row, const QModelIndex &parent, bool span)
int autoExpandDelay
The delay time before items in a tree are opened during a drag and drop operation.
void mouseDoubleClickEvent(QMouseEvent *event) override
\reimp
void setAutoExpandDelay(int delay)
QModelIndexList selectedIndexes() const override
\reimp
void keyboardSearch(const QString &search) override
\reimp
void collapsed(const QModelIndex &index)
This signal is emitted when the item specified by index is collapsed.
void mouseMoveEvent(QMouseEvent *event) override
\reimp
void sortByColumn(int column, Qt::SortOrder order)
bool isColumnHidden(int column) const
Returns true if the column is hidden; otherwise returns false.
void scrollTo(const QModelIndex &index, ScrollHint hint=EnsureVisible) override
Scroll the contents of the tree view until the given model item index is visible.
void rowsRemoved(const QModelIndex &parent, int first, int last)
bool rootIsDecorated
whether to show controls for expanding and collapsing top-level items
bool expandsOnDoubleClick
whether the items can be expanded by double-clicking.
void setRowHidden(int row, const QModelIndex &parent, bool hide)
If hide is true the row with the given parent is hidden, otherwise the row is shown.
bool isRowHidden(int row, const QModelIndex &parent) const
Returns true if the item in the given row of the parent is hidden; otherwise returns false.
QRect visualRect(const QModelIndex &index) const override
Returns the rectangle on the viewport occupied by the item at index.
int horizontalOffset() const override
Returns the horizontal offset of the items in the treeview.
void rowsInserted(const QModelIndex &parent, int start, int end) override
Informs the view that the rows from the start row to the end row inclusive have been inserted into th...
void setSortingEnabled(bool enable)
int columnWidth(int column) const
Returns the width of the column.
void hideColumn(int column)
Hides the column given.
bool isFirstColumnSpanned(int row, const QModelIndex &parent) const
void setAnimated(bool enable)
void expanded(const QModelIndex &index)
This signal is emitted when the item specified by index is expanded.
int verticalOffset() const override
Returns the vertical offset of the items in the tree view.
void expandRecursively(const QModelIndex &index, int depth=-1)
void scrollContentsBy(int dx, int dy) override
Scrolls the contents of the tree view by (dx, dy).
void horizontalScrollbarAction(int action) override
EGLImageKHR int int EGLuint64KHR * modifiers
QSet< QString >::iterator it
Combined button and popup list for selecting options.
QList< QItemViewPaintPair > QItemViewPaintPairs
DBusConnection const char * rule
DBusConnection * connection
static QString header(const QString &name)
EGLOutputLayerEXT EGLint EGLAttrib value
[5]
static qint64 area(const QSize &s)
QT_BEGIN_NAMESPACE constexpr const T & qMin(const T &a, const T &b)
constexpr const T & qBound(const T &min, const T &val, const T &max)
constexpr const T & qMax(const T &a, const T &b)
constexpr T qAbs(const T &t)
GLint GLint GLint GLint GLint x
[0]
GLint GLenum GLsizei GLsizei GLsizei depth
GLenum GLuint GLint level
GLfloat GLfloat GLfloat w
[0]
GLint GLsizei GLsizei height
GLboolean GLboolean GLboolean GLboolean a
[7]
GLenum GLuint GLintptr GLsizeiptr size
[1]
GLdouble GLdouble GLdouble GLdouble top
GLenum GLenum GLsizei count
GLenum GLenum GLsizei const GLuint GLboolean enabled
GLenum GLuint GLintptr offset
GLfloat GLfloat GLfloat GLfloat h
GLenum GLenum GLsizei void GLsizei void * column
GLdouble GLdouble GLdouble GLdouble q
GLenum GLenum GLsizei void * row
GLenum GLenum GLsizei void GLsizei void void * span
GLfixed GLfixed GLint GLint order
QT_BEGIN_NAMESPACE constexpr decltype(auto) qMakePair(T1 &&value1, T2 &&value2) noexcept(noexcept(std::make_pair(std::forward< T1 >(value1), std::forward< T2 >(value2))))
static qreal position(const QQuickItem *item, QQuickAnchors::Anchor anchorLine)
QScopeGuard< typename std::decay< F >::type > qScopeGuard(F &&f)
[qScopeGuard]
static QT_BEGIN_NAMESPACE QVariant hint(QPlatformIntegration::StyleHint h)
QT_BEGIN_NAMESPACE constexpr void qSwap(T &value1, T &value2) noexcept(std::is_nothrow_swappable_v< T >)
static bool match(const uchar *found, uint foundLen, const char *target, uint targetLen)
static bool ancestorOf(QObject *widget, QObject *other)
QSqlQueryModel * model
[16]
connect(quitButton, &QPushButton::clicked, &app, &QCoreApplication::quit, Qt::QueuedConnection)
view viewport() -> scroll(dx, dy, deviceRect)
QItemSelection * selection
[0]
QPointer< QWidget > widget