Adnroid ndk 中jni访问java方法、对象、成员变量

来源:互联网 发布:行知实验园 编辑:程序博客网 时间:2024/06/05 07:50
 
 JNI文件夹下,C++源码
extern "C"{JNIEXPORT void JNICALL Java_ndk_test_JNI_accessJavaMethod(JNIEnv *env,jobject obj){jclass ClassJNI = env->FindClass("ndk/test/JNI");jmethodID returnStringID = env->GetMethodID( ClassJNI, "InstanceMethod", "()Ljava/lang/String;");jstring jstr =(jstring)env->CallObjectMethod(obj,returnStringID);//调用带返回参数的java方法const char *c_str = env->GetStringUTFChars(jstr, NULL);// 4. 将unicode编码的java字符串转换成C风格字符串LOGI("java中的方法执行结果是:%s",c_str);//调用有输入参数与返回值的方法jmethodID paramID = env->GetMethodID(ClassJNI, "paramMethod", "(Ljava/lang/String;)Ljava/lang/String;");jstring param = env->NewStringUTF("这是java方法中需要的参数");jstring jstr2 =(jstring)env->CallObjectMethod(obj, paramID, param);const char *c_str2 = env->GetStringUTFChars(jstr2, NULL);LOGI("调用有输入参数与返回值的方法java中的方法执行结果是:%s",c_str2);//调用java中多个参数的方法,并使用另一种查找方式jmethodID muitleParamId = env->GetMethodID( ClassJNI, "MuitleParamMethod", "(ILjava/lang/String;[I)Ljava/lang/String;");jint a=119;jstring tmp_jstr = env->NewStringUTF("liuzheyu");jintArray ret = env->NewIntArray(3);//实例化一个g一维数组jint* buffer = new jint[1024];  //固定数组,测试用,注意别溢出for (int i = 0; i < 3; i++){buffer[i]=i;}env->SetIntArrayRegion(ret, 0, 3, buffer);   //从NativeType类型(jint)数组中,拷贝0~y数据到jintArray对象中jstring jstr3 =(jstring)env->CallObjectMethod(obj,muitleParamId,a,tmp_jstr,ret);//调用带返回参数的java方法const char *c_str3 = env->GetStringUTFChars(jstr3, NULL);// 4. 将unicode编码的java字符串转换成C风格字符串LOGI("调用java中多个参数的方法结果是:%s",c_str3);env->DeleteLocalRef(ret);/** * 测试访问静态方法 */jmethodID staticId = env->GetStaticMethodID(ClassJNI,"staticMethod","()Ljava/lang/String;");jstring jstr_4 =(jstring) env->CallObjectMethod(obj,staticId);const char * c_str4=env->GetStringUTFChars(jstr_4,NULL);LOGI("访问java中的静态方法中结果是:%s",c_str4);}}

JNI文件夹下:java对象

package ndk.test;/** * JNI * @author Administrator * 2016-05-22 */public class JNI {    public native String getString();         public native int plus(int a,int b);                   /**     * 操作一维数组     * @param a     * @param b     * @return     */    public native int operateArray(int[] a,int[] b);        /**     * 获取原生中的二维数组     * @param row     * @param col     * @return     */    public native int[][] get2Array(int row,int col);        /**     * 获取一个数组的对象     * @param row     * @param col     * @return     */    public native int[][] get2ArrayObject(int[][] a);            /**     * 本地代码访问实例对象     * @param obj     */    public native static void accessInstanceField(ClassObject obj);          /**     * 本地代码访问静态域     */    private native static void accessStaticField();             /**     * 实例方法,在C++中调用     * @return     */    public String InstanceMethod()    {    return "JNI中通过方法id来获取实例方法";    }    /**     * 静态方法,在C++中调用     * @return     */    public static String staticMethod()    {    return "JNI中通过方法id来获取静态方法";    }    /**     * C++中测试调用带参数的方法     * @param info     * @return     */    public String paramMethod(String info)    {    return info;    }        /**     * c++能过原生方法调用带有多个不同类型的参数方法     * @param a     * @param str     * @param array     * @return     */    public String MuitleParamMethod(int a,String str,int[] array)    {    int total=0;    for(int i=0;i<array.length;i++)    {    total+=array[i];    }    String result = a+str+total;    return result;    }        /**     * 通过直接找类来访问java中的对象     * @param obj     */    public native void accessJavaMethod();}

java测试类对象:

package ndk.test;/** * 在本地代码中进行修改 * @author Administrator * */public class ClassObject {/** * 对应第一种方法:C++中访问java对象 */public native ClassObject accessJavaObject();  /** * 测试修改静态成员变量 */private static int num;      private String str;         public static int getNum() {return num;}public static void setNum(int num) {ClassObject.num = num;}public String getStr() {return str;}public void setStr(String str) {this.str = str;}}


Android activity类:

package ndk.test;import android.app.Activity;import android.os.Bundle;import android.view.View;import android.view.View.OnClickListener;import android.widget.Button;import android.widget.TextView;public class MainActivity extends Activity {static{          System.loadLibrary("NDKTest");  //导入库    }            private Button javaObjBtn;    JNI jni;    @Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);TextView text=(TextView)findViewById(R.id.t1);jni = new JNI();String tmp1 = jni.getString()+"和:"+jni.plus(2, 7);//text.setText(tmp1);int[] a = {1,2,3};int[] b = {4,5,6};int muitle = jni.operateArray(a, b);String tmp2 = "操作数组之后:"+ muitle;text.setText(tmp1+tmp2);int[][] array = {{1,2,3},{4,5,6},{7,8,9}};int[][] int2Array = jni.get2Array(3, 3);System.out.println("37-----------:"+int2Array[1][1]);int [][] tmpArray = jni.get2ArrayObject(array);System.out.println("40-----------:"+tmpArray [1][1]);//操作对象ClassObject obj = new ClassObject();obj.setStr("刘胡来");obj.setNum(26);jni.accessInstanceField(obj);/*ClassObject o = obj.accessJavaObject();System.out.println("测试修改对象,修改后名字:"+o.getStr()+":年龄:"+o.getNum());*/javaObjBtn = (Button)findViewById(R.id.button1);javaObjBtn.setOnClickListener(new BtnClick());Button javaMethodBtn = (Button)findViewById(R.id.button2);javaMethodBtn.setOnClickListener(new BtnClick());}private class BtnClick implements OnClickListener{@Overridepublic void onClick(View v) {switch(v.getId()){case R.id.button2:jni.accessJavaMethod();/*int a =119;String str="liuzeyu";int [] array={1,2,3};jni.MuitleParamMethod(a, str, array);*/break;}}}}




0 0