




版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1、C03_cJNI:从C调用J基a於軟v硬a整函合觀點数 ( c)By 高煥堂3、How基-於t軟o硬:整合觀點从C调用Java函数如果控制点摆在本地C层,就会常常1.2.3.从本地C函数去调用Java函数;从本地C函数去存取Java层对象的属性值; 从本地C函数去创建Java层的对象。 关于JNI,大家都知道如何从Java调用C函数。然而, 在Android 里, 反而由C呼叫Java的情形才更具关键性。例如,Activity 的跨进程沟通如下: 当App里的Activity透过IBinder接口来与Service进行IPC沟通实上是由Java层的Activity调用C/C+模块去进行IPC沟
2、通, 再由C模块调用Java层的Service。 所以,Java与C函数的双向调用都是Android平台的重要机制。 举例说明 在CounterNative类别里,有3个本地函数: 静态(static)的nativeExecute()和一般的nativeSetup()及nativeExec()。 其中,静态nativeExecute()会调用Java层 的一般的setV()函数;而一般的nativeExec() 会调用Java层的静态setValue()函数。/ ac01.java/ .public class ac01 extends Activity implements OnClickL
3、istener private CounterNative cn;Override public void onCreate(Bundle savedInstanceState)/.cn = new CounterNative();Override public void onClick(View v) switch(v.getId() case 101:cn.nativeExec(10); case 102:break;CounterNative.nativeExecute(11); case 103:finish();break;break; 指令:cn = new CounterNati
4、ve(); 其调用CounterNative()建构函数。执行到nativeSetup()函数,转而调用本地C函数:com_misoo_counter_CounterNative_nativeSetup() 这个函数只负责将m_class、m_object、m_static_mid和m_mid储存在C模块的静态区域里而已。 执行指令:cn.nativeExec(10); 就呼叫C函数:nativeExec(),计算出sum 值之后,透过VM的CallVoidMethod()函数而调用到目前Java对象的setValue()函数, 把sum值传入Java层,并显示出来。/ CounterNati
5、ve.java/ public class CounterNative private static Handler h;static System.loadLibrary(MyCounter);public CounterNative()h = new Handler()public void handleMessage(Message msg) ac01.ref.setTitle(msg.obj.toString();nativeSetup();private static void setValue(int value)String str = Value(static) = + Str
6、ing.valueOf(value); Message m = h.obtainMessage(1, 1, 1, str); h.sendMessage(m);private void setV(int value)String str = Value = + String.valueOf(value); Message m = h.obtainMessage(1, 1, 1, str); h.sendMessage(m);private native void nativeSetup();public native static void nativeExecute(int n); publ
7、ic native void nativeExec(int n); ac01调用CounterNative类的建构函数, 此函数诞生了一个Handler对象,并且调用本地的nativeSetup()函数。 随后,ac01将调用静态的nativeExecute() 函数,此函数则反过来调用Java层一般的setV()函数。 接着,ac01调用一般的nativeExec()函数, 此函数则反过来呼叫Java层的静态setValue()函数。 请记得,在学习Android时,从第一秒钟就持着优雅的素养:对于每一行代码,都必须能准确而正确地说出来,目前该行代码正由那一个线程(Thread)所执行的。留
8、意:目前该行代码正由那一个线程所执行 /*com.misoo.counter.CounterNative.c*/#include com_misoo_counter_CounterNative.hjclass jobjectm_class; m_object;jmethodID m_mid_static, m_mid;JNIEXPORT void JNICALLJava_com_misoo_counter_CounterNative_nativeSetup (JNIEnv *env, jobject thiz) jclass clazz = (*env)-GetObjectClass(env,
9、 thiz); m_class = (jclass)(*env)-NewGlobalRef(env, clazz); m_object = (jobject)(*env)-NewGlobalRef(env, thiz); m_mid_static= (*env)-GetStaticMethodID(env, m_class, setValue, (I)V); m_mid = (*env)-GetMethodID(env, m_class, setV, (I)V); return;JNIEXPORT void JNICALLJava_com_misoo_counter_CounterNative
10、_nativeExecute (JNIEnv *env, jclass clazz, jint n) int i, sum = 0;for(i=0; iCallVoidMethod(env, m_object, m_mid, sum); return;JNIEXPORT void JNICALLJava_com_misoo_counter_CounterNative_nativeExec (JNIEnv *env, jobject thiz, jint n)int i, sum = 0;for(i=0; iCallStaticVoidMethod(env, m_class, m_mid_sta
11、tic, sum); return; 说明nativeSetup()函数的内容 上述的nativeSetup()函数之定义:JNIEXPORT void JNICALLJava_com_misoo_counter_CounterNative_nativeSetup(JNIEnv *env, jobject thiz)/. 其中的第2个参数thiz就是Java层目前对象的参考(Reference)。所谓目前对象就是正在调用此本地函数的Java层对象。例如, 在此范例里,就是CounterNative类的对象参考。 指令:jclass clazz = (*env)-GetObjectClass(e
12、nv, thiz); 向VM(Virtual Machine)询问这thiz所参考对象的类(即CounterNative类别)。 由于这class是这本地函数的区域(Local)变量,当此函数执行完毕后,这个class变量及其所参考的值都会被删除。因此,使用指令:m_class = (jclass)(*env)-NewGlobalRef(env, clazz); 来将区域型的class参考转换为全域(Global)型的参考,并将此全域参考存入到这本地C模块的全域变数m_class里。 如此,当函数执行完毕后,这个m_class变量及其所参考的值都不会被删除掉。同理, thiz也是区域变量,函数
13、执行完毕,这个thiz及其值都会被删除。因此,使用指令:m_object = (jobject)(*env)-NewGlobalRef(env, thiz); 将区域型的class参考转换为全域(Global)型的参考,并将此全域参考存入到这本地C模块的全域变数m_object里。 接着,指令:m_mid_static = (*env)-GetStaticMethodID(env,m_class, setValue, (I)V); 这要求VM去取得m_class所参考的类(就是CounterNative类)的setValue()函数的ID值。并将此ID值存入到这本地C模块的全域变数m_mid_
14、static里。 同理,指令:m_mid = (*env)-GetMethodID(env, m_class,setV, (I)V); 这找到CounterNative类的setV()函数的ID, 并将此ID值存入到这本地C模块的全域变数m_mid里。 由于m_class和m_object两者都是参考(Reference),其必须透过VM的NewGlobalRef()来转换出全域性的参考。至于m_static_mid和m_mid则是一般的整数值,直接储存于静态变量里即可了。 于此, m_obje 当了, 和nativm_class、d储存妥ecute() 例如:JNIEXPORT void JNICALLJava_com_misoo_counter_CounterNative_nativeExecute (JNIEnv *env, jclass clazz, jint n)/ (*env)-CallVoidMethod(env, m_object, m_mid,sum); 这个m_object正指向Java层的目前对象, 而m_mid则是其setV()函数的ID。 依据这两项资料,就能透过VM的CallVoidMethod()函数而调用到目前Java对象的setV()函数,而把数据传送到Java层。 Sum
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 可行性研究报告核准的请示
- 2025年中国接触式读卡器行业发展监测及市场发展潜力预测报告
- 风能发电可行性研究报告
- 2025年中国锥子行业市场发展现状及投资战略咨询报告
- 2024-2030全球数智化服务行业调研及趋势分析报告
- 虹口区景观工程管理办法
- 血站管理办法(暂行)
- 裕安区娱乐设施管理办法
- 衡水市失业保险管理办法
- 西宁市智库建设管理办法
- 大学食堂原料采购合同
- 幼儿园中班彩虹泡泡龙课件
- 精益生产改善培训
- 大学生心理健康教育(兰州大学版)学习通超星期末考试答案章节答案2024年
- 浙江水利专业高级工程师任职资格考试题及答案
- 统计学数据的图表展示(共133张课件)
- GB/T 44208-2024馆藏文物病害描述及图示基础要素
- 2023四年级数学上册 1 大数的认识第11课时 用计算器计算教案 新人教版
- 中国共产党支部工作条例
- 2023年石嘴山市直机关遴选公务员考试真题
- GCP相关人员职责
评论
0/150
提交评论