How can I use get_dotapp_dir
?
I'm using cmake 3.6 and the Ninja generator (so not Xcode).
For example, suppose I have fred.c:
int main(void){return 0;}
And CMakeLists.txt: (the cmake version number is something I am stuck with)
cmake_minimum_required(VERSION 2.8.21.1)
include(BundleUtilities)
add_executable(fred MACOSX_BUNDLE fred.c)
set_target_properties(fred PROPERTIES BUNDLE TRUE)
get_dotapp_dir($<TARGET_FILE:fred> THING)
add_custom_command(TARGET fred POST_BUILD COMMAND ${CMAKE_COMMAND} -E echo ${THING} VERBATIM)
The output when I build is /Users/worktom/tests/cmake_get_dotapp_dir/build/fred.app/Contents/MacOS/fred
... which is not the bundle folder!
I sort-of expected this, because generator expressions are evaluated at build time, and not when cmake is running. But then... it seems to be sort-of working, because the target file's path has come through! What's going on? Is this supposed to work? When/how am I actually supposed to call get_dotapp_dir
?
(Having built the bundle, I want to copy additional files into it, and then on every build I want to copy the result into additional folders, none of which are related to the cmake projects I'm building. So it looks like I need the path in a form that can be passed into cmake -E
, as per my example.)
After hitting this problem on a second project last year, I ended up concluding that get_dotapp_dir
is just useless nowadays, makes little sense with cmake 3+, and is probably just something that's there for backwards compatibility.
If you can upgrade to cmake 3.9, there's a new generator expression that looks just the ticket: $<TARGET_BUNDLE_DIR:>
. Related SO question.
I haven't upgraded just yet, and I ended up managing to work around this. My project needed to know the bundle folder for two reasons:
Asset files that are loaded at runtime and need to be included in the bundle. What I did for this in the end was have the program find its EXE path at runtime, and load assets from folders relative to that path. Then the cmake build can just use $<TARGET_FILE_DIR:>
to decide where to put the files - somewhere in the bundle folder, but it doesn't matter exactly where.
This behaviour also makes sense for Windows, so no need for a separate code path.
Repo links, since this project is open source: copy files to places relative to EXE path, retrieve EXE path at runtime.
The .icns file that OS X uses to load the icons has to go in the Resources
folder. This can be arranged by including the file in the target's sources list, and configuring that file's package location property appropriately.
target_sources(b2 PRIVATE b2.icns)
set_source_files_properties(b2.icns PROPERTIES MACOSX_PACKAGE_LOCATION Resources)
The executable target needs to have its bundle icon file set up appropriately with something along the lines of set_target_properties(b2 PROPERTIES MACOSX_BUNDLE_ICON_FILE b2.icns)
.
Again, repo links: cmake stuff for OS X icns file.