android: 如何通过更新 Surface 缓冲区从 ndk 更新 SurfaceView?

android: how to Update a SurfaceView from the ndk by updating the Surface buffer?

我正在从事图像处理项目。我有一个 SurfaceView,我想在其中显示 "images" 从 jni 端。

我按照这个 blogNDK ANativeWindow API 指令获取缓冲区的指针并从 C 端更新。

我得到了 运行 的代码,但我的 SurfaceView 没有更新(没有显示任何图像...)。更新缓冲区时也不会调用回调 surfaceChanged

这是我正在做的事情:

JNI 端:

/*
  * Class:     com_example_myLib
  * Method:    renderImage
  * Signature: (JI)V
  */

JNIEXPORT void JNICALL com_example_myLib_renderImage
  (JNIEnv *mJNIEnv, jobject mjobject, jobject javaSurface) {

#ifdef DEBUG_I
    LOGI("renderImage attempt !");
#endif

// load an ipl image. code tested and works well with ImageView.
IplImage *iplimage = loadMyIplImage();

int iplImageWidth = iplimage->width;
int iplImageHeitgh = iplimage->height;

char * javalBmpPointer = malloc(iplimage->width * iplimage->height * 4);
int _javaBmpRowBytes = iplimage->width * 4;



 // code tested and works well with ImageView.
    copyIplImageToARGBPointer(iplimage, javalBmpPointer, _javaBmpRowBytes,
            iplimage->width, iplimage->height);
#ifdef DEBUG_I
    LOGI("ANativeWindow_fromSurface");
 #endif
ANativeWindow* window = ANativeWindow_fromSurface(env, javaSurface);

#ifdef DEBUG_I
    LOGI("Got window %p", window);
 #endif

 if(window != 0 ){
    ANativeWindow_Buffer buffer;
    if (ANativeWindow_lock(window, &buffer, NULL) == 0) {
        #ifdef DEBUG_I
            LOGI("GANativeWindow_lock %p", buffer);
         #endif
        memcpy(buffer.bits, javalBmpPointer,  iplimage->width* iplimage->height* 4); // ARGB_8888
        ANativeWindow_unlockAndPost(window);
    }

    ANativeWindow_release(window);

 }

}

java 边:

// every time that I want to reload the image:
   renderImage(mySurfaceView.getHolder().getSurface());

感谢您的宝贵时间和帮助!

导致空白 SurfaceView 的最常见问题之一是为视图设置背景。视图内容旨在成为透明的 "hole",仅用于布局。 Surface 内容位于视图层下方的单独层上,因此只有在视图保持透明时它们才可见。

View 背景通常应该被禁用,并且在 View 上不绘制任何东西,除非你想要某种 "mask" 效果(比如圆角)。