CmakeLists.txt常用命令介绍
本文档介绍 CMake 构建系统中最常用的命令和最佳实践,适合初学者和进阶开发者参考。
1. 基础配置
1.1 cmake_minimum_required
指定项目所需的最低 CMake 版本。虽然不是强制要求,但建议始终显式声明,以确保构建环境兼容并避免因版本差异导致的问题。
语法:
cmake_minimum_required(VERSION x.y)
示例:
cmake_minimum_required(VERSION 3.20)
版本选择原则:
-
基于项目使用的 CMake 特性
target_link_options需要 CMake 3.13+CMAKE_CXX_STANDARD和CMAKE_CXX_STANDARD_REQUIRED需要 CMake 3.1+qt_add_executable需要 CMake 3.16+
-
基于第三方库要求
- Qt 6 官方要求 CMake 3.16+
- OpenCV 4.5+ 推荐 CMake 3.10+
1.2 project
定义项目名称、版本号和编程语言。
语法:
project(ProjectName VERSION major.minor.patch [LANGUAGES ...])
示例:
project(MyAwesomeApp VERSION 1.2.3 LANGUAGES CXX)
参数说明:
- ProjectName: 项目名称,用于生成工程文件名和变量
PROJECT_NAME - VERSION: 版本号(主版本.次版本.补丁版本),自动生成以下变量:
PROJECT_VERSIONPROJECT_VERSION_MAJORPROJECT_VERSION_MINORPROJECT_VERSION_PATCH
- LANGUAGES: 支持的编程语言,可选值:
C: C 语言CXX: C++ 语言Fortran: Fortran 语言ASM: 汇编语言
注意事项:
- 如果不指定
LANGUAGES,默认启用 C 和 CXX - 建议明确指定所需语言以避免不必要的编译器检测
2. 目标管理
2.1 add_executable
定义并创建一个可执行文件目标,将指定的源文件编译链接成可运行的程序(如 Windows 的 .exe 文件)。
语法:
add_executable(TargetName [WIN32] [MACOSX_BUNDLE] source1 source2 ...)
参数说明:
- TargetName: 目标名称
- WIN32: Windows 平台上创建 GUI 程序(无控制台窗口)
- MACOSX_BUNDLE: macOS 平台上创建 .app 应用包
- source1 source2 ...: 源文件列表
基础示例:
add_executable(MyApp
src/main.cpp
src/app.cpp
)
跨平台示例:
# 收集源文件
file(GLOB_RECURSE SOURCES "src/*.cpp")
# 根据平台添加不同选项
if(WIN32)
add_executable(MyApp WIN32 ${SOURCES})
elseif(APPLE)
add_executable(MyApp MACOSX_BUNDLE ${SOURCES})
else()
add_executable(MyApp ${SOURCES})
endif()
注意事项:
- 头文件无需添加到源文件列表中
- 必须包含所有参与编译的 .cpp 文件
- Qt 项目推荐使用
qt_add_executable
2.2 add_library
定义并创建一个库目标,将指定的源文件编译成可重用的库文件(如静态库 .a/.lib 或动态库 .so/.dll)。
语法:
add_library(targetName [STATIC|SHARED|MODULE|INTERFACE|OBJECT] [sources...])
库类型说明:
- STATIC: 静态库(.a / .lib)
- SHARED: 动态库(.so / .dll)
- MODULE: 模块库(插件,运行时加载)
- INTERFACE: 接口库(纯头文件库)
- OBJECT: 对象文件库(.o 文件集合)
示例:
# 静态库
add_library(mylib STATIC
src/foo.cpp
src/bar.cpp
)
# 动态库
add_library(mylib_shared SHARED
src/foo.cpp
src/bar.cpp
)
# 接口库(仅头文件)
add_library(header_only_lib INTERFACE)
常见配套命令:
target_include_directories()- 设置头文件路径target_link_libraries()- 链接依赖库target_compile_options()- 编译选项target_sources()- 管理源文件
2.3 target_sources
为已存在的目标添加源文件。相比 add_library 在创建目标时一次性添加源文件,target_sources 的优势在于目标创建后可以分多次、分条件地动态添加源文件。
语法:
target_sources(targetName [PRIVATE | PUBLIC | INTERFACE] sources...)
可见性说明:
- PRIVATE: 源文件仅用于该目标本身
- PUBLIC: 目标本身使用,依赖者也可见(很少用于源文件)
- INTERFACE: 目标本身不用,仅对依赖者可见
示例:
# 先创建空库
add_library(mylib STATIC)
# 根据平台添加不同源文件
if(WIN32)
target_sources(mylib PRIVATE src/windows.cpp)
elseif(APPLE)
target_sources(mylib PRIVATE src/macos.cpp)
else()
target_sources(mylib PRIVATE src/linux.cpp)
endif()
使用场景:
- 模块化管理源文件
- 条件性添加源文件
- 提高 CMakeLists.txt 可读性
3. 依赖管理
3.1 target_include_directories
为目标设置头文件搜索路径,控制编译器在何处查找 #include 的头文件;若未设置,编译器只会在源文件目录和系统默认路径中查找头文件,其他目录下的头文件将无法找到。
语法:
target_include_directories(targetName [PUBLIC|PRIVATE|INTERFACE] dirs...)
可见性说明:
- PRIVATE: 路径仅用于该目标编译
- PUBLIC: 该目标及其依赖者都使用此路径
- INTERFACE: 仅依赖者使用此路径
示例:
# 为可执行程序添加私有头文件路径
add_executable(myapp main.cpp)
target_include_directories(myapp
PRIVATE
${CMAKE_CURRENT_SOURCE_DIR}/include
)
# 为库添加公共头文件路径
add_library(mylib src/foo.cpp)
target_include_directories(mylib
PUBLIC
${CMAKE_CURRENT_SOURCE_DIR}/include
)
目录结构示例:
project_root/
├── include/
│ ├── foo.h
│ └── utils/
│ └── helper.h
├── src/
│ └── main.cpp
└── CMakeLists.txt
代码中的使用:
// main.cpp
#include "foo.h" // 正确
#include "utils/helper.h" // 正确
#include "helper.h" // 错误:需要包含完整路径
重要提示:
- CMake 不会递归搜索子目录
- 需在代码中提供相对于 include(target_include_directories 指定的目录)目录的完整路径
3.2 target_link_libraries
为目标链接库依赖。也就是告诉 CMake:在编译 target 时,需要额外链接哪些库(依赖的库),才能正常运行。
语法:
target_link_libraries(targetName [PUBLIC|PRIVATE|INTERFACE] libraries...)
可见性说明:
- PRIVATE: 仅该目标使用
- PUBLIC: 该目标及其依赖者都链接
- INTERFACE: 仅依赖者链接
库类型:
- CMake 目标(如自定义库)
- 系统库(如 pthread)
- 第三方库的导入目标(如 Qt6::Core)
示例:
# 链接自定义库
add_library(mylib STATIC foo.cpp)
add_executable(myapp main.cpp)
target_link_libraries(myapp PRIVATE mylib)
# 链接第三方库
find_package(Qt6 REQUIRED COMPONENTS Core Widgets)
target_link_libraries(myapp
PRIVATE
Qt6::Core
Qt6::Widgets
)
# 链接系统库
target_link_libraries(myapp PRIVATE pthread)
4. 库和包查找
4.1 find_package
用来自动查找和配置外部依赖库或包,当你的项目依赖第三方库或系统库时就需要。
语法:
find_package(PackageName [Version] [REQUIRED] [COMPONENTS components...])
参数说明:
- PackageName: 包名称(如 Qt6、OpenCV、Boost)
- Version: 最低版本要求
- REQUIRED: 找不到时停止构建
- COMPONENTS: 指定所需子模块
示例:
find_package(Qt6 6.6 REQUIRED COMPONENTS Core Widgets Gui)
4.2 查找机制详解
CMake 使用严格的优先级顺序查找包,找到第一个匹配项就立即停止搜索。
4.2.1 完整查找流程
- 检查缓存变量:如果
<PackageName>_DIR已经在缓存中,直接使用 - 模块模式(Module Mode):搜索
Find<PackageName>.cmake文件 - 配置模式(Config Mode):搜索
<PackageName>Config.cmake或<lowercase-name>-config.cmake文件
重要: 一旦在模块模式中找到 Find<PackageName>.cmake,CMake 就会停止搜索,不会继续尝试配置模式。
4.2.2 模块模式(Module Mode)
按以下顺序搜索 Find<PackageName>.cmake 文件:
CMAKE_MODULE_PATH指定路径(按添加顺序)- CMake 内置模块路径(如
/usr/share/cmake/Modules)
示例:
# 如果存在 FindQt6.cmake(不太可能),就会使用模块模式
find_package(Qt6 REQUIRED)
4.2.3 配置模式(Config Mode)
只有在模块模式失败后才会尝试配置模式,搜索 <PackageName>Config.cmake 文件:
<PackageName>_DIR变量指定路径CMAKE_PREFIX_PATH路径(最重要):<prefix>/<prefix>/cmake/<prefix>/lib/cmake/<PackageName>/<prefix>/lib/<PackageName>/<prefix>/lib/<PackageName>/cmake/<prefix>/share/<PackageName>/<prefix>/share/<PackageName>/cmake/
CMAKE_FRAMEWORK_PATH(macOS 框架)CMAKE_APPBUNDLE_PATH(macOS App Bundle)CMAKE_FIND_ROOT_PATH(交叉编译)- 系统默认路径:
/usr/lib/cmake/<PackageName>//usr/local/lib/cmake/<PackageName>//opt/local/lib/cmake/<PackageName>/- Windows:
C:/Program Files/<PackageName>/
- 环境变量
PATH路径 - 平台注册表(Windows)
4.2.4 强制使用配置模式
可以通过 CONFIG 关键字强制跳过模块模式:
# 强制使用配置模式,跳过 FindQt6.cmake 查找
find_package(Qt6 CONFIG REQUIRED)
# 等价写法
find_package(Qt6 CONFIG REQUIRED COMPONENTS Core Widgets)
4.2.5 Windows 查找 Qt6 实例
假设在 Windows 上安装了 Qt6 到 C:/Qt/6.7.0/msvc2022_64/,执行以下查找:
find_package(Qt6 REQUIRED COMPONENTS Core Widgets)
查找流程:
-
检查缓存变量
检查 CMakeCache.txt 中是否有 Qt6_DIR如果有:Qt6_DIR:PATH=C:/Qt/6.7.0/msvc2022_64/lib/cmake/Qt6 -
模块模式(通常 Qt6 不使用此模式)
查找 FindQt6.cmake:- CMAKE_MODULE_PATH 路径- C:/Program Files/CMake/share/cmake-3.x/Modules/FindQt6.cmake(不存在) -
配置模式(Qt6 的标准方式)
查找 Qt6Config.cmake,按以下顺序:a) Qt6_DIR 变量指定路径:- C:/Qt/6.7.0/msvc2022_64/lib/cmake/Qt6/Qt6Config.cmake ✓b) CMAKE_PREFIX_PATH 路径(如果设置了):假设设置了 CMAKE_PREFIX_PATH=C:/Qt/6.7.0/msvc2022_64- C:/Qt/6.7.0/msvc2022_64/Qt6Config.cmake- C:/Qt/6.7.0/msvc2022_64/cmake/Qt6Config.cmake- C:/Qt/6.7.0/msvc2022_64/lib/cmake/Qt6/Qt6Config.cmake ✓- C:/Qt/6.7.0/msvc2022_64/lib/Qt6/Qt6Config.cmake- C:/Qt/6.7.0/msvc2022_64/share/Qt6/Qt6Config.cmakec) 系统默认路径:- C:/Program Files/Qt6/lib/cmake/Qt6/Qt6Config.cmake- C:/Program Files (x86)/Qt6/lib/cmake/Qt6/Qt6Config.cmake- C:/Qt6/lib/cmake/Qt6/Qt6Config.cmaked) 注册表查找:- HKEY_CURRENT_USER\Software\Kitware\CMake\Packages\Qt6- HKEY_LOCAL_MACHINE\Software\Kitware\CMake\Packages\Qt6
4.2.6 默认搜索的局限性
重要: 如果 Qt 安装在 C:/Qt/ 下(如 C:/Qt/6.7.0/msvc2022_64/),不设置 CMAKE_PREFIX_PATH 通常找不到。
原因分析:
-
CMake 默认搜索路径:
C:/Program Files/Qt6/lib/cmake/Qt6/C:/Program Files (x86)/Qt6/lib/cmake/Qt6/C:/Qt6/lib/cmake/Qt6/ # 注意:只查找 C:/Qt6,不查找 C:/Qt/ -
Qt 实际安装路径:
C:/Qt/6.7.0/msvc2022_64/lib/cmake/Qt6/Qt6Config.cmake # 不在默认搜索路径中 -
路径不匹配:
- 默认搜索:
C:/Qt6/lib/cmake/Qt6/ - 实际路径:
C:/Qt/6.7.0/msvc2022_64/lib/cmake/Qt6/ - 两者不匹配!
- 默认搜索:
测试验证:
# 清除所有前缀路径,仅使用默认搜索
unset(CMAKE_PREFIX_PATH)
unset(CMAKE_PREFIX_PATH CACHE)
unset(Qt6_DIR CACHE)
# 尝试查找 Qt6
find_package(Qt6 COMPONENTS Core)
if(Qt6_FOUND)
message(STATUS "✓ 在默认路径找到 Qt6: ${Qt6_DIR}")
else()
message(WARNING "✗ 默认路径未找到 Qt6")
message(STATUS "需要设置 CMAKE_PREFIX_PATH 或 Qt6_DIR")
endif()
可能的例外情况:
-
注册表信息:
如果 Qt 安装程序向注册表写入了路径信息:HKEY_LOCAL_MACHINE\Software\Kitware\CMake\Packages\Qt6 -
符号链接:
如果存在符号链接:C:/Qt6 -> C:/Qt/6.7.0/msvc2022_64 -
环境变量:
如果系统环境变量中设置了相关路径(不常见)
解决方案(按推荐程度排序):
# 方案1:设置前缀路径(推荐)
set(CMAKE_PREFIX_PATH "C:/Qt/6.7.0/msvc2022_64")
# 方案2:直接指定 Qt6 路径
set(Qt6_DIR "C:/Qt/6.7.0/msvc2022_64/lib/cmake/Qt6")
# 方案3:环境变量
# set CMAKE_PREFIX_PATH=C:\Qt\6.7.0\msvc2022_64
# 方案4:命令行参数
# cmake -DCMAKE_PREFIX_PATH="C:/Qt/6.7.0/msvc2022_64" ..
总结: C:/Qt/ 路径下的 Qt 安装需要手动配置路径,CMake 默认搜索机制无法自动找到。
重要提示:
CMAKE_PREFIX_PATH是最常用的配置变量- 添加
NO_DEFAULT_PATH可限制搜索范围 CMAKE_FIND_ROOT_PATH主要用于交叉编译
4.2.7 默认搜索路径(不设置前缀路径时)
如果不手动设置 CMAKE_PREFIX_PATH,CMake 会使用系统默认路径进行搜索:
Linux/Unix 系统:
/usr/
/usr/local/
/opt/
/usr/lib/x86_64-linux-gnu/ (架构相关)
/usr/share/
/usr/local/share/
macOS 系统:
/usr/
/usr/local/
/opt/
/opt/local/ (MacPorts)
/usr/local/Cellar/ (Homebrew)
/Applications/ (应用程序)
/System/Library/Frameworks/ (系统框架)
/Library/Frameworks/ (用户框架)
Windows 系统:
C:/Program Files/
C:/Program Files (x86)/
C:/
注册表路径 (Registry)
常见问题:
-
找不到包:如果库安装在非标准路径(如
/opt/Qt6),CMake 在默认路径中找不到,需要设置CMAKE_PREFIX_PATH。 -
找到错误版本:系统中安装多个版本时,CMake 可能找到旧版本而不是期望的版本。
验证默认搜索:
# 查看系统默认前缀路径
message(STATUS "CMAKE_SYSTEM_PREFIX_PATH: ${CMAKE_SYSTEM_PREFIX_PATH}")
# 测试不设置前缀路径的查找
unset(CMAKE_PREFIX_PATH)
find_package(Qt6)
if(Qt6_FOUND)
message(STATUS "Found Qt6 in system default paths: ${Qt6_DIR}")
else()
message(WARNING "Qt6 not found in system default paths")
endif()
4.3 find_library
查找指定库文件的路径,当库没有 CMake 配置文件或你只想手动指定库路径时使用。
语法:
find_library(variable_name library_name [PATHS path_list] [REQUIRED] [NO_DEFAULT_PATH])
示例:
find_library(MYLIB_PATH mylib
PATHS /usr/local/lib
REQUIRED
)
target_link_libraries(myapp PRIVATE ${MYLIB_PATH})
4.4 find_path
查找指定文件的目录,返回包含该文件的完整目录路径,可以用于 target_include_directories。
语法:
find_path(variable_name file_name [PATHS path_list] [REQUIRED] [NO_DEFAULT_PATH])
示例:
find_path(MYLIB_INCLUDE_DIR mylib.h
PATHS /usr/local/include
REQUIRED
)
target_include_directories(myapp PRIVATE ${MYLIB_INCLUDE_DIR})
5. 编译配置
5.1 set
设置变量值。
语法:
set(VAR value)
常用预定义变量:
# C++ 标准配置
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
# 构建类型
set(CMAKE_BUILD_TYPE Release)
# 输出目录
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin)
set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib)
5.2 target_compile_definitions
target_compile_definitions 用来给目标添加编译宏,在需要条件编译、传递特性标记或调试开关时使用
语法:
target_compile_definitions(target_name [PUBLIC|PRIVATE|INTERFACE] <definition>...)
示例:
# 编译 app 时会定义 USE_FEATURE_X,启用条件代码
target_compile_definitions(app PRIVATE USE_FEATURE_X)
条件编译:
#ifdef USE_FEATURE_X
void featureX() { ... }
#endif
5.3 target_compile_options
用来为目标添加编译器选项。
语法:
target_compile_options(targetName [PUBLIC|PRIVATE|INTERFACE] options...)
示例:
# GCC/Clang 编译选项, -Wall启用一组常用的编译器警告
target_compile_options(myapp
PRIVATE
-Wall
)
6. 安装和导出
6.1 install(TARGETS)
编译生成的可执行文件或库安装到指定目录或打包中,当你需要发布、共享或正式部署目标文件时使用
语法:
install(TARGETS target1 target2 ...
[RUNTIME DESTINATION <dir>]
[LIBRARY DESTINATION <dir>]
[ARCHIVE DESTINATION <dir>]
[BUNDLE DESTINATION <dir>]
)
参数说明:
- RUNTIME DESTINATION: 可执行文件安装路径
- LIBRARY DESTINATION: 动态库安装路径
- ARCHIVE DESTINATION: 静态库安装路径
- BUNDLE DESTINATION: macOS 应用包安装路径
示例:
install(TARGETS myapp
RUNTIME DESTINATION bin
LIBRARY DESTINATION lib
ARCHIVE DESTINATION lib
)
6.2 install(FILES)
用来把指定的文件直接安装到目标目录,和 install(TARGETS ...) 不同,它不是安装编译生成的目标,而是安装已有文件(比如头文件、配置文件、资源文件等)。
语法:
install(FILES file1 file2 ... DESTINATION path)
示例:
install(FILES
${CMAKE_SOURCE_DIR}/config/config.json
${CMAKE_SOURCE_DIR}/README.md
DESTINATION share/myapp
)
7. 控制流程
7.1 if/elseif/else/endif
条件控制语句。
语法:
if(condition)
# commands
elseif(condition)
# commands
else()
# commands
endif()
常用条件:
# 平台检测
if(WIN32)
message("Building on Windows")
elseif(APPLE)
message("Building on macOS")
elseif(UNIX)
message("Building on Linux/Unix")
endif()
# 变量检测
if(DEFINED MY_VARIABLE)
message("MY_VARIABLE is defined")
endif()
# 字符串比较
if(CMAKE_BUILD_TYPE STREQUAL "Debug")
add_definitions(-DDEBUG_BUILD)
endif()
7.2 option
用来定义布尔开关,让用户选择开启或关闭某个功能,编译流程可根据这个开关灵活控制。
语法:
option(OptionName "description" [ON|OFF])
示例:
option(BUILD_TESTS "Build unit tests" ON)
if(BUILD_TESTS)
enable_testing()
add_subdirectory(tests)
endif()
#CMake 的 option() 定义的开关,用户可以 在命令行配置项目时指定 ON 或 OFF,从而控制编译流程
cmake -S . -B build -DBUILD_TESTS=OFF
8. 实用工具
8.1 add_subdirectory
用来将另一个子目录加入到当前构建中,并处理该子目录下的 CMakeLists.txt。 换句话说,它让你可以组织项目为多个模块或子项目,并把它们编译到同一个构建中。
语法:
add_subdirectory(path)
示例:
假设项目结构:
project_root/
├── CMakeLists.txt
├── src/
│ └── main.cpp
└── tests/
└── CMakeLists.txt
└── test_main.cpp
主 CMakeLists.txt:
cmake_minimum_required(VERSION 3.15)
project(MyApp)
add_executable(myapp src/main.cpp)
option(BUILD_TESTS "Build unit tests" ON)
if(BUILD_TESTS)
enable_testing()
add_subdirectory(tests)
endif()
8.2 include
包含外部 CMake 脚本文件。
语法:
include(path/to/file.cmake)
8.3 message
输出信息到控制台。
语法:
message([level] "text")
级别说明:
- STATUS: 状态信息(绿色)
- WARNING: 警告信息(黄色)
- FATAL_ERROR: 致命错误(红色,停止构建)
示例:
message(STATUS "Configuring project ${PROJECT_NAME}")
message(WARNING "This feature is deprecated")
message(FATAL_ERROR "Required dependency not found")
9. Qt 特有配置
9.1 自动化工具
set(CMAKE_AUTOMOC ON) # 自动处理 MOC(Meta-Object Compiler)
set(CMAKE_AUTORCC ON) # 自动处理资源文件(.qrc)
set(CMAKE_AUTOUIC ON) # 自动处理界面文件(.ui)
功能说明:
- CMAKE_AUTOMOC: 自动为包含
Q_OBJECT宏的类生成 moc 文件 - CMAKE_AUTORCC: 自动编译 .qrc 资源文件为 C++ 代码
- CMAKE_AUTOUIC: 自动将 .ui 界面文件转换为头文件
9.2 qt_standard_project_setup()
Qt 6 推荐的项目设置函数,内部已包含上述自动化配置。
语法:
qt_standard_project_setup(REQUIRES 6.5)
10. 完整示例
10.1 Python 扩展模块(.pyd)
cmake_minimum_required(VERSION 3.16)
project(QComposer VERSION 0.1 LANGUAGES CXX)
# C++ 标准配置
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
# 项目路径配置
set(PROJECT_ROOT_DIR ${CMAKE_CURRENT_LIST_DIR}/..)
# Conda 环境配置
if(DEFINED ENV{CONDA_PREFIX})
list(PREPEND CMAKE_PREFIX_PATH "$ENV{CONDA_PREFIX}")
endif()
# 常见的前缀路径自动检测
if(DEFINED ENV{VCPKG_ROOT})
list(APPEND CMAKE_PREFIX_PATH "$ENV{VCPKG_ROOT}/installed/${VCPKG_TARGET_TRIPLET}")
endif()
if(DEFINED ENV{Qt6_DIR})
list(APPEND CMAKE_PREFIX_PATH "$ENV{Qt6_DIR}")
endif()
# 查找依赖
find_package(Python3 REQUIRED COMPONENTS Interpreter Development.Module)
find_package(Qt6 REQUIRED COMPONENTS Quick QuickControls2)
find_package(pybind11 REQUIRED)
# Qt 标准配置
qt_standard_project_setup(REQUIRES 6.5)
# 收集源文件
file(GLOB_RECURSE SOURCES ${PROJECT_ROOT_DIR}/src/*.cpp)
# 添加资源
qt_add_resources(RESOURCES ${PROJECT_ROOT_DIR}/src/resources.qrc)
# 创建 Python 模块
pybind11_add_module(QComposer
${PROJECT_ROOT_DIR}/python-module/binding.cpp
${SOURCES}
${RESOURCES}
)
# 配置包含目录
target_include_directories(QComposer
PRIVATE ${PROJECT_ROOT_DIR}
)
# 链接库
target_link_libraries(QComposer
PRIVATE
Qt6::Quick
Qt6::Gui
Qt6::QuickControls2
)
# 设置输出属性
set_target_properties(QComposer PROPERTIES
OUTPUT_NAME "QComposer"
PREFIX ""
SUFFIX ".pyd"
LIBRARY_OUTPUT_DIRECTORY ${PROJECT_SOURCE_DIR}
)
10.2 Qt 桌面应用程序
cmake_minimum_required(VERSION 3.16)
project(QComposer VERSION 0.1 LANGUAGES CXX)
# C++ 标准配置
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
# 查找 Qt6
find_package(Qt6 REQUIRED COMPONENTS Quick QuickControls2)
# Qt 标准配置
qt_standard_project_setup(REQUIRES 6.5)
# 收集源文件
file(GLOB_RECURSE SOURCES src/*.cpp src/*.h)
# 创建可执行程序
qt_add_executable(QComposer
src/app/main.cpp
${CMAKE_SOURCE_DIR}/Resources/icon.png
)
# 添加 QML 模块
qt_add_qml_module(QComposer
URI QComposer
VERSION 1.0
SOURCES ${SOURCES}
RESOURCES src/resources.qrc
)
# 设置程序属性
set_target_properties(QComposer PROPERTIES
MACOSX_BUNDLE TRUE
MACOSX_BUNDLE_BUNDLE_VERSION ${PROJECT_VERSION}
MACOSX_BUNDLE_SHORT_VERSION_STRING ${PROJECT_VERSION_MAJOR}.${PROJECT_VERSION_MINOR}
MACOSX_BUNDLE_ICON_FILE icon.png
WIN32_EXECUTABLE TRUE
)
# 配置资源文件位置(macOS)
set_source_files_properties(${CMAKE_SOURCE_DIR}/Resources/icon.png
PROPERTIES MACOSX_PACKAGE_LOCATION "Resources"
)
# 链接库
target_link_libraries(QComposer
PRIVATE
Qt6::Quick
Qt6::Gui
Qt6::QuickControls2
)
# 安装规则
install(TARGETS QComposer BUNDLE DESTINATION .)
11. 总结
本文档涵盖了 CMake 的核心命令和最佳实践。在实际使用中,建议:
- 从简单开始: 先掌握基础命令,再学习高级特性
- 使用现代 CMake: 优先使用
target_*系列命令 - 保持一致性: 统一代码风格和项目结构
- 合理组织: 将复杂项目拆分为多个 CMakeLists.txt
- 版本管理: 明确指定最低 CMake 版本和依赖版本
通过掌握这些命令,你可以构建从简单到复杂的各种项目。