**View和**Widget的区别?
**View的实现更底层,**Widget是基于**View封装实现的更易用的类型。
**View使用MVC结构
MVC是软件开发中 经典的 软件结构 组织形式,软件设计模式。
M(model)模型。管理应用程序的核心数据和业务逻辑。并且通知视图和控制器数据已经发生变化。
V(view)视图,界面。显示数据,并接受用户输入。
C(controller)控制器。衔接M和V,处理用户输入,更新模型和视图。
**View只负责视图,并不具备其他功能,如数据存储、业务逻辑。
使用**View需要程序员自己写,model和controller部分。
**Widget已经封装好,具备各部分功能,并提供接口设置自定义部分。
1.QListWidget 列表控件
- 功能:显示纵向的列表,每个选项都可以被选中
currentRow 当前被选中的的是第几行 count 一共多少行 sortingEnabled 是否允许排序
isWrapping 是否允许换行 itemAlinment 元素对齐方式 selectRectVisible 被选中元素的矩形是否可见 spacing 元素之间的间隔
- 方法:
addItem(const QString& label)
addItem(QListWidget Item* item)
添加元素 currentItem() 返回QListWidgetItem*,返回当前选中元素指针 setCurrentItem(QListWidgetItem* item) 设置选中元素,参数指针。 setCurrentRow(int row) 设置选中元素,参数行号(从0开始) insertItem(const QString& label,int row) insertItem(QListWidgetItem *item , int row) 指定行号,插入一个新元素。 item(int row) 返回指定行号的元素,返回QListWidgetItem* takeItem(int row) 删除指定行的元素,返回被删除元素的QListWidgetItem*
- 信号:
currentItemChanged(QListWidgetItem* current,QListWidgetItem*old) 选中元素改变时触发。
参数是新当前选中,和上一个选中的元素指针。
currentRowChanged(int) 选中元素改变时触发。
参数是当前选中元素的行号。
itemClicked(QListWidgetItem* item) 点击某个元素时触发。 itemDoubleClicked(QListWidgetItem* item) 双击某个元素时触发。 itemEntered(QListWidgetItem* item) 鼠标悬停在选项之上时触发。
例:通过按钮添加/删除行
#include "widget.h"
#include "ui_widget.h"
#include<QString>
#include<QDebug>
Widget::Widget(QWidget *parent)
: QWidget(parent)
, ui(new Ui::Widget)
{
ui->setupUi(this);
//添加元素
ui->listWidget->addItem("C++");
ui->listWidget->addItem("Java");
ui->listWidget->addItem(new QListWidgetItem("Python"));
}
Widget::~Widget()
{
delete ui;
}
void Widget::on_pushButton_clicked()//新增选项
{
//获取输入框内容
QString str=ui->lineEdit->text();
if(str==""){return ;}
//新增列表选项
ui->listWidget->addItem(str);
}
void Widget::on_pushButton_2_clicked()//删除元素
{
//获取当前选中元素
int row=ui->listWidget->currentRow();
ui->listWidget->takeItem(row);
}
void Widget::on_listWidget_currentItemChanged(QListWidgetItem *current, QListWidgetItem *previous)
{
if(current!=nullptr)
{
qDebug()<<"当前选中元素:"<<current->text();
}
if(previous!=nullptr)
{
qDebug()<<"上一个选中元素:"<<previous->text();
}
}
2.QTabelWidget 表格控件
- QTableWidget核心方法:
item(int row, int column) 获取指定行列的元素,QTableWidgetItem* setItem(int row, int column, QTableWidget*) 指定行列,设置单元格的元素 currentItem() 获取当前选中元素 currentRow() 获取当前选中元素的行号 currentColumn() 获取当前选中元素的列号 row(QTableWidgetItem*) 获取指定元素的行号 column(QTableWidgetItem*) 获取指定元素的列号 rowCount() 获取总行数 columnCount() 获取总列数 insertRow(int row) 插入新的一行,在指定行号 insertColumn(int column) 插入新的一列,在指定列号 removeRow(int row) 删除指定行 removeColumn(int column) 删除指定列 setHorizontalHeaderItem(int column, QTableWidget*) 设置水平方向的表头,每一列的表头 setVerticalHeaderItem(int row, QTableWidget*) 设置垂直方向的表头,每一行的表头 QTableWidgetItem核心信号
cellClicked(int row, int column)
点击单元格时触发 cellDoubleClicked(int row,int column) 双击单元格时触发 cellEntered(int row, int column) 鼠标进入单元格时触发 currentCellChanged(int row, int column, int previousRow, int previousColumn) 选中不同单元格时触发
- QTableWidgetItem核心方法
row() 获取元素行号 column() 获取元素列号 setText(const QSting&) 设置文本 setTextAlignment(int) 设置文本对齐方式 setIcon(const QIcon&) 设置图标 setSelected(bool) 设置被选中 setSizeHints(const QSize&) 设置尺寸 setFont(const QFont&) 设置字体
例:通过按钮,添加行/列,删除行/列
#include "widget.h"
#include "ui_widget.h"
#include<QDebug>
Widget::Widget(QWidget *parent)
: QWidget(parent)
, ui(new Ui::Widget)
{
ui->setupUi(this);
//初始化表格
ui->tableWidget->insertRow(0);
ui->tableWidget->insertRow(1);
ui->tableWidget->insertRow(2);
ui->tableWidget->insertColumn(0);
ui->tableWidget->insertColumn(1);
ui->tableWidget->insertColumn(2);
ui->tableWidget->setHorizontalHeaderItem(0,new QTableWidgetItem("学号"));
ui->tableWidget->setHorizontalHeaderItem(1,new QTableWidgetItem("姓名"));
ui->tableWidget->setHorizontalHeaderItem(2,new QTableWidgetItem("班级"));
for(int i=0;i<3;i++)
{
for(int j=0;j<3;j++)
{
ui->tableWidget->setItem(i,j,new QTableWidgetItem("0"));
}
}
}
Widget::~Widget()
{
delete ui;
}
void Widget::on_pushButton_insertRow_clicked()
{
//默认在末尾插入一行
//获取当前的行数
int row_count=ui->tableWidget->rowCount();
ui->tableWidget->insertRow(row_count);
}
void Widget::on_pushButton_insetColumn_clicked()
{
int column_count=ui->tableWidget->columnCount();
ui->tableWidget->insertColumn(column_count);
//设置表头
QString s=ui->lineEdit->text();
if(s.isEmpty()==true)
{
return ;
}
ui->tableWidget->setHorizontalHeaderItem(column_count,new QTableWidgetItem(s));
}
void Widget::on_pushButton_deleteRow_clicked(bool checked)
{
//删除选中的行
int current=ui->tableWidget->currentRow();
ui->tableWidget->removeRow(current);
}
void Widget::on_pushButton_4_clicked()
{
//删除选中的行
int current=ui->tableWidget->currentColumn();
ui->tableWidget->removeColumn(current);
}
行列数过多后,表格会自动添加滚动条。
3.QTreeWidget 树形控件
- 功能:树形控件,每一个元素是QTreeWidgetItem,每个QTreeWidgetItem 可以包含多个⽂本和图标,每个⽂本/图标为⼀个列。
但这个树形结构,不一定只有一个根节点,把顶层节点称为topLevelItem。
- 方法
clear() 清空所有子节点 addTopLevelItem(QTreeWidgetItem* item) 新增顶层节点 topLevelItem(int index) 获取指定下标的顶层节点 topLevelItemCount() 获取顶层节点的个数 indexOfTopLevelItem(QTreeWidgetItem* item) 获取节点在顶层节点中的下标 takeTopLevelItem(int index) 根据下标,删除指定的顶层节点。返回被删除元素指针。
只能这样删除顶层元素,必须先获取下标。
currentItem() 获取当前选中节点的指针 setCurrentItem(QTreeWidgetItem* item) 设置选中节点 setExpanded(bool) 展开/关闭子节点 setHeaderLabel(const QString& text)
setHeaderItem()
设置TreeWidget的header名称
- QTreeWidget核心信号
currentItemChanged(QTreeWidgetItem* current,QTreeWidgetItem* old) 切换选中元素时触发 itemClicked(QTreeWidgetItem* item, int col) 点击元素时触发 itemDoubleClicked(QTreeWidgetItem* item, int col) 双击元素时触发 itemEntered(QTreeWidgetItem* item, int col) 鼠标进入时触发 itemExpanded(QTreeWidgetItem* item) 元素被展开时触发 itemCollapsend(QTreeWidgetItem* item) 元素被折叠时触发 QTreeWidgetItem核心属性
text 文本 textAlign 文本对齐方式 icon 持有的图标 font 字体 hidden
是否隐藏 disabled 是否禁用 expand 是否展开 sizeHint 尺寸大小 selected 是否选中
- QTreeWidgetItem核心方法
addChild(QTreeWidgetItem* child) 新增子节点 childCount() 子节点个数 child(int index) 获取指定下标的子节点,返回指针 takeChild(int index) 删除对应下标的子节点 removeChild(QTreeWidgetItem* child) 删除对应的子节点 parent() 获取该元素的父节点
例:添加节点的方式
图形化方式添加节点
代码方式
#include "widget.h"
#include "ui_widget.h"
Widget::Widget(QWidget *parent)
: QWidget(parent)
, ui(new Ui::Widget)
{
ui->setupUi(this);
//设置整棵树的名称,根节点名称
ui->treeWidget->setHeaderLabel("动物");
//新增顶层节点
QTreeWidgetItem* item1 =new QTreeWidgetItem();
item1->setText(0,"猫");//每个节点都可以有多列,指定不同下标就可以
ui->treeWidget->addTopLevelItem(item1);
QTreeWidgetItem* item2 =new QTreeWidgetItem();
item2->setText(0,"狗");//每个节点都可以有多列,指定不同下标就可以
ui->treeWidget->addTopLevelItem(item2);
QTreeWidgetItem* item3 =new QTreeWidgetItem();
item3->setText(0,"鸟");//每个节点都可以有多列,指定不同下标就可以
ui->treeWidget->addTopLevelItem(item3);
QTreeWidgetItem* item4 =new QTreeWidgetItem();
item4->setText(0,"暹罗");
QTreeWidgetItem* item5 =new QTreeWidgetItem();
item5->setText(0,"加菲");
QTreeWidgetItem* item6 =new QTreeWidgetItem();
item6->setText(0,"虎斑");
item1->addChild(item4);
item1->addChild(item5);
item1->addChild(item6);
}
Widget::~Widget()
{
delete ui;
}
例:通过按钮,添加顶层节点/普通节点/删除节点
#include "widget.h"
#include "ui_widget.h"
Widget::Widget(QWidget *parent)
: QWidget(parent)
, ui(new Ui::Widget)
{
ui->setupUi(this);
//设置整棵树的名称,根节点名称
ui->treeWidget->setHeaderLabel("动物");
//新增顶层节点
QTreeWidgetItem* item1 =new QTreeWidgetItem();
item1->setText(0,"猫");//每个节点都可以有多列,指定不同下标就可以
ui->treeWidget->addTopLevelItem(item1);
QTreeWidgetItem* item2 =new QTreeWidgetItem();
item2->setText(0,"狗");//每个节点都可以有多列,指定不同下标就可以
ui->treeWidget->addTopLevelItem(item2);
QTreeWidgetItem* item3 =new QTreeWidgetItem();
item3->setText(0,"鸟");//每个节点都可以有多列,指定不同下标就可以
ui->treeWidget->addTopLevelItem(item3);
QTreeWidgetItem* item4 =new QTreeWidgetItem();
item4->setText(0,"暹罗");
QTreeWidgetItem* item5 =new QTreeWidgetItem();
item5->setText(0,"加菲");
QTreeWidgetItem* item6 =new QTreeWidgetItem();
item6->setText(0,"虎斑");
item1->addChild(item4);
item1->addChild(item5);
item1->addChild(item6);
}
Widget::~Widget()
{
delete ui;
}
void Widget::on_pushButton_insertTop_clicked()
{
QString text=ui->lineEdit->text();
if(text.isEmpty()==true)
{
return ;
}
QTreeWidgetItem* item=new QTreeWidgetItem();
item->setText(0,text);
ui->treeWidget->addTopLevelItem(item);
}
void Widget::on_pushButton_insert_clicked()
{
//获取选中的元素
QTreeWidgetItem* it=ui->treeWidget->currentItem();
if(it==nullptr)
{
return ;
}
QString text=ui->lineEdit->text();
if(text.isEmpty()==true)
{
return ;
}
QTreeWidgetItem* item=new QTreeWidgetItem();
item->setText(0,text);
it->addChild(item);
}
void Widget::on_pushButton_delete_clicked()
{
QTreeWidgetItem* it=ui->treeWidget->currentItem();
if(it==nullptr)
{
return ;
}
//获取当前元素的父节点
QTreeWidgetItem* parent=it->parent();
//父节点为空。说明当前节点为顶层节点
//获取当前选中节点的下标
if(parent==nullptr)
{
int index=ui->treeWidget->indexOfTopLevelItem(it);
ui->treeWidget->takeTopLevelItem(index);//删除顶层节点
}
else
{
parent->removeChild(it);
}
}
上述对界面的操作都是内存级别的操作,程序重启后就会恢复到初始状态。
想要保留操作变化,需要额外的数据持久化操作。写入文件,运行时重写读取文件加载数据。