qml中,eglCreatePbufferSurface渲染后,怎么显示出来
时间: 2024-03-11 16:48:42 浏览: 225
在QML中使用OpenGL ES进行渲染可以通过QQuickFramebufferObject类实现。QQuickFramebufferObject是一个QML元素,它允许你通过OpenGL ES渲染,可以将OpenGL ES渲染结果直接显示到QML界面上。
使用QQuickFramebufferObject需要自定义一个QQuickFramebufferObject子类,并实现createFramebufferObject()和Renderer两个函数。其中,createFramebufferObject()函数创建一个QOpenGLFramebufferObject对象,用于渲染,Renderer则负责OpenGL ES渲染。
在实现Renderer时,可以在rendererInitialized()函数中创建Pbuffer表面,将其和OpenGL ES上下文绑定。在render()函数中,可以使用OpenGL ES渲染Pbuffer表面,然后将渲染结果绘制到QOpenGLFramebufferObject对象中。最后,在synchronize()函数中可以将QQuickFramebufferObject元素和OpenGL ES上下文同步,确保渲染结果正确显示。
以下是一个简单的QQuickFramebufferObject子类的示例代码:
```qml
import QtQuick 2.0
import QtQuick.Window 2.0
import QtQuick.Controls 2.0
import QtQuick.Scene3D 2.0
import QtQuick.Particles 2.0
Item {
width: 640
height: 480
MyFramebuffer {
anchors.fill: parent
}
}
// MyFramebuffer.qml
import QtQuick 2.0
import QtQuick.Window 2.0
import QtQuick.Controls 2.0
import QtQuick.Scene3D 2.0
import QtQuick.Particles 2.0
Item {
width: 640
height: 480
MyFramebufferObject {
id: fbo
anchors.fill: parent
}
Rectangle {
anchors.fill: parent
color: "white"
opacity: 0.7
}
}
// MyFramebufferObject.qml
import QtQuick 2.0
import QtQuick.Window 2.0
import QtQuick.Controls 2.0
import QtQuick.Scene3D 2.0
import QtQuick.Particles 2.0
import QtQuick.Controls.Material 2.0
import QtQuick.Controls.impl 2.0
Item {
width: 640
height: 480
property int textureWidth: 512
property int textureHeight: 512
// Create Pbuffer surface and OpenGL ES context
function createFramebufferObject(size) {
var fbo = new QOpenGLFramebufferObject(size);
var context = Qt.createQmlObject("import QtQuick 2.0; import QtQuick.Window 2.0; Qt.createQmlObject('Window { visible: false; width: 1; height: 1; visibility: Window.Hidden; }', parent, 'PbufferWindow')");
var surface = context.createSurface(fbo.handle);
context.makeCurrent(surface);
return {fbo: fbo, context: context};
}
// Renderer for OpenGL ES
function MyFramebufferRenderer() {
var pbufferSurface = null;
var context = null;
var program = null;
var vertexBuffer = null;
var indexBuffer = null;
var texture = null;
var textureLocation = -1;
var vertexLocation = -1;
var texCoordLocation = -1;
var transformLocation = -1;
var matrix = mat4.create();
this.rendererInitialized = function() {
// Create Pbuffer surface and OpenGL ES context
pbufferSurface = eglCreatePbufferSurface(EGL_DEFAULT_DISPLAY, EGL_NO_CONFIG, [EGL_WIDTH, textureWidth, EGL_HEIGHT, textureHeight, EGL_NONE]);
context = eglCreateContext(EGL_DEFAULT_DISPLAY, EGL_NO_CONFIG, EGL_NO_CONTEXT, null);
eglMakeCurrent(EGL_DEFAULT_DISPLAY, pbufferSurface, pbufferSurface, context);
// Initialize OpenGL ES resources
program = glCreateProgram();
var vertexShader = glCreateShader(GL_VERTEX_SHADER);
var fragmentShader = glCreateShader(GL_FRAGMENT_SHADER);
glShaderSource(vertexShader, "attribute vec4 vertex; attribute vec2 texCoord; uniform mat4 transform; varying vec2 texCoordVar; void main() { gl_Position = transform * vertex; texCoordVar = texCoord; }");
glCompileShader(vertexShader);
glShaderSource(fragmentShader, "precision mediump float; uniform sampler2D texture; varying vec2 texCoordVar; void main() { gl_FragColor = texture2D(texture, texCoordVar); }");
glCompileShader(fragmentShader);
glAttachShader(program, vertexShader);
glAttachShader(program, fragmentShader);
glLinkProgram(program);
glUseProgram(program);
vertexLocation = glGetAttribLocation(program, "vertex");
texCoordLocation = glGetAttribLocation(program, "texCoord");
textureLocation = glGetUniformLocation(program, "texture");
transformLocation = glGetUniformLocation(program, "transform");
var vertices = new Float32Array([-1.0, -1.0, 0.0, 1.0, 1.0, -1.0, 0.0, 1.0, 1.0, 1.0, 0.0, 1.0, -1.0, 1.0, 0.0, 1.0]);
var indices = new Uint16Array([0, 1, 2, 0, 2, 3]);
vertexBuffer = glCreateBuffer();
glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
glBufferData(GL_ARRAY_BUFFER, vertices, GL_STATIC_DRAW);
indexBuffer = glCreateBuffer();
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, indices, GL_STATIC_DRAW);
texture = glCreateTexture();
glBindTexture(GL_TEXTURE_2D, texture);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, textureWidth, textureHeight, 0, GL_RGBA, GL_UNSIGNED_BYTE, null);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
}
this.render = function() {
// Render Pbuffer surface
glViewport(0, 0, textureWidth, textureHeight);
glClearColor(1.0, 1.0, 1.0, 1.0);
glClear(GL_COLOR_BUFFER_BIT);
glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
glEnableVertexAttribArray(vertexLocation);
glVertexAttribPointer(vertexLocation, 4, GL_FLOAT, false, 0, 0);
glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
glEnableVertexAttribArray(texCoordLocation);
glVertexAttribPointer(texCoordLocation, 2, GL_FLOAT, false, 0, 0);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);
glUniformMatrix4fv(transformLocation, 1, false, matrix);
glUniform1i(textureLocation, 0);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, texture);
glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_SHORT, 0);
}
this.releaseResources = function() {
// Release OpenGL ES resources
glDeleteProgram(program);
glDeleteBuffers(1, [vertexBuffer]);
glDeleteBuffers(1, [indexBuffer]);
glDeleteTextures(1, [texture]);
eglDestroyContext(EGL_DEFAULT_DISPLAY, context);
eglDestroySurface(EGL_DEFAULT_DISPLAY, pbufferSurface);
}
}
// Create framebuffer object and renderer
MyFramebufferRenderer.prototype = new QQuickFramebufferObject.Renderer;
MyFramebufferObject {
id: myFbo
width: textureWidth
height: textureHeight
antialiasing: true
textureWidth: 512
textureHeight: 512
framebufferObject: createFramebufferObject(Qt.size(textureWidth, textureHeight))
renderer: MyFramebufferRenderer {}
}
}
```
这个示例将一个自定义的QQuickFramebufferObject元素添加到界面中,然后在这个元素中创建一个Pbuffer表面,并将其和OpenGL ES上下文绑定。在渲染时,将Pbuffer表面渲染到QOpenGLFramebufferObject对象中,并通过QQuickFramebufferObject元素显示出来。
阅读全文