Android студия, Gradle и NDK


153

Я очень новичок во всем этом Gradle и поддержке Android Studio. Мне удалось преобразовать мой проект Android в Gradle, используя опцию экспорта.

Но я ищу некоторую документацию или отправную точку, как интегрировать сборку NDK в процесс сборки gradle.

Если возможно, мне также нужен какой-то этап «после», который копирует двоичные файлы сборки (файлы .so) в каталог ресурсов.


Я разместил свой ответ в указанной ниже ссылке stackoverflow.com/questions/20900814/…
Ахмад Али Насир

24
Новые читатели: имейте в виду, что этот вопрос изначально задавался во время бета-тестирования Android Studio; ответ со временем изменился. Обратите внимание на версию Gradle, упомянутую в ответах, а также на то, когда ответы были фактически опубликованы.
Шон Бич

Если что-то действительно изменится, я отредактирую вопрос, чтобы отразить статус
plaisthos

Android Studio 1.3 на канальном канале полностью поддерживает NDK. Ссылка: tools.android.com/download/studio/canary/latest
Викасдип Сингх

18 июня 2015: Android Studio 1.3 Beta теперь доступна на бета-канале! Извините, эта сборка еще не содержит поддержку C / C ++; источник: tools.android.com/recent/androidstudio13betaavailable
fastr.de

Ответы:


85

Мы выпустили первую версию интеграции в качестве предварительного просмотра в 1.3: http://tools.android.com/tech-docs/android-ndk-preview

Интеграция останется предварительным просмотром даже после того, как 1.3 станет окончательным. Нет текущего ETA относительно того, когда он будет окончательным (по состоянию на 2015/07/10).

Более подробная информация здесь: http://tools.android.com/tech-docs/android-ndk-preview


2
Было бы здорово, если бы я мог использовать NDK и завершение команд с отладкой в ​​Android Studio (и с поддержкой Gradle)
powder366

1
@GREnvoy - Как настроить правильного NDK-компоновщика в Android-студии? Можете ли вы дать мне шаги? :)
Шраван

7
@DirtyBeach Почему это устарело? Все еще нет интеграции NDK в Studio. Мы работаем над этим, но пока нет ETA.
Ксавье Дюкрохет

2
Мои действия основывались на том, как я определял «интеграцию». Я понял, что это означает «способ использовать NDK с Gradle», который сейчас существует, хотя ни один из них не является фантастическим решением. Однако, основываясь на вашем комментарии, кажется, что ваша команда думает о том, что такое настоящая интеграция. Я отказываюсь от своего предыдущего заявления.
Шон Бич

2
Интеграция с NDK была анонсирована во время Google IO 2015. Она доступна в Android Studio 1.3 (предварительный просмотр можно скачать в ближайшее время. Я опубликую ссылку, когда она будет доступна).
Кипарис Франкенфельд

43

ОБНОВЛЕНИЕ: Android Studio с поддержкой NDK уже не доступен: http://tools.android.com/tech-docs/android-ndk-preview

Для сборки с помощью скрипта должно работать следующее решение:

Я использую свой сценарий сборки и добавил его в свой файл (кажется, для работы 0.8+): это, кажется, эквивалентно решению ниже (но выглядит лучше в файле Gradle):

 android {
    sourceSets {
        main {
            jniLibs.srcDirs = ['native-libs']
            jni.srcDirs = [] //disable automatic ndk-build
        }
    }
 }

К сожалению, сборка не завершится ошибкой, если каталог отсутствует или не содержит .soфайлов.


5
Это больше не работает с новой версией Android Studio, обходной путь?
powder366

@ powder366 Смотрите мой ответ.
Леандрос

2
Немного Groovy магии tasks.withType(com.android.build.gradle.tasks.PackageApplication) { it.jniFolders = [file("libs")] as Set }. Спасибо ребята за помощь!
trnl

Какая процедура для андроида Studio 0.8.9
Пандири Дипак

1
@plaisthos Большое спасибо за указание правильного направления! Вторая строка в скрипте gradle jni.srcDirs = [] //disable automatic ndk-buildочень важна, поскольку она не позволяет Android Studio перестраивать исходный код C / C ++. Я пытался понять это в течение двух дней, пока я не увидел ваш пост, и это решило мою проблему. Я действительно думаю, что сборка NDK лучше собирать отдельно с помощью только make-файла командной строки Android.mk, а не сценария gradle, поскольку C / C ++ создавался Makefile уже более 40 лет!
Тонга

40

С обновлением Android Studio до версии 1.0 поддержка набора инструментов NDK значительно улучшилась ( обратите внимание: пожалуйста, прочтите мои обновления в нижней части этого поста, чтобы узнать, как использовать новый экспериментальный плагин Gradle и Android Studio 1.5 ).

Android Studio и NDK достаточно хорошо интегрированы, так что вам просто нужно создать блок ndk {} в build.gradle вашего модуля и установить исходные файлы в каталог (module) / src / main / jni - и вы сделано!

Нет больше ndk-build из командной строки.

Я написал все об этом в своем блоге здесь: http://www.sureshjoshi.com/mobile/android-ndk-in-android-studio-with-swig/

Существенные моменты:

Здесь нужно знать две вещи. По умолчанию, если у вас есть внешние библиотеки, которые вы хотите загрузить в приложение Android, они по умолчанию ищутся в (module) / src / main / jniLibs. Вы можете изменить это, используя параметр sourceSets.main.jniLibs.srcDirs в build.gradle вашего модуля. Вам понадобится подкаталог с библиотеками для каждой целевой архитектуры (например, x86, arm, mips, arm64-v8a и т. Д.)

Код, который вы хотите скомпилировать по умолчанию с помощью цепочки инструментов NDK, будет расположен в (module) / src / main / jni и, как и выше, вы можете изменить его, установив sourceSets.main.jni.srcDirs в build.gradle вашего модуля.

и поместите это в build.gradle вашего модуля:

ndk {
  moduleName "SeePlusPlus" // Name of C++ module (i.e. libSeePlusPlus)
  cFlags "-std=c++11 -fexceptions" // Add provisions to allow C++11 functionality
  stl "gnustl_shared" // Which STL library to use: gnustl or stlport
}

Это процесс компиляции вашего кода C ++, оттуда вам нужно загрузить его и создать обертки - но, судя по вашему вопросу, вы уже знаете, как все это сделать, поэтому я не буду повторно хэшировать.

Кроме того, я разместил репозиторий Github этого примера здесь: http://github.com/sureshjoshi/android-ndk-swig-example

ОБНОВЛЕНИЕ: 14 июня 2015 г.

Когда выйдет Android Studio 1.3, должна быть улучшена поддержка C ++ через плагин JetBrains CLion. В настоящее время я предполагаю, что это позволит разрабатывать Java и C ++ из Android Studio; однако я думаю, что нам все еще нужно будет использовать раздел Gradle NDK, как я уже говорил выше. Кроме того, я думаю, что все еще будет необходимость писать файлы-оболочки Java <-> C ++, если только CLion не сделает это автоматически.

ОБНОВЛЕНИЕ: 5 января 2016 г.

Я обновил свой блог и репозиторий Github (в ветке разработки) для использования Android Studio 1.5 с последним экспериментальным плагином Gradle (0.6.0-alpha3).

http://www.sureshjoshi.com/mobile/android-ndk-in-android-studio-with-swig/ http://github.com/sureshjoshi/android-ndk-swig-example

Сборка Gradle для раздела NDK теперь выглядит следующим образом:

android.ndk {
    moduleName = "SeePlusPlus" // Name of C++ module (i.e. libSeePlusPlus)
    cppFlags.add("-std=c++11") // Add provisions to allow C++11 functionality
    cppFlags.add("-fexceptions")
    stl = "gnustl_shared" // Which STL library to use: gnustl or stlport
}

Кроме того, довольно удивительно, что Android Studio имеет автозаполнение для C ++ - сгенерированные Java обертки, использующие ключевое слово «native»:

Пример автозаполнения C ++ - Оболочка Java

Тем не менее, это не совсем радужно ... Если вы используете SWIG, чтобы обернуть библиотеку для автоматической генерации кода, а затем попытаетесь использовать автогенерацию нативного ключевого слова, он поместит код не в том месте в вашем Swig _wrap Файл .cxx ... Так что вам нужно переместить его в блок "extern C":

C ++ - Java-оболочка перемещена в правильное местоположение

ОБНОВЛЕНИЕ: 15 октября 2017 г.

Я был бы упущен, если бы не упомянул, что Android Studio 2.2 и выше имеет по существу «нативную» (без каламбура) поддержку для цепочки инструментов NDK через Gradle и CMake. Теперь, когда вы создаете новый проект, просто выберите поддержку C ++, и все готово.

Вам все еще нужно будет сгенерировать свой собственный код слоя JNI или использовать технику SWIG, о которой я упоминал выше, но поддержка C ++ в проекте Android теперь тривиальна.

Изменения в файле CMakeLists (где вы размещаете исходные файлы C ++) будут обнаружены Android Studio, и он автоматически перекомпилирует все связанные библиотеки.


1
положить * .so в (модуль) / src / main / jniLibs
fawkes

почему NDEBUG всегда устанавливается при использовании Android Studio, даже при отладочных сборках
pt123

35

В Google IO 2015 Google объявил о полной интеграции NDK в Android Studio 1.3.

Теперь он недоступен для предварительного просмотра и доступен всем: https://developer.android.com/studio/projects/add-native-code.html

Старый ответ: Gradle автоматически вызывает, ndk-buildесли у вас есть jniкаталог в источниках вашего проекта.

Это работает на Android Studio 0.5.9 (канарейка).

  1. Скачать НДК

  2. Либо добавить ANDROID_NDK_HOMEк вашей переменной окружения или добавить ndk.dir=/path/to/ndkк вашему local.propertiesв проекте Android Studio. Это позволяет Android-студии автоматически запускать ndk.

  3. Загрузите последние примеры проектов Gradle, чтобы увидеть пример проекта ndk. (Они внизу страницы). Хороший пример проекта есть ndkJniLib.

  4. Скопируйте gradle.buildиз примеров проектов NDK. Это будет выглядеть примерно так. Это gradle.buildсоздает разные apk для каждой архитектуры. Вы должны выбрать, какую архитектуру вы хотите использовать, используя build variantsпанель. панель вариантов сборки

    apply plugin: 'android'
    
    dependencies {
        compile project(':lib')
    }
    
    android {
        compileSdkVersion 19
        buildToolsVersion "19.0.2"
    
        // This actual the app version code. Giving ourselves 100,000 values [0, 99999]
        defaultConfig.versionCode = 123
    
        flavorDimensions "api", "abi"
    
        productFlavors {
            gingerbread {
                flavorDimension "api"
                minSdkVersion 10
                versionCode = 1
            }
            icecreamSandwich {
                flavorDimension "api"
                minSdkVersion 14
                versionCode = 2
            }
            x86 {
                flavorDimension "abi"
                ndk {
                    abiFilter "x86"
                }
                // this is the flavor part of the version code.
                // It must be higher than the arm one for devices supporting
                // both, as x86 is preferred.
                versionCode = 3
            }
            arm {
                flavorDimension "abi"
                ndk {
                    abiFilter "armeabi-v7a"
                }
                versionCode = 2
            }
            mips {
                flavorDimension "abi"
                ndk {
                    abiFilter "mips"
                }
                versionCode = 1
            }
            fat {
                flavorDimension "abi"
                // fat binary, lowest version code to be
                // the last option
                versionCode = 0
            }
        }
    
        // make per-variant version code
        applicationVariants.all { variant ->
            // get the version code of each flavor
            def apiVersion = variant.productFlavors.get(0).versionCode
            def abiVersion = variant.productFlavors.get(1).versionCode
    
            // set the composite code
            variant.mergedFlavor.versionCode = apiVersion * 1000000 + abiVersion * 100000 + defaultConfig.versionCode
        }
    
    }

Обратите внимание, что это будет игнорировать ваши файлы Android.mk и Application.mk. В качестве обходного пути вы можете указать gradle отключить atuomatic вызов ndk-build, а затем вручную указать каталог для источников ndk.

sourceSets.main {
    jniLibs.srcDir 'src/main/libs' // use the jni .so compiled from the manual ndk-build command
    jni.srcDirs = [] //disable automatic ndk-build call
}

Кроме того, вы, вероятно, захотите явно вызвать ndk-build в вашем скрипте сборки gradle, потому что вы просто отключили автоматический вызов.

task ndkBuild(type: Exec) {
   commandLine 'ndk-build', '-C', file('src/main/jni').absolutePath
}

tasks.withType(JavaCompile) {
    compileTask -> compileTask.dependsOn ndkBuild
}

Да. Но это работает только на платформах Unix и также ограничено, если вы более сложная, чем очень простая конфигурация / make-файлы ndk.
plaisthos

Да, он автоматически сгенерирует make-файлы для ограниченных вещей, которые вы можете установить в файле сборки gradle, однако есть обходной путь. Я добавил это в свой ответ.
Кипарис Франкенфельд

1
Вызов ndk-build будет работать только в командной строке, а не в Android Studio.
Кэмерон Лоуэлл Палмер

Хотя это не самый последний ответ, он, вероятно, будет наиболее точным. Обратите особое внимание на шаг 3: «Загрузите последние примеры проектов Gradle».
Шон Бич

4
Я использую этот хак вместо отключения src dir, чтобы я мог редактировать файлы c / c ++ внутри idetasks.all { task -> if (task.name.contains('Ndk')) task.enabled = false }
sherpya

23

Я обнаружил, что «gradle 1.11 com.android.tools.build:gradle:0.9.+» теперь поддерживает предварительную сборку ndk, вы можете просто поместить * .so в dir src / main / jniLibs. при сборке gradle упакует ндк в нужное место.

вот мой проект

Проект:
| --src
| - | --main
| - | - | --java
| - | - | --jniLibs
| - | - | - | --armeabi
| - | - | - | - | -. so файлы
| --libs
| - | --other.jar

18

Как сказал Ксавье, вы можете поместить свои предварительные сборки в / src / main / jniLibs /, если вы используете gradle 0.7.2+

взяты из: https://groups.google.com/d/msg/adt-dev/nQobKd2Gl_8/ctDp9viWaxoJ


Как мы можем увидеть образец, указанный в 0.7.2 ndkJniLib?
Райан Heitner

Полезно для использования библиотек, таких как SqlCipher
personne3000

16

На данный момент (Android Studio v0.8.6) все довольно просто. Вот шаги для создания приложения типа «Hello world»:

  1. Загрузите Android NDK и поместите корневую папку где-нибудь в здравом уме - возможно, там же, где и папка SDK.

  2. Добавьте следующее в ваш local.propertiesфайл: ndk.dir=<path-to-ndk>

  3. Добавьте следующее в свой файл build.gradle внутри defaultConfigзамыкания сразу после versionNameстроки:ndk { moduleName="hello-world" }

  4. В каталоге модуля приложения mainсоздайте новую папку с именем jni.

  5. В этой папке создайте файл с именем hello-world.c, которое вы видите ниже.

  6. Смотрите пример Activityкода ниже для примера того , как вызвать метод (или это функция?) В hello-world.c.


hello-world.c

#include <string.h>
#include <jni.h>

jstring
Java_me_mattlogan_ndktest_MainActivity_stringFromJNI(JNIEnv* env, jobject thiz)
{
    return (*env)->NewStringUTF(env, "Hello world!");
}

MainActivity.java

public class MainActivity extends Activity {

    static {
        System.loadLibrary("hello-world");
    }

    public native String stringFromJNI();

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        String testString = stringFromJNI();

        TextView mainText = (TextView) findViewById(R.id.main_text);
        mainText.setText(testString);
    }
}

build.gradle

apply plugin: 'com.android.application'

android {
    compileSdkVersion 20
    buildToolsVersion "20.0.0"

    defaultConfig {
        applicationId "me.mattlogan.ndktest"
        minSdkVersion 15
        targetSdkVersion 20
        versionCode 1
        versionName "1.0"

        ndk {
            moduleName "hello-world"
        }
    }
    buildTypes {
        release {
            runProguard false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }
}

dependencies {
    compile fileTree(dir: 'libs', include: ['*.jar'])
}

Найдите полный исходный код очень похожего приложения здесь (за исключением NDK).


Я делаю именно так, как указано в моем текущем проекте, но материал NDK все еще не создается. Любые идеи? Кажется, что он строит все остальное, но просто пропускает jni.
alice.harrison

@NannuoLei спасибо, я пытался, но у меня проблема с тем, что .so не генерируются. Все остальное работает, но когда я запускаю apkg в эмуляторе, он жалуется, что не может загрузить общий объект.
aaa90210

@ aaa90210 Ваш эмулятор основан на образе x86? По умолчанию NDK просто создает библиотеку ARMEABI. Если вы хотите создать образ x86, вы можете добавить эту строку в Application.mk: APP_ABI: = armeabi x86
Лео поддерживает Monica Cellio

1
это работало со мной. PS: кто видит этот ответ, не забудьте поменять Java_me_mattlogan_ndktest_MainActivity_stringFromJNIна свой :)
AbdulMomen عبدالمؤمن

8

Если вы работаете в Unix, последняя версия (0.8) добавляет ndk-build. Вот как это добавить:

android.ndk {
    moduleName "libraw"
}

Он ожидает найти JNI в 'src / main / jni', в противном случае вы можете определить его с помощью:

sourceSets.main {
    jni.srcDirs = 'path'
}

Начиная с 28 января 2014 года с версией 0.8 сборка не работает на Windows, вы должны отключить сборку с помощью:

sourceSets.main {
    jni.srcDirs = [] //disable automatic ndk-build call (currently broken for windows)
}

1
Есть ли документация по этой функции? Я не мог найти ни одного. На данный момент, кажется, полностью игнорировать мой Android.mk/Application.mk.
Плейстос

Я не нашел ни одного. Это, возможно, пробралось в сборку, наполовину испеченную. Я нахожусь на Windows, поэтому я могу только подтвердить, что это не удается при попытке вызвать сценарий Unix ndk-build. Не было бы никакой другой причины вызывать это, чтобы интегрировать нативную компиляцию в Gradle. Ты в юниксе?
Энтони


на самом деле он ожидает найти готовые * .so файлы в jniLibs.srcDirs
Alpine

Я бы не согласился, основываясь на том факте, что он вызывает сбой вызова ndk-build, что абсолютно не нужно, если для этого требуются встроенные библиотеки. Я не могу подтвердить, так как у меня сейчас нет времени на vm Linux.
Энтони

7

Элегантный обходной путь показан в https://groups.google.com/d/msg/adt-dev/nQobKd2Gl_8/Z5yWAvCh4h4J .

По сути, вы создаете jar, который содержит «lib / armeabi / yourlib.so», а затем включаете jar в сборку.


Да. Это хорошо работает, только если вы не часто меняете свой код. И вам придется включить двоичные файлы JAR в хранилище. В противном случае вы получите скрипт сборки, который создает флягу на лету.
Плейстос,

1
Я изменил пример Hello-JNI для Android с помощью простого скрипта bash, который обертывает ndk-build, генерирует .jars для каждого .soи помещает их в путь сборки gradle, чтобы облегчить эту боль. Проверьте это.
ДБРО

4

Хороший ответ, автоматизирующий упаковку готовых .soфайлов, дан в другом (закрытом) потоке . Чтобы это работало, мне пришлось изменить строку:

from fileTree(dir: 'libs', include: '**/*.so')

в:

from fileTree(dir: 'src/main/libs', include: '**/*.so') 

Без этого изменения .soфайлы не были найдены, поэтому задача их упаковки никогда не выполнялась бы.


Обновление: обратите внимание, что в более новых Android Studios (по крайней мере, в версии 1.5) встроенный код гораздо лучше включен, и нет необходимости выполнять эту отдельную задачу для упаковки вашего кода.
HYS

4

Ответ от @plaisthos сломался в последней версии Gradle, но есть еще способ сделать это. Создайте native-libsкаталог в корневом каталоге вашего проекта и скопируйте все эти библиотеки в этот каталог.

Добавьте следующие строки в ваш build.gradle. Строй и будь счастлив.

task copyNativeLibs(type: Copy) {
    from(new File(project(':<your project>').getProjectDir(), 'native-libs')) { include '**/*.so' }
    into new File(buildDir, 'native-libs')
}

tasks.withType(Compile) { compileTask -> compileTask.dependsOn copyNativeLibs }

clean.dependsOn 'cleanCopyNativeLibs'

3

Это код, который я использую для сборки с помощью Android-ndk из Gradle. Для этого добавьте ndk путь к каталогу в gradle.propertiesie. добавить ndkdir=/home/user/android-ndk-r9dи поставить все JNI файлов в папке nativeв , src/main/как вы можете видеть из кода размещены ниже. Это создаст банку с родными библиотеками, которые вы можете использовать как обычноSystem.loadLibrary("libraryname");

dependencies {
    compile fileTree(dir: "$buildDir/native-libs", include: '*.jar')
}

task ndkBuild(type: Exec) {
    commandLine "$ndkdir/ndk-build", "--directory", "$projectDir/src/main/native", '-j', Runtime.runtime.availableProcessors(),
            "APP_PLATFORM=android-8",
            "APP_BUILD_SCRIPT=$projectDir/src/main/native/Android.mk",
            "NDK_OUT=$buildDir/native/obj",
            "NDK_APP_DST_DIR=$buildDir/native/libs/\$(TARGET_ARCH_ABI)"
}

task nativeLibsToJar(type: Jar, description: 'create a jar with native libs') {
    destinationDir file("$buildDir/native-libs")
    baseName 'native-libs'
    from fileTree(dir: "$buildDir/native/libs", include: '**/*.so')
    into 'lib/'
}

tasks.withType(JavaCompile) {
    compileTask -> compileTask.dependsOn nativeLibsToJar
}

nativeLibsToJar.dependsOn 'ndkBuild'

3

Я использовал следующий код для компиляции собственных библиотек Dropbox, я использую Android Studio v1.1.

task nativeLibsToJar(type: Zip) {
    destinationDir file("$buildDir/native-libs")
    baseName 'native-libs'
    extension 'jar'
    from fileTree(dir: 'src/main/libs', include: '**/*.so')
    into 'lib/'
}

tasks.withType(JavaCompile) {
    compileTask -> compileTask.dependsOn(nativeLibsToJar)
}


1

Чтобы подробнее рассказать о том, что сказал Наксос (спасибо Наксосу за то, что он направил меня в правильном направлении!), Я многому научился из недавно выпущенных примеров NDK и разместил ответ на аналогичный вопрос здесь.

Как настроить NDK с помощью плагина Android Gradle 0.7

Этот пост содержит полную информацию о связывании встроенных библиотек в ваше приложение для различных архитектур, а также информацию о том, как добавить поддержку NDK непосредственно в сценарий build.gradle. По большей части вам больше не нужно обходить zip и копировать.


1

Вот шаги, которые я использовал, чтобы заставить NDK работать в моем проекте Android Studio. Я использовал этот учебник, чтобы помочь мне https://software.intel.com/en-us/videos/using-the-ndk-with-android-studio

Чтобы использовать NDK, вы должны добавить строку NDK в local.properties. Так что под свой sdk.dir добавь

ndk.dir=C\:\\MyPathToMyNDK\ndk

В моих приложениях build.gradle у меня есть следующий код

        ndk {
            moduleName "myLib"
            ldLibs "log"
            stl "gnustl_shared"
            cFlags "-std=c++11 -frtti -fexceptions -pthread"
        }

moduleName - это имя, которое вы хотите дать своему собственному коду. Я верю, что так будет называться разделяемая библиотека. ldLibs позволяет мне войти в LogCat, stl - это stl, который вы хотите импортировать. Есть много вариантов, таких как Eclipse NDK. ( http://www.kandroid.org/ndk/docs/CPLUSPLUS-SUPPORT.html )

cFlags - все еще определенное количество черной магии для меня. Я не нашел хорошего источника для всех вариантов и того, что они дают мне. Ищите в StackOverflow все, что вам нужно, именно там я его и нашел. Я знаю, что c ++ 11 позволяет мне использовать новый стандарт c ++ 11.

Вот пример того, как я вхожу в LogCat из родного кода

__android_log_print(ANDROID_LOG_DEBUG, "TestApp", "Adding - String %d has a field name of %s and a value of %s", i, lKeyUTF8.c_str(), lValueUTF8.c_str());

1

настроить проект в Android Studio из Eclipse: вы должны импортировать проект Eclipse ndk в Android Studio без экспорта в Gradle, и это работает, также вам нужно добавить путь ndk в local.properties , если показывает ошибку, затем добавьте

sourceSets.main {
        jniLibs.srcDir 'src/main/libs' 
        jni.srcDirs = [] //disable automatic ndk-build callenter code here
    }

в build.gradle файл затем создать JNI папку и файл , используя терминал и запустить его будет работать


1
Смотрите, смотрите мой собственный ответ. Это обходной путь, который я сейчас использую, но на самом деле это не решение.
plaisthos

1

Теперь, когда Android Studio находится в стабильном канале, довольно просто запустить образцы android-ndk . Эти примеры используют экспериментальный плагин ndk и являются более новыми, чем те, на которые есть ссылки в онлайн-документации Android NDK. Как только вы узнаете, что они работают, вы можете изучить файлы build.gradle, local.properties и gradle-wrapper.properties и соответствующим образом изменить свой проект. Ниже приведены шаги, чтобы заставить их работать.

  1. Перейдите в раздел «Настройки», «Внешний вид и поведение», «Системные настройки», Android SDK, выберите вкладку «Инструменты SDK» и проверьте Android NDK версии 1.0.0 в нижней части списка. Это загрузит NDK.

  2. Укажите местоположение недавно загруженного NDK. Обратите внимание, что он будет помещен в каталог sdk / ndk-bundle. Для этого выберите «Файл», «Структура проекта», «Расположение SDK» (слева) и укажите путь в разделе «Расположение Android NDK». Это добавит запись ndk в local.properties, подобную этой:

    Mac / Linux: ndk.dir = / Android / sdk / ndk-bundle
    Windows: ndk.dir = C: \ Android \ sdk \ ndk-bundle

Таким образом, я успешно собрал и развернул все проекты в хранилище, кроме gles3gni, native-codec и builder. Я использую следующее:

Android Studio 1.3 build AI-141.2117773 Примеры
Android-ndk, опубликованные 28 июля 2015 г. (ссылка выше)
SDK Tools 24.3.3
NDK r10e, извлеченный в C: \ Android \ sdk \ ndk-bundle
Gradle 2.5
Gradle plugin 0.2.0
Windows 8.1 64 bit


1

NDK Builds и Gradle (базовый уровень)

Как правило, сборка с использованием NDK так же проста, как и правильное указание пути ndkBuild к Android.mk или пути cmake к CMakeLists.txt. Я рекомендую CMake поверх более старого Android.mk, потому что поддержка C / C ++ в Android Studio основана на CLion и использует CMake в качестве формата проекта. По моему опыту, это привело к тому, что среда IDE стала более отзывчивой в более крупных проектах. Все скомпилированные в вашем проекте будут автоматически собраны и скопированы в APK.

apply plugin: 'com.android.library'

android {
    compileSdkVersion 19
    buildToolsVersion "25.0.2"

    defaultConfig {
        minSdkVersion 19
        targetSdkVersion 19

        ndk {
            abiFilters 'armeabi', 'armeabi-v7a', 'x86'
            // 64-bit support requires an Android API level higher than 19; Namely 21 and higher
            //abiFilters 'armeabi', 'armeabi-v7a', 'arm64-v8a', 'x86', 'x86_64'
        }

        externalNativeBuild {
            cmake {
                arguments '-DANDROID_TOOLCHAIN=clang',
                        '-DANDROID_PLATFORM=android-19',
                        '-DANDROID_STL=gnustl_static',
                        '-DANDROID_ARM_NEON=TRUE'

            }
        }
    }

    externalNativeBuild {
        cmake {
            path 'src/main/jni/CMakeLists.txt'
        }
    }
}

dependencies {
    compile fileTree(dir: 'libs', include: ['*.jar'])
}

Добавление готовых библиотек в проект (дополнительно)

Статические библиотеки (.a) в вашей сборке NDK будут автоматически включены, но предварительно встроенные динамические библиотеки (.so) должны быть размещены в jniLibs. Это можно настроить с помощью sourceSets, но вы должны принять стандарт. Вам НЕ НУЖНЫ никакие дополнительные команды build.gradleпри включении готовых библиотек.

Макет jniLibs

Вы можете найти более подробную информацию о структуре в Руководстве пользователя плагина Android Gradle .

|--app:
|--|--build.gradle
|--|--src:
|--|--|--main
|--|--|--|--java
|--|--|--|--jni
|--|--|--|--|--CMakeLists.txt
|--|--|--|--jniLibs
|--|--|--|--|--armeabi
|--|--|--|--|--|--.so Files
|--|--|--|--|--armeabi-v7a
|--|--|--|--|--|--.so Files
|--|--|--|--|--x86
|--|--|--|--|--|--.so Files

Затем вы можете проверить полученный APK-файл, содержащий ваши файлы .so, как правило, в разделе build/outputs/apk/, используя unzip -l myApp.apkсписок содержимого.

Создание общих библиотек

Если вы создаете общую библиотеку в NDK, вам больше ничего не нужно делать. Он будет правильно упакован в APK.


0

Просто добавьте эти строки в приложение build.gradle

dependencies {
    ...
    compile fileTree(dir: "$buildDir/native-libs", include: 'native-libs.jar')
}

task nativeLibsToJar(type: Zip, description: 'create a jar archive of the native libs') {
    destinationDir file("$buildDir/native-libs")
    baseName 'native-libs'
    extension 'jar'
    from fileTree(dir: 'libs', include: '**/*.so')
    into 'lib/armeabi/'
}

tasks.withType(JavaCompile) {
    compileTask -> compileTask.dependsOn(nativeLibsToJar)
}

Я думаю, что подход jniLibs.srcDirs более чистый, чем этот, поскольку вы можете использовать abiFilter / flavors, но ваш подход также должен работать.
plaisthos

0

сейчас. Я могу загрузить так успех!

1. добавить файл .so к этому пути

Project:

| --src | - | --основной | - | - | --java | - | - | --jniLibs | - | - | - | --armeabi | - | - | - | - | -. так файлы

2. добавить этот код в gradle.build

android {
splits {
    abi {
        enable true
        reset()
        include 'x86', 'x86_64', 'arm64-v8a', 'armeabi-v7a', 'armeabi'
        universalApk false
    }
}

}

3.System.loadLibrary("yousoname");

  1. Удачи вам, все в порядке с Gradle 1.2.3

0
  1. Если ваш проект экспортирован из Eclipse, добавьте приведенные ниже коды в файл Gradle:

    android {
       sourceSets{
            main{
               jniLibs.srcDir['libs']  
          }  
        }
    }

2. Если вы создаете проект в Android студии:

создайте папку с именем jniLibs в src / main / , и поместите файлы * .so в папку jniLibs.

И скопируйте код, как показано ниже в вашем файле Gradle:

android {
    sourceSets{  
       main{  
         jniLibs.srcDir['jniLibs']  
      }  
    }
}

0

Хотя я считаю, что SJoshi (оракул) имеет наиболее полный ответ, проект SWIG - это особый случай, интересный и полезный, но не обобщенный для большинства проектов, которые хорошо справляются со стандартными проектами на основе муравьев SDK + NDK. Мы все хотели бы использовать Android studio сейчас, скорее всего, или хотеть более дружественный к CI инструментарий сборки для мобильных устройств, который теоретически предлагает gradle.

Я опубликовал свой подход, где-то позаимствовал (я нашел это на SO, но опубликовал суть приложения build.gradle: https://gist.github.com/truedat101/c45ff2b69e91d5c8e9c7962d4b96e841 ). В двух словах, я рекомендую следующее:

  • Не обновляйте свой проект до последней сборки Gradle
  • Используйте com.android.tools.build:gradle:1.5.0 в корне вашего проекта
  • Используйте com.android.application в своем проекте приложения
  • Убедитесь, что gradle.properties имеет: android.useDeprecatedNdk = true (если это жалоба)
  • Используйте описанный выше подход, чтобы убедиться, что ваши усилия по созданию файлов Android.mk не будут отброшены. Вы контролируете, какие цели арка (ы), чтобы построить. И эти инструкции любезны для пользователей Windows, которые теоретически должны иметь возможность строить на Windows без особых проблем.

На мой взгляд, Gradle для Android был беспорядком, так же как мне нравятся заимствованные концепции maven и продуманная структура каталогов для проекта. Эта особенность NDK "скоро" уже более 3 лет.

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.