在Android上使用像素缓冲区对象(PBO的) [英] Using Pixel Buffer Objects (PBO's) on Android

查看:2591
本文介绍了在Android上使用像素缓冲区对象(PBO的)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在Android上,我试图在镜头帧进行一些OpenGL的处理,显示在相机preVIEW这些帧,然后连接$ C C在视频文件中的帧$。我试图用OpenGL做到这一点,使用GLSurfaceView和GLSurfaceView.Renderer和FFMPEG的视频编码。

我已经成功地处理的图像帧使用着色器。现在我需要连接code处理过的帧的视频。该GLSurfaceView.Renderer提供onDrawFrame(GL10 ..)方法。这是在此方法中,我正在试图读取使用刚刚glReadPixels()的图像帧,然后将帧上的队列,用于编码视频。在它自己的,glReadPixels()实在太慢 - 我的帧速率是个位数。我试图用像素缓冲对象加快这。这是行不通的。堵在PBO后,帧速率不变。这是我第一次使用OpenGL,我不知道从哪里开始查找问题。我这样做对吗?任何人都可以给我一些指导?先谢谢了。

 公共类MainRenderer实现GLSurfaceView.Renderer,SurfaceTexture.OnFrameAvailableListener {

。
。

    公共无效onDrawFrame(GL10 GL10){

        //创建一个缓冲器来保存图像帧
        ByteBuffer的byte_buffer = ByteBuffer.allocateDirect(this.width * this.height * 4);
        byte_buffer.order(ByteOrder.nativeOrder());

        //生成的指针帧缓冲器
        IntBuffer image_buffers = IntBuffer.allocate(1);
        GLES20.glGenBuffers(1,image_buffers);

        //创建缓冲区
        GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER,image_buffers.get(0));
        GLES20.glBufferData(GLES20.GL_ARRAY_BUFFER,byte_buffer.limit(),byte_buffer,GLES20.GL_STATIC_DRAW);
        GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER,image_buffers.get(0));

        //像素数据读入缓冲
        gl10.glReadPixels(0,0,this.width,this.height,GL10.GL_RGBA,GL10.GL_UNSIGNED_BYTE,byte_buffer);

        // EN code中的帧视频
        enQueueForEncoding(byte_buffer);

        //取消绑定缓冲
        GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER,0);
    }

。
。

}
 

解决方案

我记得glBufferData不映射内部缓冲到GPU内存,它只是将文件从你的记忆中,以缓冲区(初始化)数据。 要访问它是由glBufferData分配你应该使用glMapBufferRange内存。 该函数返回的Java缓冲区对象,你可以阅读。

On Android, I'm trying to perform some OpenGL processing on camera frames, show those frames in the camera preview and then encode the frames in a video file. I'm trying to do this with OpenGL, using the GLSurfaceView and GLSurfaceView.Renderer and with FFMPEG for video encoding.

I've successfully processed the image frames using a shader. Now I need to encode the processed frames to video. The GLSurfaceView.Renderer provides the onDrawFrame(GL10 ..) method. It's in this method that I'm attempting to read the image frames using just glReadPixels() and then place the frames on a queue for encoding to video. On it's own, glReadPixels() is much too slow - my frame rate is in the single digits. I'm attempting to speed this up using Pixel Buffer Objects. This is not working. After plugging in the pbo, the frame rate is unchanged. This is my first time using OpenGL and I do not know where to begin looking for the problem. Am I doing this right? Can anyone give me some direction? Thanks in advance.

public class MainRenderer implements GLSurfaceView.Renderer, SurfaceTexture.OnFrameAvailableListener {

.
.

    public void onDrawFrame ( GL10 gl10 ) {

        //Create a buffer to hold the image frame     
        ByteBuffer byte_buffer = ByteBuffer.allocateDirect(this.width * this.height * 4);
        byte_buffer.order(ByteOrder.nativeOrder());

        //Generate a pointer to the frame buffers
        IntBuffer image_buffers = IntBuffer.allocate(1); 
        GLES20.glGenBuffers(1, image_buffers);

        //Create the buffer
        GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, image_buffers.get(0));
        GLES20.glBufferData(GLES20.GL_ARRAY_BUFFER, byte_buffer.limit(), byte_buffer, GLES20.GL_STATIC_DRAW);
        GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, image_buffers.get(0));

        //Read the pixel data into the buffer
        gl10.glReadPixels(0, 0, this.width, this.height, GL10.GL_RGBA, GL10.GL_UNSIGNED_BYTE, byte_buffer);

        //encode the frame to video
        enQueueForEncoding(byte_buffer);

        //unbind the buffer
        GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, 0);
    }

.
.

}

解决方案

As I remember glBufferData is not mapping your internal buffer onto GPU memory, it just copies data from your memory in to the buffer(initializes). To get access to the memory which is allocated by glBufferData you should use glMapBufferRange. That function returns Java Buffer object which you can read.

这篇关于在Android上使用像素缓冲区对象(PBO的)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆