CMake头文件仅库项目头文件包含路径保留及安装打包方案咨询
解决CMake接口库的两个核心问题
问题1:保留头文件目录路径进行包含
你现在的问题根源是把每个子目录直接加到了target_include_directories里,导致编译器只能直接匹配头文件名,没法通过目录层级访问。要实现#include "A/A.hpp"这种形式,咱们得把父目录加入包含路径,而非子目录本身。
修改你的接口库CMake配置如下:
# 改为添加父目录,而非单个子目录 set(project_includes_internal ${CMAKE_CURRENT_LIST_DIR}) # 生成文件的父目录是CMAKE_CURRENT_BINARY_DIR/include,直接添加这个路径 set(project_gen_includes ${CMAKE_CURRENT_BINARY_DIR}/include) # nlohmann的父目录是dep/nlohmann,这样就能用json/json.hpp的形式包含 set(project_dep_inludes ${CMAKE_HOME_DIRECTORY}/dep/nlohmann) set(PROJECT_INCLUDES ${project_includes_internal} ${project_gen_includes} ${project_dep_inludes}) add_library(${PROJECT_NAME} INTERFACE) target_include_directories(${PROJECT_NAME} INTERFACE $<BUILD_INTERFACE:${PROJECT_INCLUDES}> $<INSTALL_INTERFACE:include> )
这样调整后的好处:
- 源码里的头文件可以用
#include "A/A.hpp"访问,接口库内部的头文件也能互相通过目录名引用(比如A目录里的头文件可以#include "B/B.hpp") - 生成的头文件能通过
#include "AGen/AGen.hpp"正常访问 - nlohmann的json头文件可以用
#include "json/json.hpp"的标准形式包含
另外要注意安装阶段的目录一致性:安装时需要把A、B、C、AGen等目录完整复制到include目录下,这样INSTALL_INTERFACE:include才能正常工作,后续其他项目安装后也能保持同样的包含方式。
问题2:将头文件复制到构建目录用于发布
完全可以实现,咱们有两种方案可选,分别适配构建阶段临时复制和正式打包发布的需求:
方案1:构建阶段直接复制到构建目录
在接口库的CMake配置里添加以下代码,把所有需要的头文件复制到构建目录的include下,保持原目录结构:
# 复制源码中的头文件 file(COPY ${CMAKE_CURRENT_LIST_DIR}/A ${CMAKE_CURRENT_LIST_DIR}/B ${CMAKE_CURRENT_LIST_DIR}/C DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/include ) # 复制生成的头文件(如果生成位置不在include下,需要调整源路径) file(COPY ${CMAKE_CURRENT_BINARY_DIR}/include/AGen ${CMAKE_CURRENT_BINARY_DIR}/include/BGen ${CMAKE_CURRENT_BINARY_DIR}/include/CGen DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/include ) # 复制依赖的nlohmann头文件 file(COPY ${CMAKE_HOME_DIRECTORY}/dep/nlohmann/json DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/include )
如果生成的头文件是通过其他目标生成的,记得添加依赖确保复制时文件已生成:
# 假设generate_headers是生成头文件的目标 add_dependencies(${PROJECT_NAME} generate_headers)
方案2:用install命令支持正式打包发布
如果需要支持make install或者打包成标准安装包,用install命令更合适,它会把文件复制到指定的安装目录(默认是CMAKE_INSTALL_PREFIX下的include):
install(DIRECTORY ${CMAKE_CURRENT_LIST_DIR}/A ${CMAKE_CURRENT_LIST_DIR}/B ${CMAKE_CURRENT_LIST_DIR}/C DESTINATION include ) install(DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/include/AGen ${CMAKE_CURRENT_BINARY_DIR}/include/BGen ${CMAKE_CURRENT_BINARY_DIR}/include/CGen DESTINATION include ) install(DIRECTORY ${CMAKE_HOME_DIRECTORY}/dep/nlohmann/json DESTINATION include )
执行cmake --install .后,所有头文件会被复制到CMAKE_INSTALL_PREFIX/include目录下,方便直接打包或者复制到其他机器使用。
内容的提问来源于stack exchange,提问作者0x52616A657368
相关产品推荐
相关产品推荐

