Qt 学习(一) addressbook

Qt Demo: addressbook
(1)创建项目:选择不创建界面,即UI,此时会自动生成的文件如图所示:
在这里插入图片描述
QApplication:
MainWindow 继承自 QMainWindow,根据需要设计的界面样式。

(2)确定MainWindow 的成员变量
在这里插入图片描述
首先,从此张界面图推断出 MainWindow 的组成:

  1. 一个QTabWidget;
  2. 两个QMenu: Files Tools;点击之后弹出的选项为:QAction;QAction 绑定槽函数
    MainWindow 包含的成员对象:
class MainWindow : public QMainWindow
{Q_OBJECT
public:MainWindow();
private slots:void updateActions(const QItemSelection &selection);void openFile();void saveFile();
private:void createMenus();AddressWidget *addressWidget;QMenu *fileMenu;QMenu *toolMenu;QAction *openAct;QAction *saveAct;QAction *exitAct;QAction *addAct;QAction *editAct;QAction *removeAct;
};

(3)在MainWindow中设置 centralwidget 以及 title, 并添加menu 以及 action,再绑定槽函数

setCentralWidget
setWindowTitle
fileMenu = menuBar()->addMenu(tr("&File"));
openAct = new QAction(tr("&Open"),this);
fileMenu->addAction(openAct);
connect(openAct,&QAction::triggered,this,&MainWindow::open_file);

为两个menu 添加了三个可点击的控件,对应的槽函数需要根据代码架构来设计。

// Open file
QString file_name = QFileDialog().getOpenFileName(this);
// Save file
QString file_name = QFileDialog().getSaveFileName(this);

(4)QTabWidget
添加tab: QtableView、 QWidget

QTableView* tableview = new QtableView();
// QTableView 设置一系列属性
// int addTab(QWidget* widget, const QString&);
addTab(tableview, str); 

model-view
QAbstractListModel QAbstractTableModel
索引:QModelIndex
role: ItemDataRole
实现自己的model类:

class tableModel : public QAbstractTableModel
{
public:tableModel(QObject* parent = nullptr);// virtual function
//  must override this 3 funciton when use QAbstractTableModelint rowCount(const QModelIndex &parent) const override;int columnCount(const QModelIndex &parent) const override;QVariant data(const QModelIndex &index, int role) const override;//  must override this 2 funciton when edit dataQt::ItemFlags flags(const QModelIndex &index) const override;bool setData(const QModelIndex &index, const QVariant &value, int role = Qt::EditRole) override;//  must override this 2 funciton when change rowsbool insertRows(int position, int rows, const QModelIndex &index = QModelIndex()) override;bool removeRows(int position, int rows, const QModelIndex &index = QModelIndex()) override;//  must override this 1 funciton when use table headerQVariant headerData(int section, Qt::Orientation orientation, int role) const override;const QVector<Contact> &getContacts() const;private:QVector<Contact> _contacts;
};

(5) 槽函数:添加,修改,删除
每一个{name, address} 都是通过一个 QDialog 添加;
此界面包含的控件:QLineEdit;QTextEdit;QLabel;QPushButton
layout:QGridLayout;QHBoxLayout;QVBoxLayout
在这里插入图片描述

addDialog::addDialog(QWidget* parent)
{_name = new QLineEdit();_address = new QTextEdit();auto nameLabel = new QLabel("Name");auto addressLabel = new QLabel("Address");auto layout = new QGridLayout();layout->setColumnStretch(1,2);layout->addWidget(nameLabel,0,0);layout->addWidget(_name,0,1);layout->addWidget(addressLabel,1,0,Qt::AlignLeft|Qt::AlignTop);layout->addWidget(_address,1,1,Qt::AlignLeft);auto okBtn = new QPushButton("OK");auto cancelBtn = new QPushButton("Cancel");auto btnLayout = new QHBoxLayout;btnLayout->addWidget(okBtn);btnLayout->addWidget(cancelBtn);layout->addLayout(btnLayout,2,1,Qt::AlignRight);auto mainLayout = new QVBoxLayout;mainLayout->addLayout(layout);setLayout(mainLayout);setWindowTitle("Add a Contact");connect(okBtn,&QAbstractButton::clicked,this,&QDialog::accept);connect(cancelBtn, &QAbstractButton::clicked, this, &QDialog::reject);
}

添加:

void addressWidget::show_add_entry_dialog()
{qDebug()<<"show_add_entry_dialog"<<endl;addDialog add_dialog;if(add_dialog.exec()){qDebug()<<"add_dialog.exec()"<<endl;add_entry(add_dialog.name(),add_dialog.address());}
}
void addressWidget::add_entry(const QString& name, const QString& address)
{qDebug()<<"add_entry"<<"name:"<<name<<"address:"<<address<<endl;if(!_table_model->getContacts().contains({name,address})){_table_model->insertRows(0,1,QModelIndex());QModelIndex index = _table_model->index(0,0,QModelIndex());_table_model->setData(index,name,Qt::EditRole);index = _table_model->index(0,1,QModelIndex());_table_model->setData(index,address);removeTab(indexOf(_new_address_tab));}else{qDebug()<<"duplicate name"<<endl;}
}

修改

void AddressWidget::editEntry()
{QTableView *temp = static_cast<QTableView*>(currentWidget());QSortFilterProxyModel *proxy = static_cast<QSortFilterProxyModel*>(temp->model());QItemSelectionModel *selectionModel = temp->selectionModel();const QModelIndexList indexes = selectionModel->selectedRows();QString name;QString address;int row = -1;for (const QModelIndex &index : indexes) {row = proxy->mapToSource(index).row();QModelIndex nameIndex = table->index(row, 0, QModelIndex());QVariant varName = table->data(nameIndex, Qt::DisplayRole);name = varName.toString();QModelIndex addressIndex = table->index(row, 1, QModelIndex());QVariant varAddr = table->data(addressIndex, Qt::DisplayRole);address = varAddr.toString();}AddDialog aDialog;aDialog.setWindowTitle(tr("Edit a Contact"));aDialog.editAddress(name, address);if (aDialog.exec()) {const QString newAddress = aDialog.address();if (newAddress != address) {const QModelIndex index = table->index(row, 1, QModelIndex());table->setData(index, newAddress, Qt::EditRole);}}
}

删除

void AddressWidget::removeEntry()
{QTableView *temp = static_cast<QTableView*>(currentWidget());QSortFilterProxyModel *proxy = static_cast<QSortFilterProxyModel*>(temp->model());QItemSelectionModel *selectionModel = temp->selectionModel();const QModelIndexList indexes = selectionModel->selectedRows();for (QModelIndex index : indexes) {int row = proxy->mapToSource(index).row();table->removeRows(row, 1, QModelIndex());}if (table->rowCount(QModelIndex()) == 0)insertTab(0, newAddressTab, tr("Address Book"));
}

(6)存储数据

void AddressWidget::writeToFile(const QString &fileName)
{QFile file(fileName);if (!file.open(QIODevice::WriteOnly)) {QMessageBox::information(this, tr("Unable to open file"), file.errorString());return;}QDataStream out(&file);out << table->getContacts();
}

读取数据:

void AddressWidget::readFromFile(const QString &fileName)
{QFile file(fileName);if (!file.open(QIODevice::ReadOnly)) {QMessageBox::information(this, tr("Unable to open file"),file.errorString());return;}QVector<Contact> contacts;QDataStream in(&file);in >> contacts;if (contacts.isEmpty()) {QMessageBox::information(this, tr("No contacts in file"),tr("The file you are attempting to open contains no contacts."));} else {for (const auto &contact: qAsConst(contacts))addEntry(contact.name, contact.address);}
}

Contacts 需要重载流运算符

inline QDataStream &operator<<(QDataStream &stream, const Contact &contact)
{return stream << contact.name << contact.address;
}inline QDataStream &operator>>(QDataStream &stream, Contact &contact)
{return stream >> contact.name >> contact.address;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/361999.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

告别模糊时代,扫描全能王带来清晰世界

模糊碑文引发的思考 上个月中旬去洛阳拜访了著名的龙门石窟&#xff0c;本就对碑文和文字图画感兴趣的我们&#xff0c;准备好好欣赏一下龙门石窟的历史文化古迹。到了地方之后&#xff0c;我发现石窟的高度和宽度远远超出了想象&#xff0c;正因如此&#xff0c;拍出来的文字…

计算机网络之数据通信原理

1.通信系统的基本组成 信源&#xff1a;信息的发出者&#xff1b; 信宿&#xff1a;信息的接收者&#xff1b; 载体&#xff1a;信息的传送通道&#xff1b; 变换器&#xff1a;将信息变换成载体上可传输的信号&#xff1b; 反变换器&#xff1a;将载体上传输的信号变换成信…

【启明智显技术分享】MOEDL3芯片通用接口如CAN、I2S、I2C、SPI、UART、USB、emac的介绍和比较

启明智显MODEL3芯片提供的通用接口包括CAN、I2S、I2C、SPI、UART、USB和emac&#xff0c;每种接口都有其独特的功能和应用场景。 以下是这些接口的介绍和比较&#xff1a; CAN接口 功能&#xff1a; 支持CAN2.0A和CAN2.0B协议。支持11位标识符&#xff08;标准格式&#xf…

已解决javax.security.auth.DestroyFailedException:在尝试销毁某个对象时失败的正确解决方法,亲测有效!!!

已解决javax.security.auth.DestroyFailedException&#xff1a;在尝试销毁某个对象时失败的正确解决方法&#xff0c;亲测有效&#xff01;&#xff01;&#xff01; 目录 问题分析 报错原因 解决思路 解决方法 检查对象状态 确认权限设置 检查资源锁定情况 修正实现…

栈,ASCII编码

栈 LinkedList stack new LinkedList<>(); int i 0; while (i < s.length()) { char c s.charAt(i); if (c <) {if (stack.isEmpty()) {i;continue;}stack.removeLast(); //从栈的末尾移除一个元素} else {stack.addLast(c); //压入栈的末尾栈是只允许在一端…

批量邮件推送的最佳策略?如何个性化营销?

批量邮件推送有哪些高效工具&#xff1f;怎么评估邮件推送效果&#xff1f; 通过有效的批量邮件推送&#xff0c;可以提升品牌知名度、增加客户参与度&#xff0c;并最终促进销售。AoKSend将探讨批量邮件推送的最佳策略&#xff0c;帮助您在复杂的邮件营销环境中脱颖而出。 批…

5个顶级开源Agent框架,你必须知道!

进入2024年&#xff0c;人工智能的发展已经达到了前所未有的高度&#xff0c;尤其是在Agent框架这一领域&#xff0c;出现了几个引人注目的技术成果。这些框架在智能规划、用户体验增强、记忆处理、以及大型模型调用等方面有着卓越表现&#xff0c;对AI界的未来发展提供了值得期…

【分布式文件系统HDFS】文件操作基本命令的使用

目录 一、按照下述要求写出相应的文件操作命令&#xff0c;执行并观察结果 1. 新建目录 1.1 在本地文件系统按要求创建如下的文件夹 1.2 在HDFS文件系统按要求创建如下的文件夹 2. 编辑文件test1.txt&#xff0c;放入本地文件夹 /opt/user/myfile 3. 使用moveFromLocal命令…

IT入门知识第八部分《云计算》(8/10)

目录 云计算&#xff1a;现代技术的新篇章 1. 云计算基础 1.1 云计算的起源和发展 云计算的早期概念 云计算的发展历程 1.2 云计算的核心特点 按需自助服务 广泛的网络访问 资源池化 快速弹性 按使用量付费 1.3 云计算的优势和挑战 成本效益 灵活性和可扩展性 维…

【AIGC】用 AI 绘画 诠释印象派!关键词、安装包分享!

前言 印象派艺术运动是19世纪60年代法国的一场艺术革命&#xff0c;它不仅革新了绘画技法&#xff0c;更重新诠释了光与色彩、自然与美。印象派艺术家&#xff0c;如莫奈、雷诺阿和德加&#xff0c;通过捕捉自然光线的瞬息变化&#xff0c;用色彩和笔触表达对现实世界的独特感…

每个 Node.js 开发人员都应该知道的13个库(上)

1. Sequelize Sequelize是一个基于promise的Node.js对象关系映射器&#xff08;ORM&#xff09;&#xff0c;它使开发人员更容易使用关系数据库。 支持PostgreSQL&#xff0c;MySQL&#xff0c;MariaDB&#xff0c;SQLite和更多数据库。 Sequelize使用JavaScript对象对数据库…

入门JavaWeb之 Response 验证码和重定向

Response 写验证码&#xff1a; package com.demo.response;import javax.imageio.ImageIO; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse…

人工神经网络是什么,其应用有哪些?

人工神经网络是什么&#xff0c;其应用有哪些&#xff1f; 当你阅读这篇文章时&#xff0c;你身体的哪个器官正在考虑它&#xff1f;当然是大脑&#xff01;但是你知道大脑是如何工作的吗&#xff1f;嗯&#xff0c;它有神经元或神经细胞&#xff0c;它们是大脑和神经系统的主要…

Python笔记 json数据格式的转换

一、json数据格式 1.什么是json json是一种轻量级的数据交互格式。可以按照json指定的格式去组织和封装数据 json本质上是一个带有特定格式的字符串 主要功能&#xff1a;json就是一种在各个编程语言中流通的数据格式&#xff0c;负责不同编程语言中的数据传递和交互。类似…

基于SpringBoot音乐网站与分享平台详细设计和实现(源码+LW+调试文档+讲解等)

&#x1f497;博主介绍&#xff1a;✌全网粉丝10W,CSDN作者、博客专家、全栈领域优质创作者&#xff0c;博客之星、平台优质作者、专注于Java、小程序技术领域和毕业项目实战✌&#x1f497; Java精品实战案例《600套》 2023-2025年最值得选择的Java毕业设计选题大全&#xff1…

Xilinx FPGA:vivado实现串口的接收端

补充一些串口里用到的数值的相关知识点 接收端串口时序图&#xff1a; 程序设计&#xff1a; timescale 1ns / 1ps /串口接收端 串行转并行 module uart_rx(input sys_clk ,input rst_n ,input rx_data , //输入…

JDBC以及事务

1、JDBC是什么&#xff1f; JDBC是Java DataBase Connectivity&#xff08;Java语言链接数据库&#xff09; 2、JDBC的本质 JDBC是一套接口&#xff0c;有调用者&#xff08;java工程师&#xff09;和实现者&#xff08;SUN公司&#xff09;&#xff08;实现类被称为驱动&…

electron线上跨域问题

一、配置background.js win new BrowserWindow({webPreferences: {nodeIntegration: true, // 使渲染进程拥有node环境//关闭web权限检查&#xff0c;允许跨域webSecurity: false,// Use pluginOptions.nodeIntegration, leave this alone// See nklayman.github.io/vue-cli-p…

终于找到能在mac上正常保存密码的navicat了- navicat v17.0.9

找了一晚上&#xff0c;终于找到能在mac上正常保存密码的navicat了。 免费分享&#xff0c;不用关注公众号&#xff0c;不用看广告。如果帮助到你&#xff0c;可以的话帮忙给 https://github.com/gone-io/gone 点个星星。 链接: https://pan.baidu.com/s/1ZvGqSMNcv8uMCIpwf0…

Charls数据库+预测模型发二区top | CHARLS等七大老年公共数据库周报(6.19)

七大老年公共数据库 七大老年公共数据库共涵盖33个国家的数据&#xff0c;包括&#xff1a;美国健康与退休研究 (Health and Retirement Study, HRS)&#xff1b;英国老龄化纵向研究 &#xff08;English Longitudinal Study of Ageing, ELSA&#xff09;&#xff1b;欧洲健康、…