Android studio NDK开发 从入门到实践三
2017-12-05 16:48
369 查看
这节我们讲解怎么将jni函数运用到我们的代码,这些都是我自己摸索了,肯定有更好的解决方法.但是,没那个多时间去研究了. 所以希望,有更好解决方法的大神,能指点指点.<1. 将java当中参数传入的string转换成char*
JNIEXPORT jint JNICALL Java_com_viking_myapplication_JniMethod_NetFreeBuffer (JNIEnv *env, jobject jobj, jstring pBuffer){ char * pbuffer = (char *)env->GetStringUTFChars(pBuffer,0); //将java当中参数传入的string转换成char* jint result =Net_FreeBuffer(pbuffer); //Net_FreeBuffer() c代码的接口 env->ReleaseStringUTFChars(pBuffer,pbuffer); //释放内存 return result; }<2. 通过java对象作为参数,传递数据.
JNIEXPORT jint JNICALL Java_com_viking_myapplication_JniMethod_NetImageSnap (JNIEnv *env, jobject jobj, jint tHandle,jobject ptImageSnap){ jclass jclazz = env->GetObjectClass(ptImageSnap); //通过对象获取jclass类 jfieldID uiImageIdID = env->GetFieldID(jclazz,"uiImageId","I"); //通过jclass,跟变量名,获取变量id jint a = env->GetIntField(ptImageSnap,uiImageIdID); //通过对象和变量id,获取Java对象中变量的值 jfieldID ucLightIndexID =env->GetFieldID(jclazz,"ucLightIndex","B"); jbyte b = (unsigned char)env->GetByteField(ptImageSnap,ucLightIndexID); jint result =Net_ImageSnap(a,b); return result; }<3. jni中创建java对象
//创建java对象TImageUserInfo jclass jimageuserinfobean = env1->FindClass("com/viking/bean/TImageUserInfo"); //获取java对象的构造方法id jmethodID jimageuserinfobeanID = env1->GetMethodID(jimageuserinfobean,"<init>","()V"); //创建java对象 jobject jimageuserinfo = env1->NewObject(jimageuserinfobean,jimageuserinfobeanID);<4. 在jni中,给创建出来的java对象中变量赋值
//通过java对象的jclass,跟类中变量名称,和变量的类型,获取变量的id
jfieldID ucVehicleColorID = env2->GetFieldID(jimageuserinfobean(Java对象的jclass),"ucVehicleColor"(变量的名称),"B"(变量类型));
//通过SetByteField,给变量赋值. env2->SetByteField(jimageuserinfo(java对象),ucVehicleColorID(java的变量的id),ptImageInfo->ucVehicleColor(值));<5.jni中,怎么将对象中的值赋值给C结构体中
//javabean对象
public class TControlGate { public byte ucState; /*E_GateState*/ public byte[] ucReserved3; //这里我用的是byte[], 对应c中的char[]. 大家也可以用string,这样简单很多.
//我只所以用这个类型,是因为,后面讲解到面对无符号的参数我们该怎么转换. }//c结构体typedef struct
{ char ucState; /*E_GateState*/ char ucReserved[3]; }T_ControlGate;//jni中的方法体{T_ControlGatet_controlGate; //初始化结构体
//通过ptControlGate Java对象,获取该对象的jclass.
// ptControlGate 是我在java中定义的bean类对象.里面的数据类型和c中结构体类型一致,或者可以相互转换. jclass jptcontrolgateclass = env->GetObjectClass(ptControlGate);
//通过jclass,获取里面的变量的id. jfieldID ucStateID = env->GetFieldID(jptcontrolgateclass,"ucState","B");
//通过对象和变量id,获取变量的值.且将值传入到结构体中. t_controlGate.ucState =(char)env->GetByteField(ptControlGate,ucStateID);
//这是一个byte数组
jfieldID ucReserved3ID = env->GetFieldID(jptcontrolgateclass,"ucReserved3","[B");
//通过GetObjectField(); 获取到jbytearray数组对象. jbyteArray ucreservedarr = (jbyteArray)env->GetObjectField(ptControlGate,ucReserved3ID);
//我这里将数组对象转换成char*. char* ucreser =(char*) env->GetByteArrayElements(ucreservedarr,0); jsize len = env->GetArrayLength(ucreservedarr);
//这里通过赋值,一个个赋值给结构体里面,也可以通过memcpy()等赋值. for(int x=0;x<len;x++){ t_controlGate.ucReserved[x] = ucreser[x]; }
int result = Net_GateSetup(tHandle,&t_controlGate);}<6. 返回值为自定义java对象.
JNIEXPORT jobject JNICALL Java_com_viking_myapplication_JniMethod_NetGetSdkVersion (JNIEnv *env, jobject jobj){
//这个是获取需要返回的java对象的jclass jclass sdkversioclass = env->FindClass("com/viking/bean/TGetSdkVersion");
//因为接口问题,所以我直接赋值一个char数组 char szversion[256]; int ptlen ; ptlen=(unsigned int)(256); jint result = Net_GetSdkVersion(szversion,&ptlen); //这是我们公司的接口,不想去改他的接口了,直接用,所以前面我只能这么定义了. jmethodID sdkverionid = env->GetMethodID(sdkversioclass,"<init>","()V"); //获取java的构造方法id jobject sdkversionobject = env->NewObject(sdkversioclass,sdkverionid); //创建java对象 jfieldID szversionid = env->GetFieldID(sdkversioclass,"szVersion","[B"); //获取对象的变量id jbyteArray szverionarr = env->NewByteArray((int)ptlen); //创建byte数组 jbyte * szv =(jbyte*)szversion; env->SetByteArrayRegion(szverionarr,0,(int)ptlen,szv); //将jbyte*类型的数据,赋值给jbyteArray中 env->SetObjectField(sdkversionobject,szversionid,szverionarr); //直接将jbyteArray变量,赋值给对象中. return sdkversionobject; //返回java对象. }
<7. 将jbyteArray 转换成Char*
char* ch = (char *)env->GetByteArrayElements(jbyteArray,0); //jbyteArray
<8.将char[] 转换成char*
char ch[] ="hhhh";
char * cha ;
memcpy(cha ,ch ,strlen(ch)); //
<9.将char[] 转换成jbyte*
char ch[] ="hhhh";
jbyte * jb ;
memcpy(jb, ch, strlen(ch));
<10.将jbyte* 数据赋值jbyteArray中
int n =6;
jbyte* jbb = (jbyte*)env->GetByteArrayElements(jbyteArray,0); //这个jbyteArray,可以是java传入的数据.
jbyteArray jba = env->NewByteArray(n); //创建一个jbyteArray 对象
env->SetByteArrayRegion(jbb,0,n,jba); //将jbyte* 中,从0到n的值,赋值给jbyteArray中.
<11又下班了,今天就写着点了.其他的就写下节了.(后面主要是讲,1.unsigned 类型数据,跟java中数据的转换.2.c中回调函数的解决 3.将这节没贴完的代码贴完)
相关文章推荐
- Android studio NDK开发 从入门到实践-之将java代码打包成jar包
- Android studio NDK开发 从入门到实践四
- AndroidStudio NDK开发最佳入门实践
- Android studio NDK开发 从入门到实践二
- Android studio NDK开发 从入门到实践一
- Android studio NDK开发 从入门到实践五
- android studio NDK开发环境搭建实践
- AndroidStudio之NDK开发CMake CMakeLists.txt编写入门
- android studio ndk 开发入门
- Android Studio NDK开发简单入门
- Hello NDK:Android Studio + NDK开发安卓入门
- Android Studio NDK JNI开发入门记录
- Android Studio ndk-Jni开发详细入门,Aes加密demo
- Android Studio开发入门-引用jar及so文件
- 跟Google学习Android开发-工具篇-Android Studio入门
- android开发实践--新手入门
- Android开发实践:在任意目录执行NDK编译
- Android开发实践:常用NDK命令行参数
- Android 开发 之 JNI入门 - NDK从入门到精通
- 【Android 应用开发】Android 开发 之 JNI入门 - NDK从入门到精通