大家好,我是老吴,一枚勤劳的嵌入式底层劳动人民。
我又双叒叕来分享 Qt 的学习心得了。
学习 Qt 的最佳途径是阅读官方的手册和示例,
今天要分享的是 Qt 官方提供的示例:notepad。
notepad 是一个简易文本编辑器:
点击查看大图
它一个支持新建、打开、保存、复制、粘贴、剪切、撤销、重做等功能的迷你型文本编辑器,类似 Gedit。
源码文件:
`notepad/`
`├── images`
`│ ├── bold.png`
`│ ├── copy.png`
`│ ├── create.png`
`│ ├── cut.png`
`│ ├── edit_redo.png`
`│ ├── edit_undo.png`
`│ ├── exit.png`
`│ ├── font.png`
`│ ├── info.png`
`│ ├── italic.png`
`│ ├── new.png`
`│ ├── open.png`
`│ ├── paste.png`
`│ ├── pencil.png`
`│ ├── print.png`
`│ ├── save_as.png`
`│ ├── save.png`
`│ └── underline.png`
`├── main.cpp`
`├── notepad.cpp`
`├── notepad.h`
`├── notepad.pro`
`├── notepad.qrc`
`└── notepad.ui`
复制代码
下面快速地说明一下如何实现这个小工具, let’s go.
正文目录:
`1. 新建 Qt Widgets Application`
`2. 利用 Qt Designer 设计界面`
`3. 实现 New / Open / Save 文件的功能`
`4. 相关参考`
`5. 好书推荐:《就因为没时间,才什么都能办到》`
复制代码
1. 新建 Qt Widgets Application
在 Qt Creator 里 点击,
File > New File or Project > Applications > Qt Widgets Application > Choose:
点击查看大图
以 QMainWindow 作为基类,子类名为 Notepad:
新建完成后会得到下列文件:
`notepad/`
`├── main.cpp`
`├── notepad.cpp`
`├── notepad.h`
`├── notepad.pro`
`└── notepad.ui`
复制代码
notepad.cpp 和 notepad.h 是 Notepad Widget 对应的类的源代码。
notepad.ui 则是 Notepad Widget 对应的 UI 界面文件。
运行效果:
此时只有跟 QMainWindow 一样的界面,还没有任何编辑器相关的功能。
2. 利用 Qt Designer 设计界面
Notepad 的界面分为 4 部分:
点击查看大图
-
菜单栏,用 QMenuBar 实现;
-
工具栏,用 QToolBar 实现;
-
文本编辑框,用 QTextEdit 实现;
-
状态栏,用 QstatusBar 实现;
本文不会讲解 Notepad 的所有功能,而是以下面 3 个功能为例:
-
创建文件
-
打开文件
-
保存文件
只要这 3 个功能的实现逻辑理清楚,实现整个 Notepad 肯定也没有问题。
在 Qt Designer 里:
-
修改菜单栏,添加 File 菜单项
-
修改工具栏,添加 New、Open、Save Action
-
添加编辑框
运行效果:
此时的菜单栏和工具栏里按键并没有任何功能。
3. 实现 New / Open / Save 文件的功能
在 Qt 里用 Action 这个概念来简化菜单栏和工具栏的的编程,
每一个菜单项都会有自己的 Action,开发者可以在 Qt Designer 里的 Action Editor 里定制 Action。
当用户点击某个菜单项时,就会发出 QAction::triggered 信号,我们需要为其设置对应的槽函数以实现对应的业务功能。
绑定信号和槽:
`// 文件:notepad.cpp`
`Notepad::Notepad(QWidget *parent)`
`: QMainWindow(parent)`
`, ui(new Ui::Notepad)`
`{`
`...`
`connect(ui->actionNew, &QAction::triggered, this, &Notepad::newDocument);`
`connect(ui->actionOpen, &QAction::triggered, this, &Notepad::open);`
`connect(ui->actionSave, &QAction::triggered, this, &Notepad::save);`
`}`
复制代码
实现新建文件的功能
`// 文件:notepad.h`
`class Notepad : public QMainWindow`
`{`
`...`
`private slots:`
`void newDocument();`
`void open();`
`void save();`
`private:`
`Ui::Notepad *ui;`
`QString currentFile;`
`};`
复制代码
currentFile 用于保存当前文件的路径名。
`void Notepad::newDocument()`
`{`
`currentFile.clear();`
`ui->textEdit->setText(QString());`
`setWindowTitle("new File *");`
`}`
复制代码
创建新文件的过程很简单,就是清空文本框。
运行效果:
实现保存文件的功能
`// 文件:notepad.cpp`
`void Notepad::save()`
`{`
`QString fileName;`
`// 如果前面没有保存过,则询问用户保存在哪里`
`if (currentFile.isEmpty()) {`
`fileName = QFileDialog::getSaveFileName(this, "Save");`
`currentFile = fileName;`
`} else {`
`fileName = currentFile;`
`}`
`// 将文本框中的文本写到文件中`
`QFile file(fileName);`
`[...]`
`setWindowTitle(fileName);`
`QTextStream out(&file);`
`QString text = ui->textEdit->toPlainText();`
`out << text;`
`file.close();`
`}`
复制代码
Qt 提供了 QFile 类用于进行文件操作。
QFile 类本身就有读写文件的接口,但是一般用 QTextStream or QDataStream 来读写文件会更加方便。
另外:
-
处理临时文件可以使用 QTemporaryFile,
-
获取文件信息可以使用 QFileInfo,
-
处理目录可以使用 QDir,
-
监视文件和目录变化可以使用 QFileSystemWatcher。
运行效果:
实现打开文件的功能
`// 文件:notepad.cpp`
`void Notepad::open()`
`{`
`// 用户选择要打开的文件`
`QString fileName = QFileDialog::getOpenFileName(this, "Open the file");`
`QFile file(fileName);`
`[...]`
`currentFile = fileName;`
`setWindowTitle(fileName);`
`// 用文本流将文件内容读到文本框中`
`QTextStream in(&file);`
`QString text = in.readAll();`
`ui->textEdit->setText(text);`
`file.close();`
`}`
复制代码
用上面的代码里可以看出,Qt 里的文本流操作非常简单。
运行效果:
到此,这个 Notepad 示例的 核心功能就实现完毕啦。感兴趣的小伙伴们请自行阅读 Qt example 里的完整代码吧。
**文件 IO 是编程世界里非常重要的一环,**在 Qt 的许多示例里都要用到这一块知识点,这里我们先初步地了解一下 QTextStream ,后续需要在更多的示例中练习 Qt 的 IO 操作。
相关参考
《Qt 官方文档》:
-
Creating Main Windows in Qt Designer
-
File and Datastream Functions
《C++ GUI Qt4 编程 (第二版)》
《Qt5 编程入门 (第二版)》
《Qt Creator 快速入门》
思考技术,也思考人生
要学习技术,更要学习如何生活。
好书推荐:
《就因為「沒時間」,才什麼都能辦到》
作者:吉田穗波
2004年 取得名古屋大学研究所博士学位,妇产科医师。在工作和家庭多头奔忙的情况下,反而让她因有感于「若要改变现状,只能积极提升自己的程度」,而兴起再进修的念头。从申请入学哈佛,准备考试到录取,只花半年时间!2008 年带着三岁,一岁和一个月大的三个女儿,与丈夫一起前往波士顿,两年取得哈佛学位。
豆瓣评分:8.0,790人评价
点击查看大图
能收获什么?
-
不一样的时间观念;
-
实用的时间管理方法;
-
积极的心理建设;
-
接受无序的状态;
-
接受事情只做了一部分的情况;
-
抓大放小,请别人来帮助自己处理非核心任务;
你和我各有一个苹果,如果我们交换苹果的话,我们还是只有一个苹果。但当你和我各有一个想法,我们交换想法的话,我们就都有两个想法了。
觉得文章对你有价值,不妨 在看 + 分享。
推荐阅读: