demo下载地址:
https://download.csdn.net/download/u010672559/10592633
一、NDK的配置
1.下载SDK Tools里面的LLDB和NDK
2.配置NDK路径
Androidstudio的工程的project\local.properties文件下添加,不然as设置ndk路径的时候回提示选中不了
ndk.dir=E\:\\yxzwork\\soft\\android\\sdk_as\\sdk_as\\ndk\\23.0.7123448
3.配置NDK环境变量,系统环境变量里面创建NDK_ROOT内容为SDK里面的ndk-bundle路径,然后Path后面追加;%NDK_ROOT%
NDK_ROOT
D:\yxzWork\soft\android\sdk_as\ndk-bundle
Path
;%NDK_ROOT%
之后cmd内输入ndk-bundle,如果出现以下提示,则表示配置成功
======================================================================
二、JNI的使用及demo
概述:先介绍JNI使用的步骤,具体的文件源码在后面有贴出
1.先新建JNITest.java文件,然后可以通过命令javah -jni -encoding utf-8 包名+类名,生成相应的.h文件,此处如果提示javah不是内容文件可能是jdk配置有问题,我之前有碰到的问题就是jdk安装的64位,但是jdk配置是按网上的32位配的,所以不行,后面改成32位的jdk了
D:\yxzWork\workspace\asworkspace\JniTest\app\src\main\java>javah -jni -encoding utf-8 com.android.yxz.jnitest.JNITest
2.创建test.c文件,然后可以参考JNITest.h的包名类名做修改,然后添加mk文件,注意jni文件的路径不是在app下面,而是在src/main下面
3.配置工程相关配置项
在 build.gradle 文件夹的 android 下添加(buildTypes下面,不是里面):
sourceSets {
main() {
jniLibs.srcDirs = ['src/main/libs']
jni.srcDirs = [] //屏蔽掉默认的jni编译生成过程
}
}
D:\yxzWork\workspace\asworkspace\JniTest\gradle.properties下添加
android.useDeprecatedNdk=true
4.在jni的路径下执行ndk-build,然后会生成相应的so文件
D:\yxzWork\workspace\asworkspace\JniTest\app\src\main\jni>ndk-build
5.之后直接运行apk即可
6.c中加log的方法
#define LOGI(fmt, args...) __android_log_print(ANDROID_LOG_INFO, TAG, fmt, ##args)
#define LOGD(fmt, args...) __android_log_print(ANDROID_LOG_DEBUG, TAG, fmt, ##args)
#define LOGE(fmt, args...) __android_log_print(ANDROID_LOG_ERROR, TAG, fmt, ##args)
int类型
LOGD("your-tag-str(value = %d)", value);
String类型
LOGD("your-tag-str(strValue = %s)", strValue)
%d整型输出,%ld长整型输出,
%o以八进制数形式输出整数,
%x以十六进制数形式输出整数,或输出字符串的地址。
%u以十进制数输出unsigned型数据(无符号数)。注意:%d与%u有无符号的数值范围,也就是极限的值,不然数值打印出来会有误。
%c用来输出一个字符,
%s用来输出一个字符串,
%f用来输出实数,以小数形式输出,默认情况下保留小数点6位。
%.100f用来输出实数,保留小数点100位。
%e以指数形式输出实数,
%g根据大小自动选f格式或e格式,且不输出无意义的零。
=================
代码(注意不同项目c文件的包名类名需做相应更改)
---------
JNITest
public class JNITest {
// 动态导入 so 库
static {
System.loadLibrary("JNITest");
}
public native static String get();
}
-------------
MainActivity
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;
public class MainActivity extends AppCompatActivity {
public static final String TAG = "xiaozheng";
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Log.d(TAG, "JNITest.get()="+JNITest.get());
}
}
----------
Android.mk
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := JNITest
LOCAL_SRC_FILES := test.c
include $(BUILD_SHARED_LIBRARY)
--------------
Application.mk
APP_ABI := all
-----------
com_android_yxz_jnitest_JNITest.h
/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class com_android_yxz_jnitest_JNITest */
#ifndef _Included_com_android_yxz_jnitest_JNITest
#define _Included_com_android_yxz_jnitest_JNITest
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class: com_android_yxz_jnitest_JNITest
* Method: get
* Signature: ()Ljava/lang/String;
*/
JNIEXPORT jstring JNICALL Java_com_android_yxz_jnitest_JNITest_get
(JNIEnv *, jclass);
#ifdef __cplusplus
}
#endif
#endif
-------
test.c
#include<jni.h>
#include<stdio.h>
//导入我们创建的头文件
#include "com_android_yxz_jnitest_JNITest.h"
JNIEXPORT jstring JNICALL Java_com_android_yxz_jnitest_JNITest_get
(JNIEnv *env, jclass jclass){
//返回一个字符串
return (*env)->NewStringUTF(env,"print Java_com_android_yxz_jnitest_JNITest_get");
}