最近在学习NDK下的opengl es2.0开发,看过很多demos都是直接用一串字符串把shader代码写死的。并没有用一个单独的shader脚本语言文件。glShaderSource()这个方法需要的shader脚本也是通过一个char** 传入的。
而且在NDK下面也没看到有什么方式可以直接调用android工程里面的res资源文件。(目前是没发现才刚开始学)
所以我就想把shader脚本文件放在android工程的res资源目录里面,在java端读出来然后传入到jni里面去。
在java中由于是unicode编码,无论是英文字母还是汉字每个字符都是占用2个字节。但是在jni中的字符时utf-8编码,每个字符不是等长的。所以在java和jni调用的时候要注意这个问题。
下面是我在网上找到的一些把jstring和char*转换的一些sample代码:
jstring to char*
char* jstringTostring(JNIEnv* env, jstring jstr)
{
char* rtn = NULL;
jclass clsstring = env->FindClass("java/lang/String");
jstring strencode = env->NewStringUTF("utf-8");
jmethodID mid = env->GetMethodID(clsstring, "getBytes", "(Ljava/lang/String;)[B");
jbyteArray barr= (jbyteArray)env->CallObjectMethod(jstr, mid, strencode);
jsize alen = env->GetArrayLength(barr);
jbyte* ba = env->GetByteArrayElements(barr, JNI_FALSE);
if (alen > 0)
{
rtn = (char*)malloc(alen + 1);
memcpy(rtn, ba, alen);
rtn[alen] = 0;
}
env->ReleaseByteArrayElements(barr, ba, 0);
return rtn;
}
char* to jstring
jstring stoJstring(JNIEnv* env, const char* pat)
{
jclass strClass = env->FindClass("Ljava/lang/String;");
jmethodID ctorID = env->GetMethodID(strClass, "<init>", "([BLjava/lang/String;)V");
jbyteArray bytes = env->NewByteArray(strlen(pat));
env->SetByteArrayRegion(bytes, 0, strlen(pat), (jbyte*)pat);
jstring encoding = env->NewStringUTF("utf-8");
return (jstring)env->NewObject(strClass, ctorID, bytes, encoding);
}
分享到:
相关推荐
1. **获取`jstring`对象**:在JNI方法中,你可以通过参数接收Java层传递的`jstring`对象,或者通过`env->NewStringUTF()`等函数创建新的`jstring`。 2. **转换为C字符串**:使用`env->GetStringUTFChars()`函数,...
C++调用java java调用C++ 字符串参数传递 类型的转换
### JNI数据类型转换详解 ...掌握这些转换方法,不仅能提高跨语言编程的效率,还能避免潜在的内存泄漏和数据丢失风险。通过上述解析,开发者应能更加熟练地在JNI环境下进行数据交换,从而构建高效、稳定的跨平台应用。
4. **转换Java字符串**:`jstring NewStringUTF(JNIEnv *env, const char *str)`用于从C/C++字符串创建Java字符串。 5. **调用Java方法**:`jobject CallObjectMethod(JNIEnv *env, jobject obj, jmethodID method, ...
8. **字符串处理**:JNI中的字符串处理涉及到Java的`String`和C的`char*`之间的转换。`GetStringUTFChars`和`ReleaseStringUTFChars`用于获取和释放UTF-8编码的Java字符串。 9. **异常处理**:JNI提供了检查和抛出...
在JNI中,如果要在C/C++和Java之间传递结构体,就需要定义相应的Java类来匹配C/C++中的结构体,并且实现必要的JNI方法来进行转换。 #### 四、实例分析 假设有一个表示硬盘信息的结构体`DiskInfo`: ```c struct ...
7. **数据类型转换**:JNI提供了数据类型转换的方法,例如将Java的`int`转换为C的`jint`,或者将Java的`String`转换为C的`const char*`。 8. **异常处理**:在本地代码中,可以通过`ExceptionCheck`检查是否抛出了...
2. **数据类型转换**: - **字符与字符串**:Java的`char`类型在C/C++中对应`jchar`,字符串是`jstring`。在Free Pascal中,可以使用`JNIEnv`指针的`GetStringUTFChars()`和`ReleaseStringUTFChars()`方法获取和...
- **JNI接口定义**:JNI接口定义了Java和本地代码之间的桥梁,包括函数指针类型、数据类型转换以及方法ID和类ID的概念。 - **本地方法**:在Java中,使用`native`关键字声明的函数就是本地方法,它们需要在C/C++...
示例代码展示了如何在本地方法中获取和释放Java字符串的UTF-8表示。`GetStringUTFChars`用于获取字符串的C风格字符数组,而`ReleaseStringUTFChars`则用于释放这个资源。 8. **类型安全**: JNI函数通常接受并...
- **类型转换**:在Java和C/C++之间传递数据时需要注意类型转换,比如Java中的`boolean`类型对应C/C++中的`jboolean`类型。 - **内存管理**:C/C++代码需要正确处理内存分配和释放,避免内存泄漏等问题。 - **异常...
3. **对象转换**:根据需要创建 C++ 结构体,并从 Java 对象中提取数据填充结构体;反之,如果需要更新 Java 对象,也需要将 C++ 结构体的数据转换回 Java 对象。 4. **内存管理**:注意内存的分配和释放,避免内存...
对于中文字符串,使用`getBytes("UTF-8")`或`getBytes("GBK")`(根据实际编码方式)转换为字节数组,然后通过JNI的`NewDirectByteBuffer`或`GetPrimitiveArrayCritical`方法传递给C/C++。 2. **在C/C++中接收和处理...
- 定义新的类和方法。 - 处理Java对象和数组。 #### 五、Eclipse + CDT + MinGW 进行Java调用C/C++ - **安装Eclipse 3.2。** - **安装MinGW:** - 下载并安装。 - 设置环境变量。 - **安装CDT插件:** - 下载...
- **本地库实现**:在生成的头文件中,编写实际的方法实现,处理Java和C/C++之间的数据类型转换。 2. **C/C++部分(C_dllTest)**: - 可能包含一个`.c`或`.cpp`源文件,实现Java方法的本地代码。 - 通常会包含...
6. **数据类型转换**:JNI提供了一系列的类型转换函数,如`jstring`到`const char*`,`jintArray`到`int*`等,用于在Java和C/C++之间传递数据。理解这些转换函数是使用JNI的关键。 7. **异常处理**:在C/C++代码中...
7. **字符串处理**:JNI提供了处理Java字符串(`jstring`)到本地字符串(如C字符串`char*`)的函数,如`GetStringUTFChars()`和`NewStringUTF()`。 8. **异常处理**:JNI允许在本地代码中抛出和捕获Java异常,通过...
### Android JNI机制分析 ...以上步骤展示了如何在Android平台中实现Java与C/C++之间的通信以及如何利用JNI进行方法的注册和数据类型的映射。这对于理解和开发涉及高性能计算或底层操作的应用程序至关重要。
本文将详细介绍JNI中常用的函数及其使用方法,为读者提供丰富的示例源码,帮助理解这些函数如何在实际项目中应用。 #### 二、JNI基础概念与术语 - **env**: 指针,指向JNIEnv结构体,用于访问JNI接口的方法。 - **...