我正在尝试使用 CMake v3.30.5 创建一个使用 VS2022 构建的 C++ 项目。我想通过 FetchContent 包含第 3 方代码,这样我就不需要将它们添加到我的源代码树中。代码将放置在项目根目录中名为
SDKs
的目录中,并由同样放置在根目录中的项目 Core
使用。对于第一个,我想添加 FastDelegate (https://github.com/dreamcat4/FastDelegate) 作为仅标头库,因此我将其声明为 INTERFACE,因为它不编译任何源。
我的根 CMakeLists.txt 看起来像这样:
cmake_minimum_required(VERSION 3.24)
project(MyProj
LANGUAGES CXX
VERSION 0.0.1)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED True)
list(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/CMake")
set(SDK_DIR "${CMAKE_CURRENT_SOURCE_DIR}/SDKs")
set_property(GLOBAL PROPERTY USE_FOLDERS ON)
add_subdirectory(SDKs)
add_subdirectory(Core)
SDK CMakeLists.txt 成功获取源代码,将其放置在 SDKs/FastDelegate 文件夹中,并按我的预期运行
find_package
:
include (FetchContent)
FetchContent_Declare(FastDelegate
GIT_REPOSITORY https://github.com/dreamcat4/FastDelegate.git
GIT_PROGRESS true
SOURCE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/FastDelegate"
BINARY_DIR "${CMAKE_BINARY_DIR}/SDKs/FastDelegate"
FIND_PACKAGE_ARGS)
FetchContent_MakeAvailable(FastDelegate)
find_package
的 FindFastDelegate.cmake 创建一个带有标头的 INTERFACE 库并设置包含目录:
cmake_minimum_required(VERSION 3.24)
set(SRC_DIR "${SDK_DIR}/FastDelegate")
add_library(FastDelegate INTERFACE
"${SRC_DIR}/FastDelegate.h"
"${SRC_DIR}/FastDelegateBind.h")
add_library(SDK::FastDelegate ALIAS FastDelegate)
target_include_directories(FastDelegate INTERFACE ${SRC_DIR})
set_target_properties(FastDelegate PROPERTIES FOLDER "SDKs/FastDelegate")
我的 Core CMakeLists.txt 链接到 FastDelegate INTERFACE 库:
cmake_minimum_required(VERSION 3.24)
add_library(Core STATIC
Core_defines.h)
set_target_properties(Core PROPERTIES LINKER_LANGUAGE CXX)
target_include_directories(Core PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
target_link_libraries(Core
PUBLIC
SDK::FastDelegate)
# added this to make sure include directories are correct
file(GENERATE OUTPUT "$<CONFIG>output.txt"
CONTENT "$<TARGET_PROPERTY:Core,INCLUDE_DIRECTORIES>")
测试输出确实显示
Core
库的包含目录是
C:/Projects/MyProj/Core;C:/Projects/MyProj/SDKs/FastDelegate
正如我所料。但是,MSVC 项目没有列出包含目录中的任何一个,我无法 #include
FastDelegate 文件。
我错过了什么或做错了什么,或者 CMake 有问题吗?
感谢@ixSci提出了一个很好的问题,引导我走上这条道路:
我的
Core
链接到INTERFACE库的库中没有任何源文件,只有其他头文件,因此没有编译输出。这会导致 CMake 或 VS(不确定是哪一个)不引入额外的包含目录。一旦我将空的 TestSource.cpp 添加到 Core 并再次运行 CMake,包含目录就会如我所料地出现在项目属性中,并且我可以 #include 文件中的标头。