我想构建一个使用 OpenCascade 的项目。我还想构建所有的库。这取决于 freetype、tcl 和 tk。所以我也想建造所有这些。 我正在努力思考如何正确地做到这一点。我正在使用 Windows,如果这很重要的话。因此,在我开始摆弄试验/错误只是为了让它以某种方式工作之前,我想问一下使用 QtCreator 和 CMake 执行此操作的“正确”方法是什么。假设我的工具链已正确设置以构建 Qt 应用程序。
假设我的子文件夹结构是新下载的库:
mylibrary/main.cpp
occt-7_8_0/
freetype-2.10.4/
tcl8.5.0/
tk8.5.0/
我不想使用 VTK,我的 main.cpp 可能如下所示:
#include <TopoDS.hxx>
#include <BRepPrimAPI_MakeBox.hxx>
void makeBox(){
gp_Pnt gp1(0,0,0);
gp_Pnt gp2(1,1,1);
TopoDS_Solid box = BRepPrimAPI_MakeBox(gp1, gp2).Solid();
}
mylibrary/ 的 CMakesList.txt 是
message("=== Occt wrapper as a lib ===")
add_library(mylibrary_lib SHARED)
if (CMAKE_COMPILER_IS_GNUCXX)
add_compile_options(-Wa,-mbig-obj)
endif()
if (MSVC)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} /bigobj")
endif()
# find_package(<module>) uses <module>Config.cmake-file in <module>_DIR path
find_package(OpenCASCADE REQUIRED)
target_include_directories(mylibrary_lib PRIVATE "${OpenCASCADE_INCLUDE_DIR}") # OCC is needed
if(NOT OpenCASCADE_FOUND)
message(FATAL_ERROR "Cannot build the executable without OpenCASCADE. Please set the variable OpenCASCADE_DIR.")
else()
message(" found OpenCASCADE " ${OpenCASCADE_VERSION})
# include
target_include_directories(mylibrary_lib PUBLIC ${OpenCASCADE_INCLUDE_DIR})
message(" found OpenCASCADE_INCLUDE_DIR: ${OpenCASCADE_INCLUDE_DIR}" )
# link
target_link_libraries(mylibrary_lib PUBLIC ${OpenCASCADE_LIBRARIES}) # This should be private!
message(" found OpenCASCADE_LIBRARIES: ${OpenCASCADE_LIBRARIES}" )
endif()
target_sources(mylibrary_lib PUBLIC "./main.cpp")
更新: 我尝试按照建议使用 vcpkg 。这就是我所做的:
安装vcpkg: https://learn.microsoft.com/de-de/vcpkg/get_started/get-started?pivots=shell-cmd
vcpkg --install opencascade
设置 QtCreator
安装并激活插件“Vcpkg”
转到菜单编辑/首选项/CMake
重新启动QtCreator
在库的 src 目录中创建 vcpkg.json,内容如下:
{
"dependencies": [
"opencascade", "freetype", "tcl", "tk"
]
}
或者使用QtCreator中的向导: https://doc.qt.io/qtcreator/creator-how-to-create-vcpkg-manifest-files.html
在CMakesList.txt中添加:
find_package(OpenCASCADE CONFIG REQUIRED)
然后我清理了项目并单击“运行 CMake”。然而,输出是:
Could not find a package configuration file provided by "opencascade" with
any of the following names:
opencascadeConfig.cmake
opencascade-config.cmake
Add the installation prefix of "opencascade" to CMAKE_PREFIX_PATH or set
"opencascade_DIR" to a directory containing one of the above files. If
"opencascade" provides a separate development package or SDK, be sure it
has been installed.
CMakeCache.txt 包含
//Value Computed by CMake.
CMAKE_FIND_PACKAGE_REDIRECTS_DIR:STATIC=C:/path/to/build/build-projectname-Desktop_Qt_5_15_2_MSVC2015_64bit-Debug/CMakeFiles/pkgRedirects
但是该文件夹是空的。
如果您正在使用 CMake,我建议您遵循这些说明。 我个人更喜欢使用CMake用户界面,我用第三方库编译OCCT没有任何障碍。
问候!
我通过手动链接库“解决”了我的问题:
# How to use OCCT:
# - Compile OCCT using the provided CMakeLists.txt
# - Set the variable OpenCASCADE_DIR to the output directory of this build.
# - Separate debug/release builds will need separate directories.
# - Ensure the library directories are where to expect them. If not, change if for the
# compiler you are using.
# - Follow the error messages of CMake
if(NOT EXISTS "${OpenCASCADE_DIR}")
message(FATAL_ERROR "Set the variable OpenCASCADE_DIR to the output directory after building OCCT")
endif()
set(OpenCASCADE_VERSION "7.8.0")
# set(OpenCASCADE_DIR "${CMAKE_CURRENT_LIST_DIR}/../occt-vc143-64")
set(OpenCASCADE_INCLUDE_DIR "${OpenCASCADE_DIR}/inc")
set(OpenCASCADE_LIBRARIES
"TKernel" "TKMath" "TKG2d" "TKG3d" "TKGeomBase" "TKBRep" "TKGeomAlgo" "TKTopAlgo" "TKPrim" "TKBO" "TKShHealing" "TKBool" "TKHLR" "TKFillet" "TKOffset" "TKFeat" "TKMesh" "TKXMesh" "TKService" "TKV3d" "TKCDF" "TKLCAF" "TKCAF" "TKBinL" "TKXmlL" "TKBin" "TKXml" "TKStdL" "TKStd" "TKTObj" "TKBinTObj" "TKXmlTObj" "TKVCAF"
) # "TKOpenGl" "TKOpenGles" "TKMeshVS" "TKD3DHost" "TKDE" "TKXSBase" "TKDESTEP" "TKXCAF" "TKDEIGES" "TKDESTL" "TKDEVRML" "TKRWMesh" "TKDECascade" "TKBinXCAF" "TKXmlXCAF" "TKDEOBJ" "TKDEGLTF" "TKDEPLY" "TKDraw" "TKTopTest" "TKOpenGlTest" "TKViewerTest" "TKOpenGlesTest" "TKD3DHostTest" "TKXSDRAW" "TKDCAF" "TKXDEDRAW" "TKTObjDRAW" "TKQADraw" "TKIVtkDraw" "TKXSDRAWDE" "TKXSDRAWGLTF" "TKXSDRAWIGES" "TKXSDRAWOBJ" "TKXSDRAWPLY" "TKXSDRAWSTEP" "TKXSDRAWSTL" "TKXSDRAWVRML"
if( ("${CMAKE_BUILD_TYPE}" STREQUAL "Debug") OR ("${CMAKE_BUILD_TYPE}" STREQUAL "DEBUG"))
set(OpenCASCADE_LIBRARY_DIR "${OpenCASCADE_DIR}/win64/vc14/libd") # d for debug
set(OpenCASCADE_BINARY_DIR "${OpenCASCADE_DIR}/win64/vc14/bind") # d for debug
else()
set(OpenCASCADE_LIBRARY_DIR "${OpenCASCADE_DIR}/win64/vc14/lib")
set(OpenCASCADE_BINARY_DIR "${OpenCASCADE_DIR}/win64/vc14/bin")
endif()
set(OpenCASCADE_FOUND ON)
target_include_directories(occscene_lib PRIVATE "${OpenCASCADE_INCLUDE_DIR}")
if(NOT OpenCASCADE_FOUND)
message(FATAL_ERROR "Cannot build the executable without OpenCASCADE. Please set the variable OpenCASCADE_DIR.")
else()
message(" found OpenCASCADE " ${OpenCASCADE_VERSION})
if(NOT APP_USE_VTK)
list(REMOVE_ITEM OpenCASCADE_LIBRARIES TKIVtk)
endif()
# include
target_include_directories(occscene_lib PUBLIC ${OpenCASCADE_INCLUDE_DIR})
message(" found OpenCASCADE_INCLUDE_DIR: ${OpenCASCADE_INCLUDE_DIR}" )
# link
foreach(libname IN LISTS OpenCASCADE_LIBRARIES)
set(libpath "${OpenCASCADE_LIBRARY_DIR}/${libname}.lib")
if(EXISTS ${libpath})
target_link_libraries(occscene_lib PUBLIC ${libpath}) # This should be private!
else()
message("lib not found: ${libpath}")
endif()
endforeach()
# copy dlls
foreach(libname IN LISTS OpenCASCADE_LIBRARIES)
set(dllpath "${OpenCASCADE_BINARY_DIR}/${libname}.dll")
if(EXISTS ${dllpath})
file(COPY_FILE "${dllpath}" "${CMAKE_BINARY_DIR}/${libname}.dll" ONLY_IF_DIFFERENT)
# also the pdb for debugging
set(dllpath "${OpenCASCADE_BINARY_DIR}/${libname}.pdb")
if(EXISTS ${dllpath})
file(COPY_FILE "${dllpath}" "${CMAKE_BINARY_DIR}/${libname}.pdb" ONLY_IF_DIFFERENT)
endif()
else()
message("dll not found: ${dllpath}")
endif()
endforeach()
#find_library
#target_link_directories(occscene_lib PUBLIC ${OpenCASCADE_LIBRARY_DIR})
#target_link_libraries(occscene_lib PUBLIC ${OpenCASCADE_LIBRARIES}) # This should be private!
message(" found OpenCASCADE_LIBRARIES: ${OpenCASCADE_LIBRARIES}" )
endif()
我不知道这对任何人是否有帮助,我确信有更好的(=官方)方法来做到这一点。