如何以跨平台方式使用CMAKE包含库

时间:2019-01-05 04:22:26

标签: cmake cross-platform

我正在尝试在跨平台C ++项目中使用assimp库。我将回购作为git子模块包含在内,因此,有效地,如果有人下载了我的项目,他们还将下载ASSIMP项目。

在完成assimp build / CMAKE指令并(在Linux上)键入make install之后,从那时起,我就可以使用:

target_link_libraries(${PROJECT_NAME} assimp)

但是,在Windows上没有make install

我能够在Linux上包括该库的唯一其他方法是将其放入(在我的CmakeLists.txt文件中):

target_link_libraries(${PROJECT_NAME} ${CMAKE_SOURCE_DIR}/build/assimp/code/libassimp.so)

这不是跨平台的,因为它会硬编码.so文件的名称和位置,而该文件在Windows上将无法使用。

如何公开该库,以便可以在所有平台上进行类似target_link_libraries(${PROJECT_NAME} assimp)的操作?

我的目录树如下:

- src
- include
    - assimp
- bin

assimp目录中的include目录是git子模块

1 个答案:

答案 0 :(得分:1)

我认为您的做法是错误的。您无需在项目中的其他步骤中构建assimp,也不需要make install使其可用。

在Cmake中有很多处理第三方依赖项的方法,因为您已经选择了对assimp存储库进行子模块化,所以我们将从这里开始。假设assimp位于您存储库的根目录assimp/中,这将是一个包括以下内容的准项目:

cmake_minimum_required(VERSION 3.0)
project(Project myassimpproj)

# include your directories
include_directories(
  ${CMAKE_CURRENT_SOURCE_DIR}
  )

# set any variables you might need to set for your app and assimp
set(BUILD_ASSIMP_TOOLS  ON)
set(ASSIMP_BUILD_STATIC_LIB ON)

# add assimp source dir as a subdirectory, effectively making 
# assimp's CMakeLists.txt part of your build
add_subdirectory(/path/to/assimp ${CMAKE_BINARY_DIR}/assimp)

add_executable(assimp_target main.cpp)

# be sure to link in assimp, use platform-agnostic syntax for the linker
target_link_libraries(assimp_target assimp)

也许可以使用生成器表达式语法对此进行更好的措辞,但是我没有查看assimp的CMakeLists.txt来了解它是否受支持(无论如何,这是一种更为通用的方法。)

并非每个项目都使用Cmake,因此您可能无法仅使用add_subdirectory()。在这些情况下,您可以有效地“伪造”用户调用,以使用他们在各自平台上的构建命令来构建它们。 execute_process()在配置时运行命令add_custom_command()add_custom_target()在构建时运行命令。然后,您创建一个伪造目标以进行集成,并有朝一日他们会支持Cmake。

您还可以使用添加到Cmake的ExternalProject命令来创建自定义目标,以驱动外部项目的下载,更新/补丁,配置,构建,安装和测试步骤,但是请注意,此解决方案和接下来下载依赖项,而不是使用子模块的源代码。

最后,我更喜欢使用预构建的依赖项,减少构建时间,并且可以在项目外部对其进行单元测试。 Conan是一个开源,分散和多平台的软件包管理器,使用正确的方式对C ++很好地支持,对Cmake几乎透明的支持。在过去的一年中,他们的成长非常稳定。 here可以找到有关如何将Conan与Cmake结合使用的更多信息。