我正在尝试修改一个字节数组并通过 JNI 将其从 c++ 发送到 java
I'm trying to modify a byte array and send it from c++ to java via the JNI
这是我的函数:
void FrameReceived(int width, int height, const char *rawImageBytes, int size, jboolean remote)
{
if(size == 0)
return;
jboolean isAttached;
JNIEnv *env;
jint jParticipant;
jint jWidth;
jint jHeight;
jbyte *jRawImageBytes;
jbyte *modifiedRawImageBytes;
jbyteArray Array;
env = getJniEnv(&isAttached);
if (env == NULL)
goto FAIL0;
//LOGE(".... **** ....TRYING TO FIND CALLBACK");
if(remote)
{
if(frameReceivedRemoteMethod == NULL)
frameReceivedRemoteMethod = getApplicationJniMethodId(env, applicationJniObj, "vidyoConferenceFrameReceivedRemoteCallback", "(III[B)V");
if (frameReceivedRemoteMethod == NULL) {
//LOGE(".... **** ....CALLBACK NOT FOUND");
goto FAIL1;
}
}
else
{
if(frameReceivedMethod == NULL)
frameReceivedMethod = getApplicationJniMethodId(env, applicationJniObj, "vidyoConferenceFrameReceivedCallback", "(III[B)V");
if (frameReceivedMethod == NULL) {
//LOGE(".... **** ....CALLBACK NOT FOUND");
goto FAIL1;
}
}
jWidth = width;
jHeight = height;
LOGI("FrameReceived will reach here 1");
jRawImageBytes = (*env)->NewByteArray(env, size);
LOGI("FrameReceived will reach here 2");
(*env)->SetByteArrayRegion(env, jRawImageBytes, 0, size, rawImageBytes);
LOGI("FrameReceived will reach here 3");
//TODO will transform to NV21 in ndk (faster)
modifiedRawImageBytes = (*env)->NewByteArray(env, size);
LOGI("FrameReceived will reach here 4");
jint sizeWH = width * height;
jint quarter = sizeWH/4;
jint v0 = sizeWH + quarter;
LOGI("FrameReceived will reach here 5");
for (int u = sizeWH, v = v0, o = sizeWH; u < v0; u++, v++, o += 2) {
modifiedRawImageBytes[o] = jRawImageBytes[v]; // For NV21, V first
modifiedRawImageBytes[o + 1] = jRawImageBytes[u]; // For NV21, U second
}
LOGI("FrameReceived will reach here 6");
(*env)->SetByteArrayRegion(env, Array, 0, size, modifiedRawImageBytes);
LOGI("FrameReceived will reach here 7");
//LOGE(".... **** ....CALLBACK BEING CALLED");
if(remote)
{
(*env)->CallVoidMethod(env, applicationJniObj, frameReceivedRemoteMethod, 0, jWidth, jHeight, Array);
}
else
{
(*env)->CallVoidMethod(env, applicationJniObj, frameReceivedMethod, 0, jWidth, jHeight, Array);
}
//LOGE(".... **** ....CALLBACK CALLED");
(*env)->DeleteLocalRef(env, jRawImageBytes);
if (isAttached)
{
(*global_vm)->DetachCurrentThread(global_vm);
}
//LOGE("FrameReceived End");
return;
FAIL1:
if (isAttached)
{
(*global_vm)->DetachCurrentThread(global_vm);
}
FAIL0:
//LOGE("FrameReceived FAILED");
return;
}
并且它总是在此 LOG 之后崩溃:LOGI("FrameReceived will reach here 5");
在 FOR 循环中。我在这里做错了什么?这就是我试图在 NDK 中实现的目标:
公共字节[] I420toNV21(最终字节[]输入,字节[]输出,最终整数宽度,最终整数高度({ 如果(输出 == 空({ 输出 = 新字节[输入长度]; } 最终整数大小 = 宽度 * 高度; 最终整数季度 = 大小/4; 最终 int v0 = 大小 + 四分之一;
System.arraycopy(input, 0, output, 0, size); // Y is same
for (int u = size, v = v0, o = size; u < v0; u++, v++, o += 2) {
output[o] = input[v]; // For NV21, V first
output[o + 1] = input[u]; // For NV21, U second
}
return output;
}
所以我可以将 corect 格式的字节数组发送到 java。 并且不必在我的 Java 代码中执行此方法。为什么它不能将 for 循环中的值添加到 by byte 数组?
所以为了做到这一点,我稍微改变了一下逻辑。有字符 *rawImageBytes,它的大小。而不是直接创建一个 jbyteArray。我将为另一个字符数组分配空间。我将从第一个复制记忆,在第二个中。然后我调用 for Loop,以便修改我需要的内容,然后,我将创建 jbyteArray:
char *modifiedRawImageBytes = malloc(size);
memcpy(modifiedRawImageBytes, rawImageBytes, size);
jint sizeWH = width * height;
jint quarter = sizeWH/4;
jint v0 = sizeWH + quarter;
for (int u = sizeWH, v = v0, o = sizeWH; u < v0; u++, v++, o += 2) {
modifiedRawImageBytes[o] = rawImageBytes[v]; // For NV21, V first
modifiedRawImageBytes[o + 1] = rawImageBytes[u]; // For NV21, U second
}
jWidth = width;
jHeight = height;
jRawImageBytes = (*env)->NewByteArray(env, size);
(*env)->SetByteArrayRegion(env, jRawImageBytes, 0, size, modifiedRawImageBytes);
相关文章:
- 用C++包装 Java 库 (JNI)
- 如何通过 JNI 将 C 字符串表情符号传递给 Java
- JNI Java包装:如何传递byte[]参数
- Android JNI:Java通过JNI调用C++类对象
- 如何将 gnu-libstdc++ 包含在 JNI Java swing 项目中
- 如何使用 2 个字符串参数从 jni java 库调用
- JNI Java对象实例化期间的Segfault
- jni java.lang.unsatisfiedlinkerror,无法链接方法
- Error with JNI (Java and C++)
- JNI - Java 在本机线程完成执行之前退出
- c++ 插件 -> JNI --> Java 类路径
- Android JNI : java.lang.UnsatisfiedLinkError
- Jni java 启动器在 c 中工作,但在 c++ 中不起作用
- JNI : java.lang.UnsatisfiedLinkError error
- 安卓系统:JNI Java From C内存泄漏
- 当从c++调用JNI Java方法时,它会被丢弃
- JNI(Java)等效于INCREF,DECREF用于C++的python嵌入
- DLL using JNI Java classes
- JNI(Java 和 C++)在 Ubuntu 11.10 上使用 Eclipse
- JNI java.lang.UnsatisfiedLinkError: ****.***()Z