2

在我的 MacOSX 上,我开发了一个使用 Qt 和 VTK 库的应用程序。我使用 CMake 生成 makefile。

现在我想在 Windows 上编译一个最终用户自包含的包,它应该可以在最终用户机器上工作,而不需要预先安装 Qt 或 VTK 库。我认为可以通过修改 CMakeLists.txt 文件来做到这一点,但网络搜索并没有为我指明正确的方向。

如何使用 CMake 为 Windows 制作可分发的包?

4

1 回答 1

2

我在自己的一个项目中所做的是编写一个小脚本,它将为我提供来自 VTK 的 cmake-variables 和 QT_LIBRARIES 变量的 .so 文件或 .dll 文件。

之后,我将这些 .dll 或 .so 文件添加到我的安装目标(下面的示例脚本),安装目标会将这些 .dll 或 .so 文件从 VTK_DIR 或 QTDIR 复制到 ${CMAKE_INSTALL_PREFIX}\bin。这与 CPack 兼容,因此您也可以编写一个小 cpack-script。

但是请注意,您需要在 Windows 上多一点才能获得最终用户自包含的包:您还需要“系统库”(msvcrt.dll、msvcrp.dll 或 mingwm10.dll、libstdc++.dll) . 例如看看这个问题

在 Windows 上,以下脚本从 VTK_DIR 中查找所有Vtk dll。

file( GLOB VTK_DLLS ${VTK_RUNTIME_LIBRARY_DIRS}/*.dll )
if( VTK_DLLS )
    foreach( Vtk_library ${VTK_DLLS} )
        # Add it to the list of 'desired' vtk-libraries for later installation
        list( APPEND Vtk_Install_Libraries ${Vtk_library} )
    endforeach( Vtk_library ${VTK_DLLS} )
    list( REMOVE_DUPLICATES Vtk_Install_Libraries )
    install( FILES ${Vtk_Install_Libraries} DESTINATION bin COMPONENT ThirdParty  )
endif( VTK_DLLS )

对于 Qt,脚本要长一些,因为我需要同时找到调试库和发布库。好的一面:它只搜索我请求的那些组件find_package( Qt4 ... )

# If Qt-4 was used, add the 'found' Qt-libraries to the Install-target.
if ( USE_QT )
    foreach( Qt_library ${QT_LIBRARIES} )
        # With QT_USE_IMPORTED_TARGETS, we should extract the dll info 
        # from the target properties
        get_target_property( Qt_lib_name ${Qt_library} IMPORTED_LOCATION )
        get_target_property( Qt_lib_name_debug ${Qt_library} IMPORTED_LOCATION_DEBUG )
        get_target_property( Qt_lib_name_release ${Qt_library} IMPORTED_LOCATION_RELEASE )

        # Initially assume the release dlls should be installed, but 
        # fall back to debug if necessary
        if ( Qt_lib_name_release AND EXISTS ${Qt_lib_name_release} )
            set( Qt_library_location ${Qt_lib_name_release} )
        elseif ( Qt_lib_name_debug AND EXISTS ${Qt_lib_name_debug} AND ENVIRONMENT_DEBUG )
            set( Qt_library_location ${Qt_lib_name_debug} )
        elseif ( Qt_lib_name AND EXISTS ${Qt_lib_name} )
            set( Qt_library_location ${Qt_lib_name} )
        endif ( Qt_lib_name_release AND EXISTS ${Qt_lib_name_release} )

        # Extract the filename part, without the lib-prefix or the .a or ..lib suffix
        get_filename_component( Qt_library_name ${Qt_library_location} NAME_WE )
        string( REGEX REPLACE "^lib(.*)" "\\1" Qt_library_name ${Qt_library_name} )

        set( Qt_shared_library ${QT_BINARY_DIR}/${Qt_library_name}.dll )
        if ( EXISTS ${Qt_shared_library} )
            # Add it to the list of 'desired' qt-libraries for later installation
            list( APPEND Qt_Install_Libraries ${Qt_shared_library} )
        else ( EXISTS ${Qt_shared_library} )
            message( WARNING "    could not find ${Qt_shared_library}" )
        endif ( EXISTS ${Qt_shared_library} )
    endforeach( Qt_library ${QT_LIBRARIES} )
    # When building against a static Qt, the list of Qt_Install_Libraries can be empty
    if ( Qt_Install_Libraries )
        list( REMOVE_DUPLICATES Qt_Install_Libraries )
        install( FILES ${Qt_Install_Libraries} DESTINATION bin COMPONENT ThirdParty )
    endif ( Qt_Install_Libraries )
endif ( USE_QT )    
于 2012-04-05T08:21:37.533 回答