QTreeView 自定义项显示委托和 CSS
QTreeView custom item display delegate and CSS
我有一个 QTreeView 显示我的数据,我已经为其中一列安装了自定义委托以显示彩色进度条,其外观取决于内容。我能够使用 option.palette
:
提供的颜色信息来模拟默认委托行为
class ProgressBarDelegate : public QStyledItemDelegate
{
public:
ProgressBarDelegate(QObject *parent = 0) {}
~ProgressBarDelegate() {}
void paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const
{
// QStyledItemDelegate::paint(painter, option, index); // default implementation
painter->save();
// progressbar construction and drawing
painter->restore();
}
};
现在,我想突出显示鼠标悬停事件中的一行。我为树视图设置了自定义 CSS:
ui->treeView->setStyleSheet("QTreeView::item:hover{background-color:#D0E0F0;}");
悬停突出显示有效,但我的自定义委托实现预计会忽略 CSS 设置:
(深蓝色线是所选项目,浅蓝色线是 CSS 悬停突出显示的线)
启用默认实现允许 CSS 设置影响我的委托,但它弄乱了图片:
问题是:
- 有什么方法可以从委托中获知最重要的 CSS 设置数据?
option.palette
似乎不包含此信息。
我已经尝试按照描述阅读 QTreeView 属性 here:
qDebug() << treeView()->property("background");
但控制台显示 QVariant(Invalid)
我还尝试阅读 drawControl()
和 drawPrimitive()
方法的 Qt 源代码,这些方法在默认委托实现中使用,但我设法只找到了小部件调色板引用,没有找到与CSS 覆盖。
当您在paint
方法中绘制组件时,您可以绘制"hover"效果
你可以这样使用:
// detect the hover
QStyleOptionViewItemV4 styleOption(option);
bool mouseOver = (styleOption.state & QStyle::State_MouseOver);
// draw if hovered
if(mouseOver) {
...
}
阅读 source 后,我显然发现,默认情况下无法从委托内部访问 CSS 数据,因为正在处理 CSS 解析和计算通过应用程序无法直接访问的私有 QStyleSheetStyle 对象。该对象只是修改相应的 option.palette
字段以供绘图例程使用。
但是,有一种方法可以通过调用样式的 drawPrimitive()
方法强制委托绘制一些具有所需设置的元素,而无需手动解析 option.palette
字段:
// drawing background with desired colors:
option.widget->style()->drawPrimitive(QStyle::PE_PanelItemViewItem, &opt, painter);
此方法将使用相应设置绘制背景:
我 认为 应该有类似的方法来强制使用 CSS-modified 设置,如下所示:
option.widget->style()->proxy()->drawPrimitive(QStyle::PE_PanelItemViewItem, &opt, painter);
然而,由于对 Qt 样式框架的内部工作原理缺乏了解,我还没有找到它。
我有一个 QTreeView 显示我的数据,我已经为其中一列安装了自定义委托以显示彩色进度条,其外观取决于内容。我能够使用 option.palette
:
class ProgressBarDelegate : public QStyledItemDelegate
{
public:
ProgressBarDelegate(QObject *parent = 0) {}
~ProgressBarDelegate() {}
void paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const
{
// QStyledItemDelegate::paint(painter, option, index); // default implementation
painter->save();
// progressbar construction and drawing
painter->restore();
}
};
现在,我想突出显示鼠标悬停事件中的一行。我为树视图设置了自定义 CSS:
ui->treeView->setStyleSheet("QTreeView::item:hover{background-color:#D0E0F0;}");
悬停突出显示有效,但我的自定义委托实现预计会忽略 CSS 设置:
(深蓝色线是所选项目,浅蓝色线是 CSS 悬停突出显示的线)
启用默认实现允许 CSS 设置影响我的委托,但它弄乱了图片:
问题是:
- 有什么方法可以从委托中获知最重要的 CSS 设置数据?
option.palette
似乎不包含此信息。
我已经尝试按照描述阅读 QTreeView 属性 here:
qDebug() << treeView()->property("background");
但控制台显示 QVariant(Invalid)
我还尝试阅读 drawControl()
和 drawPrimitive()
方法的 Qt 源代码,这些方法在默认委托实现中使用,但我设法只找到了小部件调色板引用,没有找到与CSS 覆盖。
当您在paint
方法中绘制组件时,您可以绘制"hover"效果
你可以这样使用:
// detect the hover
QStyleOptionViewItemV4 styleOption(option);
bool mouseOver = (styleOption.state & QStyle::State_MouseOver);
// draw if hovered
if(mouseOver) {
...
}
阅读 source 后,我显然发现,默认情况下无法从委托内部访问 CSS 数据,因为正在处理 CSS 解析和计算通过应用程序无法直接访问的私有 QStyleSheetStyle 对象。该对象只是修改相应的 option.palette
字段以供绘图例程使用。
但是,有一种方法可以通过调用样式的 drawPrimitive()
方法强制委托绘制一些具有所需设置的元素,而无需手动解析 option.palette
字段:
// drawing background with desired colors:
option.widget->style()->drawPrimitive(QStyle::PE_PanelItemViewItem, &opt, painter);
此方法将使用相应设置绘制背景:
我 认为 应该有类似的方法来强制使用 CSS-modified 设置,如下所示:
option.widget->style()->proxy()->drawPrimitive(QStyle::PE_PanelItemViewItem, &opt, painter);
然而,由于对 Qt 样式框架的内部工作原理缺乏了解,我还没有找到它。