cmake多模块架构, DLL依赖编译

2023-12-15 18:49:55

整体结构:
在这里插入图片描述

最外层的cmakelist

project(cmakeMulPackage)
cmake_minimum_required(VERSION 3.17)
set(CMAKE_CXX_STANDARD 11)

#设置环境相关
message("====================set env.cmake===================")
message("CMAKE_BUILD_TYPE is ${CMAKE_BUILD_TYPE}")
set(PROJECT_LIBRARY_DIR ${PROJECT_SOURCE_DIR}/Library)
set(PROJECT_LIBRARY_INCLUDE_DIR ${PROJECT_LIBRARY_DIR}/${CMAKE_BUILD_TYPE}/include)
set(PROJECT_LIBRARY_LIB_DIR ${PROJECT_LIBRARY_DIR}/${CMAKE_BUILD_TYPE}/lib)
set(PROJECT_LIBRARY_DLL_DIR ${PROJECT_LIBRARY_DIR}/${CMAKE_BUILD_TYPE}/dll)
message("PROJECT_LIBRARY_DIR is ${PROJECT_LIBRARY_DIR}")
message("PROJECT_LIBRARY_INCLUDE_DIR is ${PROJECT_LIBRARY_INCLUDE_DIR}")
message("PROJECT_LIBRARY_LIB_DIR is ${PROJECT_LIBRARY_LIB_DIR}")
message("PROJECT_LIBRARY_DLL_DIR is ${PROJECT_LIBRARY_DLL_DIR}")

#同时生成lib与DLL
message("PROJECT_BINARY_DIR is ${PROJECT_BINARY_DIR}")
set(CMAKE_WINDOWS_EXPORT_ALL_SYMBOLS ON)
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${PROJECT_BINARY_DIR}) #DLL生成路径
set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${PROJECT_BINARY_DIR}) #lib生成路径
set(CMAKE_PDB_OUTPUT_DIRECTORY ${PROJECT_BINARY_DIR}) #pdb生成路径
#设置环境相关 END

# 处理编译字符集问题
add_compile_options("$<$<C_COMPILER_ID:MSVC>:/utf-8>")
add_compile_options("$<$<CXX_COMPILER_ID:MSVC>:/utf-8>")

message("====================set include path.cmake===================")
#定义头文件需要寻址的路径
include_directories(
        ${PROJECT_LIBRARY_INCLUDE_DIR} #头文件
        App/include #模块头文件
        AppModuleA/include #模块头文件
)
#定义库文件需要寻址的路径
link_directories(
        ${PROJECT_LIBRARY_LIB_DIR}
)

message("====================set sub directory.cmake===================")
#添加一个子目录并构建该子目录
add_subdirectory(App)
add_subdirectory(AppModuleA)

主程序

cmakelist

#定义头文件路径
include_directories(./include)

#把目录src和inc下面的所有文件作为变量存储
file(GLOB_RECURSE SRC_FILES "src/*")
file(GLOB_RECURSE INC_FILES "include/*")

#生成可执行exe
add_executable(cmakeMulPackage ${SRC_FILES} ${INC_FILES})

#加载依赖的库
target_link_libraries(cmakeMulPackage
    AppModuleA
)

#将生成的依赖复制到可执行目录下
message("====================set copy final.cmake===================")
file(GLOB_RECURSE MY_COMPONENTS "${PROJECT_LIBRARY_DLL_DIR}/*")
if (WIN32 AND NOT DEFINED CMAKE_TOOLCHAIN_FILE)
    #拷贝依赖的DLL和exe
    foreach (MY_COMPONENT ${MY_COMPONENTS})
        add_custom_command(TARGET ${PROJECT_NAME} POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy "${MY_COMPONENT}" "${PROJECT_BINARY_DIR}")
        message(STATUS "COPY DLL ${MY_COMPONENT}")
    endforeach (MY_COMPONENT)
endif ()

main_app.h

//
// Created by zhe.xiao on 2023/12/15.
//

#pragma once
#include <iostream>

class MainApp
{
public:
    static void run();
};

main_app.cpp

//
// Created by zhe.xiao on 2023/12/15.
//

#include "main_app.h"
#include "module_a.h"

void MainApp::run()
{
    std::cout << "hello main" << "\n";
    ModuleA::run();
}

main.cpp

#include "main_app.h"

int main() {
    MainApp::run();

    return 0;
}

子模块

CMakeLists.txt

#定义头文件路径
include_directories(./include)

#把目录src和inc下面的所有文件作为变量存储
file(GLOB_RECURSE SRC_FILES "src/*")
file(GLOB_RECURSE INC_FILES "include/*")

#生成库
add_library(AppModuleA SHARED ${SRC_FILES} ${INC_FILES})

module_a.h

//
// Created by zhe.xiao on 2023/12/15.
//

#pragma once


class ModuleA
{
public:
    static void run();
};

module_a.cpp

//
// Created by zhe.xiao on 2023/12/15.
//

#include "module_a.h"
#include <iostream>

void ModuleA::run()
{
    std::cout << "ModuleA run" << "\n";
}

三方依赖的DLL和头文件

主要通过设置环境变量定义具体路径。
在这里插入图片描述

然后通过add_custom_command进行拷贝dll到生成路径

message("====================set copy final.cmake===================")
file(GLOB_RECURSE MY_COMPONENTS "${PROJECT_LIBRARY_DLL_DIR}/*")
if (WIN32 AND NOT DEFINED CMAKE_TOOLCHAIN_FILE)
    #拷贝依赖的DLL和exe
    foreach (MY_COMPONENT ${MY_COMPONENTS})
        add_custom_command(TARGET ${PROJECT_NAME} POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy "${MY_COMPONENT}" "${PROJECT_BINARY_DIR}")
        message(STATUS "COPY DLL ${MY_COMPONENT}")
    endforeach (MY_COMPONENT)
endif ()

文章来源:https://blog.csdn.net/andybegin/article/details/135022421
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。