Pregunta

Hola stackoverflowers :)

Si construyo un proyecto de muestra Qt/qmake (en mi caso el "reloj analogo"ejemplo) e implementarlo en un dispositivo con iOS 7.1, todo va bien:la aplicación se ejecuta perfectamente en el dispositivo.Chapeau: la gente de digia hizo un trabajo formidable para integrar la cadena de herramientas de iOS en su flujo de trabajo Qt.

Sin embargo, si traduzco el proyecto qmake a un proyecto CMake, las cosas ya no van tan bien.Adjunté el ejemplo de reloj analógico de la versión Qt-5.3.1 (ver más abajo) donde agregué un CMakeLists.txt y un script que ejecuta CMake para generar un proyecto XCode para iOS.El proyecto compila e incluso vincula (tuve que agregar algunas bibliotecas de vínculos adicionales, consulte el archivo fuente de CMake).Hurra.

Pero aquí está la trampa:La aplicación falla en tiempo de ejecución y muestra el siguiente mensaje de error:

Error:No se pudo cargar el complemento de plataforma "ios"

Como comentario en este El hilo indica que uno tiene que "forzar la carga" de libqios a través de la configuración del proyecto.Hacer esto no mejoró mucho la situación, solo cambió el mensaje de error a:

Error:Está creando QApplication antes de llamar a UIApplicationMain.Si está escribiendo una aplicación iOS nativa, y solo desea usar QT para partes de la aplicación, un buen lugar para crear Qapplication es desde 'ApplicationDidFinishLaunching' dentro de su delegado UIAPplication.

Tengo dos preguntas:

  • ¿Alguien tiene una idea de cuál es el problema con los errores de tiempo de ejecución?Sé que qmake (y las mkspecs de ios correspondientes) hacen bastante magia.¿Pero cómo traducir eso a CMake?
  • ¿Por qué tengo que vincular varias bibliotecas (harfbuzzng, qios, libpng y varios marcos de iOS) manualmente a mi destino?¿No debería find_package(Qt5...) hacer este trabajo por mí?

Aquí es el enlace a un archivo zip que contiene mi proyecto Qt-CMake.La versión de Qt que estoy usando es Qt-5.3.1 para iOS.

Editar:Descubrí que la muestra de qmake no funciona así si la arrancas de la estructura de carpetas de ejemplos de Qt.Mire el ejemplo de Qt directamente:ruta/a/Qt/examples/widgets/widgets/analogclock.

¿Fue útil?

Solución

Después de unas horas de investigar, encontré una manera de crear un proyecto CMake para mi aplicación Qt para iOS.Las sugerencias clave las obtuve a través de Google y al verificar el resultado generado por qmake.Encontré los scripts que realmente hacen toda la magia y apliqué partes de ellos a mis fuentes de CMake.

Esta es la receta que funcionó para mí.Para completar, agregué también los pasos que ya conocía cuando publiqué la pregunta anterior:

  • Introduzca CMake en la cadena de herramientas de iOS.Consulte cmake/toolchain/ios.toolchain.cmake de mi proyecto de muestra.Establece varias propiedades de CMake y busca las herramientas y marcos necesarios.(Ya no recuerdo de dónde saqué ese archivo, pero también se usa en varios otros proyectos si lo busca en Google). Debe pasar este archivo de configuración como argumento a CMake (ver más abajo).

  • Establezca varias propiedades de destino de su ejecutable para convertirlo en un paquete de aplicaciones (iOS).Debería quedar claro.Tenga en cuenta que hay una plantilla Info.plist.in que CMake completará.

  • Arreglar 1:Vincule las bibliotecas y los marcos que faltan a la aplicación manualmente en CMake.Por alguna razón, find_package(Qt5 ...) no devuelve una lista completa de dependencias.Sin embargo, es muy probable que me esté perdiendo algo aquí.

  • Arreglar 2:Asegúrese de forzar la carga de libqios para evitar el mensaje de error sobre el complemento de iOS que falta.En CMake:

    set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -force_load ${YOUR_QT_ROOT_PATH}/plugins/platforms/libqios.a" )

  • Arreglar 3:Elimine la clave del guión gráfico en Info.plist.in.Este paso no lo entiendo en detalle.El medio se inspiró en este publicar en stackoverflow.

    <key>UIMainStoryboardFile</key> <string>main</string>

  • Arreglar 4:Y ahora la guinda del pastel:para iOS tienes que cambiar el nombre de la función main() con una versión con formato "C" correspondiente.Aparentemente, Qt viene con su propio main punto de entrada y cambia el nombre del que usted escribió como qtmn().Esta magia qmake se realiza mediante este script:su/qt/root/path/mkspecs/macx-ios-clang/rename_main.sh.No entiendo en detalle la mecánica completa detrás de esto.En mi caso, me pareció bien cambiar el nombre de la firma de la función principal:

    // Replace... int main(int argc, char *argv[])

    // ... with this line: extern "C" int qtmn(int argc, char *argv[])

Aquí Es nuevamente el mismo proyecto al que me refería en la pregunta, esta vez con las correcciones aplicadas desde arriba.Para construir este proyecto simplemente llame build_ios.sh, y abra el archivo xcodeproj que se crea en la carpeta de compilación.

Nota:Las suposiciones de trabajo son que hay disponible una versión correcta de XCode (5.1.1 en mi caso) y que usted posee una identidad de firma válida (¡cámbiela en CMakeLists.txt!).Además, en mi proyecto de muestra (ver más abajo), asumo que OpenCV creado para iOS está disponible.Lo necesitaba para solucionar un problema del vinculador:Faltaban algunos objetos en libpng que se envían con OpenCV.

Espero que esto haya sido útil.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top