Android JNI例子

Android JNI栗子 这里留意以下部分:

  1. sMethods数组定义了所要注册的JNI函数。第一个参数“NativeAdd”指的是在java层调用的函数名,第二个“(II)I”指的是函数的类型,第三个“(jint *)NativeAdd”指的是实际的C++函数
  2. “cls = env->FindClass(“com/example/mycalljni/MainActivity”); ”对应于调用调用native函数的java类。如果是其它的java类调用的话,那么这里也需要更改。
    从这里可以看出,间接注册和直接注册的最大区别在于C/C++函数名的不同。
#include "jni.h" #include jint NativeAdd(JNIEnv* env,jobject clazz,jint num_1,jint num_2) { return num_1 + num_2; } static JNINativeMethod sMethods[] = { {"NativeAdd", "(II)I", (jint *) NativeAdd}, }; /* * JNI Initialization */ JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *jvm, void *reserved) { JNIEnv *env = NULL; int status; jclass cls; printf("%s: Loading start", __FUNCTION__); printf("sMethods size : %d", sizeof(sMethods)); // Check JNI version if (jvm->GetEnv((void **)&env, JNI_VERSION_1_6)) { printf("JNI version mismatch error"); return JNI_ERR; } //Find the java class cls = env->FindClass("com/example/mycalljni/MainActivity"); if(cls == NULL) { printf("Unable to find class android.os.Message"); } //Registry the native method env->RegisterNatives(cls,sMethods,sizeof(sMethods) / sizeof(sMethods[0])); return JNI_VERSION_1_6; }

关键点
在本小节当中,我们不妨来看一下,哪些关键点在Java层是与JNI有关的。
  1. native
    在Java代码中,只要是用native进行修饰的函数,都是本地函数,是直接调用到C/C++代码中的。只不过在Java里面比较幸福,只需要在一个函数中声明native即可,更多的参数匹配都是在C/C++进行的。
  2. System.loadLibrary(string libName)
    功能:用于加载具体实现本地方法的C运行库
    这里需要注意的是,即使传入的参数相同,但在不同平台中最后加载的运行库也是不同的。比如说,我们传入一个名为“hellojni”的字符串,实际加载的C运行库在Windows环境下是“hellojni.dll”,但在Linux下则是“libhellojni.so”了。
【Android JNI例子】附Android.mk:
Android.mk解析可以阅读我博客中有关Android.mk的文章。
LOCAL_PATH := $(call my-dir) include $(CLEAR_VARS) LOCAL_MODULE := MyJni LOCAL_SRC_FILES := myjni.cpp include $(BUILD_SHARED_LIBRARY)

    推荐阅读