在Android Studio中使用预构建库和JNI

5

我正在使用Android Studio 1.0.2,试图创建一个使用NDK和本地函数的Android库。这基本上是我的项目架构:

MyProject
---| MyAndroidApp
---| MyAndroidLibrary
    ---| jni
    ---| jniLibs

在我的Android库中,我有一个单一的C++包装器,调用共享库的函数。我使用ndk-build创建了这个库(它与Eclipse完美地配合工作)。我将这个库添加到了jniLibs文件夹/体系结构(arm64-v8a、armeabi、armeabi-v7a、mips、mips64、x86和x86_64)。 我在MyAndroidLibrary/build.gradle中定义了以下Flavors:
productFlavors {
    x86 {
        flavorDimension "abi"
        ndk {
            abiFilter "x86"
        }
    }
    arm {
        flavorDimension "abi"
        ndk {
            abiFilter "armeabi-v7a"
        }
    }
    mips {
        flavorDimension "abi"
        ndk {
            abiFilter "mips"
        }
    }
    fat {
        flavorDimension "abi"
    }
}

然而,当我尝试从jni代码调用我的库函数时,会出现未定义的引用错误。换句话说,我的共享库似乎没有在jni端加载。但是,当我删除这些函数的调用并探索输出中创建的.aar文件时,我可以检索到库.so。

我对gradle不是很熟悉,所以我不确定它实际上构建了什么。

我正在寻找的是使用gradle的Android.mk的严格等效版本:
LOCAL_PATH := $(call my-dir)

include $(CLEAR_VARS)

LOCAL_MODULE            := mysharedlib
LOCAL_SRC_FILES         := ../shared/mysharedlib.so
LOCAL_EXPORT_C_INCLUDES := ../shared/includes/mysharedlib.h

include $(PREBUILT_SHARED_LIBRARY)

include $(CLEAR_VARS)

LOCAL_MODULE            := jni
LOCAL_SRC_FILES         := jni.cpp
LOCAL_C_INCLUDES        += ../shared/includes/mysharedlib.h
LOCAL_LDLIBS            := -llog
LOCAL_SHARED_LIBRARIES  := mysharedlib

include $(BUILD_SHARED_LIBRARY)

我希望在JNI代码上调用预构建库中的函数,例如:

#include "MyDLL.h"

JNIEXPORT jint JNICALL Java_com_iskn_dbapi_DBAPI_getNegative(JNIEnv *env, jclass obj, jint integer)
{
   return MyDLL::getNegative(integer);
}

感谢你的回答。

你最终修好了吗? - João Gonçalves
1个回答

1

目前Gradle插件不支持此类NDK配置。它会忽略现有的Android.mk文件并动态生成自己的文件(非常有限)。您可以在此处查看它是如何生成的(查看writeMakefile方法),并评估其生成所影响的选项集有多么有限。

实际上,为了实现您需要的功能,最好的方法是完全禁用Gradle有限的NDK支持,并显式调用ndk-build命令。请阅读此处获取详细信息。


谢谢你的回答。实际上,我需要使用gradle创建一个.aar文件。但是jniLibs文件夹不应该包含预构建的库吗?根据这个链接,请参见预构建库部分。 - Sierra
抱歉,我不明白你的问题是什么。你能换个说法再问一遍吗?顺便说一下,在上面的链接中,你可以看到 sourceSets.main.jniLibs.srcDir 'src/main/libs' 这一行代码 - 这意味着该文件夹将用于将本地库打包到 APK 中,而不是 'jniLibs'。 - Dmitry Moskalchuk
当然。我需要的是一个包含我的共享库的 .aar(Android 存档文件)。为此,我必须使用 gradle,对吧?另一件事是,我在上面发布的链接中看到,jniLibs 文件夹中的所有库都应该自动预构建,是这样吗? - Sierra
你找到解决这个问题的方法了吗? - benchuk

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接