【问题标题】:NDK Dev in an Android library project with Gradle & Android Studio使用 Gradle 和 Android Studio 的 Android 库项目中的 NDK Dev
【发布时间】:2014-06-14 04:55:00
【问题描述】:

我一直在尝试破解一个使用 JNI 的 Gradle 托管 Android 项目,但遇到了一些麻烦。我知道 NDK 支持仍然相对较新,而且大多没有记录,但我已经设法找到了将其固定到 Gradle 构建中的基本元素。显然,诀窍是将所有本机代码包含在 src/main/jni 下,并将以下内容放入您的配置之一(例如,在 defaultConfig 块中):

ndk {
    moduleName "mylib"
}

问题是,当我尝试构建我的项目时,ndk 插件会生成一个 Android.mk 文件,其中包含指向本机源的绝对路径。这会导致make 窒息,因为它仍然认为路径是相对的。在我的情况下,我有一个简单的库项目,在 src/main/jni 下有 1 个 cpp 源/标题组合,我使用这个 gradle.build

apply plugin: 'android-library'

android {
    compileSdkVersion 19
    buildToolsVersion "19.0.3"

    defaultConfig {
        minSdkVersion 9
        targetSdkVersion 19
        versionCode 1
        versionName "1.0"
        ndk {
            moduleName "mylib"
        }
    }
    buildTypes {
        release {
            runProguard false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.txt'
        }
    }
}

dependencies {
    compile fileTree(dir: 'libs', include: ['*.jar'])
    compile 'com.android.support:appcompat-v7:19.+'
}

运行构建会在 build/ndk/debug 下生成这个 Android.mk:

LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)

LOCAL_MODULE := mylib
LOCAL_SRC_FILES := \
    /Users/clifton/dev/Multi/MultiAndroid/lib/src/main/jni/Android.mk \
    /Users/clifton/dev/Multi/MultiAndroid/lib/src/main/jni/myNativeSectionTextProvider.cpp \

LOCAL_C_INCLUDES += /Users/clifton/dev/Multi/MultiAndroid/lib/src/main/jni
LOCAL_C_INCLUDES += /Users/clifton/dev/Multi/MultiAndroid/lib/src/debug/jni

include $(BUILD_SHARED_LIBRARY)

...运行时会产生此错误:

make: *** No rule to make target `/Users/clifton/dev/Multi/MultiAndroid/lib/build/ndk/debug//Users/clifton/dev/Multi/MultiAndroid/lib/src/main/jni/myNativeSectionTextProvider.cpp', needed by `/Users/clifton/dev/Multi/MultiAndroid/lib/build/ndk/debug/obj/local/armeabi-v7a/objs/mylib//Users/clifton/dev/Multi/MultiAndroid/lib/src/main/jni/myNativeSectionTextProvider.o'.  Stop.

...因为绝对路径被错误地转换为相对路径。如果我手动编辑文件并将路径更改为相对路径,如下所示:

LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)

LOCAL_MODULE := mylib
LOCAL_SRC_FILES := \
    ../../../src/main/jni/Android.mk \
    ../../../src/main/jni/myNativeSectionTextProvider.cpp \

LOCAL_C_INCLUDES += ../../../src/main/jni
LOCAL_C_INCLUDES += ../../../src/debug/jni

include $(BUILD_SHARED_LIBRARY)

...然后我得到这个错误:

/Users/clifton/dev/Multi/MultiAndroid/lib/build/ndk/debug/../../../src/main/jni/com_craig_multiandroid_app_NativeSectionTextProvider.h:2:17: fatal error: jni.h: No such file or directory

我的问题是我能做些什么来解决这个问题?我开始破解我自己对 .aar 构建的自定义 gradle 支持,但在试图弄清楚哪个 Gradle 任务负责生成 .aar 文件时迷失了方向。 (Gradle 文档虽然丰富,但很难找到有关特定 Android Gradle 任务 API 的详细信息。)我有一个部分工作的 gradle.build,它将通过 cmd 行运行 ndk-build,生成 .so 但我不能不知道如何(或者即使我应该)将 .so 内联到 .aar 中。我正在使用 Android Studio 0.5.7 和 Gradle 1.11。几个月前我已经提取了 Gradle 源代码,这就是我想出如何在常规 .apk 项目中内联 .so 和 gdbserver 文件的方法,但这些规则似乎不适用于 .aar 项目。有没有其他人尝试过这个?我在哪里可以找到答案?

【问题讨论】:

    标签: android-ndk gradle android-studio


    【解决方案1】:

    我终于明白了!您必须使用最新的 NDK 才能获得更新的 Gradle NDK 支持。我的 local.properties(和我的 ~/.bashrc)指向 android-ndk-r8e 以解决 android-ndk-r9d 中损坏的 gdb-server 支持但是当我更新到 android-ndk-r9d 我的 gradle 构建开始工作没有额外的技巧。总而言之,只要您的 local.properties 指向 NDK 的 9b+ 版本,上述示例就可以工作。

    【讨论】:

      猜你喜欢
      • 2015-02-23
      • 2013-05-16
      • 2014-01-22
      • 1970-01-01
      • 2015-07-29
      • 2014-09-23
      • 1970-01-01
      • 1970-01-01
      • 2016-08-07
      相关资源
      最近更新 更多