1.初识 Qt5
本书将为大家介绍使用 Qt 5.x 版本开发应用程序的不同方面。我们将专注于新的 Qt Quick 技术,同时提供了编写 Qt Quick 的 C++ 后端和扩展的一些必要信息。
本章提供了 Qt 5 的高级概述。我们将在本章展示开发人员可用的不同应用程序模型和一个对这些特性进行预览的 Qt 5 示例应用程序。此外,本章旨在全面概述 Qt 5 内容,以及如何与 Qt 5 的制作人员取得联系。
1.1.前言
历史
Qt 4 自 2005 年以来一直在不断地发展和演进,为数千个应用甚至完整的桌面和移动系统提供了坚实的基础。计算机用户近年来的使用模式发生了变化。从固定电脑到便携式笔记本电脑和现在的移动终端。经典桌面系统越来越多地被基于移动终端的触屏系统所替代。与此同时,桌面的用户体验也在悄然发生着改变。在过去 Windows UI 占主导地位的地方,现在却已被让我们花费更多的时间的使用另一种 UI 语言的屏幕所占据。
Qt 4 是旨在满足桌面世界的,在所有主要平台上提供一系列方便移植的 UI 小部件。Qt 用户现在正在面临更大的挑战是为客户提供由客户需求驱动的基于触摸屏的用户界面,并在所有主要桌面和移动系统上实现现代用户界面。Qt 4.7 开始引入的 Qt Quick 技术,允许用户从简单元素创建一组用户界面组件,以实现由客户需求驱动的完整新 UI。
1.1.1.聚焦 Qt 5
Qt5 基于之前非常成功的 Qt 4 发行版。到 Qt 4.8 为止,Qt 4 发行版已经将近 7 个年头。现在到了让一个惊艳的工具包更加惊艳的时候了。Qt 5 专注于以下内容:
- 杰出图形绘制技术(Outstanding Graphics):Qt Quick 2 基于使用场景图实现的 OpenGL(ES)。重新组合的图形堆栈允许新的图像效果与在此领域中从未见过的易用性结合在一起。
- 更好地提高生产力(Developer Productivity):QML 和 JavaScript 是创建 UI 的主要手段。后端将由 C++ 驱动。JavaScript 和 C++ 之间的分割允许前端开发人员快速迭代,专注于创建漂亮的用户界面,而后端 C++ 开发人员,专注于稳定性,性能和延长运行时间。
- 跨平台的可移植性(Cross-platform portability):通过统一的 Qt 平台抽象技术,现在可以更容易和更快地将 Qt 端口扩展到更广泛的平台。Qt 5 围绕 Qt Essentials 和附加组件的概念进行构建,它允许 OS 开发人员将重点放在必需的模块以及更少的运行时间上。
- 开发和活跃的社区(Open Development):Qt 现在是一个真正的开放式治理的项目 Qt-Project。它的发展是开放和社区驱动的。
1.2. Qt 5 介绍
1.2.1. Qt Quick
Qt Quick 是 Qt 5 中使用的用户界面技术的总称。Qt Quick 本身是几种技术的集合:
- QML - 用户界面的标记语言
- JavaScript - 动态脚本语言
- Qt C++ - 高度可移植的增强型 C++ 库
与 HTML 类似,QML 也是标记语言。它由包含在大括号中的 Qt Quick 中称为元素的标签组成。QML 是全新设计的,用于为开发人员提供速度更快,阅读更容易的创建用户界面的语言。在 QML 中我们可以使用 JavaScript 代码来增强用户界面的体验。通过在 Qt Quick 使用 Qt C++ 可以轻松扩展我们的本地功能。简而言之,声明式 UI 称为前端,本地部分称为后端。这样做的好处是我们可以将应用程序的密集运算及本地操作部分与用户界面部分分离。
在典型的项目中前端开发使用 QML/JaveScript,后端代码开发使用 Qt C++ 来完成系统接口和繁重的计算工作。这更大限度地将面向设计的开发人员和功能开发人员之间的工作分开开展。通常后端是使用 Qt 自己的单元测试框架进行测试,并为前端开发人员导出要使用的接口。
1.2.2.一个用户界面示例
让我们用 Qt Quick 创建一个简单的用户界面,它用于展示 QML 语言的一些特性。在这个示例中我们将实现一个带旋转叶片动画的风车。
我们从一个名为 main.qml 的空文件开始。所有的 QML 文件都用 .qml 结尾。作为标记语言(如HTML),QML 文档需要有一个唯一的根元素,在我们的例子中是基于背景图像的宽度和高度的 Image 元素:
import QtQuick 2.3
Image {
id: root
source: "images/background.png"
}
由于 QML 没有限制任何元素类型作为根元素,因此我们用将通过设置 source 属性来显示图像作为背景图的 Image 元素作为根元素。
提示:
每个元素都有属性,例如一个图像具有宽度,高度,还有其他属性,如 source 属性。像上面的代码中展示的那样,Image 元素的宽高如果不进行显示地设置为有效的像素的话,它会自动被设置为源图像的大小。
最标准的 QML 元素位于我们在第一行中使用 import 语句引入的 QtQuick 模块中。
id 特殊属性是可选的,它将包含稍后在文档中,可以作为从其他位置引用此元素对象的标识符。重要提示:id 属性设置完成后无法更改,并且在运行时无法设置。使用 root 作为根元素的 id 只是作者的一种习惯,可以在比较大的 QML 文档中方便地引用最顶层元素。
我们的示例中的界面的前景元素风车手柄和风车轮被放置作为单独的图像。
手柄放置在背景的水平中心底部。并且风车车轮可以放置在背景的中心。
通常,我们的用户界面将由许多不同的元素类型组成,而不是像本示例中这样仅仅有图像元素。
Image {
id: root
...
Image {
id: pole
anchors.horizontalCenter: parent.horizontalCenter
anchors.bottom: parent.bottom
source: "images/pole.png"
}
Image {
id: wheel
anchors.centerIn: parent
source: "images/pinwheel.png"
}
...
}
要将车轮放置在中央位置,我们使用一个称为锚点(anchors)的属性。锚定允许我们指定父对象和子对象之间的几何关系。例如:将当前元素放在另一个元素的中心(anchors.centerIn: parent)。我们用左边(left),右边(right),顶部(top),底部(bottom),中央(centerIn),填充(fill),垂直居中(verticalCenter)和水平居中(horizontalCenter)来表示元素之间的关系。当然,他们是需要匹配使用的,如果把当前元素的左侧锚定到一个元素的顶端是没有任何意义的。
至此,我们已经把风车车轮设置在父元素的中心位置。
提示:
有时我们需要对锚定的中心点进行一些微小的调整。使用 anchors.horizontalCenterOffset 或者 anchors.verticalCenterOffset 可以帮助我们轻松地实现这个功能。类似的调整属性也可以用于其他所有的锚。通过查阅 Qt 的帮助文档我们可以知道完整的锚属性列表。
提示:
将一个图像作为根矩形元素的子元素放置展示了声明式语言的重要特性。我们以层和分组的顺序描述了用户界面,最顶部的一层元素(根矩形框)先绘制,在包含元素的局部坐标系中子层元素被绘制在顶层元素的上面。
为了让我们的展示更加有趣一点,我们应该让程序有一些交互功能。策略是,当用户点击程序的某个位置时,使风车的车轮转动起来。
为了实现监测用户点击功能,我们加入 MouseArea 元素,并使其大小与根元素一样大。
Image {
id: root
...
MouseArea {
anchors.fill: parent
onClicked: wheel.rotation += 90
}
...
}
当用户在其覆盖区域内点击时,鼠标区域发出信号。我们可以通过重新 onClicked 接口来监听这个信号。上面的代码中,我们引用风车的车轮图像的 id 来引用它并将其旋转+90度。
提示:
on + SignalName 的命名方式对于每个信号都是有效的。另外当属性的值发生改变时也会发出一个信号。此时的命名方式是:on + PropertyName + Chagned。 例如:当宽度(width)属性改变时,我们可以使用 onWidthChanged:print(width) 来监控并得到这个新的宽度值。
现在风车轮子会旋转了,但是效果仍然不那么流畅。旋转属性被直接更改了。效果几乎是一闪而过。我们更希望这个旋转效果是动态实现的。动画定义了在一段时间内如何分配属性更改。为了实现这一点,我们使用一个名为 property behavior 的动画类型。对于应用于该属性的每个更改,“行为”将为属性运行指定的动画。简而言之,每次该属性更改时,都会运行动画。这只是在 QML 中声明动画的几种方式之一。
Image {
id: root
Image {
id: wheel
Behavior on rotation {
NumberAnimation {
duration: 250
}
}
}
}
现在无论何时风车车轮的旋转属性改变后,将使用持续时间为 250 ms 的 NumberAnimation 动画组件进行动画处理。所以每次 90 度旋转都需要经过 250 毫秒。
提示:
我们实际上不会看到上图中的风车车轮的模糊效果。这幅图只是为了表明车轮正在旋转。但是一个模糊的轮子在资源文件夹中。也许我们会想尝试使用它。
现在风车的轮子看起来已经好多了,以上这些,就是关于Qt Quick 程序设计是如何工作的一个大概的简介了。
1.3. Qt 的组成模块
Qt 5 由大量模块组成。一个模块一般就是供开发人员使用的一个库。某些模块对于启用 Qt 的平台是必须的。它们形成一个名为 Qt Essentials Modules 的集合。许多模块是可选的,它们形成了 Qt 的附加模块。预计大多数开发人员不需要使用它们,但是了解他们是很有价值的,因为它们为我们可能遇到的常见问题提供了宝贵的解决方案。
1.3.1. Qt 模块
Qt Essentials 模块对于启用 Qt 平台是必须的。它们为使用 Qt Quick 2 开发现代 Qt 5 应用程序提供了基础。
Core-Essential(核心基础)模块。
下表是启动 QML 编程开发的最小 Qt 5 模块。
模块名称 | 简介 |
---|---|
Qt Core | 其他模块使用的核心非图形类 |
Qt GUI | 图形用户界面(GUI)组件的基类。包括 OpenGL。 |
Qt Multimedia | 音频,视频,收音机和摄像机功能类。 |
Qt Network | 使网络编程更容易,更容易移植的类。 |
Qt QML | QML 和 JavaScript 语言的支持类。 |
Qt Quick | 用于使用自定义用户界面构建高动态应用程序的声明框架。 |
Qt SQL | 使用 SQL 进行数据库集成的类。 |
Qt Test | Qt 应用程序和库的单元测试类。 |
Qt WebKit | 基于 WebKit2 的实现和新的 QML API 的类。 另请参见附加模块中的 Qt WebKit Widgets。 |
Qt WebKit Widgets | 来自 Qt 4 的 WebKit1 和 QWidget的基础类。 |
Qt Widgets | 使用 C++ Widgets 的扩展 Qt GUI 类。 |
1.3.2. Qt 附件模块
除了必要的模块,Qt 还为软件开发人员提供了额外的模块,这些模块不一定是发行版的一部分。 以下是可用的附加模块的简短列表。
模块名称 | 简介 |
---|---|
Qt 3D | 一组使 3D 图形编程变得简单易懂的 API |
Qt Bluetooth | 在多平台上使用无线蓝牙技术的 C++ 和 QML 应用程序接口 |
Qt Contacts | 提供访问联系人与联系人数据库的 C++ 和 QML 应用程序接口 |
Qt Location | 提供了定位,地图,导航和位置搜索的 C++ 与 QML 接口。使用 NMEA 在后端进行定位 |
Qt Organizer | 提供了组织事件(任务清单,事件等等)的 C++ 和 QML 应用程序接口 |
Qt Publish and Subscribe | Qt 发布与订阅 |
Qt Sensors | 通过 QML 和 C++ 接口访问传感器 |
Qt Service Framework | 允许应用程序读取,操纵和订阅来改变通知信息 |
Qt System Info | 发现系统相关的信息和功能 |
Qt Versit | 支持vCard和iCalendar格式 |
Qt Wayland | 只用于 Linux 系统。包含了 Qt 合成器应用程序接口(server)和 Wayland 平台插件(clients) |
Qt Feedback | 反馈用户的触摸和声音操作 |
Qt JSON DB | 用于 Qt 的非 SQL(no-SQL)对象存储 |
提示:
由于这些模块不一定是发行版的一部分,所以模块之间的状态不同,取决于贡献者的数量有多少以及测试的程度。
1.4. 支持的平台
Qt 支持各种平台。Qt 支持所有主流的桌面和嵌入式平台。通过 Qt 应用抽象(Qt Application Abstraction)技术,如果需要,现在可以更容易将 Qt 应用到我们自己的平台。
在一个平台上测试 Qt 5 是非常耗时的。qt 项目选择了一组平台,构建了参考平台。这些平台通过系统测试进行彻底测试,以确保最佳质量。但是注意:没有任何代码是没有错误的。
Qt 项目
来看下qt-project wiki:
“Qt 项目(Qt-Project)是一个对 Qt 有兴趣的基于共识的精英团体,任何有兴趣的人都可以加入社区,参与决策过程,并为Qt的发展作出贡献。”
Qt-Project 是一个为 Qt 未来开发开源部分的组织。它基于使用者的贡献。最大的贡献者是 DIGIA,它也可以提供 Qt 的商业授权。
对于公司而言 Qt 有一个开源的许可和一个商业许可。商业许可适用于那些不能或不会遵守开源许可证的公司。没有获得商业许可,这些公司将无法使用 Qt,并且允许 DIGIA 不向 Qt 项目贡献这部分需要商业许可的代码。
在全球有很多公司,他们在不同的平台上使用 Qt 开发产品,提供咨询。同样也有很多开源项目和开源开发者,它们使用 Qt 作为它们的开发库。与这个令人敬畏的工具库一起工作并且成为这个充满活力的社区的一部分令人愉悦的事。它能让你成为一个更好的人吗? 为什么不会呢?:-)
开启社区贡献之旅吧!
本文参考链接:Meet Qt 5