summaryrefslogtreecommitdiffstats
path: root/src/opengl
diff options
context:
space:
mode:
Diffstat (limited to 'src/opengl')
-rw-r--r--src/opengl/opengl.pro10
-rw-r--r--src/opengl/qgl.cpp184
-rw-r--r--src/opengl/qgl.h2
-rw-r--r--src/opengl/qgl_cl_p.h2
-rw-r--r--src/opengl/qgl_mac.mm30
-rw-r--r--src/opengl/qgl_p.h5
-rw-r--r--src/opengl/qglframebufferobject.cpp36
-rw-r--r--src/opengl/qglpixelbuffer_egl.cpp8
-rw-r--r--src/opengl/qglpixelbuffer_mac.mm6
-rw-r--r--src/opengl/qglpixelbuffer_win.cpp2
-rw-r--r--src/opengl/qpaintengine_opengl.cpp66
-rw-r--r--src/opengl/qpixmapdata_gl.cpp8
-rw-r--r--src/opengl/qpixmapdata_gl_p.h2
-rw-r--r--src/opengl/qwindowsurface_gl.cpp6
14 files changed, 241 insertions, 126 deletions
diff --git a/src/opengl/opengl.pro b/src/opengl/opengl.pro
index 5be48ba..cdf31cc 100644
--- a/src/opengl/opengl.pro
+++ b/src/opengl/opengl.pro
@@ -25,7 +25,6 @@ HEADERS += qgl.h \
qglcolormap.h \
qglpixelbuffer.h \
qglframebufferobject.h \
- qglpixmapfilter_p.h \
qglshaderprogram.h
SOURCES += qgl.cpp \
@@ -33,12 +32,11 @@ SOURCES += qgl.cpp \
qglpixelbuffer.cpp \
qglframebufferobject.cpp \
qglextensions.cpp \
- qglpixmapfilter.cpp \
qglshaderprogram.cpp
!contains(QT_CONFIG, opengles2) {
- HEADERS += qpaintengine_opengl_p.h
- SOURCES += qpaintengine_opengl.cpp
+ HEADERS += qpaintengine_opengl_p.h qglpixmapfilter_p.h
+ SOURCES += qpaintengine_opengl.cpp qglpixmapfilter.cpp
}
contains(QT_CONFIG, opengles2) {
@@ -132,6 +130,10 @@ wince*: {
contains(QT_CONFIG,opengles1cl) {
QMAKE_LIBS += "libGLES_CL.lib"
}
+ contains(QT_CONFIG,opengles2) {
+ QMAKE_LIBS += "libGLESv2.lib"
+ }
+
} else {
QMAKE_LIBS += $$QMAKE_LIBS_OPENGL
}
diff --git a/src/opengl/qgl.cpp b/src/opengl/qgl.cpp
index 2d90342..2d58084 100644
--- a/src/opengl/qgl.cpp
+++ b/src/opengl/qgl.cpp
@@ -1297,6 +1297,7 @@ void QGLContextPrivate::init(QPaintDevice *dev, const QGLFormat &format)
max_texture_size = -1;
version_flags_cached = false;
version_flags = QGLFormat::OpenGL_Version_None;
+ current_fbo = 0;
}
QGLContext* QGLContext::currentCtx = 0;
@@ -1327,13 +1328,21 @@ QImage qt_gl_read_framebuffer(const QSize &size, bool alpha_format, bool include
// This is an old legacy fix for PowerPC based Macs, which
// we shouldn't remove
while (p < end) {
- *p = 0xFF000000 | (*p>>8);
+ *p = 0xff000000 | (*p>>8);
++p;
}
}
} else {
// OpenGL gives ABGR (i.e. RGBA backwards); Qt wants ARGB
- img = img.rgbSwapped();
+ for (int y = 0; y < h; y++) {
+ uint *q = (uint*)img.scanLine(y);
+ for (int x=0; x < w; ++x) {
+ const uint pixel = *q;
+ *q = ((pixel << 16) & 0xff0000) | ((pixel >> 16) & 0xff) | (pixel & 0xff00ff00);
+ q++;
+ }
+ }
+
}
return img.mirrored();
}
@@ -1676,58 +1685,105 @@ static void qt_gl_clean_cache(qint64 cacheKey)
static void convertToGLFormatHelper(QImage &dst, const QImage &img, GLenum texture_format)
{
- Q_ASSERT(dst.size() == img.size());
Q_ASSERT(dst.depth() == 32);
Q_ASSERT(img.depth() == 32);
- const int width = img.width();
- const int height = img.height();
- const uint *p = (const uint*) img.scanLine(img.height() - 1);
- uint *q = (uint*) dst.scanLine(0);
-
- if (texture_format == GL_BGRA) {
- if (QSysInfo::ByteOrder == QSysInfo::BigEndian) {
- // mirror + swizzle
- for (int i=0; i < height; ++i) {
- const uint *end = p + width;
- while (p < end) {
- *q = ((*p << 24) & 0xff000000)
- | ((*p >> 24) & 0x000000ff)
- | ((*p << 8) & 0x00ff0000)
- | ((*p >> 8) & 0x0000ff00);
- p++;
- q++;
+ if (dst.size() != img.size()) {
+ int target_width = dst.width();
+ int target_height = dst.height();
+ qreal sx = target_width / qreal(img.width());
+ qreal sy = target_height / qreal(img.height());
+
+ quint32 *dest = (quint32 *) dst.scanLine(0); // NB! avoid detach here
+ uchar *srcPixels = (uchar *) img.scanLine(img.height() - 1);
+ int sbpl = img.bytesPerLine();
+ int dbpl = dst.bytesPerLine();
+
+ int ix = 0x00010000 / sx;
+ int iy = 0x00010000 / sy;
+
+ quint32 basex = int(0.5 * ix);
+ quint32 srcy = int(0.5 * iy);
+
+ // scale, swizzle and mirror in one loop
+ while (target_height--) {
+ const uint *src = (const quint32 *) (srcPixels - (srcy >> 16) * sbpl);
+ int srcx = basex;
+ for (int x=0; x<target_width; ++x) {
+ uint src_pixel = src[srcx >> 16];
+ if (texture_format == GL_BGRA) {
+ if (QSysInfo::ByteOrder == QSysInfo::BigEndian) {
+ dest[x] = ((src_pixel << 24) & 0xff000000)
+ | ((src_pixel >> 24) & 0x000000ff)
+ | ((src_pixel << 8) & 0x00ff0000)
+ | ((src_pixel >> 8) & 0x0000ff00);
+ } else {
+ dest[x] = src_pixel;
+ }
+ } else { // GL_RGBA
+ if (QSysInfo::ByteOrder == QSysInfo::BigEndian) {
+ dest[x] = (src_pixel << 8) | ((src_pixel >> 24) & 0xff);
+ } else {
+ dest[x] = ((src_pixel << 16) & 0xff0000)
+ | ((src_pixel >> 16) & 0xff)
+ | (src_pixel & 0xff00ff00);
+ }
}
- p -= 2 * width;
- }
- } else {
- const uint bytesPerLine = img.bytesPerLine();
- for (int i=0; i < height; ++i) {
- memcpy(q, p, bytesPerLine);
- q += width;
- p -= width;
+ srcx += ix;
}
+ dest = (quint32 *)(((uchar *) dest) + dbpl);
+ srcy += iy;
}
} else {
- if (QSysInfo::ByteOrder == QSysInfo::BigEndian) {
- for (int i=0; i < height; ++i) {
- const uint *end = p + width;
- while (p < end) {
- *q = (*p << 8) | ((*p >> 24) & 0xFF);
- p++;
- q++;
+ const int width = img.width();
+ const int height = img.height();
+ const uint *p = (const uint*) img.scanLine(img.height() - 1);
+ uint *q = (uint*) dst.scanLine(0);
+
+ if (texture_format == GL_BGRA) {
+ if (QSysInfo::ByteOrder == QSysInfo::BigEndian) {
+ // mirror + swizzle
+ for (int i=0; i < height; ++i) {
+ const uint *end = p + width;
+ while (p < end) {
+ *q = ((*p << 24) & 0xff000000)
+ | ((*p >> 24) & 0x000000ff)
+ | ((*p << 8) & 0x00ff0000)
+ | ((*p >> 8) & 0x0000ff00);
+ p++;
+ q++;
+ }
+ p -= 2 * width;
+ }
+ } else {
+ const uint bytesPerLine = img.bytesPerLine();
+ for (int i=0; i < height; ++i) {
+ memcpy(q, p, bytesPerLine);
+ q += width;
+ p -= width;
}
- p -= 2 * width;
}
} else {
- for (int i=0; i < height; ++i) {
- const uint *end = p + width;
- while (p < end) {
- *q = ((*p << 16) & 0xff0000) | ((*p >> 16) & 0xff) | (*p & 0xff00ff00);
- p++;
- q++;
+ if (QSysInfo::ByteOrder == QSysInfo::BigEndian) {
+ for (int i=0; i < height; ++i) {
+ const uint *end = p + width;
+ while (p < end) {
+ *q = (*p << 8) | ((*p >> 24) & 0xff);
+ p++;
+ q++;
+ }
+ p -= 2 * width;
+ }
+ } else {
+ for (int i=0; i < height; ++i) {
+ const uint *end = p + width;
+ while (p < end) {
+ *q = ((*p << 16) & 0xff0000) | ((*p >> 16) & 0xff) | (*p & 0xff00ff00);
+ p++;
+ q++;
+ }
+ p -= 2 * width;
}
- p -= 2 * width;
}
}
}
@@ -1770,19 +1826,18 @@ GLuint QGLContextPrivate::bindTexture(const QImage &image, GLenum target, GLint
}
// Scale the pixmap if needed. GL textures needs to have the
- // dimensions 2^n+2(border) x 2^m+2(border).
+ // dimensions 2^n+2(border) x 2^m+2(border), unless we're using GL
+ // 2.0 or use the GL_TEXTURE_RECTANGLE texture target
int tx_w = qt_next_power_of_two(image.width());
int tx_h = qt_next_power_of_two(image.height());
+ bool scale = false;
- // Note: the clean param is only true when a texture is bound
- // from the QOpenGLPaintEngine - in that case we have to force
- // a premultiplied texture format
QImage img = image;
if (( !(QGLFormat::openGLVersionFlags() & QGLFormat::OpenGL_Version_2_0) &&
!(QGLFormat::openGLVersionFlags() & QGLFormat::OpenGL_ES_Version_2_0) )
&& (target == GL_TEXTURE_2D && (tx_w != image.width() || tx_h != image.height())))
{
- img = image.scaled(tx_w, tx_h);
+ scale = true;
}
GLuint tx_id;
@@ -1814,17 +1869,24 @@ GLuint QGLContextPrivate::bindTexture(const QImage &image, GLenum target, GLint
ptr = reinterpret_cast<uchar *>(glMapBufferARB(GL_PIXEL_UNPACK_BUFFER_ARB, GL_WRITE_ONLY_ARB));
}
- if (ptr) {
- QImage::Format target_format = img.format();
- if (clean || img.format() != QImage::Format_ARGB32)
- target_format = QImage::Format_ARGB32_Premultiplied;
+ QImage::Format target_format = img.format();
+ // Note: the clean param is only true when a texture is bound
+ // from the QOpenGLPaintEngine - in that case we have to force
+ // a premultiplied texture format
+ if (clean || img.format() != QImage::Format_ARGB32)
+ target_format = QImage::Format_ARGB32_Premultiplied;
+ if (img.format() != target_format)
+ img = img.convertToFormat(target_format);
+ if (ptr) {
QImage buffer(ptr, img.width(), img.height(), target_format);
- convertToGLFormatHelper(buffer, img.convertToFormat(target_format), texture_format);
+ convertToGLFormatHelper(buffer, img, texture_format);
glUnmapBufferARB(GL_PIXEL_UNPACK_BUFFER_ARB);
- glTexImage2D(target, 0, format, img.width(), img.height(), 0, texture_format, GL_UNSIGNED_BYTE, 0);
+ glTexImage2D(target, 0, format, img.width(), img.height(), 0, texture_format,
+ GL_UNSIGNED_BYTE, 0);
} else {
- QImage tx = convertToGLFormat(img, clean, texture_format);
+ QImage tx(scale ? QSize(tx_w, tx_h) : img.size(), target_format);
+ convertToGLFormatHelper(tx, img, texture_format);
glTexImage2D(target, 0, format, tx.width(), tx.height(), 0, texture_format,
GL_UNSIGNED_BYTE, tx.bits());
}
@@ -2398,6 +2460,10 @@ bool QGLContext::create(const QGLContext* shareContext)
return false;
reset();
d->valid = chooseContext(shareContext);
+ if (d->valid && d->paintDevice->devType() == QInternal::Widget) {
+ QWidgetPrivate *wd = qt_widget_private(static_cast<QWidget *>(d->paintDevice));
+ wd->usesDoubleBufferedGLContext = d->glFormat.doubleBuffer();
+ }
if (d->sharing) // ok, we managed to share
qgl_share_reg()->addShare(this, shareContext);
return d->valid;
@@ -2615,6 +2681,10 @@ const QGLContext* QGLContext::currentContext()
QGLWidget. This will side-step the issue altogether, and is what
we recommend for users that need this kind of functionality.
+ On Mac OS X, when Qt is built with Cocoa support, a QGLWidget
+ can't have any sibling widgets placed ontop of itself. This is due
+ to limitations in the Cocoa API and is not supported by Apple.
+
\section1 Overlays
The QGLWidget creates a GL overlay context in addition to the
@@ -3230,6 +3300,10 @@ bool QGLWidget::event(QEvent *e)
update();
}
return true;
+# if defined(QT_MAC_USE_COCOA)
+ } else if (e->type() == QEvent::MacGLClearDrawable) {
+ d->glcx->d_ptr->clearDrawable();
+# endif
}
#endif
diff --git a/src/opengl/qgl.h b/src/opengl/qgl.h
index 01b1d6f..32fbce2 100644
--- a/src/opengl/qgl.h
+++ b/src/opengl/qgl.h
@@ -371,8 +371,8 @@ private:
friend class QMacGLWindowChangeEvent;
friend QGLContextPrivate *qt_phonon_get_dptr(const QGLContext *);
#endif
-#ifdef Q_WS_WIN
friend class QGLFramebufferObject;
+#ifdef Q_WS_WIN
friend class QGLFramebufferObjectPrivate;
friend bool qt_resolve_GLSL_functions(QGLContext *ctx);
friend bool qt_createGLSLProgram(QGLContext *ctx, GLuint &program, const char *shader_src, GLuint &shader);
diff --git a/src/opengl/qgl_cl_p.h b/src/opengl/qgl_cl_p.h
index e514ff5..c05a7d7 100644
--- a/src/opengl/qgl_cl_p.h
+++ b/src/opengl/qgl_cl_p.h
@@ -57,7 +57,7 @@ QT_BEGIN_NAMESPACE
inline void glTexParameterf (GLenum target, GLenum pname, GLfloat param)
{
- glTexParameterx(target, pname, param);
+ glTexParameterx(target, pname, FLOAT2X(param));
}
inline void glClearColor (GLclampf red, GLclampf green, GLclampf blue, GLclampf alpha)
{
diff --git a/src/opengl/qgl_mac.mm b/src/opengl/qgl_mac.mm
index 314c659..1319396 100644
--- a/src/opengl/qgl_mac.mm
+++ b/src/opengl/qgl_mac.mm
@@ -87,29 +87,6 @@ QT_FORWARD_DECLARE_CLASS(QWidget)
QT_FORWARD_DECLARE_CLASS(QWidgetPrivate)
QT_FORWARD_DECLARE_CLASS(QGLWidgetPrivate)
-@interface QT_MANGLE_NAMESPACE(QCocoaOpenGLView) : QT_MANGLE_NAMESPACE(QCocoaView)
-{
-}
-- (id)initWithQWidget:(QWidget *)widget widgetPrivate:(QWidgetPrivate *)widgetprivate;
-@end
-
-@implementation QT_MANGLE_NAMESPACE(QCocoaOpenGLView)
-- (id)initWithQWidget:(QWidget *)widget widgetPrivate:(QWidgetPrivate *)widgetprivate
-{
- self = [super initWithQWidget:widget widgetPrivate:widgetprivate];
- [[NSNotificationCenter defaultCenter] addObserver:self
- selector:@selector(_surfaceNeedsUpdate:)
- name:NSViewGlobalFrameDidChangeNotification
- object:self];
- return self;
-}
-
-- (void) _surfaceNeedsUpdate:(NSNotification*)notification
-{
- Q_UNUSED(notification);
- static_cast<QGLWidgetPrivate *>(qwidgetprivate)->glcx->updatePaintDevice();
-}
-@end
QT_BEGIN_NAMESPACE
void *qt_current_nsopengl_context()
@@ -435,6 +412,11 @@ void *QGLContextPrivate::tryFormat(const QGLFormat &format)
#endif
}
+void QGLContextPrivate::clearDrawable()
+{
+ [static_cast<NSOpenGLContext *>(cx) clearDrawable];
+}
+
/*!
\bold{Mac OS X only:} This virtual function tries to find a visual that
matches the format, reducing the demands if the original request
@@ -647,7 +629,7 @@ void QGLContext::updatePaintDevice()
// ideally we would use QWidget::isVisible(), but we get "invalid drawable" errors
if (![(NSWindow *)qt_mac_window_for(w) isVisible])
return;
- if ([static_cast<NSOpenGLContext *>(d->cx) view] != view)
+ if ([static_cast<NSOpenGLContext *>(d->cx) view] != view && ![view isHidden])
[static_cast<NSOpenGLContext *>(d->cx) setView:view];
} else if (d->paintDevice->devType() == QInternal::Pixmap) {
const QPixmap *pm = static_cast<const QPixmap *>(d->paintDevice);
diff --git a/src/opengl/qgl_p.h b/src/opengl/qgl_p.h
index b8bbeaf..1214f20 100644
--- a/src/opengl/qgl_p.h
+++ b/src/opengl/qgl_p.h
@@ -234,6 +234,7 @@ public:
#if defined(Q_WS_MAC)
bool update;
void *tryFormat(const QGLFormat &format);
+ void clearDrawable();
#endif
QGLFormat glFormat;
QGLFormat reqFormat;
@@ -254,6 +255,8 @@ public:
QGLExtensionFuncs extensionFuncs;
GLint max_texture_size;
+ GLuint current_fbo;
+
#ifdef Q_WS_WIN
static inline QGLExtensionFuncs& qt_get_extension_funcs(const QGLContext *ctx) { return ctx->d_ptr->extensionFuncs; }
#endif
@@ -267,7 +270,7 @@ public:
};
// ### make QGLContext a QObject in 5.0 and remove the proxy stuff
-class QGLSignalProxy : public QObject
+class Q_OPENGL_EXPORT QGLSignalProxy : public QObject
{
Q_OBJECT
public:
diff --git a/src/opengl/qglframebufferobject.cpp b/src/opengl/qglframebufferobject.cpp
index fb22272..4ba9213 100644
--- a/src/opengl/qglframebufferobject.cpp
+++ b/src/opengl/qglframebufferobject.cpp
@@ -48,6 +48,10 @@
#include <qlibrary.h>
#include <qimage.h>
+#ifdef QT_OPENGL_ES_1_CL
+#include "qgl_cl_p.h"
+#endif
+
QT_BEGIN_NAMESPACE
extern QImage qt_gl_read_framebuffer(const QSize&, bool, bool);
@@ -66,7 +70,7 @@ extern QImage qt_gl_read_framebuffer(const QSize&, bool, bool);
class QGLFramebufferObjectPrivate
{
public:
- QGLFramebufferObjectPrivate() : depth_stencil_buffer(0), valid(false), bound(false), ctx(0) {}
+ QGLFramebufferObjectPrivate() : depth_stencil_buffer(0), valid(false), bound(false), ctx(0), previous_fbo(0) {}
~QGLFramebufferObjectPrivate() {}
void init(const QSize& sz, QGLFramebufferObject::Attachment attachment,
@@ -81,6 +85,7 @@ public:
uint bound : 1;
QGLFramebufferObject::Attachment fbo_attachment;
QGLContext *ctx; // for Windows extension ptrs
+ GLuint previous_fbo;
};
bool QGLFramebufferObjectPrivate::checkFramebufferStatus() const
@@ -469,6 +474,15 @@ bool QGLFramebufferObject::isValid() const
Switches rendering from the default, windowing system provided
framebuffer to this framebuffer object.
Returns true upon success, false otherwise.
+
+ Since 4.6: if another QGLFramebufferObject instance was already bound
+ to the current context, then its handle() will be remembered and
+ automatically restored when release() is called. This allows multiple
+ framebuffer rendering targets to be stacked up. It is important that
+ release() is called on the stacked framebuffer objects in the reverse
+ order of the calls to bind().
+
+ \sa release()
*/
bool QGLFramebufferObject::bind()
{
@@ -478,6 +492,12 @@ bool QGLFramebufferObject::bind()
QGL_FUNC_CONTEXT;
glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, d->fbo);
d->bound = d->valid = d->checkFramebufferStatus();
+ const QGLContext *context = QGLContext::currentContext();
+ if (d->valid && context) {
+ // Save the previous setting to automatically restore in release().
+ d->previous_fbo = context->d_ptr->current_fbo;
+ context->d_ptr->current_fbo = d->fbo;
+ }
return d->valid;
}
@@ -487,6 +507,12 @@ bool QGLFramebufferObject::bind()
Switches rendering back to the default, windowing system provided
framebuffer.
Returns true upon success, false otherwise.
+
+ Since 4.6: if another QGLFramebufferObject instance was already bound
+ to the current context when bind() was called, then this function will
+ automatically re-bind it to the current context.
+
+ \sa bind()
*/
bool QGLFramebufferObject::release()
{
@@ -497,6 +523,14 @@ bool QGLFramebufferObject::release()
glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
d->valid = d->checkFramebufferStatus();
d->bound = false;
+ const QGLContext *context = QGLContext::currentContext();
+ if (d->valid && context) {
+ // Restore the previous setting for stacked framebuffer objects.
+ context->d_ptr->current_fbo = d->previous_fbo;
+ if (d->previous_fbo)
+ glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, d->previous_fbo);
+ d->previous_fbo = 0;
+ }
return d->valid;
}
diff --git a/src/opengl/qglpixelbuffer_egl.cpp b/src/opengl/qglpixelbuffer_egl.cpp
index 964efa2..5390fd1 100644
--- a/src/opengl/qglpixelbuffer_egl.cpp
+++ b/src/opengl/qglpixelbuffer_egl.cpp
@@ -47,6 +47,10 @@
#include <qimage.h>
#include <private/qgl_p.h>
+#ifdef QT_OPENGL_ES_1_CL
+#include "qgl_cl_p.h"
+#endif
+
QT_BEGIN_NAMESPACE
#ifdef EGL_BIND_TO_TEXTURE_RGBA
@@ -188,8 +192,8 @@ GLuint QGLPixelBuffer::generateDynamicTexture() const
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, d->req_size.width(), d->req_size.height(), 0, GL_RGB, GL_UNSIGNED_BYTE, 0);
else
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, d->req_size.width(), d->req_size.height(), 0, GL_RGBA, GL_UNSIGNED_BYTE, 0);
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
+ glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
+ glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
return texture;
#else
return 0;
diff --git a/src/opengl/qglpixelbuffer_mac.mm b/src/opengl/qglpixelbuffer_mac.mm
index 14941ab..9a679b1 100644
--- a/src/opengl/qglpixelbuffer_mac.mm
+++ b/src/opengl/qglpixelbuffer_mac.mm
@@ -308,10 +308,6 @@ GLuint QGLPixelBuffer::generateDynamicTexture() const
GLuint texture;
glGenTextures(1, &texture);
glBindTexture(GL_TEXTURE_2D, texture);
- [static_cast<NSOpenGLContext *>(d->share_ctx)
- setTextureImageToPixelBuffer:static_cast<NSOpenGLPixelBuffer *>(d->pbuf)
- colorBuffer:GL_FRONT];
- glBindTexture(GL_TEXTURE_2D, texture); // updates texture target
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
@@ -322,8 +318,6 @@ GLuint QGLPixelBuffer::generateDynamicTexture() const
GLuint texture;
glGenTextures(1, &texture);
glBindTexture(GL_TEXTURE_2D, texture);
- aglTexImagePBuffer(d->share_ctx, d->pbuf, GL_FRONT);
- glBindTexture(GL_TEXTURE_2D, texture); // updates texture target
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
return texture;
diff --git a/src/opengl/qglpixelbuffer_win.cpp b/src/opengl/qglpixelbuffer_win.cpp
index e81a576..e3228cc 100644
--- a/src/opengl/qglpixelbuffer_win.cpp
+++ b/src/opengl/qglpixelbuffer_win.cpp
@@ -43,7 +43,7 @@
#include <qgl.h>
#include <private/qgl_p.h>
-#include <qglpixelbuffer_p.h>
+#include <private/qglpixelbuffer_p.h>
#include <qimage.h>
#include <qdebug.h>
diff --git a/src/opengl/qpaintengine_opengl.cpp b/src/opengl/qpaintengine_opengl.cpp
index f332a50..77ff9fb 100644
--- a/src/opengl/qpaintengine_opengl.cpp
+++ b/src/opengl/qpaintengine_opengl.cpp
@@ -1924,15 +1924,15 @@ static void drawTrapezoid(const QGLTrapezoid &trap, const qreal offscreenHeight,
qreal leftB = trap.bottomLeftX + (trap.topLeftX - trap.bottomLeftX) * reciprocal;
qreal rightB = trap.bottomRightX + (trap.topRightX - trap.bottomRightX) * reciprocal;
- const bool topZero = qFuzzyCompare(topDist + 1, 1);
+ const bool topZero = qFuzzyIsNull(topDist);
reciprocal = topZero ? 1.0 / bottomDist : 1.0 / topDist;
qreal leftA = topZero ? (trap.bottomLeftX - leftB) * reciprocal : (trap.topLeftX - leftB) * reciprocal;
qreal rightA = topZero ? (trap.bottomRightX - rightB) * reciprocal : (trap.topRightX - rightB) * reciprocal;
- qreal invLeftA = qFuzzyCompare(leftA + 1, 1) ? 0.0 : 1.0 / leftA;
- qreal invRightA = qFuzzyCompare(rightA + 1, 1) ? 0.0 : 1.0 / rightA;
+ qreal invLeftA = qFuzzyIsNull(leftA) ? 0.0 : 1.0 / leftA;
+ qreal invRightA = qFuzzyIsNull(rightA) ? 0.0 : 1.0 / rightA;
// fragment program needs the negative of invRightA as it mirrors the line
glTexCoord4f(topDist, bottomDist, invLeftA, -invRightA);
@@ -1983,7 +1983,7 @@ public:
void QOpenGLTrapezoidToArrayTessellator::addTrap(const Trapezoid &trap)
{
// On OpenGL ES we convert the trap to 2 triangles
-#ifndef QT_OPENGL_ES_1
+#ifndef QT_OPENGL_ES
if (size > allocated - 8) {
#else
if (size > allocated - 12) {
@@ -1994,31 +1994,31 @@ void QOpenGLTrapezoidToArrayTessellator::addTrap(const Trapezoid &trap)
QGLTrapezoid t = toGLTrapezoid(trap);
-#ifndef QT_OPENGL_ES_1
- vertices[size++] = t.topLeftX;
- vertices[size++] = t.top;
- vertices[size++] = t.topRightX;
- vertices[size++] = t.top;
- vertices[size++] = t.bottomRightX;
- vertices[size++] = t.bottom;
- vertices[size++] = t.bottomLeftX;
- vertices[size++] = t.bottom;
+#ifndef QT_OPENGL_ES
+ vertices[size++] = f2vt(t.topLeftX);
+ vertices[size++] = f2vt(t.top);
+ vertices[size++] = f2vt(t.topRightX);
+ vertices[size++] = f2vt(t.top);
+ vertices[size++] = f2vt(t.bottomRightX);
+ vertices[size++] = f2vt(t.bottom);
+ vertices[size++] = f2vt(t.bottomLeftX);
+ vertices[size++] = f2vt(t.bottom);
#else
// First triangle
- vertices[size++] = t.topLeftX;
- vertices[size++] = t.top;
- vertices[size++] = t.topRightX;
- vertices[size++] = t.top;
- vertices[size++] = t.bottomRightX;
- vertices[size++] = t.bottom;
+ vertices[size++] = f2vt(t.topLeftX);
+ vertices[size++] = f2vt(t.top);
+ vertices[size++] = f2vt(t.topRightX);
+ vertices[size++] = f2vt(t.top);
+ vertices[size++] = f2vt(t.bottomRightX);
+ vertices[size++] = f2vt(t.bottom);
// Second triangle
- vertices[size++] = t.bottomLeftX;
- vertices[size++] = t.bottom;
- vertices[size++] = t.topLeftX;
- vertices[size++] = t.top;
- vertices[size++] = t.bottomRightX;
- vertices[size++] = t.bottom;
+ vertices[size++] = f2vt(t.bottomLeftX);
+ vertices[size++] = f2vt(t.bottom);
+ vertices[size++] = f2vt(t.topLeftX);
+ vertices[size++] = f2vt(t.top);
+ vertices[size++] = f2vt(t.bottomRightX);
+ vertices[size++] = f2vt(t.bottom);
#endif
}
@@ -3445,8 +3445,7 @@ QVector<QGLTrapezoid> QGLRectMaskGenerator::generateTrapezoids()
// manhattan distance (no rotation)
qreal width = qAbs(delta.x()) + qAbs(delta.y());
- Q_ASSERT(qFuzzyCompare(delta.x() + 1, static_cast<qreal>(1))
- || qFuzzyCompare(delta.y() + 1, static_cast<qreal>(1)));
+ Q_ASSERT(qFuzzyIsNull(delta.x()) || qFuzzyIsNull(delta.y()));
tessellator.tessellateRect(first, last, width);
} else {
@@ -3716,8 +3715,14 @@ void QOpenGLPaintEngine::drawRects(const QRectF *rects, int rectCount)
d->disableClipping();
GLuint program = qt_gl_program_cache()->getProgram(d->drawable.context(),
FRAGMENT_PROGRAM_MASK_TRAPEZOID_AA, 0, true);
- QGLRectMaskGenerator maskGenerator(path, d->matrix, d->offscreen, program);
- d->addItem(qt_mask_texture_cache()->getMask(maskGenerator, d));
+
+ if (d->matrix.type() >= QTransform::TxProject) {
+ QGLPathMaskGenerator maskGenerator(path, d->matrix, d->offscreen, program);
+ d->addItem(qt_mask_texture_cache()->getMask(maskGenerator, d));
+ } else {
+ QGLRectMaskGenerator maskGenerator(path, d->matrix, d->offscreen, program);
+ d->addItem(qt_mask_texture_cache()->getMask(maskGenerator, d));
+ }
d->enableClipping();
}
@@ -5328,6 +5333,9 @@ void QOpenGLPaintEnginePrivate::composite(GLuint primitive, const q_vertexType *
Q_Q(QOpenGLPaintEngine);
QGL_FUNC_CONTEXT;
+ if (current_style == Qt::NoBrush)
+ return;
+
DEBUG_ONCE qDebug() << "QOpenGLPaintEnginePrivate: Using compositing program: fragment_brush ="
<< fragment_brush << ", fragment_composition_mode =" << fragment_composition_mode;
diff --git a/src/opengl/qpixmapdata_gl.cpp b/src/opengl/qpixmapdata_gl.cpp
index 5d668cd..b079557 100644
--- a/src/opengl/qpixmapdata_gl.cpp
+++ b/src/opengl/qpixmapdata_gl.cpp
@@ -205,6 +205,14 @@ void QGLPixmapData::fromImage(const QImage &image,
m_dirty = true;
}
+bool QGLPixmapData::scroll(int dx, int dy, const QRect &rect)
+{
+ Q_UNUSED(dx);
+ Q_UNUSED(dy);
+ Q_UNUSED(rect);
+ return false;
+}
+
void QGLPixmapData::fill(const QColor &color)
{
if (!isValid())
diff --git a/src/opengl/qpixmapdata_gl_p.h b/src/opengl/qpixmapdata_gl_p.h
index 63703fd..e450f01 100644
--- a/src/opengl/qpixmapdata_gl_p.h
+++ b/src/opengl/qpixmapdata_gl_p.h
@@ -73,6 +73,8 @@ public:
void fromImage(const QImage &image,
Qt::ImageConversionFlags flags);
+ bool scroll(int dx, int dy, const QRect &rect);
+
void fill(const QColor &color);
bool hasAlphaChannel() const;
QImage toImage() const;
diff --git a/src/opengl/qwindowsurface_gl.cpp b/src/opengl/qwindowsurface_gl.cpp
index 3dd3064..b41adf9 100644
--- a/src/opengl/qwindowsurface_gl.cpp
+++ b/src/opengl/qwindowsurface_gl.cpp
@@ -76,13 +76,17 @@
#define GLX_SAMPLES_ARB 100001
#endif
+#ifdef QT_OPENGL_ES_1_CL
+#include "qgl_cl_p.h"
+#endif
+
QT_BEGIN_NAMESPACE
//
// QGLGraphicsSystem
//
#ifdef Q_WS_WIN
-Q_GUI_EXPORT bool qt_win_owndc_required;
+extern Q_GUI_EXPORT bool qt_win_owndc_required;
#endif
QGLGraphicsSystem::QGLGraphicsSystem()
: QGraphicsSystem()