8

I've a problem with QTreeView horizontal scrollbar, it doesn't appear. I've set horizontal scrollbar policy to ScrollBarAsNeeded, but it doesn't appear if needed. Have tried to connect expanded and collapsed signals to a slot:

connect(this, SIGNAL(expanded(QModelIndex)), this, SLOT(update_scroll_area(QModelIndex)));
connect(this, SIGNAL(collapsed(QModelIndex)), this, SLOT(update_scroll_area(QModelIndex)));

The slot consists of one line of code:

update_scroll_area(const QModelIndex& i)
{
    resizeColumnToContents(i.column());
}

This makes scrollbar working, but only when I'm expanding/collapsing the tree view items.

I need to have working horizontal scrollbar "every time", from starting the application till its end. How can it be organized?

Thank you.

4

5 回答 5

13

此常见问题解答条目可能会有所帮助。

简而言之:

  • 设置水平标题以根据列的内容调整大小(即使标题隐藏也适用)
  • 禁用“stretchLastHeaderSection”属性以防止水平标题自动调整到视口的宽度(这似乎覆盖了上述设置以调整到列的大小)
于 2011-07-11T10:42:38.753 回答
6

如果你使用 QT5 试试这个让 treewidget “水平”自动滚动:

  • 禁用水平标题的headerStretchLastSection. 和
  • ui->treeWidget->header()->setSectionResizeMode(QHeaderView::ResizeToContents);
于 2015-09-06T03:02:02.387 回答
2

对我有用的是:

  • horizontalScrollBarPolicy属性设置为ScrollBarAsNeeded
  • 将水平标题的headerMinimumSectionSize属性设置为与“几何宽度”值相同的值。
  • 将水平标题的headerDefaultSectionSize属性设置为值的两倍左右headerMinimumSectionSize
  • 禁用水平标题的headerStretchLastSection属性(如其他地方所述)。

我在我正在修改的表单上使用 Qt Designer 做到了这一点。

于 2014-10-08T23:05:48.520 回答
2

QTreeWidget在我看来,使用后缀椭圆(即“...”)截断树项而不是显示水平滚动条的默认行为是疯狂的、无用的,而且绝不是任何人想要的。但这就是我们得到的。

以下特定于 PySide2 的QTreeWidget子类以列感知方式智能地解决了这一缺陷,该方式扩展到当前树中的列数:

from PySide2.QtWidgets import QHeaderView, QTreeWidget

class QScrollableTreeWidget(QTreeWidget):
    '''
    :mod:`QTreeWidget`-based widget marginally improving upon the stock
    :mod:`QTreeWidget` functionality.

    This application-specific widget augments the stock :class:`QTreeWidget`
    with additional support for horizontal scrollbars, automatically displaying
    horizontal scrollbars for all columns whose content exceeds that column's
    width. For unknown reasons, the stock :class:`QTreeWidget` intentionally
    omits this functionality.
    '''

    def __init__(self, *args, **kwargs) -> None:
        super().__init__(*args, **kwargs)

        # Header view for this tree.
        header_view = self.header()

        # To display a horizontal scrollbar instead of an ellipse when resizing
        # a column smaller than its content, resize that column's section to its
        # optimal size. For further details, see the following FAQ entry:
        #     https://wiki.qt.io/Technical_FAQ#How_can_I_ensure_that_a_horizontal_scrollbar_and_not_an_ellipse_shows_up_when_resizing_a_column_smaller_than_its_content_in_a_QTreeView_.3F
        header_view.setSectionResizeMode(QHeaderView.ResizeToContents)

        # By default, all trees contain only one column. Under the safe
        # assumption this tree will continue to contain only one column, prevent
        # this column's content from automatically resizing to the width of the
        # viewport rather than this column's section (as requested by the prior
        # call). This unfortunate default overrides that request.
        header_view.setStretchLastSection(False)

    def setColumnCount(self, column_count: int) -> None:
        super().setColumnCount(column_count)

        # If this tree now contains more than one column, permit the last such
        # column's content to automatically resize to the width of the viewport.
        if column_count != 1:
            self.header().setStretchLastSection(True)

理论上,这个实现应该可以轻松地重写为 PyQt5 和 C++。因为 Qt 应该比明显的愚蠢默认值更好。

于 2017-09-07T08:57:56.480 回答
0

我刚刚发现了另一种情况,即水平滚动条不会出现在自定义 treeView 类中。那是当您将“setHeaderHidden()”设置为 true 并且不覆盖 resizeEvent() 时。这正是发生在我身上的事情,我通过调用插槽 resizeColumnToContents(0) 来覆盖 resizeEvent(),因为我的自定义树视图类中只有一列来使水平滚动条工作。

认为这可能对某人有所帮助。

于 2016-01-11T21:39:31.927 回答