src/opengl/qgl.cpp
changeset 33 3e2da88830cd
parent 30 5dc02b23752f
child 37 758a864f9613
equal deleted inserted replaced
30:5dc02b23752f 33:3e2da88830cd
    89 #include <private/qwindowsurface_gl_p.h>
    89 #include <private/qwindowsurface_gl_p.h>
    90 #include <private/qimagepixmapcleanuphooks_p.h>
    90 #include <private/qimagepixmapcleanuphooks_p.h>
    91 #include "qcolormap.h"
    91 #include "qcolormap.h"
    92 #include "qfile.h"
    92 #include "qfile.h"
    93 #include "qlibrary.h"
    93 #include "qlibrary.h"
       
    94 #include <qmutex.h>
    94 
    95 
    95 
    96 
    96 QT_BEGIN_NAMESPACE
    97 QT_BEGIN_NAMESPACE
    97 
    98 
    98 #if defined(Q_WS_X11) || defined(Q_WS_MAC) || defined(Q_WS_QWS)
    99 #if defined(Q_WS_X11) || defined(Q_WS_MAC) || defined(Q_WS_QWS)
  1253                             QGLFormat::OpenGL_Version_1_5 |
  1254                             QGLFormat::OpenGL_Version_1_5 |
  1254                             QGLFormat::OpenGL_Version_2_0 |
  1255                             QGLFormat::OpenGL_Version_2_0 |
  1255                             QGLFormat::OpenGL_Version_2_1 |
  1256                             QGLFormat::OpenGL_Version_2_1 |
  1256                             QGLFormat::OpenGL_Version_3_0;
  1257                             QGLFormat::OpenGL_Version_3_0;
  1257             switch (versionString[2].toAscii()) {
  1258             switch (versionString[2].toAscii()) {
       
  1259             case '3':
       
  1260                 versionFlags |= QGLFormat::OpenGL_Version_3_3;
  1258             case '2':
  1261             case '2':
  1259                 versionFlags |= QGLFormat::OpenGL_Version_3_2;
  1262                 versionFlags |= QGLFormat::OpenGL_Version_3_2;
  1260             case '1':
  1263             case '1':
  1261                 versionFlags |= QGLFormat::OpenGL_Version_3_1;
  1264                 versionFlags |= QGLFormat::OpenGL_Version_3_1;
  1262             case '0':
  1265             case '0':
  1263                 break;
  1266                 break;
  1264             default:
  1267             default:
  1265                 versionFlags |= QGLFormat::OpenGL_Version_3_1 |
  1268                 versionFlags |= QGLFormat::OpenGL_Version_3_1 |
  1266                                 QGLFormat::OpenGL_Version_3_2;
  1269                                 QGLFormat::OpenGL_Version_3_2 |
       
  1270                                 QGLFormat::OpenGL_Version_3_3;
  1267                 break;
  1271                 break;
  1268             }
  1272             }
       
  1273         } else if (versionString.startsWith(QLatin1String("4."))) {
       
  1274             versionFlags |= QGLFormat::OpenGL_Version_1_1 |
       
  1275                             QGLFormat::OpenGL_Version_1_2 |
       
  1276                             QGLFormat::OpenGL_Version_1_3 |
       
  1277                             QGLFormat::OpenGL_Version_1_4 |
       
  1278                             QGLFormat::OpenGL_Version_1_5 |
       
  1279                             QGLFormat::OpenGL_Version_2_0 |
       
  1280                             QGLFormat::OpenGL_Version_2_1 |
       
  1281                             QGLFormat::OpenGL_Version_3_0 |
       
  1282                             QGLFormat::OpenGL_Version_3_1 |
       
  1283                             QGLFormat::OpenGL_Version_3_2 |
       
  1284                             QGLFormat::OpenGL_Version_3_3 |
       
  1285                             QGLFormat::OpenGL_Version_4_0;
  1269         } else {
  1286         } else {
  1270             versionFlags |= QGLFormat::OpenGL_Version_1_1 |
  1287             versionFlags |= QGLFormat::OpenGL_Version_1_1 |
  1271                             QGLFormat::OpenGL_Version_1_2 |
  1288                             QGLFormat::OpenGL_Version_1_2 |
  1272                             QGLFormat::OpenGL_Version_1_3 |
  1289                             QGLFormat::OpenGL_Version_1_3 |
  1273                             QGLFormat::OpenGL_Version_1_4 |
  1290                             QGLFormat::OpenGL_Version_1_4 |
  1274                             QGLFormat::OpenGL_Version_1_5 |
  1291                             QGLFormat::OpenGL_Version_1_5 |
  1275                             QGLFormat::OpenGL_Version_2_0 |
  1292                             QGLFormat::OpenGL_Version_2_0 |
  1276                             QGLFormat::OpenGL_Version_2_1 |
  1293                             QGLFormat::OpenGL_Version_2_1 |
  1277                             QGLFormat::OpenGL_Version_3_0 |
  1294                             QGLFormat::OpenGL_Version_3_0 |
  1278                             QGLFormat::OpenGL_Version_3_1 |
  1295                             QGLFormat::OpenGL_Version_3_1 |
  1279                             QGLFormat::OpenGL_Version_3_2;
  1296                             QGLFormat::OpenGL_Version_3_2 |
       
  1297                             QGLFormat::OpenGL_Version_3_3 |
       
  1298                             QGLFormat::OpenGL_Version_4_0;
  1280         }
  1299         }
  1281     }
  1300     }
  1282     return versionFlags;
  1301     return versionFlags;
  1283 }
  1302 }
  1284 
  1303 
  1312     \value OpenGL_Version_3_1  OpenGL version 3.1 or higher is present.
  1331     \value OpenGL_Version_3_1  OpenGL version 3.1 or higher is present.
  1313     Note that OpenGL version 3.1 or higher does not necessarily support all the features of
  1332     Note that OpenGL version 3.1 or higher does not necessarily support all the features of
  1314     version 3.0 and lower.
  1333     version 3.0 and lower.
  1315 
  1334 
  1316     \value OpenGL_Version_3_2  OpenGL version 3.2 or higher is present.
  1335     \value OpenGL_Version_3_2  OpenGL version 3.2 or higher is present.
       
  1336 
       
  1337     \value OpenGL_Version_3_3  OpenGL version 3.3 or higher is present.
       
  1338 
       
  1339     \value OpenGL_Version_4_0  OpenGL version 4.0 or higher is present.
  1317 
  1340 
  1318     \value OpenGL_ES_CommonLite_Version_1_0  OpenGL ES version 1.0 Common Lite or higher is present.
  1341     \value OpenGL_ES_CommonLite_Version_1_0  OpenGL ES version 1.0 Common Lite or higher is present.
  1319 
  1342 
  1320     \value OpenGL_ES_Common_Version_1_0  OpenGL ES version 1.0 Common or higher is present.
  1343     \value OpenGL_ES_Common_Version_1_0  OpenGL ES version 1.0 Common or higher is present.
  1321     The Common profile supports all the features of Common Lite.
  1344     The Common profile supports all the features of Common Lite.
  1500         && a.d->majorVersion == b.d->majorVersion
  1523         && a.d->majorVersion == b.d->majorVersion
  1501         && a.d->minorVersion == b.d->minorVersion
  1524         && a.d->minorVersion == b.d->minorVersion
  1502         && a.d->profile == b.d->profile);
  1525         && a.d->profile == b.d->profile);
  1503 }
  1526 }
  1504 
  1527 
       
  1528 #ifndef QT_NO_DEBUG_STREAM
       
  1529 QDebug operator<<(QDebug dbg, const QGLFormat &f)
       
  1530 {
       
  1531     const QGLFormatPrivate * const d = f.d;
       
  1532 
       
  1533     dbg.nospace() << "QGLFormat("
       
  1534                   << "options " << d->opts
       
  1535                   << ", plane " << d->pln
       
  1536                   << ", depthBufferSize " << d->depthSize
       
  1537                   << ", accumBufferSize " << d->accumSize
       
  1538                   << ", stencilBufferSize " << d->stencilSize
       
  1539                   << ", redBufferSize " << d->redSize
       
  1540                   << ", greenBufferSize " << d->greenSize
       
  1541                   << ", blueBufferSize " << d->blueSize
       
  1542                   << ", alphaBufferSize " << d->alphaSize
       
  1543                   << ", samples " << d->numSamples
       
  1544                   << ", swapInterval " << d->swapInterval
       
  1545                   << ", majorVersion " << d->majorVersion
       
  1546                   << ", minorVersion " << d->minorVersion
       
  1547                   << ", profile " << d->profile
       
  1548                   << ')';
       
  1549 
       
  1550     return dbg.space();
       
  1551 }
       
  1552 #endif
       
  1553 
  1505 
  1554 
  1506 /*!
  1555 /*!
  1507     Returns false if all the options of the two QGLFormat objects
  1556     Returns false if all the options of the two QGLFormat objects
  1508     \a a and \a b are equal; otherwise returns true.
  1557     \a a and \a b are equal; otherwise returns true.
  1509 
  1558 
  1512 
  1561 
  1513 bool operator!=(const QGLFormat& a, const QGLFormat& b)
  1562 bool operator!=(const QGLFormat& a, const QGLFormat& b)
  1514 {
  1563 {
  1515     return !(a == b);
  1564     return !(a == b);
  1516 }
  1565 }
       
  1566 
       
  1567 struct QGLContextGroupList {
       
  1568     void append(QGLContextGroup *group) {
       
  1569         QMutexLocker locker(&m_mutex);
       
  1570         m_list.append(group);
       
  1571     }
       
  1572 
       
  1573     void remove(QGLContextGroup *group) {
       
  1574         QMutexLocker locker(&m_mutex);
       
  1575         m_list.removeOne(group);
       
  1576     }
       
  1577 
       
  1578     QList<QGLContextGroup *> m_list;
       
  1579     QMutex m_mutex;
       
  1580 };
       
  1581 
       
  1582 Q_GLOBAL_STATIC(QGLContextGroupList, qt_context_groups)
  1517 
  1583 
  1518 /*****************************************************************************
  1584 /*****************************************************************************
  1519   QGLContext implementation
  1585   QGLContext implementation
  1520  *****************************************************************************/
  1586  *****************************************************************************/
       
  1587 
       
  1588 QGLContextGroup::QGLContextGroup(const QGLContext *context)
       
  1589     : m_context(context), m_guards(0), m_refs(1)
       
  1590 {
       
  1591     qt_context_groups()->append(this);
       
  1592 }
  1521 
  1593 
  1522 QGLContextGroup::~QGLContextGroup()
  1594 QGLContextGroup::~QGLContextGroup()
  1523 {
  1595 {
  1524     // Clear any remaining QGLSharedResourceGuard objects on the group.
  1596     // Clear any remaining QGLSharedResourceGuard objects on the group.
  1525     QGLSharedResourceGuard *guard = m_guards;
  1597     QGLSharedResourceGuard *guard = m_guards;
  1526     while (guard != 0) {
  1598     while (guard != 0) {
  1527         guard->m_group = 0;
  1599         guard->m_group = 0;
  1528         guard->m_id = 0;
  1600         guard->m_id = 0;
  1529         guard = guard->m_next;
  1601         guard = guard->m_next;
  1530     }
  1602     }
       
  1603     qt_context_groups()->remove(this);
  1531 }
  1604 }
  1532 
  1605 
  1533 void QGLContextGroup::addGuard(QGLSharedResourceGuard *guard)
  1606 void QGLContextGroup::addGuard(QGLSharedResourceGuard *guard)
  1534 {
  1607 {
  1535     if (m_guards)
  1608     if (m_guards)
  1734 void QGLTextureCache::insert(QGLContext* ctx, qint64 key, QGLTexture* texture, int cost)
  1807 void QGLTextureCache::insert(QGLContext* ctx, qint64 key, QGLTexture* texture, int cost)
  1735 {
  1808 {
  1736     QWriteLocker locker(&m_lock);
  1809     QWriteLocker locker(&m_lock);
  1737     if (m_cache.totalCost() + cost > m_cache.maxCost()) {
  1810     if (m_cache.totalCost() + cost > m_cache.maxCost()) {
  1738         // the cache is full - make an attempt to remove something
  1811         // the cache is full - make an attempt to remove something
  1739         const QList<qint64> keys = m_cache.keys();
  1812         const QList<QGLTextureCacheKey> keys = m_cache.keys();
  1740         int i = 0;
  1813         int i = 0;
  1741         while (i < m_cache.count()
  1814         while (i < m_cache.count()
  1742                && (m_cache.totalCost() + cost > m_cache.maxCost())) {
  1815                && (m_cache.totalCost() + cost > m_cache.maxCost())) {
  1743             QGLTexture *tex = m_cache.object(keys.at(i));
  1816             QGLTexture *tex = m_cache.object(keys.at(i));
  1744             if (tex->context == ctx)
  1817             if (tex->context == ctx)
  1745                 m_cache.remove(keys.at(i));
  1818                 m_cache.remove(keys.at(i));
  1746             ++i;
  1819             ++i;
  1747         }
  1820         }
  1748     }
  1821     }
  1749     m_cache.insert(key, texture, cost);
  1822     const QGLTextureCacheKey cacheKey = {key, QGLContextPrivate::contextGroup(ctx)};
       
  1823     m_cache.insert(cacheKey, texture, cost);
       
  1824 }
       
  1825 
       
  1826 void QGLTextureCache::remove(qint64 key)
       
  1827 {
       
  1828     QWriteLocker locker(&m_lock);
       
  1829     QMutexLocker groupLocker(&qt_context_groups()->m_mutex);
       
  1830     QList<QGLContextGroup *>::const_iterator it = qt_context_groups()->m_list.constBegin();
       
  1831     while (it != qt_context_groups()->m_list.constEnd()) {
       
  1832         const QGLTextureCacheKey cacheKey = {key, *it};
       
  1833         m_cache.remove(cacheKey);
       
  1834         ++it;
       
  1835     }
  1750 }
  1836 }
  1751 
  1837 
  1752 bool QGLTextureCache::remove(QGLContext* ctx, GLuint textureId)
  1838 bool QGLTextureCache::remove(QGLContext* ctx, GLuint textureId)
  1753 {
  1839 {
  1754     QWriteLocker locker(&m_lock);
  1840     QWriteLocker locker(&m_lock);
  1755     QList<qint64> keys = m_cache.keys();
  1841     QList<QGLTextureCacheKey> keys = m_cache.keys();
  1756     for (int i = 0; i < keys.size(); ++i) {
  1842     for (int i = 0; i < keys.size(); ++i) {
  1757         QGLTexture *tex = m_cache.object(keys.at(i));
  1843         QGLTexture *tex = m_cache.object(keys.at(i));
  1758         if (tex->id == textureId && tex->context == ctx) {
  1844         if (tex->id == textureId && tex->context == ctx) {
  1759             tex->options |= QGLContext::MemoryManagedBindOption; // forces a glDeleteTextures() call
  1845             tex->options |= QGLContext::MemoryManagedBindOption; // forces a glDeleteTextures() call
  1760             m_cache.remove(keys.at(i));
  1846             m_cache.remove(keys.at(i));
  1765 }
  1851 }
  1766 
  1852 
  1767 void QGLTextureCache::removeContextTextures(QGLContext* ctx)
  1853 void QGLTextureCache::removeContextTextures(QGLContext* ctx)
  1768 {
  1854 {
  1769     QWriteLocker locker(&m_lock);
  1855     QWriteLocker locker(&m_lock);
  1770     QList<qint64> keys = m_cache.keys();
  1856     QList<QGLTextureCacheKey> keys = m_cache.keys();
  1771     for (int i = 0; i < keys.size(); ++i) {
  1857     for (int i = 0; i < keys.size(); ++i) {
  1772         const qint64 &key = keys.at(i);
  1858         const QGLTextureCacheKey &key = keys.at(i);
  1773         if (m_cache.object(key)->context == ctx)
  1859         if (m_cache.object(key)->context == ctx)
  1774             m_cache.remove(key);
  1860             m_cache.remove(key);
  1775     }
  1861     }
  1776 }
  1862 }
  1777 
  1863 
  1780   is deref'ed
  1866   is deref'ed
  1781 */
  1867 */
  1782 void QGLTextureCache::cleanupTexturesForCacheKey(qint64 cacheKey)
  1868 void QGLTextureCache::cleanupTexturesForCacheKey(qint64 cacheKey)
  1783 {
  1869 {
  1784     qt_gl_texture_cache()->remove(cacheKey);
  1870     qt_gl_texture_cache()->remove(cacheKey);
  1785     Q_ASSERT(qt_gl_texture_cache()->getTexture(cacheKey) == 0);
       
  1786 }
  1871 }
  1787 
  1872 
  1788 
  1873 
  1789 void QGLTextureCache::cleanupTexturesForPixampData(QPixmapData* pmd)
  1874 void QGLTextureCache::cleanupTexturesForPixampData(QPixmapData* pmd)
  1790 {
  1875 {
  2009     }
  2094     }
  2010 
  2095 
  2011 }
  2096 }
  2012 #undef ctx
  2097 #undef ctx
  2013 
  2098 
       
  2099 #ifdef QT_NO_EGL
       
  2100 void QGLContextPrivate::swapRegion(const QRegion *)
       
  2101 {
       
  2102     static bool firstWarning = true;
       
  2103     if (firstWarning) {
       
  2104         qWarning() << "::swapRegion called but not supported!";
       
  2105         firstWarning = false;
       
  2106     }
       
  2107 }
       
  2108 #endif
  2014 
  2109 
  2015 /*!
  2110 /*!
  2016     \overload
  2111     \overload
  2017 
  2112 
  2018     Reads the compressed texture file \a fileName and generates a 2D GL
  2113     Reads the compressed texture file \a fileName and generates a 2D GL
  2163             }
  2258             }
  2164         }
  2259         }
  2165     }
  2260     }
  2166 }
  2261 }
  2167 
  2262 
       
  2263 #if defined(Q_WS_X11) || defined(Q_WS_MAC) || defined(Q_WS_QWS)
       
  2264 QGLExtensionFuncs& QGLContextPrivate::extensionFuncs(const QGLContext *)
       
  2265 {
       
  2266     return qt_extensionFuncs;
       
  2267 }
       
  2268 #endif
       
  2269 
  2168 QImage QGLContextPrivate::convertToGLFormat(const QImage &image, bool force_premul,
  2270 QImage QGLContextPrivate::convertToGLFormat(const QImage &image, bool force_premul,
  2169                                             GLenum texture_format)
  2271                                             GLenum texture_format)
  2170 {
  2272 {
  2171     QImage::Format target_format = image.format();
  2273     QImage::Format target_format = image.format();
  2172     if (force_premul || image.format() != QImage::Format_ARGB32)
  2274     if (force_premul || image.format() != QImage::Format_ARGB32)
  2274     if (glFormat.directRendering()
  2376     if (glFormat.directRendering()
  2275         && (QGLExtensions::glExtensions() & QGLExtensions::GenerateMipmap)
  2377         && (QGLExtensions::glExtensions() & QGLExtensions::GenerateMipmap)
  2276         && target == GL_TEXTURE_2D
  2378         && target == GL_TEXTURE_2D
  2277         && (options & QGLContext::MipmapBindOption))
  2379         && (options & QGLContext::MipmapBindOption))
  2278     {
  2380     {
  2279 #ifdef QGL_BIND_TEXTURE_DEBUG
       
  2280         printf(" - generating mipmaps (%d ms)\n", time.elapsed());
       
  2281 #endif
       
  2282 #if !defined(QT_OPENGL_ES_2)
  2381 #if !defined(QT_OPENGL_ES_2)
  2283         glHint(GL_GENERATE_MIPMAP_HINT_SGIS, GL_NICEST);
  2382         glHint(GL_GENERATE_MIPMAP_HINT_SGIS, GL_NICEST);
  2284 #ifndef QT_OPENGL_ES
  2383 #ifndef QT_OPENGL_ES
  2285         glTexParameteri(target, GL_GENERATE_MIPMAP_SGIS, GL_TRUE);
  2384         glTexParameteri(target, GL_GENERATE_MIPMAP_SGIS, GL_TRUE);
  2286 #else
  2385 #else
  2290         glHint(GL_GENERATE_MIPMAP_HINT, GL_NICEST);
  2389         glHint(GL_GENERATE_MIPMAP_HINT, GL_NICEST);
  2291         genMipmap = true;
  2390         genMipmap = true;
  2292 #endif
  2391 #endif
  2293         glTexParameterf(target, GL_TEXTURE_MIN_FILTER, options & QGLContext::LinearFilteringBindOption
  2392         glTexParameterf(target, GL_TEXTURE_MIN_FILTER, options & QGLContext::LinearFilteringBindOption
  2294                         ? GL_LINEAR_MIPMAP_LINEAR : GL_NEAREST_MIPMAP_NEAREST);
  2393                         ? GL_LINEAR_MIPMAP_LINEAR : GL_NEAREST_MIPMAP_NEAREST);
       
  2394 #ifdef QGL_BIND_TEXTURE_DEBUG
       
  2395         printf(" - generating mipmaps (%d ms)\n", time.elapsed());
       
  2396 #endif
  2295     } else {
  2397     } else {
  2296         glTexParameterf(target, GL_TEXTURE_MIN_FILTER, filtering);
  2398         glTexParameterf(target, GL_TEXTURE_MIN_FILTER, filtering);
  2297     }
  2399     }
  2298 
  2400 
  2299     QImage::Format target_format = img.format();
  2401     QImage::Format target_format = img.format();
  2314     switch (target_format) {
  2416     switch (target_format) {
  2315     case QImage::Format_ARGB32:
  2417     case QImage::Format_ARGB32:
  2316         if (premul) {
  2418         if (premul) {
  2317             img = img.convertToFormat(target_format = QImage::Format_ARGB32_Premultiplied);
  2419             img = img.convertToFormat(target_format = QImage::Format_ARGB32_Premultiplied);
  2318 #ifdef QGL_BIND_TEXTURE_DEBUG
  2420 #ifdef QGL_BIND_TEXTURE_DEBUG
  2319             printf(" - converting ARGB32 -> ARGB32_Premultiplied (%d ms) \n", time.elapsed());
  2421             printf(" - converted ARGB32 -> ARGB32_Premultiplied (%d ms) \n", time.elapsed());
  2320 #endif
  2422 #endif
  2321         }
  2423         }
  2322         break;
  2424         break;
  2323     case QImage::Format_ARGB32_Premultiplied:
  2425     case QImage::Format_ARGB32_Premultiplied:
  2324         if (!premul) {
  2426         if (!premul) {
  2325             img = img.convertToFormat(target_format = QImage::Format_ARGB32);
  2427             img = img.convertToFormat(target_format = QImage::Format_ARGB32);
  2326 #ifdef QGL_BIND_TEXTURE_DEBUG
  2428 #ifdef QGL_BIND_TEXTURE_DEBUG
  2327             printf(" - converting ARGB32_Premultiplied -> ARGB32 (%d ms)\n", time.elapsed());
  2429             printf(" - converted ARGB32_Premultiplied -> ARGB32 (%d ms)\n", time.elapsed());
  2328 #endif
  2430 #endif
  2329         }
  2431         }
  2330         break;
  2432         break;
  2331     case QImage::Format_RGB16:
  2433     case QImage::Format_RGB16:
  2332         pixel_type = GL_UNSIGNED_SHORT_5_6_5;
  2434         pixel_type = GL_UNSIGNED_SHORT_5_6_5;
  2339         if (img.hasAlphaChannel()) {
  2441         if (img.hasAlphaChannel()) {
  2340             img = img.convertToFormat(premul
  2442             img = img.convertToFormat(premul
  2341                                       ? QImage::Format_ARGB32_Premultiplied
  2443                                       ? QImage::Format_ARGB32_Premultiplied
  2342                                       : QImage::Format_ARGB32);
  2444                                       : QImage::Format_ARGB32);
  2343 #ifdef QGL_BIND_TEXTURE_DEBUG
  2445 #ifdef QGL_BIND_TEXTURE_DEBUG
  2344             printf(" - converting to 32-bit alpha format (%d ms)\n", time.elapsed());
  2446             printf(" - converted to 32-bit alpha format (%d ms)\n", time.elapsed());
  2345 #endif
  2447 #endif
  2346         } else {
  2448         } else {
  2347             img = img.convertToFormat(QImage::Format_RGB32);
  2449             img = img.convertToFormat(QImage::Format_RGB32);
  2348 #ifdef QGL_BIND_TEXTURE_DEBUG
  2450 #ifdef QGL_BIND_TEXTURE_DEBUG
  2349             printf(" - converting to 32-bit (%d ms)\n", time.elapsed());
  2451             printf(" - converted to 32-bit (%d ms)\n", time.elapsed());
  2350 #endif
  2452 #endif
  2351         }
  2453         }
  2352     }
  2454     }
  2353 
  2455 
  2354     if (options & QGLContext::InvertedYBindOption) {
  2456     if (options & QGLContext::InvertedYBindOption) {
  2355 #ifdef QGL_BIND_TEXTURE_DEBUG
       
  2356             printf(" - flipping bits over y (%d ms)\n", time.elapsed());
       
  2357 #endif
       
  2358         if (img.isDetached()) {
  2457         if (img.isDetached()) {
  2359             int ipl = img.bytesPerLine() / 4;
  2458             int ipl = img.bytesPerLine() / 4;
  2360             int h = img.height();
  2459             int h = img.height();
  2361             for (int y=0; y<h/2; ++y) {
  2460             for (int y=0; y<h/2; ++y) {
  2362                 int *a = (int *) img.scanLine(y);
  2461                 int *a = (int *) img.scanLine(y);
  2369             // above in-place code then a full copy of the image is
  2468             // above in-place code then a full copy of the image is
  2370             // made before the lines are swapped, which processes the
  2469             // made before the lines are swapped, which processes the
  2371             // data twice.  This version should only do it once.
  2470             // data twice.  This version should only do it once.
  2372             img = img.mirrored();
  2471             img = img.mirrored();
  2373         }
  2472         }
       
  2473 #ifdef QGL_BIND_TEXTURE_DEBUG
       
  2474             printf(" - flipped bits over y (%d ms)\n", time.elapsed());
       
  2475 #endif
  2374     }
  2476     }
  2375 
  2477 
  2376     if (externalFormat == GL_RGBA) {
  2478     if (externalFormat == GL_RGBA) {
  2377 #ifdef QGL_BIND_TEXTURE_DEBUG
       
  2378             printf(" - doing byte swapping (%d ms)\n", time.elapsed());
       
  2379 #endif
       
  2380         // The only case where we end up with a depth different from
  2479         // The only case where we end up with a depth different from
  2381         // 32 in the switch above is for the RGB16 case, where we set
  2480         // 32 in the switch above is for the RGB16 case, where we set
  2382         // the format to GL_RGB
  2481         // the format to GL_RGB
  2383         Q_ASSERT(img.depth() == 32);
  2482         Q_ASSERT(img.depth() == 32);
  2384         qgl_byteSwapImage(img, pixel_type);
  2483         qgl_byteSwapImage(img, pixel_type);
       
  2484 #ifdef QGL_BIND_TEXTURE_DEBUG
       
  2485             printf(" - did byte swapping (%d ms)\n", time.elapsed());
       
  2486 #endif
  2385     }
  2487     }
  2386 #ifdef QT_OPENGL_ES
  2488 #ifdef QT_OPENGL_ES
  2387     // OpenGL/ES requires that the internal and external formats be
  2489     // OpenGL/ES requires that the internal and external formats be
  2388     // identical.
  2490     // identical.
  2389     internalFormat = externalFormat;
  2491     internalFormat = externalFormat;
  2408 #endif
  2510 #endif
  2409 
  2511 
  2410 #ifdef QGL_BIND_TEXTURE_DEBUG
  2512 #ifdef QGL_BIND_TEXTURE_DEBUG
  2411     static int totalUploadTime = 0;
  2513     static int totalUploadTime = 0;
  2412     totalUploadTime += time.elapsed();
  2514     totalUploadTime += time.elapsed();
  2413     printf(" - upload done in (%d ms) time=%d\n", time.elapsed(), totalUploadTime);
  2515     printf(" - upload done in %d ms, (accumulated: %d ms)\n", time.elapsed(), totalUploadTime);
  2414 #endif
  2516 #endif
  2415 
  2517 
  2416 
  2518 
  2417     // this assumes the size of a texture is always smaller than the max cache size
  2519     // this assumes the size of a texture is always smaller than the max cache size
  2418     int cost = img.width()*img.height()*4/1024;
  2520     int cost = img.width()*img.height()*4/1024;
  2423 }
  2525 }
  2424 
  2526 
  2425 QGLTexture *QGLContextPrivate::textureCacheLookup(const qint64 key, GLenum target)
  2527 QGLTexture *QGLContextPrivate::textureCacheLookup(const qint64 key, GLenum target)
  2426 {
  2528 {
  2427     Q_Q(QGLContext);
  2529     Q_Q(QGLContext);
  2428     QGLTexture *texture = QGLTextureCache::instance()->getTexture(key);
  2530     QGLTexture *texture = QGLTextureCache::instance()->getTexture(q, key);
  2429     if (texture && texture->target == target
  2531     if (texture && texture->target == target
  2430         && (texture->context == q || QGLContext::areSharing(q, texture->context)))
  2532         && (texture->context == q || QGLContext::areSharing(q, texture->context)))
  2431     {
  2533     {
  2432         return texture;
  2534         return texture;
  2433     }
  2535     }
  3617     Q_D(QGLWidget);
  3719     Q_D(QGLWidget);
  3618 #if defined(GLX_MESA_release_buffers) && defined(QGL_USE_MESA_EXT)
  3720 #if defined(GLX_MESA_release_buffers) && defined(QGL_USE_MESA_EXT)
  3619     bool doRelease = (glcx && glcx->windowCreated());
  3721     bool doRelease = (glcx && glcx->windowCreated());
  3620 #endif
  3722 #endif
  3621     delete d->glcx;
  3723     delete d->glcx;
  3622 #if defined(Q_WGL)
  3724     d->glcx = 0;
       
  3725 #if defined(Q_WS_WIN)
  3623     delete d->olcx;
  3726     delete d->olcx;
       
  3727     d->olcx = 0;
  3624 #endif
  3728 #endif
  3625 #if defined(GLX_MESA_release_buffers) && defined(QGL_USE_MESA_EXT)
  3729 #if defined(GLX_MESA_release_buffers) && defined(QGL_USE_MESA_EXT)
  3626     if (doRelease)
  3730     if (doRelease)
  3627         glXReleaseBuffersMESA(x11Display(), winId());
  3731         glXReleaseBuffersMESA(x11Display(), winId());
  3628 #endif
  3732 #endif
  4935 #endif
  5039 #endif
  4936 
  5040 
  4937 /*!
  5041 /*!
  4938     \since 4.4
  5042     \since 4.4
  4939 
  5043 
  4940     Calls the corresponding QGLContext::drawTexture() on
  5044     Calls the corresponding QGLContext::drawTexture() with
  4941     this widget's context.
  5045     \a target, \a textureId, and \a textureTarget for this
       
  5046     widget's context.
  4942 */
  5047 */
  4943 void QGLWidget::drawTexture(const QRectF &target, GLuint textureId, GLenum textureTarget)
  5048 void QGLWidget::drawTexture(const QRectF &target, GLuint textureId, GLenum textureTarget)
  4944 {
  5049 {
  4945     Q_D(QGLWidget);
  5050     Q_D(QGLWidget);
  4946     d->glcx->drawTexture(target, textureId, textureTarget);
  5051     d->glcx->drawTexture(target, textureId, textureTarget);
  4956 #endif
  5061 #endif
  4957 
  5062 
  4958 /*!
  5063 /*!
  4959     \since 4.4
  5064     \since 4.4
  4960 
  5065 
  4961     Calls the corresponding QGLContext::drawTexture() on
  5066     Calls the corresponding QGLContext::drawTexture() with
  4962     this widget's context.
  5067     \a point, \a textureId, and \a textureTarget for this
       
  5068     widget's context.
  4963 */
  5069 */
  4964 void QGLWidget::drawTexture(const QPointF &point, GLuint textureId, GLenum textureTarget)
  5070 void QGLWidget::drawTexture(const QPointF &point, GLuint textureId, GLenum textureTarget)
  4965 {
  5071 {
  4966     Q_D(QGLWidget);
  5072     Q_D(QGLWidget);
  4967     d->glcx->drawTexture(point, textureId, textureTarget);
  5073     d->glcx->drawTexture(point, textureId, textureTarget);
  5102         glExtensions |= PackedDepthStencil;
  5208         glExtensions |= PackedDepthStencil;
  5103     if (extensions.match("GL_NV_float_buffer"))
  5209     if (extensions.match("GL_NV_float_buffer"))
  5104         glExtensions |= NVFloatBuffer;
  5210         glExtensions |= NVFloatBuffer;
  5105     if (extensions.match("GL_ARB_pixel_buffer_object"))
  5211     if (extensions.match("GL_ARB_pixel_buffer_object"))
  5106         glExtensions |= PixelBufferObject;
  5212         glExtensions |= PixelBufferObject;
       
  5213     if (extensions.match("GL_IMG_texture_format_BGRA8888"))
       
  5214         glExtensions |= BGRATextureFormat;
  5107 #if defined(QT_OPENGL_ES_2)
  5215 #if defined(QT_OPENGL_ES_2)
  5108     glExtensions |= FramebufferObject;
  5216     glExtensions |= FramebufferObject;
  5109     glExtensions |= GenerateMipmap;
  5217     glExtensions |= GenerateMipmap;
  5110     glExtensions |= FragmentShader;
  5218     glExtensions |= FragmentShader;
  5111 #endif
  5219 #endif