参考文档: https://doc.qt.io/qt-6/qmake-manual.html
构建常见项目类型
基于QT的三种常见的项目类型:
编译应用程序
使用app模板时,可以从以下选项选择一个添加到CONFIG变量中:
选项 | 描述 |
windows | app is windows gui |
console | console application |
testcase | app is an automated test. |
app模板下,下以的qmake系统变量将被使用:
编译测试用例
Qt测试用例?? 真没用过...,有机会研究下,先把相关的链接贴上来:https://doc.qt.io/qt-6/qtest-overview.html
编译库
在这个模板下, 支持VERSION变量,以下的选项可以被添加到CONFIG以决定哪种类型的类库
选项 | 描述 |
dll | 共享库 |
staticlib | 静态库 |
plugin | 插件? |
目标名依赖于平台,比如在linux下libxxxx(添加lib前缀)
编译插件
TEMPLATE = lib
CONFIG += plugin
编译qt设计器的插件
前面有两句话,没明白是什么意思,或话要先学习其它知识后才能理解吧,想了解更多,请参考此链接:https://doc.qt.io/qt-6/examples-designer.html
Debug和Release模式下的编译和安装
两种模式都编译
# 指定编译模式,另外两种是 debug 和 release
CONFIG += debug_and_release
CONFIG(debug, debug|release) {
TARGET = debug_binary
} else {
TARGET = release_binary
}
或者
两种模式都安装
如果指定了CONFIG += build_all
make install # debub 和 release 都会执行安装...
可以根据不同平台指定不同的编译名称
CONFIG(debug, debug|release) {
mac: TARGET = $$join(TARGET,,,_debug)
win32: TARGET = $$join(TARGET,,d)
}
运行qmake
挺简单的,都是一些参数说明:https://doc.qt.io/qt-6/qmake-running.html
平台说明
用qt主要是写桌面应用,主要在windows下使用,所以只关心这一块内容:https://doc.qt.io/qt-6/qmake-running.html
也不需要把QT项目编译成vs项目....
qmake语言
许多qmake项目文件使用名称=值和名称+=值定义列表,简单地描述项目使用的源文件和头文件。Qmake还提供了其他操作符、函数和作用域,可用于处理变量声明中提供的信息。这些高级特性允许从单个项目文件为多个平台生成makefile。
操作符
赋值
追加
移除
添加唯一值
# 只当 DEFINES 中没有 USE_MY_STUFF 时,才会被添加到列表中
DEFINES *= USE_MY_STUFF
unique函数也可以达到类似的效果
ARGS = 1 2 3 2 5 1
ARGS = $$unique(ARGS) #1 2 3 5
替换
# 以QT_D 或 QT_T 开头的都被换成 QT
DEFINES ~= s/QT_[DT].+/QT
TEST_VALUE += QT_THELLO QT_DTEST QT_WORLD
message($$TEST_VALUE)
TEST_VALUE ~= s/QT_[TD].+/QT
TEST_VALUE ~= s/QT_[TD].+/QT
message($$TEST_VALUE)
输出:
Project MESSAGE: QT_THELLO QT_DTEST QT_WORLD
Project MESSAGE: QT QT QT_WORLD
结论: 一次只替换一个值
变量拓展
EVERYTHING = $$SOURCES $$HEADERS
message("The project contains the following files:")
message($$EVERYTHING)
获取环境变量的值
DESTDIR = $$(PWD)
message(The project will be installed in $$DESTDIR)
DESTDIR = $(PWD)
message(The project will be installed in the value of PWD)
message(when the Makefile is processed.)
访问qmake属性
message(Qt version: $$[QT_VERSION])
message(Qt is installed in $$[QT_INSTALL_PREFIX])
message(Qt resources can be found in the following locations:)
message(Documentation: $$[QT_INSTALL_DOCS])
message(Header files: $$[QT_INSTALL_HEADERS])
message(Libraries: $$[QT_INSTALL_LIBS])
message(Binary files (executables): $$[QT_INSTALL_BINS])
message(Plugins: $$[QT_INSTALL_PLUGINS])
message(Data files: $$[QT_INSTALL_DATA])
message(Translation files: $$[QT_INSTALL_TRANSLATIONS])
message(Settings: $$[QT_INSTALL_CONFIGURATION])
message(Examples: $$[QT_INSTALL_EXAMPLES])
更多信息 Configuring qmake
作用域(Scopes)
类似于if语句,如果条件为真则作用域中声明的语句将会被执行。
语法
# { 必须要和条件写在同一行内
<condition> {
<command or definition>
...
}
作用域和条件
win32 {
SOURCES += paintwidget_win.cpp
}
# 逻辑非
!win32 {
SOURCES -= paintwidget_win.cpp
}
# 可以嵌套
macx {
CONFIG(debug, debug|release) {
HEADERS += debugging.h
}
}
# 使用:避免嵌套, 下面的代码和第9+行的代码作用一样
macx:CONFIG(debug, debug|release) {
HEADERS += debugging.h
}
# 单行条件赋值
win32:DEFINES += USE_MY_STUFF
# :相当于条件与的功能
win32:debug{
...
}
# | 逻辑或
if(win32|macos):CONFIG(debug, debug|release) {
# Do something on Windows and macOS,
# but only for the debug configuration.
}
win32|if(macos:CONFIG(debug, debug|release)) {
# Do something on Windows (regardless of debug or release)
# and on macOS (only for debug).
}
# 使用通配符
win32-* {
# Matches every mkspec starting with "win32-"
SOURCES += win32_specific.cpp
}
# else if
win32:xml {
message(Building for Windows)
SOURCES += xmlhandler_win.cpp
} else:xml {
SOURCES += xmlhandler.cpp
} else {
message("Unknown configuration")
}
配置和作用域
CONFIG += opengl
# 配置选项中是否有 opengl
opengl {
TARGET = application-gl
} else {
TARGET = application
}
平台作用域值
# 与平台相关的变量win32 macx unix linux
message($$QMAKESPEC)
linux-g++ {
message(Linux)
}
它们基于Qt的mkspecs目录中提供的平台规范:
变量
# 定义一个变量
MY_VARIABLE = value
# $$ 获得变量的内容
MY_DEFINES = $$DEFINES
# 等价于
MY_DEFINES = $${DEFINES}
# 追加功能
TARGET = myproject_$${TEMPLATE}
替换函数
HEADERS = model.h
HEADERS += $$OTHER_HEADERS
# 使用$$ 接收返回值
HEADERS = $$unique(HEADERS)
# 自定义函数
defineReplace(functionName){
#function code
}
defineReplace(headersAndSources) {
variable = $$1
names = $$eval($$variable)
headers =
sources =
for(name, names) {
header = $${name}.h
exists($$header) {
headers += $$header
}
source = $${name}.cpp
exists($$source) {
sources += $$source
}
}
return($$headers $$sources)
}
测试函数
count(options, 2) {
message(Both release and debug specified.)
}
# 自定义测试函数
defineTest(allFiles) {
files = $$ARGS
for(file, files) {
!exists($$file) {
return(false)
}
}
return(true)
}