QStandardItemModel
标准数据模型,每个项都是一个QStandardItem类的变量
QTableView
二维数据表视图组件,通过将QStandardItemModel设置为数据模型后,每一个基本单元格显示一个QStandardItemModel的项(即QStandardItem)
QItemSelectionModel
用于追踪视图组件单元格状态,可以获得QTableView选中的单元格索引,基本单元也是QStandardItem。
将QStandardItemModel,QItemSelectionModel设置为QTableView数据模型和选择模型。
//数据模型 2行,6列,parent:this
theModel = new QStandardItemModel(2,FixedColumnCount, this);
//选择模型
theSelection = new QItemSelectionModel(theModel);
ui->tableView->setModel(theModel);
ui->tableView->setSelectionModel(theSelection);
当单元格发生变化
connect(theSelection, SIGNAL(currentChanged(QModelIndex,QModelIndex)),this,SLOT(on_currentChange(QModelIndex,QModelIndex)));
//在状态栏上显示信息
void MainWindow::on_currentChange(const QModelIndex ¤t, const QModelIndex &previous)
{
if(current.isValid())
{
LabCellPos->setText(QString::asprintf("当前单元格:%d, %d",current.row(),current.column()));
//获取当前项
QStandardItem* aItem = theModel->itemFromIndex(current);
this->LabCellText->setText("单元格内容 "+aItem->text());
QFont font = aItem->font();
ui->actionFontBold->setChecked(font.bold());
}
}
打开文件,按格式导入数据
//在plainText上显示文本 并初始化数据模型
void MainWindow::on_actOpen_triggered()
{
QString curPath = QCoreApplication::applicationDirPath();
QString aFileName = QFileDialog::getOpenFileName(this, "打开一个文件", curPath, "数据文件(*.txt);;所有文件(*.*)");//文件窗口
if(aFileName.isEmpty())
{
return;
}
QStringList fFileContent;
QFile aFile(aFileName);
if(aFile.open(QIODevice::ReadOnly) | QIODevice::Text) //打开文件
{
QTextStream aStream(&aFile); //用文本流读取文件
ui->plainTextEdit->clear();
while(!aStream.atEnd())
{
QString str = aStream.readLine();//从流中读取一行文本,返回不以\n \r\n结尾
ui->plainTextEdit->appendPlainText(str);
fFileContent.append(str);
}
aFile.close();
this->LabCurFile->setText("当前文件:"+aFileName);
iniModelFromStringList(fFileContent);//初始化数据模型
}
}
//在tableView中显示数据
void MainWindow::iniModelFromStringList(QStringList &aFileContent)
{
//从打开的文件返回的stringList中获取数据
int rowCnt = aFileContent.count(); //文本行数
theModel->setRowCount(rowCnt-1); //设置行数
//将数据中的第0行设置为表头
QString header = aFileContent.at(0);
//根据给定的正则表达式 拆分字符串 \\s表示 空格,回车,换行等空白符,+号表示一个或多个的意思
QStringList headerList = header.split(QRegExp("\\s+"),QString::SkipEmptyParts);
theModel->setHorizontalHeaderLabels(headerList); //设置表头文字
//设置表格数据
QStandardItem *aItem;
QStringList tmpList;
int j;
for(int i = 1; i<rowCnt; i++)
{
QString aLineText = aFileContent.at(i);//遍历stringList每一行
tmpList = aLineText.split(QRegExp("\\s+"),QString::SkipEmptyParts);
for(j=0; j<FixedColumnCount-1; j++)
{
aItem = new QStandardItem(tmpList.at(j));//每行数据有6列 将每个数据赋给aItem
theModel->setItem(i-1, j, aItem);//显示aItem
}
aItem = new QStandardItem(headerList.at(j));
aItem->setCheckable(true); //将最后一列 设置为复选框
if(tmpList.at(j) == "0")
{
aItem->setCheckState(Qt::Unchecked);
}
else
aItem->setCheckState(Qt::Checked);
theModel->setItem(i-1, j, aItem);//显示最后一列
}
}
添加一行数据
void MainWindow::on_actAppend_triggered()
{
QList<QStandardItem*> aItemList; //列表类
QStandardItem *aItem;
for(int i = 0; i<FixedColumnCount-1; i++)//将1到5列设置为0
{
aItem = new QStandardItem("0");
aItemList<<aItem; //添加到列表
}
QString str = theModel->headerData(theModel->columnCount()-1, Qt::Horizontal).toString();
aItem = new QStandardItem(str);
aItem->setCheckable(true);
aItemList<<aItem; //第六列添加进列表
theModel->insertRow(theModel->rowCount(), aItemList); //插入一行,(行数,QList<QStandardItem*>)
QModelIndex curIndex = theModel->index(theModel->rowCount()-1,0); //(行数, 列数)
theSelection->clearSelection();
theSelection->setCurrentIndex(curIndex, QItemSelectionModel::Select);//选择到 新增那一行上
}
插入一行数据【将上面代码稍微修改即可】
void MainWindow::on_actInsert_triggered()
{
//....同上.....
QModelIndex curIndex = theSelection->currentIndex();//取得当前选择的索引
theModel->insertRow(curIndex.row(), aItemList); //插入一行,(行数,QList<QStandardItem*>)
//....同上.....
}
数据文件另存
void MainWindow::on_actSave_triggered()
{
QString curPath = QCoreApplication::applicationDirPath();
QString aFileName = QFileDialog::getSaveFileName(this, "选择一个文件", curPath, "数据文件(*.txt);;所有文件(*.*)");//保存文件窗口getSaveFileName
if(aFileName.isEmpty())
return;
QFile aFile(aFileName);
if(!(aFile.open(QIODevice::ReadWrite | QIODevice::Text | QIODevice::Truncate)))
return;
QTextStream aStream(&aFile);
QStandardItem *aItem;
int i,j;
QString str="";
ui->plainTextEdit->clear();
//获取列表头
for(i = 0; i<theModel->columnCount(); i++)
{
aItem = theModel->horizontalHeaderItem(i);
str+=aItem->text()+"\t\t";
}
aStream<<str<<"\n";
ui->plainTextEdit->appendPlainText(str);
//获取内容
for(i = 0; i<theModel->rowCount(); i++)
{
str = "";
for(j = 0; j<theModel->columnCount()-1; j++)
{
aItem = theModel->item(i,j);
str = str+aItem->text()+QString::asprintf("\t\t");
}
aItem = theModel->item(i,j);
if(aItem->checkState() == Qt::Checked)
str+="1";
else
str+="0";
//在plainTextEdit上显示
ui->plainTextEdit->appendPlainText(str);
aStream<<str<<"\n";
}
aFile.close();
}