Как настроить CMake для создания приложения для iPhone - PullRequest
24 голосов
/ 05 мая 2009

Это тесно связано с моим предыдущим вопросом , который касался использования CMake для создания статической библиотеки на iPhone. Я получил это на работу, установив CMAKE_OSX_SYSROOT.

Однако это не работает для создания приложения. Мой CMakeLists.txt выглядит так:

project(TEST)

set(CMAKE_OSX_SYSROOT iphoneos2.2.1)
set(CMAKE_OSX_ARCHITECTURES "$(ARCHS_STANDARD_32_BIT)")
set(CMAKE_EXE_LINKER_FLAGS
"-framework Foundation -framework OpenGLES -framework AudioToolbox -framework CoreGraphics -framework QuartzCore -framework UIKit -framework OpenAL"
)

set(SRC --my files--)

add_executable(iphone-test MACOSX_BUNDLE ${SRC})

Несколько заметок:

  • Я явно даю опцию связывания -framework, потому что find_library не работал для всех фреймворков (он нашел большинство из них, но не OpenGLES). Я не понимаю почему, так как они все в одной папке ${SDK}/System/Library/Frameworks. Это заставляет меня поверить, что я что-то делал не так, но я не знаю, что.
  • Я добавил MACOSX_BUNDLE к команде add_executable, чтобы сгенерированный тип продукта был com.apple.product-type.application вместо com.apple.product-type.tool, которого, по-видимому, нет в iPhone.

В любом случае, приложение правильно компилируется и связывается, но когда я запускаю его в симуляторе, я получаю ужас

Failed to launch simulated application: Unknown error.

Существует множество сообщений об этой проблеме в google и stackoverflow, но все решения включают очистку или создание нового проекта и перемещение файлов; но я собираю свежую копию после того, как CMake выполнит свою работу, поэтому ничего из этого не применимо.

Я нашел эту ветку в списке рассылки CMake, но он только сообщает об успешном построении библиотеки, а затем прекращается.

Ответы [ 3 ]

42 голосов
/ 10 июня 2009

Я наконец-то понял, как это сделать. Вот как выглядит мой CMakeLists.txt файл:

project(test)
set(NAME test)

file(GLOB headers *.h)
file(GLOB sources *.cpp)

set(CMAKE_OSX_SYSROOT iphoneos2.2.1)
set(CMAKE_OSX_ARCHITECTURES $(ARCHS_STANDARD_32_BIT))
set(CMAKE_CXX_FLAGS "-x objective-c++")
set(CMAKE_EXE_LINKER_FLAGS
    "-framework AudioToolbox -framework CoreGraphics -framework QuartzCore -framework UIKit"
)
link_directories(\${HOME}/\${SDKROOT}/lib)

set(MACOSX_BUNDLE_GUI_IDENTIFIER "com.mycompany.\${PRODUCT_NAME:identifier}")
set(APP_TYPE MACOSX_BUNDLE)

add_executable(${NAME}
    ${APP_TYPE}
    ${headers}
    ${sources}
)

target_link_libraries(${NAME}
    # other libraries to link
)

# code signing
set_target_properties(${NAME} PROPERTIES XCODE_ATTRIBUTE_CODE_SIGN_IDENTITY "iPhone Developer: My Name")

Очевидно, замените mycompany на название вашей компании и замените My Name на свое имя. Я обнаружил, что очень полезно добавить каталог ссылок \${HOME}/\${SDKROOT}/lib, как указано выше, так что если ваше приложение ссылается на статическую библиотеку (особенно универсальную (не iPhone)), вы можете создавать отдельные библиотеки iPhoneOS и iPhoneSimulator и легко ссылаться на правильный, вместо того, чтобы беспокоиться об универсальном бинарном файле.

Кроме того, Xcode, похоже, неправильно добавляет ресурсы при сборке проекта с использованием CMake, поэтому я добавил этот фрагмент в файл CMakeLists.txt. Он копирует всю папку /data в мою папку ресурсов (как если бы я добавил «синюю» ссылку на папку в XCode).

# copy resource phase

set(APP_NAME \${TARGET_BUILD_DIR}/\${FULL_PRODUCT_NAME})
set(RES_DIR ${test_SOURCE_DIR}/data)
add_custom_command(
    TARGET ${NAME}
    POST_BUILD
    COMMAND /Developer/Library/PrivateFrameworks/DevToolsCore.framework/Resources/pbxcp -exclude .DS_Store -exclude CVS -exclude .svn -resolve-src-symlinks ${RES_DIR} ${APP_NAME}
)
8 голосов
/ 31 октября 2009

Для каркасов я нашел это сообщение http://www.mail-archive.com/cmake@cmake.org/msg24659.html Я собрал достаточно информации для этого:

SET(TARGETSDK iPhoneOS3.1.2.sdk)
SET(CMAKE_OSX_SYSROOT /Developer/Platforms/iPhoneOS.platform/Developer/SDKs/${TARGETSDK})
macro(ADD_FRAMEWORK fwname appname)
    find_library(FRAMEWORK_${fwname}
        NAMES ${fwname}
        PATHS ${CMAKE_OSX_SYSROOT}/System/Library
        PATH_SUFFIXES Frameworks
        NO_DEFAULT_PATH)
    if( ${FRAMEWORK_${fwname}} STREQUAL FRAMEWORK_${fwname}-NOTFOUND)
        MESSAGE(ERROR ": Framework ${fwname} not found")
    else()
        TARGET_LINK_LIBRARIES(${appname} ${FRAMEWORK_${fwname}})
        MESSAGE(STATUS "Framework ${fwname} found at ${FRAMEWORK_${fwname}}")
    endif()
endmacro(ADD_FRAMEWORK)

Вместо установки CMAKE_EXE_LINKER_FLAGS теперь я делаю:

ADD_FRAMEWORK(AudioToolbox MyApp)
ADD_FRAMEWORK(CoreGraphics MyApp)
ADD_FRAMEWORK(QuartzCore MyApp)
ADD_FRAMEWORK(UIKit MyApp)

Это работает и для OpenGLES.

1 голос
/ 08 июля 2009

Последние версии CMake передают файлы .m и .mm в компилятор C ++, который определяет язык через расширение, поэтому вам не нужно явно добавлять «-xjective-c ++» к флагам.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...