Add the egl xcomposite extension
authorJørgen Lind <jorgen.lind@nokia.com>
Thu, 7 Apr 2011 16:05:02 +0000 (18:05 +0200)
committerJørgen Lind <jorgen.lind@nokia.com>
Thu, 7 Apr 2011 16:07:46 +0000 (18:07 +0200)
examples/qwidget-compositor/qt-compositor.pro
src/qt-compositor/hardware_integration/hardware_integration.pri
src/qt-compositor/hardware_integration/xcomposite_egl/xcomposite_egl.pri [new file with mode: 0644]
src/qt-compositor/hardware_integration/xcomposite_egl/xcompositeeglintegration.cpp [new file with mode: 0644]
src/qt-compositor/hardware_integration/xcomposite_egl/xcompositeeglintegration.h [new file with mode: 0644]

index b31c02e..0c0001f 100644 (file)
@@ -8,6 +8,7 @@ INCLUDEPATH += .
 #CONFIG += mesa_egl
 #CONFIG += dri2_xcb
 #CONFIG += xcomposite_glx
+#CONFIG += xcomposite_egl
 
 # comment out the following to not use pkg-config in the pri files
 CONFIG += use_pkgconfig
index 381c428..7e5ec42 100644 (file)
@@ -18,6 +18,9 @@ wayland_gl{
                 include (dri2_xcb/dri2_xcb.pri)
                 DEFINES += QT_COMPOSITOR_DRI2_XCB
             }
+            xcomposite_egl {
+                include (xcomposite_egl/xcomposite_egl.pri)
+            }
         } else {
             xcomposite_glx {
                 include (xcomposite_glx/xcomposite_glx.pri)
diff --git a/src/qt-compositor/hardware_integration/xcomposite_egl/xcomposite_egl.pri b/src/qt-compositor/hardware_integration/xcomposite_egl/xcomposite_egl.pri
new file mode 100644 (file)
index 0000000..21aa45c
--- /dev/null
@@ -0,0 +1,9 @@
+include (../xcomposite_share/xcomposite_share.pri)
+
+LIBS += -lXcomposite -lEGL
+
+HEADERS += \
+    $$PWD/xcompositeeglintegration.h
+
+SOURCES += \
+    $$PWD/xcompositeeglintegration.cpp
diff --git a/src/qt-compositor/hardware_integration/xcomposite_egl/xcompositeeglintegration.cpp b/src/qt-compositor/hardware_integration/xcomposite_egl/xcompositeeglintegration.cpp
new file mode 100644 (file)
index 0000000..720cec6
--- /dev/null
@@ -0,0 +1,104 @@
+#include "xcompositeeglintegration.h"
+
+#include "waylandobject.h"
+#include "wayland_wrapper/wlcompositor.h"
+#include "wayland-xcomposite-server-protocol.h"
+
+#include <QtGui/QPlatformNativeInterface>
+#include <QtGui/QPlatformGLContext>
+#include <private/qapplication_p.h>
+
+#include "xcompositebuffer.h"
+#include "xcompositehandler.h"
+#include <X11/extensions/Xcomposite.h>
+
+#include <QtCore/QDebug>
+
+QVector<EGLint> eglbuildSpec()
+{
+    QVector<EGLint> spec;
+
+    spec.append(EGL_SURFACE_TYPE); spec.append(EGL_PIXMAP_BIT);
+    spec.append(EGL_RENDERABLE_TYPE); spec.append(EGL_OPENGL_ES2_BIT);
+    spec.append(EGL_BIND_TO_TEXTURE_RGB); spec.append(EGL_TRUE);
+    spec.append(EGL_NONE);
+    return spec;
+}
+
+
+struct wl_xcomposite_interface XCompositeHandler::xcomposite_interface = {
+    XCompositeHandler::create_buffer
+};
+
+GraphicsHardwareIntegration *GraphicsHardwareIntegration::createGraphicsHardwareIntegration(WaylandCompositor *compositor)
+{
+    return new XCompositeEglIntegration(compositor);
+}
+
+XCompositeEglIntegration::XCompositeEglIntegration(WaylandCompositor *compositor)
+    : GraphicsHardwareIntegration(compositor)
+    , mDisplay(0)
+{
+    QPlatformNativeInterface *nativeInterface = QApplicationPrivate::platformIntegration()->nativeInterface();
+    if (nativeInterface) {
+        mDisplay = static_cast<Display *>(nativeInterface->nativeResourceForWidget("Display",m_compositor->topLevelWidget()));
+        if (!mDisplay)
+            qFatal("could not retireve Display from platform integration");
+        mEglDisplay = static_cast<EGLDisplay>(nativeInterface->nativeResourceForWidget("EGLDisplay",m_compositor->topLevelWidget()));
+        if (!mEglDisplay)
+            qFatal("could not retrieve EGLDisplay from plaform integration");
+    } else {
+        qFatal("Platform integration doesn't have native interface");
+    }
+    mScreen = XDefaultScreen(mDisplay);
+}
+
+void XCompositeEglIntegration::initializeHardware(Wayland::Display *waylandDisplay)
+{
+    XCompositeHandler *handler = new XCompositeHandler(m_compositor->handle(),mDisplay,m_compositor->topLevelWidget());
+    waylandDisplay->addGlobalObject(handler->base(), &wl_xcomposite_interface, &XCompositeHandler::xcomposite_interface,XCompositeHandler::send_root_information);
+
+    QPlatformGLContext *glContext = m_compositor->topLevelWidget()->platformWindow()->glContext();
+
+}
+
+GLuint XCompositeEglIntegration::createTextureFromBuffer(wl_buffer *buffer)
+{
+    XCompositeBuffer *compositorBuffer = Wayland::wayland_cast<XCompositeBuffer *>(buffer);
+    Pixmap pixmap = XCompositeNameWindowPixmap(mDisplay, compositorBuffer->window());
+
+    QVector<EGLint> eglConfigSpec = eglbuildSpec();
+
+    EGLint matching = 0;
+    EGLConfig config;
+    bool matched = eglChooseConfig(mEglDisplay,eglConfigSpec.constData(),&config,1,&matching);
+    if (!matched || !matching) {
+        qWarning("Could not retrieve a suitable EGL config");
+        return 0;
+    }
+
+    QVector<EGLint> attribList;
+
+    attribList.append(EGL_TEXTURE_FORMAT);
+    attribList.append(EGL_TEXTURE_RGB);
+    attribList.append(EGL_TEXTURE_TARGET);
+    attribList.append(EGL_TEXTURE_2D);
+    attribList.append(EGL_NONE);
+
+    EGLSurface surface = eglCreatePixmapSurface(mEglDisplay,config,pixmap,attribList.constData());
+    if (surface == EGL_NO_SURFACE) {
+        qDebug() << "Failed to create eglsurface" << pixmap << compositorBuffer->window();
+    }
+    GLuint textureId;
+    glGenTextures(1,&textureId);
+    glBindTexture(GL_TEXTURE_2D, textureId);
+
+    if (!eglBindTexImage(mEglDisplay,surface,EGL_BACK_BUFFER)) {
+        qDebug() << "Failed to bind";
+    }
+
+    //    eglDestroySurface(mEglDisplay,surface);
+
+    return textureId;
+
+}
diff --git a/src/qt-compositor/hardware_integration/xcomposite_egl/xcompositeeglintegration.h b/src/qt-compositor/hardware_integration/xcomposite_egl/xcompositeeglintegration.h
new file mode 100644 (file)
index 0000000..9274626
--- /dev/null
@@ -0,0 +1,25 @@
+#ifndef XCOMPOSITEEGLINTEGRATION_H
+#define XCOMPOSITEEGLINTEGRATION_H
+
+#include "hardware_integration/graphicshardwareintegration.h"
+
+#include "xlibinclude.h"
+
+#include <EGL/egl.h>
+
+class XCompositeEglIntegration : public GraphicsHardwareIntegration
+{
+public:
+    XCompositeEglIntegration(WaylandCompositor *compositor);
+
+    void initializeHardware(Wayland::Display *waylandDisplay);
+
+    GLuint createTextureFromBuffer(struct wl_buffer *buffer);
+
+private:
+    Display *mDisplay;
+    EGLDisplay mEglDisplay;
+    int mScreen;
+};
+
+#endif // XCOMPOSITEEGLINTEGRATION_H