Configura CMake

Uno script di build CMake è un file di testo normale a cui devi assegnare un nome CMakeLists.txt e include i comandi utilizzati da CMake per creare librerie C/C++. Se le origini native non dispongono già di una build CMake devi crearne uno personalmente e includere lo script CMake appropriato tramite comandi SQL. Per scoprire come installare CMake, consulta Installare e configurare NDK e CMake.

Questa sezione illustra alcuni comandi di base da includere nella build script per indicare a CMake quali origini utilizzare per creare libreria. Per saperne di più, leggi la documentazione ufficiale sui comandi CMake.

Dopo aver configurato un nuovo script di build CMake, devi configurare Gradle per includere il progetto CMake come dipendenza nella build, in modo che Gradle crei pacchettizza la tua libreria nativa con l'APK dell'app.

Nota: se il progetto utilizza ndk-build, non è necessario per creare uno script di build CMake. Puoi semplicemente configura Gradle per includere il progetto esistente della libreria nativa fornendo un percorso Android.mk.

Creare uno script di build CMake

Per creare un file di testo normale da utilizzare come script di build CMake, procedi nel seguente modo:

  1. Apri il riquadro Progetto dal lato sinistro dell'IDE e seleziona la Vista Progetto dal menu a discesa.
  2. Fai clic con il tasto destro del mouse sulla directory principale di your-module e seleziona Nuovo > File.

    Nota:puoi creare lo script di compilazione in qualsiasi posizione. Tuttavia, quando configuri lo script di build, i percorsi dell'origine nativa i file e le librerie sono relativi alla posizione dello script di build.

  3. Inserisci "CMakeLists.txt" come nome file e fai clic su OK.

Ora puoi configurare lo script di build aggiungendo i comandi CMake. Per indicare CMake per creare una libreria nativa da codice sorgente nativo, aggiungi i comandi cmake_minimum_required() e add_library() al tuo script di build:

# Sets the minimum version of CMake required to build your native library.
# This ensures that a certain set of CMake features is available to
# your build.

cmake_minimum_required(VERSION 3.4.1)

# Specifies a library name, specifies whether the library is STATIC or
# SHARED, and provides relative paths to the source code. You can
# define multiple libraries by adding multiple add_library() commands,
# and CMake builds them for you. When you build your app, Gradle
# automatically packages shared libraries with your APK.

add_library( # Specifies the name of the library.
             native-lib

             # Sets the library as a shared library.
             SHARED

             # Provides a relative path to your source file(s).
             src/main/cpp/native-lib.cpp )

Suggerimento:in modo simile a come puoi chiedere a CMake di creare una libreria nativa di origine, puoi utilizzare . add_executable() per indicare a CMake di creare invece eseguibile dai file di origine. Tuttavia, la creazione di eseguibili le origini native sono facoltative e la creazione di librerie native da pacchettizzare L'APK soddisfa la maggior parte dei requisiti di progetto.

Quando aggiungi un file sorgente o una libreria allo script di build CMake utilizzando add_library(), Android Studio mostra anche i file di intestazione associati nella vista Progetto dopo aver sincronizzato il progetto. Tuttavia, per consentire a CMake di individuare i file di intestazione durante la compilazione, aggiungi il comando include_directories() a CMake script di compilazione e specifica il percorso delle tue intestazioni:

add_library(...)

# Specifies a path to native header files.
include_directories(src/main/cpp/include/)

La convenzione utilizzata da CMake per assegnare un nome al file della tua raccolta è la seguente:

liblibrary-name.so

Ad esempio, se specifichi "native-lib" come nome della tua libreria condivisa nello script di build, CMake crea un file denominato libnative-lib.so. Tuttavia, quando carichi questa libreria nel tuo Nel codice Java o Kotlin, utilizza il nome specificato nello script di build CMake:

Kotlin

companion object {
    init {
        System.loadLibrary("native-lib");
    }
}

Java

static {
    System.loadLibrary("native-lib");
}

Nota: se rinomini o rimuovi una libreria nella build CMake devi pulire il progetto prima che Gradle applichi le modifiche rimuove la versione precedente della libreria dall'APK. Per pulire progetto, seleziona Crea > Cancella progetto dalla barra dei menu.

Android Studio aggiunge automaticamente i file di origine e le intestazioni gruppo cpp nel riquadro Progetto. Utilizzando più comandi add_library(), puoi definire altre impostazioni per creare le librerie di CMake da altri file di origine.

Aggiungi API NDK

Android NDK fornisce un insieme di API e librerie native che potresti trovare utile. Puoi utilizzare una qualsiasi di queste API includendo le librerie NDK nella libreria CMakeLists.txt.

Le librerie NDK predefinite esistono già sulla piattaforma Android, quindi devi crearle o pacchettizzarle nell'APK. Poiché le librerie NDK fanno già parte del percorso di ricerca di CMake, non occorre neppure specificare della libreria nell'installazione NDK locale, devi solo fornire a CMake il nome della libreria che vuoi utilizzare e collegarla rispetto alla tua libreria nativa.

Aggiungi il comando find_library() alla tua build CMake per individuare una libreria NDK e memorizzare il relativo percorso come variabile. Utilizzi questa variabile per fare riferimento alla libreria NDK in altre parti dello script di build. L'esempio seguente individua la libreria di supporto dei log specifica per Android e archivia il proprio percorso in log-lib:

find_library( # Defines the name of the path variable that stores the
              # location of the NDK library.
              log-lib

              # Specifies the name of the NDK library that
              # CMake needs to locate.
              log )

Affinché la tua libreria nativa possa chiamare le funzioni in log di archiviazione, devi collegare le librerie utilizzando il comando target_link_libraries() in il tuo script di build CMake:

find_library(...)

# Links your native library against one or more other native libraries.
target_link_libraries( # Specifies the target library.
                       native-lib

                       # Links the log library to the target library.
                       ${log-lib} )

NDK include anche alcune librerie come codice sorgente che devi creare e collegalo alla tua libreria nativa. Puoi compilare il codice sorgente in un libreria nativa utilizzando il comando add_library() in CMake di compilazione. Per fornire un percorso alla libreria NDK locale, puoi utilizzare il metodo Variabile di percorso ANDROID_NDK, utilizzata automaticamente da Android Studio che definisce automaticamente.

Il seguente comando indica a CMake di creare android_native_app_glue.c, che gestisce NativeActivity degli eventi del ciclo di vita e input tocco, in una libreria statica e native-lib:

add_library( app-glue
             STATIC
             ${ANDROID_NDK}/sources/android/native_app_glue/android_native_app_glue.c )

# You need to link static libraries against your shared native library.
target_link_libraries( native-lib app-glue ${log-lib} )

Aggiungi altre librerie predefinite

Aggiungere una libreria predefinita è simile a specificare un'altra libreria nativa per CMake per creare. Tuttavia, poiché la libreria è già stata creata, dovrai utilizzare il flag IMPORTED per indicare a CMake che Vuoi importare la libreria nel tuo progetto:

add_library( imported-lib
             SHARED
             IMPORTED )

Devi quindi specificare il percorso della libreria utilizzando il metodo Comando set_target_properties() come come mostrato di seguito.

Alcune librerie forniscono pacchetti separati per architetture CPU specifiche oppure Application Binary Interfaces (ABI) e e organizzarli in directory separate. Questo approccio aiuta le librerie di alcune architetture della CPU, consentendo allo stesso tempo di usare o versioni successive della libreria. Aggiunta di più versioni ABI di una libreria allo script di build CMake, senza dover scrivere più comandi ogni versione della libreria, puoi usare il percorso ANDROID_ABI . Questa variabile utilizza un elenco di ABI predefinite supportate dall'NDK o un elenco filtrato di ABI che . configurare manualmente Gradle da utilizzare. Ad esempio:

add_library(...)
set_target_properties( # Specifies the target library.
                       imported-lib

                       # Specifies the parameter you want to define.
                       PROPERTIES IMPORTED_LOCATION

                       # Provides the path to the library you want to import.
                       imported-lib/src/${ANDROID_ABI}/libimported-lib.so )

Affinché CMake possa individuare i file di intestazione durante la compilazione, è necessario utilizzare il comando include_directories() e includi il percorso file di intestazione:

include_directories( imported-lib/include/ )

Nota:se vuoi creare un pacchetto per una libreria predefinita che non sia una dipendenza in tempo di build, ad esempio, quando aggiungi una libreria predefinita che della dipendenza di imported-lib, non devi eseguire seguendo le istruzioni per collegare la libreria.

Per collegare la libreria predefinita alla tua libreria nativa, aggiungila alla Comando target_link_libraries() nello script di build CMake:

target_link_libraries( native-lib imported-lib app-glue ${log-lib} )

Per pacchettizzare la libreria predefinita nell'APK, devi: configurare manualmente Gradle con il blocco sourceSets per includi il percorso del file .so. Dopo aver creato l'APK, puoi verificare quali librerie dei pacchetti Gradle nel tuo APK utilizzando Strumento di analisi APK.

Includi altri progetti CMake

Se vuoi creare più progetti CMake e includerne gli output nel tuo progetto Android, puoi utilizzare un file CMakeLists.txt come script di build CMake di primo livello (che è quello che link a Gradle) e aggiungi altri progetti CMake come dipendenze di quella build lo script. Il seguente script di build CMake di primo livello utilizza Comando add_subdirectory() per specificare un altro file CMakeLists.txt come dipendenza della build, quindi si collega rispetto al suo output, proprio come farebbe con qualsiasi altra libreria predefinita.

# Sets lib_src_DIR to the path of the target CMake project.
set( lib_src_DIR ../gmath )

# Sets lib_build_DIR to the path of the desired output directory.
set( lib_build_DIR ../gmath/outputs )
file(MAKE_DIRECTORY ${lib_build_DIR})

# Adds the CMakeLists.txt file located in the specified directory
# as a build dependency.
add_subdirectory( # Specifies the directory of the CMakeLists.txt file.
                  ${lib_src_DIR}

                  # Specifies the directory for the build outputs.
                  ${lib_build_DIR} )

# Adds the output of the additional CMake build as a prebuilt static
# library and names it lib_gmath.
add_library( lib_gmath STATIC IMPORTED )
set_target_properties( lib_gmath PROPERTIES IMPORTED_LOCATION
                       ${lib_build_DIR}/${ANDROID_ABI}/lib_gmath.a )
include_directories( ${lib_src_DIR}/include )

# Links the top-level CMake build output against lib_gmath.
target_link_libraries( native-lib ... lib_gmath )

Chiama CMake dalla riga di comando

Utilizza il comando seguente per chiamare CMake e generare un progetto Ninja all'esterno di Android Studio:

cmake
-Hpath/to/cmakelists/folder
-Bpath/to/generated/ninja/project/debug/ABI
-DANDROID_ABI=ABI                               // For example, arm64-v8a
-DANDROID_PLATFORM=platform-version-string      // For example, android-16
-DANDROID_NDK=android-sdk/ndk/ndk-version
-DCMAKE_TOOLCHAIN_FILE=android-sdk/ndk/ndk-version/build/cmake/android.toolchain.cmake
-G Ninja

Questo comando genererà il progetto Ninja che può essere eseguito per creare Librerie eseguibili di Android (.so file). Il valore CMAKE_TOOLCHAIN_FILE è necessaria per utilizzare l'assistenza CMake di NDK. Per CMake 3.21 o versioni successive, il software In alternativa, è possibile utilizzare il supporto NDK, ma è necessario utilizzare un gruppo diverso di variabili come descritto nella documentazione Cross Compiling for Android di CMake.