You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何解决PySide/Qt QColumnView点击上层空白处视图不更新问题?

QColumnView点击上层目录空白处不更新视图的解决方案

我在开发一款仿macOS Finder米勒列(Miller Columns)的文件浏览器,使用Qt的QColumnView搭配QFileSystemModel组件,但遇到了一个问题:当进入多层目录后,点击当前目录上层区域的空白处,视图不会切换到对应目录,仅会移除当前文件夹的高亮效果;点击根目录空白处时甚至不会触发任何事件。

解决方案

核心思路是重写QColumnView的mousePressEvent,手动处理空白区域的点击事件,定位到点击列对应的父目录索引并设置为当前选中项。

修改CustomColumns类如下:

from PySide6.QtCore import QPoint, Qt
from PySide6.QtWidgets import QColumnView, QAbstractItemView

class CustomColumns(QColumnView):
    def mousePressEvent(self, event):
        # 先处理默认的项点击逻辑
        super().mousePressEvent(event)
        
        # 如果点击的是空白区域(未命中任何项)
        if event.button() == Qt.LeftButton:
            # 获取点击位置对应的子视图(列)
            view = self.viewAt(event.pos())
            if view:
                # 获取该列的根索引(即对应上层目录的索引)
                root_index = view.rootIndex()
                # 如果根索引有效,设置为当前选中项
                if root_index.isValid():
                    self.selectionModel().setCurrentIndex(
                        root_index,
                        QAbstractItemView.ClearAndSelect | QAbstractItemView.Rows
                    )

完整修改后的MCVE

from pathlib import Path
from PySide6.QtCore import QPoint, Qt
from PySide6.QtWidgets import (
    QApplication,
    QFileSystemModel,
    QColumnView,
    QMainWindow,
    QAbstractItemView
)


class CustomColumns(QColumnView):
    def mousePressEvent(self, event):
        super().mousePressEvent(event)
        
        if event.button() == Qt.LeftButton:
            view = self.viewAt(event.pos())
            if view:
                root_index = view.rootIndex()
                if root_index.isValid():
                    self.selectionModel().setCurrentIndex(
                        root_index,
                        QAbstractItemView.ClearAndSelect | QAbstractItemView.Rows
                    )


class BrowserWindow(QMainWindow):
    def __init__(self, location=None):
        super().__init__()
        if location is None:
            location = Path.home()
        location = Path(location)
        self.setGeometry(625, 333, 1395, 795)
        self.setWindowTitle(location.name)

        self._root = str(location)
        self._files = QFileSystemModel()
        self._files.setRootPath(self._root)

        self._view = CustomColumns()
        self._view.setModel(self._files)

        self.setCentralWidget(self._view)

    def show(self):
        super().show()
        self._view.setRootIndex(self._files.index(self._root))


class FileBrowser(QApplication):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.setQuitOnLastWindowClosed(False)
        self.window = BrowserWindow(location=Path.home())
        self.window.show()


def main():
    app = FileBrowser()
    app.exec()


if __name__ == "__main__":
    main()

效果说明

修改后,点击任意上层目录列的空白区域,视图会自动切换到该列对应的目录,完全匹配macOS Finder的米勒列交互逻辑。

内容的提问来源于stack exchange,提问作者Darrick Herwehe

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.27 01:14:58