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

如何在PySide6 QTreeWidget中仅禁用复选框列而非整行?

解决方案

要实现仅禁用QTreeWidget中特定列的复选框(而非整行),可以通过**自定义项委托(QStyledItemDelegate)**来拦截交互事件并控制复选框的绘制状态。以下是修改后的完整代码:

import sys
import random
from PyQt5.QtWidgets import (QApplication, QTreeWidgetItem, QTreeWidget, 
                             QHeaderView, QWidget, QStyledItemDelegate)
from PyQt5.QtCore import Qt, QEvent
from PyQt5.QtGui import QFont, QStyle

class CheckboxDisableDelegate(QStyledItemDelegate):
    def editorEvent(self, event, model, option, index):
        # 仅拦截复选框所在列(这里是列0)的鼠标点击/按键事件
        if index.column() == 0:
            # 阻止用户修改复选框状态
            return True
        return super().editorEvent(event, model, option, index)

    def paint(self, painter, option, index):
        if index.column() == 0:
            # 绘制禁用状态的复选框
            option.state &= ~QStyle.State_Enabled
            # 保留原有的选中状态样式
            if index.data(Qt.CheckStateRole) == Qt.Checked:
                option.state |= QStyle.State_On
            else:
                option.state |= QStyle.State_Off
        super().paint(painter, option, index)

class TreeWidget(QWidget): 
    def __init__(self): 
        super().__init__() 
        self.setWindowTitle("List Box Samples") 
        self.TreeWidget = QTreeWidget(self) 
        self.TreeWidget.resize(600,700) 
        ch_font = QFont() 
        ch_font.setBold(True) 
        ch_font.setPointSize(12) 
        
        self.TreeWidget.setColumnCount(2) 
        self.TreeWidget.setHeaderLabels(['  Test1  ','  Test2  ']) 
        self.TreeWidget.setAlternatingRowColors(True) 
        
        self.TreeWidget.header().setDefaultAlignment(Qt.AlignCenter) 
        self.TreeWidget.header().setFont(ch_font) 
        self.TreeWidget.header().setSectionResizeMode(0, QHeaderView.ResizeToContents) 
        self.TreeWidget.header().setSectionResizeMode(1, QHeaderView.ResizeToContents) 
        
        self.TreeWidget.setFont(ch_font) 

        # 为列0绑定自定义委托,禁用复选框交互
        delegate = CheckboxDisableDelegate(self.TreeWidget)
        self.TreeWidget.setItemDelegateForColumn(0, delegate)

        for i in range(5): 
            item = QTreeWidgetItem(self.TreeWidget) 
            item.setText(0,"Test root") 
            item.setText(1,"Test str") 
            for i in range(10): 
                child_item = QTreeWidgetItem(item) 
                child_item.setCheckState(0,Qt.Checked) 
                child_item.setText(0,str(i)) 
                child_item.setText(1,"Test"+str(i)) 

if __name__ == "__main__": 
    app = QApplication(sys.argv) 
    win = TreeWidget() 
    win.show() 
    sys.exit(app.exec_()) 

核心逻辑说明

  • 自定义委托类:CheckboxDisableDelegate 继承自QStyledItemDelegate,通过两个方法实现需求:
    1. editorEvent:拦截目标列的鼠标/按键事件,直接返回True阻止用户修改复选框状态。
    2. paint:绘制目标列的复选框时,强制设置为禁用状态,同时保留原有的选中/未选中样式,让用户直观感知复选框不可交互。
  • 绑定委托:通过setItemDelegateForColumn方法将自定义委托绑定到指定列,不影响其他列的正常交互。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.30 20:09:25