当前位置: 首页 > web >正文

QT6(QStandardItemModel和QTableView及自定义代理)

QT6


QStandardItemModel和QTableView

  • QStandardItemModel:jag:基于项的模型类在,每个项是一个QStandarditem对象
  • QtableView:显示二维数据的组件
  • QItemSelectionModel:选择模型,用于跟踪视图组件的单元格选择状态,通过它可以获得选中单元格的模型索引,设置选择状态

QTableView常用方法和属性

外观属性

属性/方法名类型/返回值说明
showGridbool是否显示网格线
gridStyleQt::PenStyle网格线样式(如 Qt::SolidLine, Qt::DotLine
alternatingRowColorsbool是否使用交替行颜色

表头控制

属性/方法名类型/返回值说明
horizontalHeader()QHeaderView*获取水平表头对象
verticalHeader()QHeaderView*获取垂直表头对象
horizontalHeaderVisiblebool水平表头是否可见
verticalHeaderVisiblebool垂直表头是否可见

选择行为

属性/方法名类型/返回值说明
selectionBehaviorQAbstractItemView::SelectionBehavior选择行为(选择项、行或列)
selectionModeQAbstractItemView::SelectionMode选择模式(如单选、多选)

编辑特性

属性/方法名类型/返回值说明
editTriggersQAbstractItemView::EditTriggers编辑触发器(如双击编辑)

排序功能

属性/方法名类型/返回值说明
sortingEnabledbool是否启用排序

调整尺寸

属性/方法名类型/返回值说明
resizeColumnToContents(int)void调整某列宽度以适应内容
resizeColumnsToContents()void调整所有列宽度以适应内容
resizeRowToContents(int)void调整某行高度以适应内容
resizeRowsToContents()void调整所有行高度以适应内容

模型操作

属性/方法名类型/返回值说明
setModel(QAbstractItemModel*)void设置数据模型
model()QAbstractItemModel*获取当前数据模型

交互相关

属性/方法名类型/返回值说明
setIndexWidget(const QModelIndex &, QWidget*)void在指定索引处设置部件

代码测试

#include "mainwindow.h"
#include "./ui_mainwindow.h"
#include <QLabel>
#include <QStandardItemModel>
#include <QItemSelectionModel>
#include <QFileDialog>
#include <QFile>
#include <QRegularExpression>MainWindow::MainWindow(QWidget *parent): QMainWindow(parent), ui(new Ui::MainWindow)
{ui->setupUi(this);labCurrFile = new QLabel("当前文件",this);labCurrFile->setMinimumWidth(200);labCellpos = new QLabel("当前单元格",this);labCurrFile->setMinimumWidth(200);labCellText = new QLabel("单元格内容",this);labCellText->setMinimumWidth(200);ui->statusbar->addWidget(labCurrFile);ui->statusbar->addWidget(labCellpos);ui->statusbar->addWidget(labCellText);m_model = new QStandardItemModel(2,FixedColumCount,this);m_selection = new QItemSelectionModel(m_model,this);ui->tableView->setModel(m_model);ui->tableView->setSelectionModel(m_selection);ui->tableView->setSelectionMode(QAbstractItemView::ExtendedSelection);ui->tableView->setSelectionBehavior(QAbstractItemView::SelectItems);connect(m_selection,&QItemSelectionModel::currentChanged,this,&MainWindow::do_currentChanged);
}MainWindow::~MainWindow()
{delete ui;
}void MainWindow::do_currentChanged(const QModelIndex &current, const QModelIndex &prevous)
{if(current.isValid()){labCellpos->setText(QString::asprintf("当前单元格:%d行,%d列",current.row(),current.column()));QStandardItem* aItem = m_model->itemFromIndex(current);labCellText->setText("单元格内容:"+ aItem->text());// 判断当前选择的item是否为粗体ui->actionBold->setChecked(aItem->font().bold());}
}void MainWindow::on_actionOpenFile_triggered()
{QString curPath = QCoreApplication::applicationFilePath();QString aFileName = QFileDialog::getOpenFileName(this,"打开一个文件",curPath,"数据文件(*.txt);;所有文件(*.*)");if(aFileName.isEmpty())return;QFile aFile(aFileName);if(!aFile.open(QIODevice::ReadOnly|QIODevice::Text))return;QStringList aFileContent;ui->plainTextEdit->clear();QTextStream aStream(&aFile);while(!aStream.atEnd()){QString str = aStream.readLine();ui->plainTextEdit->appendPlainText(str);aFileContent.append(str);}aFile.close();labCurrFile->setText("当前文件" + aFileName);ui->actionAddLine->setEnabled(true);ui->actionInsertLine->setEnabled(true);ui->actionDelLine->setEnabled(true);iniModelData(aFileContent);
}void MainWindow::iniModelData(QStringList& aFileContext)
{int rowCnt = aFileContext.size();m_model->setRowCount(rowCnt - 1);QString header = aFileContext.at(0);QStandardItem *aItem;int j;// 获取表头QStringList headerList = header.split(QRegularExpression(R"(\s)"),Qt::SkipEmptyParts);// 设置表头m_model->setHorizontalHeaderLabels(headerList);for(int i = 0; i < rowCnt ; i++){QString aLineText = aFileContext.at(i);QStringList tempList = aLineText.split(QRegularExpression(R"(\s)"),Qt::SkipEmptyParts);for(j = 0 ; j < FixedColumCount -1 ; ++j){aItem = new QStandardItem(tempList.at(j));// 设置每一项m_model->setItem(i-1,j,aItem);}// 设置最后一项aItem = new QStandardItem(headerList.at(j));aItem->setCheckable(true);aItem->setBackground(QBrush(Qt::yellow));if(tempList.at(j) == "0")aItem->setCheckState(Qt::Unchecked);elseaItem->setCheckState(Qt::Checked);m_model->setItem(i-1,j,aItem);}
}void MainWindow::on_actionDataPreview_triggered()
{ui->plainTextEdit->clear();QStandardItem* aItem;QString str;int j;for(int i = 0; i<m_model->columnCount();i++){aItem = m_model->horizontalHeaderItem(i);str+=aItem->text();str+="\t";}ui->plainTextEdit->appendPlainText(str);for(int i = 0;i < m_model->rowCount();i++){str="";for(j = 0; j<m_model->columnCount() -1;j++){aItem = m_model->item(i,j);str+=aItem->text();str+="\t";}aItem = m_model->item(i,j);if(aItem->checkState()==Qt::Checked){str+="是";}else{str+="否";}ui->plainTextEdit->appendPlainText(str);}
}void MainWindow::on_actionAddLine_triggered()
{QList<QStandardItem*> aItemList;QStandardItem* aItem;for(int i = 0;i<m_model->columnCount()-1;i++){aItem = new QStandardItem("0");aItemList << aItem;}QString str = m_model->headerData(m_model->columnCount() - 1,Qt::Horizontal).toString();aItem = new QStandardItem(str);aItem->setCheckable(true);aItem->setBackground(QBrush(Qt::yellow));aItemList << aItem;m_model->insertRow(m_model->rowCount(),aItemList);m_selection->clearSelection();m_selection->setCurrentIndex(m_model->index(m_model->rowCount() - 1,0),QItemSelectionModel::Select);
}void MainWindow::on_actionInsertLine_triggered()
{QList<QStandardItem*> aItemList;QStandardItem* aItem;for(int i = 0;i<m_model->columnCount()-1;i++){aItem = new QStandardItem("123");aItemList << aItem;}QString str = m_model->headerData(m_model->columnCount() - 1,Qt::Horizontal).toString();aItem = new QStandardItem(str);aItem->setCheckable(true);aItem->setBackground(QBrush(Qt::yellow));aItemList << aItem;QModelIndex curIndex = m_selection->currentIndex();m_model->insertRow(m_selection->currentIndex().row(),aItemList);m_selection->clearSelection();m_selection->setCurrentIndex(curIndex,QItemSelectionModel::Select);
}void MainWindow::on_actionDelLine_triggered()
{QModelIndex curIndex = m_selection->currentIndex();if(curIndex.row() != m_model->columnCount()-1){m_selection->setCurrentIndex(curIndex,QItemSelectionModel::Select);m_model->removeRow(curIndex.row());}else{m_model->removeRow(curIndex.row());}
}void MainWindow::on_actionLeft_triggered()
{if(!m_selection->hasSelection())return;QModelIndexList indexList = m_selection->selectedIndexes();for(auto index:indexList){m_model->itemFromIndex(index)->setTextAlignment(Qt::AlignLeft|Qt::AlignVCenter);}
}void MainWindow::on_actionCenter_triggered()
{if(!m_selection->hasSelection())return;QModelIndexList indexList = m_selection->selectedIndexes();for(auto index:indexList){m_model->itemFromIndex(index)->setTextAlignment(Qt::AlignHCenter|Qt::AlignVCenter);}
}void MainWindow::on_actionRight_triggered()
{if(!m_selection->hasSelection())return;QModelIndexList indexList = m_selection->selectedIndexes();for(auto index:indexList){m_model->itemFromIndex(index)->setTextAlignment(Qt::AlignRight|Qt::AlignVCenter);}
}void MainWindow::on_actionBold_triggered(bool checked)
{if(!m_selection->hasSelection())return;QModelIndexList indexList = m_selection->selectedIndexes();for(auto index:indexList){QFont font = m_model->itemFromIndex(index)->font();font.setBold(checked);m_model->itemFromIndex(index)->setFont(font);}
}

效果展示

在这里插入图片描述


自定义代理

  • 在模型视图结构中,代理的作用就是在视图组件进入编辑状态编辑某个项时,提供一个临时的编辑器用于数据编辑,默认的代理编辑器是QLineEdit编辑框
  • 可以对这个默认的编辑框进行替换,比如QSpinBox、QDoubleSpinBox、ComboBox

继承关系

QObject
QAbstractItemDelegate
QStyledItemDelegate
QItemDelegate
QSqqlRelationalDelegate
自定义委托
自定义委托

必须实现以下几个函数

  • createEditor():创建用于编辑模型数据的widget组件,如QSpinBox,QComboBox
  • setEditorData():从数据模型获取数据,供widget组件进行编辑
  • setModelData():将widget上的数据更新到数据模型
  • updateditorGeometry():用于给widget组件设置一个合适的大小

代码测试

TComboBoxDelegate.cpp
#include "tcomboboxdelegate.h"
#include <QComboBox>
TComboBoxDelegate::TComboBoxDelegate(QObject *parent): QStyledItemDelegate{parent}
{}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_editTable);for(auto item:m_itemList){editor->addItem(item);}return editor;
}void TComboBoxDelegate::setEditorData(QWidget *editor, const QModelIndex &index) const
{QComboBox* comBoBox = dynamic_cast<QComboBox*>(editor);QString str = index.model()->data(index,Qt::EditRole).toString();comBoBox->setCurrentText(str);
}void TComboBoxDelegate::setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const
{QComboBox* comBoBox = dynamic_cast<QComboBox*>(editor);QString str = comBoBox->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);}void TComboBoxDelegate::setItems(QStringList itemList, bool editTable)
{m_itemList = itemList;m_editTable = editTable;
}
TFloatSpinDelegate.cpp
#include "tfloatspindelegate.h"
#include <QDoubleSpinBox>
TFloatSpinDelegate::TFloatSpinDelegate(QObject *parent): QStyledItemDelegate{parent}
{}QWidget *TFloatSpinDelegate::createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const
{QDoubleSpinBox* editor = new QDoubleSpinBox(parent);editor->setFrame(false);editor->setMinimum(0);editor->setMaximum(5000);return editor;
}void TFloatSpinDelegate::setEditorData(QWidget *editor, const QModelIndex &index) const
{QDoubleSpinBox* spinBox = dynamic_cast<QDoubleSpinBox*>(editor);double value = index.model()->data(index,Qt::EditRole).toDouble();spinBox->setValue(value);
}void TFloatSpinDelegate::setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const
{QDoubleSpinBox* spinBox = dynamic_cast<QDoubleSpinBox*>(editor);double value = spinBox->value();model->setData(index,value,Qt::EditRole);
}void TFloatSpinDelegate::updateEditorGeometry(QWidget *editor, const QStyleOptionViewItem &option, const QModelIndex &index) const
{Q_UNUSED(index);editor->setGeometry(option.rect);
}
TSpinBoxDelegate.cpp
#include "tspinboxdelegate.h"
#include <QSpinBox>
TSpinBoxDelegate::TSpinBoxDelegate(QObject *parent): QStyledItemDelegate{parent}{}QWidget *TSpinBoxDelegate::createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const
{QSpinBox* editor = new QSpinBox(parent);editor->setFrame(false);editor->setMinimum(0);editor->setMaximum(5000);return editor;
}void TSpinBoxDelegate::setEditorData(QWidget *editor, const QModelIndex &index) const
{QSpinBox* spinBox = dynamic_cast<QSpinBox*>(editor);int value = index.model()->data(index,Qt::EditRole).toInt();spinBox->setValue(value);
}void TSpinBoxDelegate::setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const
{QSpinBox* spinBox = dynamic_cast<QSpinBox*>(editor);int value = spinBox->value();model->setData(index,value,Qt::EditRole);
}void TSpinBoxDelegate::updateEditorGeometry(QWidget *editor, const QStyleOptionViewItem &option, const QModelIndex &index) const
{Q_UNUSED(index);editor->setGeometry(option.rect);
}
MainWindow.cpp
	// 创建代理类对象intSpinDelegate = new TSpinBoxDelegate(this);// 通过列来设置ui->tableView->setItemDelegateForColumn(0,intSpinDelegate);doubleSpinDelegate = new TFloatSpinDelegate(this);ui->tableView->setItemDelegateForColumn(1,doubleSpinDelegate);ui->tableView->setItemDelegateForColumn(2,doubleSpinDelegate);ui->tableView->setItemDelegateForColumn(3,doubleSpinDelegate);comBoDelegate = new TComboBoxDelegate(this);QStringList strList;strList << "优" << "良" << "中" << "差";comBoDelegate->setItems(strList,false);ui->tableView->setItemDelegateForColumn(4,comBoDelegate);

效果展示

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

http://www.xdnf.cn/news/19523.html

相关文章:

  • 【数据结构】并查集
  • Nodejs之HelloWord Hello-Http
  • 深度学习篇---MobileNet
  • 【系列12】端侧AI:构建与部署高效的本地化AI模型 第11章:边缘设备与IoT部署
  • C++ 面试高频考点 力扣 69. x 的平方根 二分查找 题解 每日一题
  • 鸿蒙创新赛活动——Mac提交压缩失败后续
  • [知识点记录]SQLite 数据库和MySQL 数据库有什么区别?
  • 服务器音频查找
  • 【MD文本编辑器Typora】实用工具推荐之——轻量级 Markdown 编辑器Typora下载安装使用教程 办公学习神器
  • 【Android】LayoutInflater 控件实例化的桥梁类
  • 【Linux】模拟实现Shell(上)
  • 【大模型面试宝典之微调篇】(一)
  • 【C++详解】C++11(二) lambda表达式、类型分类、引⽤折叠、完美转发
  • JavaEE初阶网络原理-初识
  • ArrayList源码解析之序列化
  • 【LeetCode 热题 100】64. 最小路径和——(解法二)递推
  • DSPFilters实现低通滤波器(QT)
  • 【开题答辩全过程】以 留守儿童志愿者服务系统为例,包含答辩的问题和答案
  • Java全局异常处理器:优雅处理系统异常
  • 数学运算符号:跨越千年的智慧结晶与文明印记
  • strtok()字符串分隔函数
  • VideoPoet:Google发布的用于视频生成的大语言模型
  • 【C#】在一个任意旋转的矩形(由四个顶点定义)内绘制一个内切椭圆
  • SpringAI应用开发面试实录:核心技术、架构设计与业务场景全解析
  • 华为研发投资与管理实践(IPD)读书笔记
  • VSCode `tasks.json` 中 `tasks` 数组的详细解析
  • 语义分析:从读懂到理解的深度跨越
  • Photoshop - Ps 标尺
  • JVM参数配置调优指南
  • 在开发过程中经常遇到 OOM(内存溢出)问题,如何解决?