设计自定义代理与使用笔记

一、设计float型spinbox代理类(定义int型spinbox和combox选项列表同此步骤)

        1、新建对话框

选择new file -> C/C++ -> C++ class 创建

        2、新建C++类对话框

        类名称(class name)为新建的类的名称设置为TFloatSpinDelegate。Base class基类名称,选择自定义,输入QStyledItemDelegate。Header file Souce file根据class name自动生成。

        勾选 include QObject 与 add Q_OBJECT,建议勾上无论是否使用元对象系统 。

二、重新实现createEditor() setEditorData() setModelData() updateEditorGeometry()四个函数

        1、函数原型

1)createEditor():可创建用于编辑模型数据的界面组件,称为代理编辑器。

QWidget *QStyledItemDelegate::createEditor(
    QWidget *parent,
    const QStyleOptionViewItem &option,
    const QModelIndex &index
)

        参数2:QStyleOptionViewItem 是 Qt 中用于描述视图项外观和行为的类,继承自QStyleOption

2)setEditorData():从数据模型获取项的某个角色,一般是EditRole角色的数据(EditRole为模型索引QModelIndex中Qt::ItemDataRole的枚举值,见Qt6 C++开发指南p175)

void QStyledItemDelegate::setEditorData(QWidget *editor,const QModelIndex &index)

Qt::ItemDataRole常用枚举值

枚举值角色数据类型含义
Qt::DisplayRoleQString界面上显示的字符串
Qt::DecorationRoleQIcon、QColor界面上的装饰
Qt::EditRoleQString界面上适合再编辑器中显示的数据
Qt::ToolTipRoleQString项的toolTip字符串
Qt::StatusTipRole       QString

项的statusTip字符串

Qt::FontRoleQFont项的字体
Qt::TextAlignmentRoleQt::Alignment项的对齐方式
Qt::BackgroundRoleQBrush项的背景色
Qt::ForegroundRoleQBrush项的前景色
Qt::CheckStateRoleQt::CheckState项的复选状态
Qt::UserRoleQVariant自定义的项目数据

3)setModelData():完成对当前单元格的编辑。

void QStyledItemDelegate::setModelData(
    QWidget *editor,
    QAbstractItemModel *model,
    const QModleIndex &index
)

        参数2:QAbstractItemModel在Qt框架中中的一个核心抽象基类,在Qt的模型/视图架构中主要功能是为视图组件提供一个标准化的接口,使其能够访问和操作数据。

4)updateEditorGeometry():调用此函数时为组件设置合适大小。

                

void QStyledItemDelegate::updateEditorGeometry(
    QWidget *editor,
    const QStyleOptionViewItem &option,
    const QModelIndex &index
)

        2、.h定义,.cpp重新实现

1)浮点型spinbox代理器

        tfloatspinboxdelegate.h

class TFloatSpinDelegate : public QStyledItemDelegate
{
    Q_OBJECT
public:
    explicit TFloatSpinDelegate(QObject *parent=nullptr);
    QWidget *createEditor(QWidget *parent,const QStyleOptionViewItem &option,const QModelIndex &index)const;
    void setEditorData(QWidget *editor,const QModelIndex &index)const;
    void setModelData(QWidget *editor,QAbstractItemModel *model,const QModelIndex &index)const;
    void updateEidtorGeometry(QWidget *editor,const QStyleOptionViewItem &option,const QModelIndex &index)const;
};

        tfloatspinboxdelegate.cpp文件

#include "tfloatspindelegate.h"
#include <QStyleOptionViewItem>
#include <QModelIndex>//头文件class声明,cpp文件引入
#include <QAbstractItemModel>
#include <QDoubleSpinBox>

TFloatSpinDelegate::TFloatSpinDelegate(QObject *parent): QStyledItemDelegate{parent} {}

QWidget *TFloatSpinDelegate::createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const
{
    //创建代理编辑器
    Q_UNUSED(option);
    Q_UNUSED(index);
    QDoubleSpinBox *editor=new QDoubleSpinBox(parent);
    editor->setFrame(false);//设置无边框
    editor->setMinimum(0);
    editor->setMaximum(2000);
    editor->setDecimals(2);//设置显示小数位
    return editor;//返回创建的spinBox
}

void TFloatSpinDelegate::setEditorData(QWidget *editor, const QModelIndex &index) const
{
    //QAbstractItemModel定义了函数data(),可以返回不同角色的数据
   
    float value=index.model()->data(index,Qt::EditRole).toFloat();//EditRole界面上适合在编辑器中显示的数据,一般是文字
    //设置为代理编辑器的值
    QDoubleSpinBox *spinbox=static_cast<QDoubleSpinBox*>(editor);//比较自然和低风险的转换,但static_cast不能用于在不同类型的指针之间的转换
    spinbox->setValue(value);
}

void TFloatSpinDelegate::setModelData(QWidget *editor,QAbstractItemModel *model, const QModelIndex &index) const
{
    QDoubleSpinBox* spinbox=static_cast<QDoubleSpinBox*>(editor);
    float value=spinbox->value();
    QString str=QString::asprintf("%.2f",value);//后2位显示
    model->setData(index,str,Qt::EditRole);//保存数据模型
}

void TFloatSpinDelegate::updateEidtorGeometry(QWidget *editor, const QStyleOptionViewItem &option, const QModelIndex &index) const
{
    Q_UNUSED(index);
    //QStyleOptionViewItem继承自QStyleOption,用于描述外观和行为的类
    //通用方法:rect,size获取、设置选项的矩形区域大小
    editor->setGeometry(option.rect);//设置组件大小
}

        updateEditorGemometry()函数中QStyleOptionViewItem继承子QStyleOption,描述外观和行为的类,rect()为获取option矩形区域大小。

2)选项列表代理类设计

        除重新重新实现四个函数外,令定义选项列表QStringList变量和bool变量,用来存放列表内容和是否可编辑状态,下面tcomboboxdelegate.h文件

private:
    QStringList m_itemList;//选项列表
    bool m_editable;

public:
    explicit TComboBoxDelegate(QObject *parent = nullptr);
    void setItems(QStringList items,bool editable);//初始化列表内容,是否可编辑

    QWidget *createEditor(QWidget *parent,const QStyleOptionViewItem &option,const QModelIndex &index)const;
    void setEditorData(QWidget *editor,const QModelIndex &index)const;
    void setModelData(QWidget *editor,QAbstractItemModel *model,const QModelIndex &index)const;
    void updateEditorGeometry(QWidget *editor,const QStyleOptionViewItem &option,const QModelIndex &index)const;

        tcomboboxdelegate.cpp文件

void TComboBoxDelegate::setItems(QStringList items, bool editable)
{
    m_itemList=items;
    m_editable=editable;

}

QWidget *TComboBoxDelegate::createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const
{
    //初始化编辑器
    Q_UNUSED(option);
    Q_UNUSED(index);
    QComboBox *editor=new QComboBox(parent);
    editor->setEditable(m_editable);//设置是否可编辑
    for(int i=0;i<m_itemList.count();i++)
        editor->addItem(m_itemList.at(i));
    return editor;
}

void TComboBoxDelegate::setEditorData(QWidget *editor, const QModelIndex &index) const
{
    //编辑器数据修改
    QString str=index.model()->data(index,Qt::EditRole).toString();
    QComboBox *combox=static_cast<QComboBox*>(editor);
    combox->setCurrentText(str);//设置文本

}

void TComboBoxDelegate::setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const
{
    //将编辑器数据保存到模型
    QComboBox* combox=static_cast<QComboBox*>(editor);
    QString str=combox->currentText();
    model->setData(index,str,Qt::EditRole);//设置模型数据
}

void TComboBoxDelegate::updateEditorGeometry(QWidget *editor, const QStyleOptionViewItem &option, const QModelIndex &index) const
{
    Q_UNUSED(index);
    editor->setGeometry(option.rect);
}

3)int型spinbox代理编辑器

        同1)

三、使用自定义代理类

1、定义代理变量

        引入tfloatspinboxdelegate.h,tspinboxdelegate.h,tcomboboxdelegate.h头文件后

TSpinboxDelegate *intSpinDelegate;
TFloatSpinboxDelegate *floatSpinDelegate;
TComboBoxDelegate *comboDelegate;

2、设置委托

ntspinBoxDelegate=new TSpinBoxDelegate(this);
//设置委托
ui->tableView->setItemDelegateForColumn(0,intspinBoxDelegate);//为测深设置委托

floatSpinDelegate=new TFloatSpinDelegate(this);
//设置委托
ui->tableView->setItemDelegateForColumn(1,floatSpinDelegate);//垂深
ui->tableView->setItemDelegateForColumn(2,floatSpinDelegate);//方位
ui->tableView->setItemDelegateForColumn(3,floatSpinDelegate);//总位移

comboBoxDelegate=new TComboBoxDelegate(this);
QStringList strList;
strList<<"优"<<"良"<<"可"<<"不合格";//选项列表
comboBoxDelegate->setItems(strList,false);//设置可编辑状态
ui->tableView->setItemDelegateForColumn(4,comboBoxDelegate);

        QAbstractItemView类设置自定义代理函数,以下:

1)将delegate设置为整个视图的代理

void setItemDelegate(QAbstractItemDelegate *delegate);

2)为某一列设置自定义代理

void setItemDelegateForColumn(int column,QAbstractItemDelegate* *delegate);

3)为某一行设置自定义代理

void setItemDelegateForRow(int Row,QAbstractItemDelegate *delegate);

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值