Android中建立JNI调用

1、安装Cygwin 

再配置一下环境变量,编译的时候方便。打开D:\ndk\cygwin\home\FHP\.bash_profile(我电脑登录用户名为FHP),在文件最后添加:
NDK="/cygdrive/d/ndk/android-ndk-r5c"  (注明:后面是ndk的路径)
export NDK

2、Eclipse需要安装CDT


3、建立JNI的编译器,实际上有两种方法,一种是自己建立原生的编译,如下所示:

装完后,新建一个Android项目,我这里为NDKTest,包为com.ndk,类为Main。我的项目路径:D:\ndk\NDKTest
建好项目后,在项目上点右键,新建一个名为jni的文件夹,所有的c或c++文件必须放这里。
下面配置一下Eclipse,让它自动编译我们的c或者c++源代码。在项目上点右键-属性,选择构建器,点右边的新建-程序,看图:

位置跟工作目录就不解释了,自变量解释一下,这个就是编译时执行的命令,/cygdrive/d/ndk/NDKTest是Android项目的路径,$NDK/ndk-build,就是D:\ndk\android-ndk-r5c\ndk-build 因为我们刚才设置了环境变量。
所以这个自变量的意思就是进入项目所在目录,执行ndk-build编译。
刷新选项卡要勾选“完成时刷新资源”
构建选项卡:

点击“指定资源”,勾选项目NDKTest的jni目录,这样,只要是jni下面的文件改变了,就会自动重新编译。
最后,保存,把刚才建的构建器移动最顶端(必须先编译c文件才能编译apk).

还有一种是基于CDT的:

 使用Eclipse将生成的项目转换为C++项目,如下图所示:(这是http://docs.opencv.org/doc/tutorials/introduction/android_binary_package/android_binary_package_using_with_NDK.html

所推荐的一种方法,但设置起来挺麻烦的,我是没弄懂)(下面的说明摘自:http://www.cnblogs.com/xiaomiao/default.html

    

                                                      (图二)

----    新建并配置一个Builder,使项目能够自动编译C/C++代码。

----   在项目上点击右键,Properties-> C/C++ General-> Path and Symbols,找到Includes那一栏,

         添加三个环境变量,如图三所示。

 

                                                                           (图三)

         注:此处三个变量分别指向:

    ${env_var:ANDROID_NDK}/platforms/android-9/arch-arm/usr/include;                        

    ${env_var:ANDROID_NDK}/toolchains/arm-linux-androideabi-4.4.3/prebuilt/windows/lib/gcc/arm-linux-androideabi/4.4.3/include;

    ${env_var:ANDROID_NDK}/sources/android/native_app_glue;

    ANDROID_NDK为系统环境变量,代表NDK的安装目录。


接下来就是Java里面的调用,Main.java:

package com.ndk;
 
import android.app.Activity;
import android.os.Bundle;
 
public class Main extends Activity {
    /** Called when the activity is first created. */
    static {
        System.loadLibrary("ndkc");
        //调用编译C语言生成的库
    }
    public native String StringBack();
    //定义一下来自C的方法
    public native int Add(int a,int b);
    //同上,返回类型为int,参数是两个int
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        System.out.println(StringBack());
        System.out.println(Add(5,6));
      //输出返回值
    }
}


在src的路径下,在终端运行命令:javah -classpath . -jni package_name.class_name,这样在src文件下就生成了JNI对应的头文件,JNI的C语言文件就是根据这个头文件编写。

然后是代码部分,在jni目录下建一个ndkc.c文件,把c语言的代码都写这里:

#include <string.h>
#include <jni.h>
 
jstring Java_com_ndk_Main_StringBack(JNIEnv* env, jobject obj){
	 return (*env)->NewStringUTF(env, "TESTsfsfdaas标杆s!");
	 //(*env)->NewStringUTF方法是把c语言的字符串转换成jstring(Java语言的字符串)
	 //
}
//函数名有限制,必须为Java_调用它的类名_调用方法,JNIEnv* env, jobject obj,这两个参数是必须加的
jint Java_com_ndk_Main_Add(JNIEnv * env, jobject obj, jint a, jint b){
	return a+b;
	//好像基本数据类型不用转
	//jint就是int
}


在jni目录下建一个Android.mk文件,这个差不多就是编译的参数:


LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := ndkc
LOCAL_SRC_FILES := ndkc.c
#LOCAL_MODULE 指的是编译后的库名,java文件中直接就调用这个名字
#LOCAL_SRC_FILES c语言源文件名
include $(BUILD_SHARED_LIBRARY)

最后是运行,可以在logcat看到结果


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值