使用NDK生成Linux平台下的so文件和使用MinGW生成Windows平台下的dll文件前半部分是一样的,都是用javah生成头文件,再根据头文件编写.c(C文件)或者.cpp文件(C++文件),最后利用这个文件生成各自的库

先下载好自己平台下的NDK文件,下载地址:NDK 下载

 

流程如下:

1.编写包含native方法的类

2.将此类使用javah生成对应的头文件(推荐下里面我总结的内容:IDEA开发,Jni中javah使用方式的探索

3.利用此头文件编写.c或者.cpp文件:这一步很简单

这是随便写的一个native方法生成的.h头文件

 

/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class test_ndkdemo_MainActivity */

#ifndef _Included_test_ndkdemo_MainActivity
#define _Included_test_ndkdemo_MainActivity
#ifdef __cplusplus
extern "C" {
#endif
/*
 * Class:     test_ndkdemo_MainActivity
 * Method:    getStr
 * Signature: ()Ljava/lang/String;
 */
JNIEXPORT jstring JNICALL Java_test_ndkdemo_MainActivity_getStr//看这里看这里看这里,我写的native在头文件里的表现形式
  (JNIEnv *, jobject);

#ifdef __cplusplus
}
#endif
#endif

之后直接新建文件命名为.c或者.cpp格式,然后#include"你生成的类名.h",实现你.h里只是单单声明的方法,比如这样

 

 

#include"test_ndkdemo_MainActivity.h"//导入你的头文件
JNIEXPORT jstring JNICALL Java_test_ndkdemo_MainActivity_getStr//然后实现里面的具体内容
  (JNIEnv *env, jobject obj){
    char buf[128]="test";
    return (*env)->NewStringUTF(env,buf);
  }

4.使用NDK:使用NDK你需要编写一个Android.mk的文件,有过Linux下使用gcc命令的看到mk应该会想到make和make file相关的内容,Android.mk的底层也是他们

 

编写Android.mk的资料我推荐这个,Android.mk详解

在编写好之后我们就可以使用NDK工具了(其实是使用NDK路径下的ndk-build.cmd文件,有兴趣的可以去找找,然后把编译相关的文件拷过来尝试就在那个目录下执行这个命令)

比如我的是

 

LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := test
LOCAL_SRC_FILES := test_ndkdemo_MainActivity.c
include $(BUILD_SHARED_LIBRARY)

很简单的- -。

 

不过请读者老爷们注意几点:你的.h,.c,.cpp和Android.mk得放一个文件夹下(不放也可以,你路径在Android.mk里多写几个字母也行);要是还要使用其他的库的话记得在Android.mk添加进去

 

 

然后,我们就不跑到NDK安装路径下使用ndk-build.cmd命令了,我们使用前面介绍过的一键生成方式

 

之后随便选你Android.mk所在目录下随便一个文件执行此External Tools就行了。

 

剩余几点想说的

1.生成了两个文件夹,不知道为什么,有读者知道的话请告知一下

。。。。。。。。。。。。。。。。。。。。。。。。。。。。

2018.1.8

后面研究SO文件的时候,竟然偶然得知了这个答案

使用ndk生成的so文件时会经过strip这样一个操作,strip会将so里动态链接库末尾的.symtab和.strtab这两个section去掉。

可以在\obj\local下找到未经过strip的.so文件。

。。。。。。。。。。。。。。。。。。。。。。。。。。。。

2.Gradle在java的同级目录中定义了一个jniLibs的变量用于存放jni的库,记得以前的做法是把jni的库都放在lib目录下,然后声明jniLibs的值

android{     
02.   sourceSets {  
03.        main {  
04.            jniLibs.srcDirs = ['libs']  
05.        }  
06.}  

现在很简单了,新建和java同级的目录命名为jniLibs,放入jni的库就能在编译时加入了

 

3.关于ndk-build.cmd:

 

Logo

更多推荐