remove OpenVG support

Qt5 will require OpenGL, so there's no need for
supporting OpenVG anymore.
This commit is contained in:
Lars Knoll 2011-05-04 20:57:35 +02:00
parent 5c2282ffa3
commit 4ece3fc24e
18 changed files with 0 additions and 7931 deletions

View File

@ -1,74 +0,0 @@
TARGET = QtOpenVG
QT += core \
gui
CONFIG += module
MODULE_PRI = ../modules/qt_openvg.pri
DEFINES+=QT_BUILD_OPENVG_LIB
contains(QT_CONFIG, shivavg) {
DEFINES += QVG_NO_DRAW_GLYPHS
DEFINES += QVG_NO_RENDER_TO_MASK
DEFINES += QVG_SCISSOR_CLIP
}
HEADERS += \
qvg.h \
qvg_p.h \
qpaintengine_vg_p.h \
qpixmapdata_vg_p.h \
qpixmapfilter_vg_p.h \
qvgcompositionhelper_p.h \
qvgimagepool_p.h \
qvgfontglyphcache_p.h
SOURCES += \
qpaintengine_vg.cpp \
qpixmapdata_vg.cpp \
qpixmapfilter_vg.cpp \
qvgimagepool.cpp
contains(QT_CONFIG, egl) {
HEADERS += \
qwindowsurface_vgegl_p.h \
qwindowsurface_vg_p.h
SOURCES += \
qwindowsurface_vg.cpp \
qwindowsurface_vgegl.cpp
}
symbian {
DEFINES += QVG_RECREATE_ON_SIZE_CHANGE QVG_BUFFER_SCROLLING QVG_SCISSOR_CLIP
SOURCES += \
qvg_symbian.cpp
contains(QT_CONFIG, freetype) {
DEFINES += QT_NO_FONTCONFIG
INCLUDEPATH += \
../3rdparty/freetype/src \
../3rdparty/freetype/include
}
}
include(../qbase.pri)
unix|win32-g++*:QMAKE_PKGCONFIG_REQUIRES = QtCore QtGui
symbian:TARGET.UID3 = 0x2001E62F
!isEmpty(QMAKE_INCDIR_OPENVG): INCLUDEPATH += $$QMAKE_INCDIR_OPENVG
!isEmpty(QMAKE_LIBDIR_OPENVG): LIBS_PRIVATE += -L$$QMAKE_LIBDIR_OPENVG
!isEmpty(QMAKE_LIBS_OPENVG): LIBS_PRIVATE += $$QMAKE_LIBS_OPENVG
contains(QT_CONFIG, egl) {
!isEmpty(QMAKE_INCDIR_EGL): INCLUDEPATH += $$QMAKE_INCDIR_EGL
!isEmpty(QMAKE_LIBDIR_EGL): LIBS_PRIVATE += -L$$QMAKE_LIBDIR_EGL
!isEmpty(QMAKE_LIBS_EGL): LIBS_PRIVATE += $$QMAKE_LIBS_EGL
}
contains(QT_CONFIG, openvg_on_opengl) {
!isEmpty(QMAKE_INCDIR_OPENGL): INCLUDEPATH += $$QMAKE_INCDIR_OPENGL
!isEmpty(QMAKE_LIBDIR_OPENGL): LIBS_PRIVATE += -L$$QMAKE_LIBDIR_OPENGL
!isEmpty(QMAKE_LIBS_OPENGL): LIBS_PRIVATE += $$QMAKE_LIBS_OPENGL
}
INCLUDEPATH += ../3rdparty/harfbuzz/src

File diff suppressed because it is too large Load Diff

View File

@ -1,178 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef QPAINTENGINE_VG_P_H
#define QPAINTENGINE_VG_P_H
//
// W A R N I N G
// -------------
//
// This file is not part of the Qt API. It exists purely as an
// implementation detail. This header file may change from version to
// version without notice, or even be removed.
//
// We mean it.
//
#include <QtGui/private/qpaintengineex_p.h>
#include <QtGui/private/qtextureglyphcache_p.h>
QT_BEGIN_NAMESPACE
struct QFixedPoint;
class QVGPaintEnginePrivate;
class QPixmapData;
class QVGEGLWindowSurfacePrivate;
class Q_OPENVG_EXPORT QVGPainterState : public QPainterState
{
public:
QVGPainterState(QVGPainterState& other);
QVGPainterState();
~QVGPainterState();
bool isNew;
QRegion clipRegion;
QPaintEngine::DirtyFlags savedDirty;
};
class Q_OPENVG_EXPORT QVGPaintEngine : public QPaintEngineEx
{
Q_DECLARE_PRIVATE(QVGPaintEngine)
public:
QVGPaintEngine();
~QVGPaintEngine();
Type type() const { return OpenVG; }
QPainterState *createState(QPainterState *orig) const;
bool begin(QPaintDevice *pdev);
bool end();
void draw(const QVectorPath &path);
void fill(const QVectorPath &path, const QBrush &brush);
void stroke(const QVectorPath &path, const QPen &pen);
void clip(const QVectorPath &path, Qt::ClipOperation op);
void clip(const QRect &rect, Qt::ClipOperation op);
void clip(const QRegion &region, Qt::ClipOperation op);
void clip(const QPainterPath &path, Qt::ClipOperation op);
void clipEnabledChanged();
void penChanged();
void brushChanged();
void brushOriginChanged();
void opacityChanged();
void compositionModeChanged();
void renderHintsChanged();
void transformChanged();
void fillRect(const QRectF &rect, const QBrush &brush);
void fillRect(const QRectF &rect, const QColor &color);
void drawRoundedRect(const QRectF &rect, qreal xrad, qreal yrad, Qt::SizeMode mode);
void drawRects(const QRect *rects, int rectCount);
void drawRects(const QRectF *rects, int rectCount);
void drawLines(const QLine *lines, int lineCount);
void drawLines(const QLineF *lines, int lineCount);
void drawEllipse(const QRectF &r);
void drawEllipse(const QRect &r);
void drawPath(const QPainterPath &path);
void drawPoints(const QPointF *points, int pointCount);
void drawPoints(const QPoint *points, int pointCount);
void drawPolygon(const QPointF *points, int pointCount, PolygonDrawMode mode);
void drawPolygon(const QPoint *points, int pointCount, PolygonDrawMode mode);
void drawPixmap(const QRectF &r, const QPixmap &pm, const QRectF &sr);
void drawPixmap(const QPointF &pos, const QPixmap &pm);
void drawImage(const QRectF &r, const QImage &pm, const QRectF &sr,
Qt::ImageConversionFlags flags = Qt::AutoColor);
void drawImage(const QPointF &pos, const QImage &image);
void drawTiledPixmap(const QRectF &r, const QPixmap &pixmap, const QPointF &s);
void drawPixmapFragments(const QPainter::PixmapFragment *drawingData, int dataCount, const QPixmap &pixmap,
QFlags<QPainter::PixmapFragmentHint> hints);
void drawTextItem(const QPointF &p, const QTextItem &textItem);
void drawStaticTextItem(QStaticTextItem *staticTextItem);
bool drawCachedGlyphs(int numGlyphs, const glyph_t *glyphs, const QFont &font,
QFontEngine *fontEngine, const QPointF &p,
const QFixedPoint *positions);
void setState(QPainterState *s);
QVGPainterState *state() { return static_cast<QVGPainterState *>(QPaintEngineEx::state()); }
const QVGPainterState *state() const { return static_cast<const QVGPainterState *>(QPaintEngineEx::state()); }
void beginNativePainting();
void endNativePainting();
QPixmapFilter *pixmapFilter(int type, const QPixmapFilter *prototype);
QVGPaintEnginePrivate *vgPrivate() { Q_D(QVGPaintEngine); return d; }
void fillRegion(const QRegion& region, const QColor& color, const QSize& surfaceSize);
protected:
QVGPaintEngine(QVGPaintEnginePrivate &data);
private:
void restoreState(QPaintEngine::DirtyFlags dirty);
void updateScissor();
QRegion defaultClipRegion();
bool isDefaultClipRegion(const QRegion& region);
bool isDefaultClipRect(const QRect& rect);
bool clearRect(const QRectF &rect, const QColor &color);
bool canVgWritePixels(const QImage &image) const;
};
QT_END_NAMESPACE
#endif

View File

@ -1,575 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#include "qpixmapdata_vg_p.h"
#include "qpaintengine_vg_p.h"
#include <QtGui/private/qdrawhelper_p.h>
#if !defined(QT_NO_EGL)
#include <QtGui/private/qegl_p.h>
#endif
#include "qvg_p.h"
#include "qvgimagepool_p.h"
#include <QBuffer>
#include <QImageReader>
#include <QtGui/private/qimage_p.h>
#include <QtGui/private/qnativeimagehandleprovider_p.h>
#include <QtGui/private/qfont_p.h>
QT_BEGIN_NAMESPACE
static int qt_vg_pixmap_serial = 0;
QVGPixmapData::QVGPixmapData(PixelType type)
: QPixmapData(type, OpenVGClass)
{
Q_ASSERT(type == QPixmapData::PixmapType);
vgImage = VG_INVALID_HANDLE;
vgImageOpacity = VG_INVALID_HANDLE;
cachedOpacity = 1.0f;
recreate = true;
inImagePool = false;
inLRU = false;
failedToAlloc = false;
#if defined(Q_OS_SYMBIAN)
nativeImageHandleProvider = 0;
nativeImageHandle = 0;
#endif
#if !defined(QT_NO_EGL)
context = 0;
qt_vg_register_pixmap(this);
#endif
updateSerial();
}
QVGPixmapData::~QVGPixmapData()
{
destroyImageAndContext();
#if !defined(QT_NO_EGL)
qt_vg_unregister_pixmap(this);
#endif
}
void QVGPixmapData::destroyImages()
{
if (inImagePool) {
QVGImagePool *pool = QVGImagePool::instance();
if (vgImage != VG_INVALID_HANDLE)
pool->releaseImage(this, vgImage);
if (vgImageOpacity != VG_INVALID_HANDLE)
pool->releaseImage(this, vgImageOpacity);
} else {
if (vgImage != VG_INVALID_HANDLE)
vgDestroyImage(vgImage);
if (vgImageOpacity != VG_INVALID_HANDLE)
vgDestroyImage(vgImageOpacity);
}
vgImage = VG_INVALID_HANDLE;
vgImageOpacity = VG_INVALID_HANDLE;
inImagePool = false;
#if defined(Q_OS_SYMBIAN)
releaseNativeImageHandle();
#endif
}
void QVGPixmapData::destroyImageAndContext()
{
if (vgImage != VG_INVALID_HANDLE) {
// We need to have a context current to destroy the image.
#if !defined(QT_NO_EGL)
if (!context)
context = qt_vg_create_context(0, QInternal::Pixmap);
if (context->isCurrent()) {
destroyImages();
} else {
// We don't currently have a widget surface active, but we
// need a surface to make the context current. So use the
// shared pbuffer surface instead.
context->makeCurrent(qt_vg_shared_surface());
destroyImages();
context->lazyDoneCurrent();
}
#else
destroyImages();
#endif
} else {
#if defined(Q_OS_SYMBIAN)
releaseNativeImageHandle();
#endif
}
#if !defined(QT_NO_EGL)
if (context) {
qt_vg_destroy_context(context, QInternal::Pixmap);
context = 0;
}
#endif
recreate = true;
}
QPixmapData *QVGPixmapData::createCompatiblePixmapData() const
{
return new QVGPixmapData(pixelType());
}
bool QVGPixmapData::isValid() const
{
return (w > 0 && h > 0);
}
void QVGPixmapData::updateSerial()
{
setSerialNumber(++qt_vg_pixmap_serial);
}
void QVGPixmapData::resize(int wid, int ht)
{
if (w == wid && h == ht) {
updateSerial();
return;
}
w = wid;
h = ht;
d = 32; // We always use ARGB_Premultiplied for VG pixmaps.
is_null = (w <= 0 || h <= 0);
source = QVolatileImage();
recreate = true;
updateSerial();
}
void QVGPixmapData::fromImage(const QImage &image, Qt::ImageConversionFlags flags)
{
if (image.isNull())
return;
QImage img = image;
createPixmapForImage(img, flags, false);
}
void QVGPixmapData::fromImageReader(QImageReader *imageReader,
Qt::ImageConversionFlags flags)
{
QImage image = imageReader->read();
if (image.isNull())
return;
createPixmapForImage(image, flags, true);
}
bool QVGPixmapData::fromFile(const QString &filename, const char *format,
Qt::ImageConversionFlags flags)
{
QImage image = QImageReader(filename, format).read();
if (image.isNull())
return false;
createPixmapForImage(image, flags, true);
return !isNull();
}
bool QVGPixmapData::fromData(const uchar *buffer, uint len, const char *format,
Qt::ImageConversionFlags flags)
{
QByteArray a = QByteArray::fromRawData(reinterpret_cast<const char *>(buffer), len);
QBuffer b(&a);
b.open(QIODevice::ReadOnly);
QImage image = QImageReader(&b, format).read();
if (image.isNull())
return false;
createPixmapForImage(image, flags, true);
return !isNull();
}
QImage::Format QVGPixmapData::idealFormat(QImage *image, Qt::ImageConversionFlags flags) const
{
QImage::Format format = sourceFormat();
int d = image->depth();
if (d == 1 || d == 16 || d == 24 || (d == 32 && !image->hasAlphaChannel()))
format = QImage::Format_RGB32;
else if (!(flags & Qt::NoOpaqueDetection) && image->data_ptr()->checkForAlphaPixels())
format = sourceFormat();
else
format = image->hasAlphaChannel() ? sourceFormat() : QImage::Format_RGB32;
return format;
}
void QVGPixmapData::createPixmapForImage(QImage &image, Qt::ImageConversionFlags flags, bool inPlace)
{
resize(image.width(), image.height());
QImage::Format format = idealFormat(&image, flags);
if (inPlace && image.data_ptr()->convertInPlace(format, flags)) {
source = QVolatileImage(image);
} else {
QImage convertedImage = image.convertToFormat(format);
// convertToFormat won't detach the image if format stays the
// same. Detaching is needed to prevent issues with painting
// onto this QPixmap later on.
convertedImage.detach();
source = QVolatileImage(convertedImage);
}
recreate = true;
}
void QVGPixmapData::fill(const QColor &color)
{
if (!isValid())
return;
forceToImage();
if (source.depth() == 1) {
// Pick the best approximate color in the image's colortable.
int gray = qGray(color.rgba());
if (qAbs(qGray(source.imageRef().color(0)) - gray)
< qAbs(qGray(source.imageRef().color(1)) - gray))
source.fill(0);
else
source.fill(1);
} else {
source.fill(PREMUL(color.rgba()));
}
}
bool QVGPixmapData::hasAlphaChannel() const
{
ensureReadback(true);
if (!source.isNull())
return source.hasAlphaChannel();
else
return isValid();
}
void QVGPixmapData::setAlphaChannel(const QPixmap &alphaChannel)
{
if (!isValid())
return;
forceToImage();
source.setAlphaChannel(alphaChannel);
}
QImage QVGPixmapData::toImage() const
{
if (!isValid())
return QImage();
ensureReadback(true);
if (source.isNull()) {
source = QVolatileImage(w, h, sourceFormat());
recreate = true;
}
return source.toImage();
}
void QVGPixmapData::copy(const QPixmapData *data, const QRect &rect)
{
// toImage() is potentially expensive with QVolatileImage so provide a
// more efficient implementation of copy() that does not rely on it.
if (!data) {
return;
}
if (data->classId() != OpenVGClass) {
fromImage(data->toImage(rect), Qt::NoOpaqueDetection);
return;
}
const QVGPixmapData *pd = static_cast<const QVGPixmapData *>(data);
QRect r = rect;
if (r.isNull() || r.contains(QRect(0, 0, pd->w, pd->h))) {
r = QRect(0, 0, pd->w, pd->h);
}
resize(r.width(), r.height());
recreate = true;
if (!pd->source.isNull()) {
source = QVolatileImage(r.width(), r.height(), pd->source.format());
source.copyFrom(&pd->source, r);
}
}
QImage *QVGPixmapData::buffer()
{
// Cannot be safely implemented and QVGPixmapData is not (must not be) RasterClass anyway.
return 0;
}
QPaintEngine* QVGPixmapData::paintEngine() const
{
// If the application wants to paint into the QPixmap, we first
// force it to QImage format and then paint into that.
// This is simpler than juggling multiple VG contexts.
const_cast<QVGPixmapData *>(this)->forceToImage();
return source.paintEngine();
}
VGImage QVGPixmapData::toVGImage()
{
if (!isValid() || failedToAlloc)
return VG_INVALID_HANDLE;
#if !defined(QT_NO_EGL)
// Increase the reference count on the shared context.
if (!context)
context = qt_vg_create_context(0, QInternal::Pixmap);
#endif
if (recreate && prevSize != QSize(w, h))
destroyImages();
else if (recreate)
cachedOpacity = -1.0f; // Force opacity image to be refreshed later.
#if defined(Q_OS_SYMBIAN)
if (recreate && nativeImageHandleProvider && !nativeImageHandle) {
createFromNativeImageHandleProvider();
}
#endif
if (vgImage == VG_INVALID_HANDLE) {
vgImage = QVGImagePool::instance()->createImageForPixmap
(qt_vg_image_to_vg_format(source.format()), w, h, VG_IMAGE_QUALITY_FASTER, this);
// Bail out if we run out of GPU memory - try again next time.
if (vgImage == VG_INVALID_HANDLE) {
failedToAlloc = true;
return VG_INVALID_HANDLE;
}
inImagePool = true;
} else if (inImagePool) {
QVGImagePool::instance()->useImage(this);
}
if (!source.isNull() && recreate) {
source.beginDataAccess();
vgImageSubData
(vgImage,
source.constBits(), source.bytesPerLine(),
qt_vg_image_to_vg_format(source.format()), 0, 0, w, h);
source.endDataAccess(true);
}
recreate = false;
prevSize = QSize(w, h);
return vgImage;
}
VGImage QVGPixmapData::toVGImage(qreal opacity)
{
#if !defined(QT_SHIVAVG)
// Force the primary VG image to be recreated if necessary.
if (toVGImage() == VG_INVALID_HANDLE)
return VG_INVALID_HANDLE;
if (opacity == 1.0f)
return vgImage;
// Create an alternative image for the selected opacity.
if (vgImageOpacity == VG_INVALID_HANDLE || cachedOpacity != opacity) {
if (vgImageOpacity == VG_INVALID_HANDLE) {
if (inImagePool) {
vgImageOpacity = QVGImagePool::instance()->createImageForPixmap
(VG_sARGB_8888_PRE, w, h, VG_IMAGE_QUALITY_FASTER, this);
} else {
vgImageOpacity = vgCreateImage
(VG_sARGB_8888_PRE, w, h, VG_IMAGE_QUALITY_FASTER);
}
// Bail out if we run out of GPU memory - try again next time.
if (vgImageOpacity == VG_INVALID_HANDLE)
return VG_INVALID_HANDLE;
}
VGfloat matrix[20] = {
1.0f, 0.0f, 0.0f, 0.0f,
0.0f, 1.0f, 0.0f, 0.0f,
0.0f, 0.0f, 1.0f, 0.0f,
0.0f, 0.0f, 0.0f, opacity,
0.0f, 0.0f, 0.0f, 0.0f
};
vgColorMatrix(vgImageOpacity, vgImage, matrix);
cachedOpacity = opacity;
}
return vgImageOpacity;
#else
// vgColorMatrix() doesn't work with ShivaVG, so ignore the opacity.
Q_UNUSED(opacity);
return toVGImage();
#endif
}
void QVGPixmapData::detachImageFromPool()
{
if (inImagePool) {
QVGImagePool::instance()->detachImage(this);
inImagePool = false;
}
}
void QVGPixmapData::hibernate()
{
// If the image was imported (e.g, from an SgImage under Symbian), then
// skip the hibernation, there is no sense in copying it back to main
// memory because the data is most likely shared between several processes.
bool skipHibernate = (vgImage != VG_INVALID_HANDLE && source.isNull());
#if defined(Q_OS_SYMBIAN)
// However we have to proceed normally if the image was retrieved via
// a handle provider.
skipHibernate &= !nativeImageHandleProvider;
#endif
if (skipHibernate)
return;
forceToImage(false); // no readback allowed here
destroyImageAndContext();
}
void QVGPixmapData::reclaimImages()
{
if (!inImagePool)
return;
forceToImage();
destroyImages();
}
int QVGPixmapData::metric(QPaintDevice::PaintDeviceMetric metric) const
{
switch (metric) {
case QPaintDevice::PdmWidth:
return w;
case QPaintDevice::PdmHeight:
return h;
case QPaintDevice::PdmNumColors:
return 0;
case QPaintDevice::PdmDepth:
return d;
case QPaintDevice::PdmWidthMM:
return qRound(w * 25.4 / qt_defaultDpiX());
case QPaintDevice::PdmHeightMM:
return qRound(h * 25.4 / qt_defaultDpiY());
case QPaintDevice::PdmDpiX:
case QPaintDevice::PdmPhysicalDpiX:
return qt_defaultDpiX();
case QPaintDevice::PdmDpiY:
case QPaintDevice::PdmPhysicalDpiY:
return qt_defaultDpiY();
default:
qWarning("QVGPixmapData::metric(): Invalid metric");
return 0;
}
}
// Ensures that the pixmap is backed by some valid data and forces the data to
// be re-uploaded to the VGImage when toVGImage() is called next time.
void QVGPixmapData::forceToImage(bool allowReadback)
{
if (!isValid())
return;
if (allowReadback)
ensureReadback(false);
if (source.isNull())
source = QVolatileImage(w, h, sourceFormat());
recreate = true;
}
void QVGPixmapData::ensureReadback(bool readOnly) const
{
if (vgImage != VG_INVALID_HANDLE && source.isNull()) {
source = QVolatileImage(w, h, sourceFormat());
source.beginDataAccess();
vgGetImageSubData(vgImage, source.bits(), source.bytesPerLine(),
qt_vg_image_to_vg_format(source.format()),
0, 0, w, h);
source.endDataAccess();
if (readOnly) {
recreate = false;
} else {
// Once we did a readback, the original VGImage must be destroyed
// because it may be shared (e.g. created via SgImage) and a subsequent
// upload of the image data may produce unexpected results.
const_cast<QVGPixmapData *>(this)->destroyImages();
#if defined(Q_OS_SYMBIAN)
// There is now an own copy of the data so drop the handle provider,
// otherwise toVGImage() would request the handle again, which is wrong.
nativeImageHandleProvider = 0;
#endif
recreate = true;
}
}
}
QImage::Format QVGPixmapData::sourceFormat() const
{
return QImage::Format_ARGB32_Premultiplied;
}
/*
\internal
Returns the VGImage that is storing the contents of \a pixmap.
Returns VG_INVALID_HANDLE if \a pixmap is not owned by the OpenVG
graphics system or \a pixmap is invalid.
This function is typically used to access the backing store
for a pixmap when executing raw OpenVG calls. It must only
be used when a QPainter is active and the OpenVG paint engine
is in use by the QPainter.
\sa {QtOpenVG Module}
*/
Q_OPENVG_EXPORT VGImage qPixmapToVGImage(const QPixmap& pixmap)
{
QPixmapData *pd = pixmap.pixmapData();
if (!pd)
return VG_INVALID_HANDLE; // null QPixmap
if (pd->classId() == QPixmapData::OpenVGClass) {
QVGPixmapData *vgpd = static_cast<QVGPixmapData *>(pd);
if (vgpd->isValid())
return vgpd->toVGImage();
}
return VG_INVALID_HANDLE;
}
QT_END_NAMESPACE

View File

@ -1,202 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef QPIXMAPDATA_VG_P_H
#define QPIXMAPDATA_VG_P_H
//
// W A R N I N G
// -------------
//
// This file is not part of the Qt API. It exists for the convenience
// of other Qt classes. This header file may change from version to
// version without notice, or even be removed.
//
// We mean it.
//
#include <QtGui/private/qpixmap_raster_p.h>
#include <QtGui/private/qvolatileimage_p.h>
#include "qvg_p.h"
#if defined(Q_OS_SYMBIAN)
class RSGImage;
#endif
QT_BEGIN_NAMESPACE
class QEglContext;
class QVGImagePool;
class QImageReader;
#if !defined(QT_NO_EGL)
class QVGPixmapData;
class QVGSharedContext;
void qt_vg_register_pixmap(QVGPixmapData *pd);
void qt_vg_unregister_pixmap(QVGPixmapData *pd);
void qt_vg_hibernate_pixmaps(QVGSharedContext *context);
#endif
class QNativeImageHandleProvider;
class Q_OPENVG_EXPORT QVGPixmapData : public QPixmapData
{
public:
QVGPixmapData(PixelType type);
~QVGPixmapData();
QPixmapData *createCompatiblePixmapData() const;
// Is this pixmap valid (i.e. non-zero in size)?
bool isValid() const;
void resize(int width, int height);
void fromImage(const QImage &image, Qt::ImageConversionFlags flags);
void fromImageReader(QImageReader *imageReader,
Qt::ImageConversionFlags flags);
bool fromFile(const QString &filename, const char *format,
Qt::ImageConversionFlags flags);
bool fromData(const uchar *buffer, uint len, const char *format,
Qt::ImageConversionFlags flags);
void fill(const QColor &color);
bool hasAlphaChannel() const;
void setAlphaChannel(const QPixmap &alphaChannel);
QImage toImage() const;
void copy(const QPixmapData *data, const QRect &rect);
QImage *buffer();
QPaintEngine* paintEngine() const;
// Return the VGImage form of this pixmap, creating it if necessary.
// This assumes that there is a VG context current.
virtual VGImage toVGImage();
// Return the VGImage form for a specific opacity setting.
virtual VGImage toVGImage(qreal opacity);
// Detach this image from the image pool.
virtual void detachImageFromPool();
// Release the VG resources associated with this pixmap and copy
// the pixmap's contents out of the GPU back into main memory.
// The VG resource will be automatically recreated the next time
// toVGImage() is called. Does nothing if the pixmap cannot be
// hibernated for some reason (e.g. VGImage is shared with another
// process via a SgImage).
virtual void hibernate();
// Called when the QVGImagePool wants to reclaim this pixmap's
// VGImage objects to reuse storage.
virtual void reclaimImages();
// If vgImage is valid but source is null, copies pixel data from GPU back
// into main memory and destroys vgImage. For a normal pixmap this function
// does nothing, however if the pixmap was created directly from a VGImage
// (e.g. via SgImage on Symbian) then by doing the readback this ensures
// that QImage-based functions can operate too.
virtual void ensureReadback(bool readOnly) const;
QSize size() const { return QSize(w, h); }
#if defined(Q_OS_SYMBIAN)
void* toNativeType(NativeType type);
void fromNativeType(void* pixmap, NativeType type);
bool initFromNativeImageHandle(void *handle, const QString &type);
void createFromNativeImageHandleProvider();
void releaseNativeImageHandle();
#endif
protected:
int metric(QPaintDevice::PaintDeviceMetric metric) const;
void createPixmapForImage(QImage &image, Qt::ImageConversionFlags flags, bool inPlace);
#if defined(Q_OS_SYMBIAN)
void cleanup();
#endif
private:
QVGPixmapData *nextLRU;
QVGPixmapData *prevLRU;
bool inLRU;
bool failedToAlloc;
friend class QVGImagePool;
friend class QVGPaintEngine;
#if !defined(QT_NO_EGL)
QVGPixmapData *next;
QVGPixmapData *prev;
friend void qt_vg_register_pixmap(QVGPixmapData *pd);
friend void qt_vg_unregister_pixmap(QVGPixmapData *pd);
friend void qt_vg_hibernate_pixmaps(QVGSharedContext *context);
#endif
protected:
QSize prevSize;
VGImage vgImage;
VGImage vgImageOpacity;
qreal cachedOpacity;
mutable QVolatileImage source;
mutable bool recreate;
bool inImagePool;
#if !defined(QT_NO_EGL)
mutable QEglContext *context;
#endif
#if defined(Q_OS_SYMBIAN)
mutable QNativeImageHandleProvider *nativeImageHandleProvider;
void *nativeImageHandle;
QString nativeImageType;
#endif
void forceToImage(bool allowReadback = true);
QImage::Format sourceFormat() const;
QImage::Format idealFormat(QImage *image, Qt::ImageConversionFlags flags) const;
void updateSerial();
void destroyImageAndContext();
void destroyImages();
};
QT_END_NAMESPACE
#endif

View File

@ -1,356 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#include "qpixmapfilter_vg_p.h"
#include "qvgimagepool_p.h"
#include <QtCore/qvarlengtharray.h>
#include <QtGui/qpainter.h>
QT_BEGIN_NAMESPACE
#if !defined(QT_SHIVAVG)
QVGPixmapConvolutionFilter::QVGPixmapConvolutionFilter()
: QPixmapConvolutionFilter()
{
}
QVGPixmapConvolutionFilter::~QVGPixmapConvolutionFilter()
{
}
extern void qt_vg_drawVGImage
(QPainter *painter, const QPointF& pos, VGImage vgImg);
extern void qt_vg_drawVGImageStencil
(QPainter *painter, const QPointF& pos, VGImage vgImg, const QBrush& brush);
void QVGPixmapConvolutionFilter::draw
(QPainter *painter, const QPointF &dest,
const QPixmap &src, const QRectF &srcRect) const
{
if (src.isNull())
return;
if (src.pixmapData()->classId() != QPixmapData::OpenVGClass) {
// The pixmap data is not an instance of QVGPixmapData, so fall
// back to the default convolution filter implementation.
QPixmapConvolutionFilter::draw(painter, dest, src, srcRect);
return;
}
QVGPixmapData *pd = static_cast<QVGPixmapData *>(src.pixmapData());
VGImage srcImage = pd->toVGImage();
if (srcImage == VG_INVALID_HANDLE)
return;
QSize size = pd->size();
VGImage dstImage = QVGImagePool::instance()->createTemporaryImage
(VG_sARGB_8888_PRE, size.width(), size.height(),
VG_IMAGE_QUALITY_FASTER, pd);
if (dstImage == VG_INVALID_HANDLE)
return;
int kernelWidth = rows();
int kernelHeight = columns();
const qreal *kern = convolutionKernel();
QVarLengthArray<VGshort> kernel;
for (int i = 0; i < kernelWidth; ++i) {
for (int j = 0; j < kernelHeight; ++j) {
kernel.append((VGshort)(kern[j * kernelWidth + i] * 1024.0f));
}
}
VGfloat values[4];
values[0] = 0.0f;
values[1] = 0.0f;
values[2] = 0.0f;
values[3] = 0.0f;
vgSetfv(VG_TILE_FILL_COLOR, 4, values);
vgConvolve(dstImage, srcImage,
kernelWidth, kernelHeight, 0, 0,
kernel.constData(), 1.0f / 1024.0f, 0.0f,
VG_TILE_FILL);
VGImage child = VG_INVALID_HANDLE;
if (srcRect.isNull() ||
(srcRect.topLeft().isNull() && srcRect.size() == size)) {
child = dstImage;
} else {
QRect src = srcRect.toRect();
child = vgChildImage(dstImage, src.x(), src.y(), src.width(), src.height());
}
qt_vg_drawVGImage(painter, dest, child);
if(child != dstImage)
vgDestroyImage(child);
QVGImagePool::instance()->releaseImage(0, dstImage);
}
QVGPixmapColorizeFilter::QVGPixmapColorizeFilter()
: QPixmapColorizeFilter()
{
}
QVGPixmapColorizeFilter::~QVGPixmapColorizeFilter()
{
}
void QVGPixmapColorizeFilter::draw(QPainter *painter, const QPointF &dest, const QPixmap &src, const QRectF &srcRect) const
{
if (src.isNull())
return;
if (src.pixmapData()->classId() != QPixmapData::OpenVGClass) {
// The pixmap data is not an instance of QVGPixmapData, so fall
// back to the default colorize filter implementation.
QPixmapColorizeFilter::draw(painter, dest, src, srcRect);
return;
}
QVGPixmapData *pd = static_cast<QVGPixmapData *>(src.pixmapData());
VGImage srcImage = pd->toVGImage();
if (srcImage == VG_INVALID_HANDLE)
return;
QSize size = pd->size();
VGImage dstImage = QVGImagePool::instance()->createTemporaryImage
(VG_sARGB_8888_PRE, size.width(), size.height(),
VG_IMAGE_QUALITY_FASTER, pd);
if (dstImage == VG_INVALID_HANDLE)
return;
// Determine the weights for the matrix from the color and strength.
QColor c = color();
VGfloat strength = this->strength();
VGfloat weights[3];
VGfloat invweights[3];
VGfloat alpha = c.alphaF();
weights[0] = c.redF() * alpha;
weights[1] = c.greenF() * alpha;
weights[2] = c.blueF() * alpha;
invweights[0] = (1.0f - weights[0]) * strength;
invweights[1] = (1.0f - weights[1]) * strength;
invweights[2] = (1.0f - weights[2]) * strength;
// Grayscale weights.
static const VGfloat redGray = 11.0f / 32.0f;
static const VGfloat greenGray = 16.0f / 32.0f;
static const VGfloat blueGray = 1.0f - (redGray + greenGray);
VGfloat matrix[5][4];
matrix[0][0] = redGray * invweights[0] + (1.0f - strength);
matrix[0][1] = redGray * invweights[1];
matrix[0][2] = redGray * invweights[2];
matrix[0][3] = 0.0f;
matrix[1][0] = greenGray * invweights[0];
matrix[1][1] = greenGray * invweights[1] + (1.0f - strength);
matrix[1][2] = greenGray * invweights[2];
matrix[1][3] = 0.0f;
matrix[2][0] = blueGray * invweights[0];
matrix[2][1] = blueGray * invweights[1];
matrix[2][2] = blueGray * invweights[2] + (1.0f - strength);
matrix[2][3] = 0.0f;
matrix[3][0] = 0.0f;
matrix[3][1] = 0.0f;
matrix[3][2] = 0.0f;
matrix[3][3] = 1.0f;
matrix[4][0] = weights[0] * strength;
matrix[4][1] = weights[1] * strength;
matrix[4][2] = weights[2] * strength;
matrix[4][3] = 0.0f;
vgColorMatrix(dstImage, srcImage, matrix[0]);
VGImage child = VG_INVALID_HANDLE;
if (srcRect.isNull() ||
(srcRect.topLeft().isNull() && srcRect.size() == size)) {
child = dstImage;
} else {
QRect src = srcRect.toRect();
child = vgChildImage(dstImage, src.x(), src.y(), src.width(), src.height());
}
qt_vg_drawVGImage(painter, dest, child);
if(child != dstImage)
vgDestroyImage(child);
QVGImagePool::instance()->releaseImage(0, dstImage);
}
QVGPixmapDropShadowFilter::QVGPixmapDropShadowFilter()
: QPixmapDropShadowFilter()
{
}
QVGPixmapDropShadowFilter::~QVGPixmapDropShadowFilter()
{
}
void QVGPixmapDropShadowFilter::draw(QPainter *painter, const QPointF &dest, const QPixmap &src, const QRectF &srcRect) const
{
if (src.isNull())
return;
if (src.pixmapData()->classId() != QPixmapData::OpenVGClass) {
// The pixmap data is not an instance of QVGPixmapData, so fall
// back to the default drop shadow filter implementation.
QPixmapDropShadowFilter::draw(painter, dest, src, srcRect);
return;
}
QVGPixmapData *pd = static_cast<QVGPixmapData *>(src.pixmapData());
VGImage srcImage = pd->toVGImage();
if (srcImage == VG_INVALID_HANDLE)
return;
QSize size = pd->size();
VGImage dstImage = QVGImagePool::instance()->createTemporaryImage
(VG_A_8, size.width(), size.height(),
VG_IMAGE_QUALITY_FASTER, pd);
if (dstImage == VG_INVALID_HANDLE)
return;
// Clamp the radius range. We divide by 2 because the OpenVG blur
// is "too blurry" compared to the default raster implementation.
VGfloat maxRadius = VGfloat(vgGeti(VG_MAX_GAUSSIAN_STD_DEVIATION));
VGfloat radiusF = VGfloat(blurRadius()) / 2.0f;
if (radiusF < 0.001f)
radiusF = 0.001f;
else if (radiusF > maxRadius)
radiusF = maxRadius;
// Blur the blackened source image.
vgGaussianBlur(dstImage, srcImage, radiusF, radiusF, VG_TILE_PAD);
VGImage child = VG_INVALID_HANDLE;
QRect srect;
if (srcRect.isNull() ||
(srcRect.topLeft().isNull() && srcRect.size() == size)) {
child = dstImage;
srect = QRect(0, 0, size.width(), size.height());
} else {
srect = srcRect.toRect();
child = vgChildImage(dstImage, srect.x(), srect.y(), srect.width(), srect.height());
}
qt_vg_drawVGImageStencil(painter, dest + offset(), child, color());
if(child != dstImage)
vgDestroyImage(child);
QVGImagePool::instance()->releaseImage(0, dstImage);
// Now draw the actual pixmap over the top.
painter->drawPixmap(dest, src, srect);
}
QVGPixmapBlurFilter::QVGPixmapBlurFilter(QObject *parent)
: QPixmapBlurFilter(parent)
{
}
QVGPixmapBlurFilter::~QVGPixmapBlurFilter()
{
}
void QVGPixmapBlurFilter::draw(QPainter *painter, const QPointF &dest, const QPixmap &src, const QRectF &srcRect) const
{
if (src.isNull())
return;
if (src.pixmapData()->classId() != QPixmapData::OpenVGClass) {
// The pixmap data is not an instance of QVGPixmapData, so fall
// back to the default blur filter implementation.
QPixmapBlurFilter::draw(painter, dest, src, srcRect);
return;
}
QVGPixmapData *pd = static_cast<QVGPixmapData *>(src.pixmapData());
VGImage srcImage = pd->toVGImage();
if (srcImage == VG_INVALID_HANDLE)
return;
QSize size = pd->size();
VGImage dstImage = QVGImagePool::instance()->createTemporaryImage
(VG_sARGB_8888_PRE, size.width(), size.height(),
VG_IMAGE_QUALITY_FASTER, pd);
if (dstImage == VG_INVALID_HANDLE)
return;
// Clamp the radius range. We divide by 2 because the OpenVG blur
// is "too blurry" compared to the default raster implementation.
VGfloat maxRadius = VGfloat(vgGeti(VG_MAX_GAUSSIAN_STD_DEVIATION));
VGfloat radiusF = VGfloat(radius()) / 2.0f;
if (radiusF < 0.001f)
radiusF = 0.001f;
else if (radiusF > maxRadius)
radiusF = maxRadius;
vgGaussianBlur(dstImage, srcImage, radiusF, radiusF, VG_TILE_PAD);
VGImage child = VG_INVALID_HANDLE;
if (srcRect.isNull() ||
(srcRect.topLeft().isNull() && srcRect.size() == size)) {
child = dstImage;
} else {
QRect src = srcRect.toRect();
child = vgChildImage(dstImage, src.x(), src.y(), src.width(), src.height());
}
qt_vg_drawVGImage(painter, dest, child);
if(child != dstImage)
vgDestroyImage(child);
QVGImagePool::instance()->releaseImage(0, dstImage);
}
#endif
QT_END_NAMESPACE

View File

@ -1,108 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef QPIXMAPFILTER_VG_P_H
#define QPIXMAPFILTER_VG_P_H
//
// W A R N I N G
// -------------
//
// This file is not part of the Qt API. It exists for the convenience
// of other Qt classes. This header file may change from version to
// version without notice, or even be removed.
//
// We mean it.
//
#include "qpixmapdata_vg_p.h"
#include <QtGui/private/qpixmapfilter_p.h>
#include <QtCore/qvarlengtharray.h>
QT_BEGIN_NAMESPACE
#if !defined(QT_SHIVAVG)
class QVGPixmapConvolutionFilter : public QPixmapConvolutionFilter
{
Q_OBJECT
public:
QVGPixmapConvolutionFilter();
~QVGPixmapConvolutionFilter();
void draw(QPainter *painter, const QPointF &dest, const QPixmap &src, const QRectF &srcRect) const;
};
class QVGPixmapColorizeFilter : public QPixmapColorizeFilter
{
Q_OBJECT
public:
QVGPixmapColorizeFilter();
~QVGPixmapColorizeFilter();
void draw(QPainter *painter, const QPointF &dest, const QPixmap &src, const QRectF &srcRect) const;
};
class QVGPixmapDropShadowFilter : public QPixmapDropShadowFilter
{
Q_OBJECT
public:
QVGPixmapDropShadowFilter();
~QVGPixmapDropShadowFilter();
void draw(QPainter *p, const QPointF &pos, const QPixmap &px, const QRectF &src) const;
};
class QVGPixmapBlurFilter : public QPixmapBlurFilter
{
Q_OBJECT
public:
QVGPixmapBlurFilter(QObject *parent = 0);
~QVGPixmapBlurFilter();
void draw(QPainter *painter, const QPointF &dest, const QPixmap &src, const QRectF &srcRect = QRectF()) const;
};
#endif
QT_END_NAMESPACE
#endif

View File

@ -1,65 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef QVG_H
#define QVG_H
#include <QtCore/qglobal.h>
// Include the OpenVG headers for use in applications that
// issue raw OpenVG function calls.
#if defined(QT_LOWER_CASE_VG_INCLUDES)
#include <vg/openvg.h>
#else
#include <VG/openvg.h>
#endif
QT_BEGIN_HEADER
QT_BEGIN_NAMESPACE
QT_MODULE(OpenVG)
QT_END_NAMESPACE
QT_END_HEADER
#endif

View File

@ -1,112 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef QVG_P_H
#define QVG_P_H
#include "qvg.h"
//
// W A R N I N G
// -------------
//
// This file is not part of the Qt API. It exists for the convenience
// of other Qt classes. This header file may change from version to
// version without notice, or even be removed.
//
// We mean it.
//
// vgDrawGlyphs() only exists in OpenVG 1.1 and higher.
#if !defined(OPENVG_VERSION_1_1) && !defined(QVG_NO_DRAW_GLYPHS)
#define QVG_NO_DRAW_GLYPHS 1
#endif
#include <QtGui/qimage.h>
#if !defined(QT_NO_EGL)
#include <QtGui/private/qeglcontext_p.h>
#endif
QT_BEGIN_NAMESPACE
class QVGPaintEngine;
#if !defined(QT_NO_EGL)
class QEglContext;
// Create an EGL context, but don't bind it to a surface. If single-context
// mode is enabled, this will return the previously-created context.
// "devType" indicates the type of device using the context, usually
// QInternal::Widget or QInternal::Pixmap.
Q_OPENVG_EXPORT QEglContext *qt_vg_create_context
(QPaintDevice *device, int devType);
// Destroy an EGL context that was created by qt_vg_create_context().
// If single-context mode is enabled, this will decrease the reference count.
// "devType" indicates the type of device destroying the context, usually
// QInternal::Widget or QInternal::Pixmap.
Q_OPENVG_EXPORT void qt_vg_destroy_context
(QEglContext *context, int devType);
// Return the shared pbuffer surface that can be made current to
// destroy VGImage objects when there is no other surface available.
Q_OPENVG_EXPORT EGLSurface qt_vg_shared_surface(void);
// Convert the configuration format in a context to a VG or QImage format.
Q_OPENVG_EXPORT VGImageFormat qt_vg_config_to_vg_format(QEglContext *context);
Q_OPENVG_EXPORT QImage::Format qt_vg_config_to_image_format(QEglContext *context);
#endif
// Create a paint engine. Returns the common engine in single-context mode.
Q_OPENVG_EXPORT QVGPaintEngine *qt_vg_create_paint_engine(void);
// Destroy a paint engine. Does nothing in single-context mode.
Q_OPENVG_EXPORT void qt_vg_destroy_paint_engine(QVGPaintEngine *engine);
// Convert between QImage and VGImage format values.
Q_OPENVG_EXPORT VGImageFormat qt_vg_image_to_vg_format(QImage::Format format);
QT_END_NAMESPACE
#endif

View File

@ -1,366 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtGui module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#include "qpixmapdata_vg_p.h"
#include "qvgfontglyphcache_p.h"
#include <QtGui/private/qnativeimagehandleprovider_p.h>
#include <private/qt_s60_p.h>
#include <fbs.h>
#ifdef QT_SYMBIAN_SUPPORTS_SGIMAGE
# include <sgresource/sgimage.h>
# ifdef SYMBIAN_FBSERV_GLYPHDATA // defined in fbs.h
# define QT_SYMBIAN_HARDWARE_GLYPH_CACHE
# include <graphics/fbsglyphdataiterator.h>
# include <private/qfontengine_s60_p.h>
# endif
#endif
QT_BEGIN_NAMESPACE
typedef VGImage (*_vgCreateEGLImageTargetKHR)(VGeglImageKHR);
static _vgCreateEGLImageTargetKHR qt_vgCreateEGLImageTargetKHR = 0;
namespace QVG
{
VGImage vgCreateEGLImageTargetKHR(VGeglImageKHR eglImage);
}
VGImage QVG::vgCreateEGLImageTargetKHR(VGeglImageKHR eglImage)
{
if (!qt_vgCreateEGLImageTargetKHR && QEgl::hasExtension("EGL_KHR_image"))
qt_vgCreateEGLImageTargetKHR = (_vgCreateEGLImageTargetKHR) eglGetProcAddress("vgCreateEGLImageTargetKHR");
return qt_vgCreateEGLImageTargetKHR ? qt_vgCreateEGLImageTargetKHR(eglImage) : 0;
}
extern int qt_vg_pixmap_serial;
#ifdef QT_SYMBIAN_SUPPORTS_SGIMAGE
static VGImage sgImageToVGImage(QEglContext *context, const RSgImage &sgImage)
{
// when "0" used as argument then
// default display, context are used
if (!context)
context = qt_vg_create_context(0, QInternal::Pixmap);
VGImage vgImage = VG_INVALID_HANDLE;
if (sgImage.IsNull())
return vgImage;
const EGLint KEglImageAttribs[] = {EGL_IMAGE_PRESERVED_SYMBIAN, EGL_TRUE, EGL_NONE};
EGLImageKHR eglImage = QEgl::eglCreateImageKHR(QEgl::display(),
EGL_NO_CONTEXT,
EGL_NATIVE_PIXMAP_KHR,
(EGLClientBuffer)&sgImage,
(EGLint*)KEglImageAttribs);
if (!eglImage)
return vgImage;
vgImage = QVG::vgCreateEGLImageTargetKHR(eglImage);
QEgl::eglDestroyImageKHR(QEgl::display(), eglImage);
return vgImage;
}
#endif
void QVGPixmapData::cleanup()
{
is_null = w = h = 0;
recreate = false;
source = QVolatileImage();
}
bool QVGPixmapData::initFromNativeImageHandle(void *handle, const QString &type)
{
if (type == QLatin1String("RSgImage")) {
fromNativeType(handle, QPixmapData::SgImage);
return true;
} else if (type == QLatin1String("CFbsBitmap")) {
fromNativeType(handle, QPixmapData::FbsBitmap);
return true;
}
return false;
}
void QVGPixmapData::createFromNativeImageHandleProvider()
{
void *handle = 0;
QString type;
nativeImageHandleProvider->get(&handle, &type);
if (handle) {
if (initFromNativeImageHandle(handle, type)) {
nativeImageHandle = handle;
nativeImageType = type;
} else {
qWarning("QVGPixmapData: Unknown native image type '%s'", qPrintable(type));
}
} else {
qWarning("QVGPixmapData: Native handle is null");
}
}
void QVGPixmapData::releaseNativeImageHandle()
{
if (nativeImageHandleProvider && nativeImageHandle) {
nativeImageHandleProvider->release(nativeImageHandle, nativeImageType);
nativeImageHandle = 0;
nativeImageType = QString();
}
}
static inline bool conversionLessFormat(QImage::Format format)
{
switch (format) {
case QImage::Format_RGB16: // EColor64K
case QImage::Format_RGB32: // EColor16MU
case QImage::Format_ARGB32: // EColor16MA
case QImage::Format_ARGB32_Premultiplied: // EColor16MAP
case QImage::Format_Indexed8: // EGray256, EColor256
return true;
default:
return false;
}
}
void QVGPixmapData::fromNativeType(void* pixmap, NativeType type)
{
if (type == QPixmapData::SgImage && pixmap) {
#if defined(QT_SYMBIAN_SUPPORTS_SGIMAGE) && !defined(QT_NO_EGL)
RSgImage *sgImage = reinterpret_cast<RSgImage*>(pixmap);
destroyImages();
prevSize = QSize();
vgImage = sgImageToVGImage(context, *sgImage);
if (vgImage != VG_INVALID_HANDLE) {
w = vgGetParameteri(vgImage, VG_IMAGE_WIDTH);
h = vgGetParameteri(vgImage, VG_IMAGE_HEIGHT);
d = 32; // We always use ARGB_Premultiplied for VG pixmaps.
}
is_null = (w <= 0 || h <= 0);
source = QVolatileImage(); // readback will be done later, only when needed
recreate = false;
prevSize = QSize(w, h);
updateSerial();
#endif
} else if (type == QPixmapData::FbsBitmap && pixmap) {
CFbsBitmap *bitmap = reinterpret_cast<CFbsBitmap *>(pixmap);
QSize size(bitmap->SizeInPixels().iWidth, bitmap->SizeInPixels().iHeight);
resize(size.width(), size.height());
source = QVolatileImage(bitmap); // duplicates only, if possible
if (source.isNull())
return;
if (!conversionLessFormat(source.format())) {
// Here we may need to copy if the formats do not match.
// (e.g. for display modes other than EColor16MAP and EColor16MU)
source.beginDataAccess();
QImage::Format format = idealFormat(&source.imageRef(), Qt::AutoColor);
source.endDataAccess(true);
source.ensureFormat(format);
}
recreate = true;
} else if (type == QPixmapData::VolatileImage && pixmap) {
QVolatileImage *img = static_cast<QVolatileImage *>(pixmap);
resize(img->width(), img->height());
source = *img;
recreate = true;
} else if (type == QPixmapData::NativeImageHandleProvider && pixmap) {
destroyImages();
nativeImageHandleProvider = static_cast<QNativeImageHandleProvider *>(pixmap);
// Cannot defer the retrieval, we need at least the size right away.
createFromNativeImageHandleProvider();
}
}
void* QVGPixmapData::toNativeType(NativeType type)
{
if (type == QPixmapData::SgImage) {
#if defined(QT_SYMBIAN_SUPPORTS_SGIMAGE) && !defined(QT_NO_EGL)
toVGImage();
if (!isValid() || vgImage == VG_INVALID_HANDLE)
return 0;
TInt err = 0;
RSgDriver driver;
err = driver.Open();
if (err != KErrNone)
return 0;
TSgImageInfo sgInfo;
sgInfo.iPixelFormat = EUidPixelFormatARGB_8888_PRE;
sgInfo.iSizeInPixels.SetSize(w, h);
sgInfo.iUsage = ESgUsageBitOpenVgImage | ESgUsageBitOpenVgSurface;
QScopedPointer<RSgImage> sgImage(new RSgImage());
err = sgImage->Create(sgInfo, NULL, NULL);
if (err != KErrNone) {
driver.Close();
return 0;
}
const EGLint KEglImageAttribs[] = {EGL_IMAGE_PRESERVED_SYMBIAN, EGL_TRUE, EGL_NONE};
EGLImageKHR eglImage = QEgl::eglCreateImageKHR(QEgl::display(),
EGL_NO_CONTEXT,
EGL_NATIVE_PIXMAP_KHR,
(EGLClientBuffer)sgImage.data(),
(EGLint*)KEglImageAttribs);
if (!eglImage || eglGetError() != EGL_SUCCESS) {
sgImage->Close();
driver.Close();
return 0;
}
VGImage dstVgImage = QVG::vgCreateEGLImageTargetKHR(eglImage);
if (!dstVgImage || vgGetError() != VG_NO_ERROR) {
QEgl::eglDestroyImageKHR(QEgl::display(), eglImage);
sgImage->Close();
driver.Close();
return 0;
}
vgCopyImage(dstVgImage, 0, 0,
vgImage, 0, 0,
w, h, VG_FALSE);
if (vgGetError() != VG_NO_ERROR) {
sgImage->Close();
sgImage.reset();
}
// release stuff
vgDestroyImage(dstVgImage);
QEgl::eglDestroyImageKHR(QEgl::display(), eglImage);
driver.Close();
return reinterpret_cast<void*>(sgImage.take());
#endif
} else if (type == QPixmapData::FbsBitmap && isValid()) {
ensureReadback(true);
if (source.isNull()) {
source = QVolatileImage(w, h, sourceFormat());
}
// Just duplicate the bitmap handle, no data copying happens.
return source.duplicateNativeImage();
}
return 0;
}
QSymbianVGFontGlyphCache::QSymbianVGFontGlyphCache() : QVGFontGlyphCache()
{
#ifdef QT_SYMBIAN_HARDWARE_GLYPH_CACHE
invertedGlyphs = true;
#endif
}
void QSymbianVGFontGlyphCache::cacheGlyphs(QVGPaintEnginePrivate *d,
QFontEngine *fontEngine,
const glyph_t *g, int count)
{
#ifdef QT_SYMBIAN_HARDWARE_GLYPH_CACHE
QFontEngineS60 *s60fontEngine = static_cast<QFontEngineS60*>(fontEngine);
if (s60fontEngine->m_activeFont->TypeUid() != KCFbsFontUid)
return QVGFontGlyphCache::cacheGlyphs(d, fontEngine, g, count);
QVector<glyph_t> uncachedGlyphs;
while (count-- > 0) {
// Skip this glyph if we have already cached it before.
glyph_t glyph = *g++;
if (((glyph < 256) && ((cachedGlyphsMask[glyph / 32] & (1 << (glyph % 32))) != 0))
|| cachedGlyphs.contains(glyph))
continue;
if (!uncachedGlyphs.contains(glyph))
uncachedGlyphs.append(glyph);
}
if (!uncachedGlyphs.isEmpty()) {
CFbsFont *cfbsFont = static_cast<CFbsFont *>(s60fontEngine->m_activeFont);
RFbsGlyphDataIterator iter;
int err = iter.Open(*cfbsFont, (const unsigned int*)uncachedGlyphs.constData(), uncachedGlyphs.count());
if (err == KErrNotSupported || err == KErrInUse) { // Fallback in possibly supported error cases
iter.Close();
qWarning("Falling back to default QVGFontGlyphCache");
return QVGFontGlyphCache::cacheGlyphs(d, fontEngine, g, count);
}
for (; err == KErrNone; err = iter.Next()) {
const unsigned int glyph = iter.GlyphCode();
const RSgImage& image = iter.Image();
const TOpenFontCharMetrics& metrics = iter.Metrics();
TRect glyphBounds;
metrics.GetHorizBounds(glyphBounds);
VGImage vgImage = sgImageToVGImage(0, image);
VGfloat origin[2];
VGfloat escapement[2];
origin[0] = -glyphBounds.iTl.iX;
origin[1] = glyphBounds.iBr.iY;
escapement[0] = 0;
escapement[1] = 0;
vgSetGlyphToImage(font, glyph, vgImage, origin, escapement);
vgDestroyImage(vgImage);
// Add to cache
if (glyph < 256)
cachedGlyphsMask[glyph / 32] |= (1 << (glyph % 32));
else
cachedGlyphs.insert(glyph);
}
iter.Close();
if (err == KErrNoMemory || err == KErrNoGraphicsMemory)
qWarning("Not enough memory to cache glyph");
else if (err != KErrNotFound)
qWarning("Received error %d from glyph cache", err);
}
#else
QVGFontGlyphCache::cacheGlyphs(d, fontEngine, g, count);
#endif
}
QT_END_NAMESPACE

View File

@ -1,90 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef QVGCOMPOSITIONHELPER_H
#define QVGCOMPOSITIONHELPER_H
//
// W A R N I N G
// -------------
//
// This file is not part of the Qt API. It exists purely as an
// implementation detail. This header file may change from version to
// version without notice, or even be removed.
//
// We mean it.
//
#include "qwindowsurface_vgegl_p.h"
QT_BEGIN_NAMESPACE
#if !defined(QVG_NO_SINGLE_CONTEXT) && !defined(QT_NO_EGL)
class QVGPaintEnginePrivate;
class QVGEGLWindowSurfacePrivate;
class Q_OPENVG_EXPORT QVGCompositionHelper
{
public:
QVGCompositionHelper();
virtual ~QVGCompositionHelper();
void startCompositing(const QSize& screenSize);
void endCompositing();
void blitWindow(VGImage image, const QSize& imageSize,
const QRect& rect, const QPoint& topLeft, int opacity);
void fillBackground(const QRegion& region, const QBrush& brush);
void drawCursorPixmap(const QPixmap& pixmap, const QPoint& offset);
void setScissor(const QRegion& region);
void clearScissor();
private:
QVGPaintEnginePrivate *d;
QSize screenSize;
};
#endif
QT_END_NAMESPACE
#endif

View File

@ -1,101 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef QVGFONTGLYPHCACHE_H
#define QVGFONTGLYPHCACHE_H
//
// W A R N I N G
// -------------
//
// This file is not part of the Qt API. It exists purely as an
// implementation detail. This header file may change from version to
// version without notice, or even be removed.
//
// We mean it.
//
#include <QtCore/qvarlengtharray.h>
#include <QtGui/private/qfontengine_p.h>
#include "qvg_p.h"
QT_BEGIN_NAMESPACE
class QVGPaintEnginePrivate;
#ifndef QVG_NO_DRAW_GLYPHS
class QVGFontGlyphCache
{
public:
QVGFontGlyphCache();
virtual ~QVGFontGlyphCache();
virtual void cacheGlyphs(QVGPaintEnginePrivate *d,
QFontEngine *fontEngine,
const glyph_t *g, int count);
void setScaleFromText(const QFont &font, QFontEngine *fontEngine);
VGFont font;
VGfloat scaleX;
VGfloat scaleY;
bool invertedGlyphs;
uint cachedGlyphsMask[256 / 32];
QSet<glyph_t> cachedGlyphs;
};
#if defined(Q_OS_SYMBIAN)
class QSymbianVGFontGlyphCache : public QVGFontGlyphCache
{
public:
QSymbianVGFontGlyphCache();
void cacheGlyphs(QVGPaintEnginePrivate *d,
QFontEngine *fontEngine,
const glyph_t *g, int count);
};
#endif
#endif
QT_END_NAMESPACE
#endif // QVGFONTGLYPHCACHE_H

View File

@ -1,233 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#include "qvgimagepool_p.h"
#include "qpixmapdata_vg_p.h"
QT_BEGIN_NAMESPACE
static QVGImagePool *qt_vg_image_pool = 0;
class QVGImagePoolPrivate
{
public:
QVGImagePoolPrivate() : lruFirst(0), lruLast(0) {}
QVGPixmapData *lruFirst;
QVGPixmapData *lruLast;
};
QVGImagePool::QVGImagePool()
: d_ptr(new QVGImagePoolPrivate())
{
}
QVGImagePool::~QVGImagePool()
{
}
QVGImagePool *QVGImagePool::instance()
{
if (!qt_vg_image_pool)
qt_vg_image_pool = new QVGImagePool();
return qt_vg_image_pool;
}
void QVGImagePool::setImagePool(QVGImagePool *pool)
{
if (qt_vg_image_pool != pool)
delete qt_vg_image_pool;
qt_vg_image_pool = pool;
}
VGImage QVGImagePool::createTemporaryImage(VGImageFormat format,
VGint width, VGint height,
VGbitfield allowedQuality,
QVGPixmapData *keepData)
{
VGImage image;
do {
image = vgCreateImage(format, width, height, allowedQuality);
if (image != VG_INVALID_HANDLE)
return image;
} while (reclaimSpace(format, width, height, keepData));
qWarning("QVGImagePool: cannot reclaim sufficient space for a %dx%d temporary image",
width, height);
return VG_INVALID_HANDLE;
}
VGImage QVGImagePool::createImageForPixmap(VGImageFormat format,
VGint width, VGint height,
VGbitfield allowedQuality,
QVGPixmapData *data)
{
VGImage image;
do {
image = vgCreateImage(format, width, height, allowedQuality);
if (image != VG_INVALID_HANDLE) {
if (data)
moveToHeadOfLRU(data);
return image;
}
} while (reclaimSpace(format, width, height, data));
qWarning("QVGImagePool: cannot reclaim sufficient space for a %dx%d pixmap",
width, height);
return VG_INVALID_HANDLE;
}
VGImage QVGImagePool::createPermanentImage(VGImageFormat format,
VGint width, VGint height,
VGbitfield allowedQuality)
{
VGImage image;
do {
image = vgCreateImage(format, width, height, allowedQuality);
if (image != VG_INVALID_HANDLE)
return image;
} while (reclaimSpace(format, width, height, 0));
qWarning("QVGImagePool: cannot reclaim sufficient space for a %dx%d image",
width, height);
return VG_INVALID_HANDLE;
}
void QVGImagePool::releaseImage(QVGPixmapData *data, VGImage image)
{
// Very simple strategy at the moment: just destroy the image.
if (data)
removeFromLRU(data);
vgDestroyImage(image);
}
void QVGImagePool::useImage(QVGPixmapData *data)
{
moveToHeadOfLRU(data);
}
void QVGImagePool::detachImage(QVGPixmapData *data)
{
removeFromLRU(data);
}
bool QVGImagePool::reclaimSpace(VGImageFormat format,
VGint width, VGint height,
QVGPixmapData *data)
{
Q_UNUSED(format); // For future use in picking the best image to eject.
Q_UNUSED(width);
Q_UNUSED(height);
bool succeeded = false;
bool wasInLRU = false;
if (data) {
wasInLRU = data->inLRU;
moveToHeadOfLRU(data);
}
QVGPixmapData *lrudata = pixmapLRU();
if (lrudata && lrudata != data) {
lrudata->reclaimImages();
succeeded = true;
}
if (data && !wasInLRU)
removeFromLRU(data);
return succeeded;
}
void QVGImagePool::hibernate()
{
Q_D(QVGImagePool);
QVGPixmapData *pd = d->lruLast;
while (pd) {
QVGPixmapData *prevLRU = pd->prevLRU;
pd->inImagePool = false;
pd->inLRU = false;
pd->nextLRU = 0;
pd->prevLRU = 0;
pd->hibernate();
pd = prevLRU;
}
d->lruFirst = 0;
d->lruLast = 0;
}
void QVGImagePool::moveToHeadOfLRU(QVGPixmapData *data)
{
Q_D(QVGImagePool);
if (data->inLRU) {
if (!data->prevLRU)
return; // Already at the head of the list.
removeFromLRU(data);
}
data->inLRU = true;
data->nextLRU = d->lruFirst;
data->prevLRU = 0;
if (d->lruFirst)
d->lruFirst->prevLRU = data;
else
d->lruLast = data;
d->lruFirst = data;
}
void QVGImagePool::removeFromLRU(QVGPixmapData *data)
{
Q_D(QVGImagePool);
if (!data->inLRU)
return;
if (data->nextLRU)
data->nextLRU->prevLRU = data->prevLRU;
else
d->lruLast = data->prevLRU;
if (data->prevLRU)
data->prevLRU->nextLRU = data->nextLRU;
else
d->lruFirst = data->nextLRU;
data->inLRU = false;
}
QVGPixmapData *QVGImagePool::pixmapLRU()
{
Q_D(QVGImagePool);
return d->lruLast;
}
QT_END_NAMESPACE

View File

@ -1,157 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef QVGIMAGEPOOL_P_H
#define QVGIMAGEPOOL_P_H
//
// W A R N I N G
// -------------
//
// This file is not part of the Qt API. It exists for the convenience
// of other Qt classes. This header file may change from version to
// version without notice, or even be removed.
//
// We mean it.
//
#include "qvg.h"
#include <QtCore/qscopedpointer.h>
QT_BEGIN_NAMESPACE
class QVGPixmapData;
class QVGImagePoolPrivate;
class Q_OPENVG_EXPORT QVGImagePool
{
public:
QVGImagePool();
virtual ~QVGImagePool();
static QVGImagePool *instance();
// This function can be used from system-specific graphics system
// plugins to alter the image allocation strategy.
static void setImagePool(QVGImagePool *pool);
// Create a new VGImage from the pool with the specified parameters
// that is not associated with a pixmap. The VGImage is returned to
// the pool when releaseImage() is called.
//
// This function will call reclaimSpace() when vgCreateImage() fails.
//
// This function is typically called when allocating temporary
// VGImage's for pixmap filters. The "keepData" object will not
// be reclaimed if reclaimSpace() needs to be called.
virtual VGImage createTemporaryImage(VGImageFormat format,
VGint width, VGint height,
VGbitfield allowedQuality,
QVGPixmapData *keepData = 0);
// Create a new VGImage with the specified parameters and associate
// it with "data". The QVGPixmapData will be notified when the
// VGImage needs to be reclaimed by the pool.
//
// This function will call reclaimSpace() when vgCreateImage() fails.
virtual VGImage createImageForPixmap(VGImageFormat format,
VGint width, VGint height,
VGbitfield allowedQuality,
QVGPixmapData *data);
// Create a permanent VGImage with the specified parameters.
// If there is insufficient space for the vgCreateImage call,
// then this function will call reclaimSpace() and try again.
//
// The caller is responsible for calling vgDestroyImage()
// when it no longer needs the VGImage, as the image is not
// recorded in the image pool.
//
// This function is typically used for pattern brushes where
// the OpenVG engine is responsible for managing the lifetime
// of the VGImage, destroying it automatically when the brush
// is no longer in use.
virtual VGImage createPermanentImage(VGImageFormat format,
VGint width, VGint height,
VGbitfield allowedQuality);
// Release a VGImage that is no longer required.
virtual void releaseImage(QVGPixmapData *data, VGImage image);
// Notify the pool that a QVGPixmapData object is using
// an image again. This allows the pool to move the image
// within a least-recently-used list of QVGPixmapData objects.
virtual void useImage(QVGPixmapData *data);
// Notify the pool that the VGImage's associated with a
// QVGPixmapData are being detached from the pool. The caller
// will become responsible for calling vgDestroyImage().
virtual void detachImage(QVGPixmapData *data);
// Reclaim space for an image allocation with the specified parameters.
// Returns true if space was reclaimed, or false if there is no
// further space that can be reclaimed. The "data" parameter
// indicates the pixmap that is trying to obtain space which should
// not itself be reclaimed.
virtual bool reclaimSpace(VGImageFormat format,
VGint width, VGint height,
QVGPixmapData *data);
// Hibernate the image pool because the context is about to be
// destroyed. All VGImage's left in the pool should be released.
virtual void hibernate();
protected:
// Helper functions for managing the LRU list of QVGPixmapData objects.
void moveToHeadOfLRU(QVGPixmapData *data);
void removeFromLRU(QVGPixmapData *data);
QVGPixmapData *pixmapLRU();
private:
QScopedPointer<QVGImagePoolPrivate> d_ptr;
Q_DECLARE_PRIVATE(QVGImagePool)
Q_DISABLE_COPY(QVGImagePool)
};
QT_END_NAMESPACE
#endif

View File

@ -1,137 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#include "qwindowsurface_vg_p.h"
#include "qwindowsurface_vgegl_p.h"
#include "qpaintengine_vg_p.h"
#include "qpixmapdata_vg_p.h"
#include "qvg_p.h"
#if !defined(QT_NO_EGL)
#include <QtGui/private/qeglcontext_p.h>
#include <QtGui/private/qwidget_p.h>
QT_BEGIN_NAMESPACE
QVGWindowSurface::QVGWindowSurface(QWidget *window)
: QWindowSurface(window)
{
// Create the default type of EGL window surface for windows.
d_ptr = new QVGEGLWindowSurfaceDirect(this);
}
QVGWindowSurface::QVGWindowSurface
(QWidget *window, QVGEGLWindowSurfacePrivate *d)
: QWindowSurface(window), d_ptr(d)
{
}
QVGWindowSurface::~QVGWindowSurface()
{
delete d_ptr;
}
QPaintDevice *QVGWindowSurface::paintDevice()
{
return this;
}
void QVGWindowSurface::flush(QWidget *widget, const QRegion &region, const QPoint &offset)
{
Q_UNUSED(offset);
QWidget *parent = widget->internalWinId() ? widget : widget->nativeParentWidget();
d_ptr->endPaint(parent, region);
}
void QVGWindowSurface::setGeometry(const QRect &rect)
{
QWindowSurface::setGeometry(rect);
}
bool QVGWindowSurface::scroll(const QRegion &area, int dx, int dy)
{
if (!d_ptr->scroll(window(), area, dx, dy))
return QWindowSurface::scroll(area, dx, dy);
return true;
}
void QVGWindowSurface::beginPaint(const QRegion &region)
{
d_ptr->beginPaint(window());
// If the window is not opaque, then fill the region we are about
// to paint with the transparent color.
if (!qt_widget_private(window())->isOpaque &&
window()->testAttribute(Qt::WA_TranslucentBackground)) {
QVGPaintEngine *engine = static_cast<QVGPaintEngine *>
(d_ptr->paintEngine());
engine->fillRegion(region, Qt::transparent, d_ptr->surfaceSize());
}
}
void QVGWindowSurface::endPaint(const QRegion &region)
{
// Nothing to do here.
Q_UNUSED(region);
}
QPaintEngine *QVGWindowSurface::paintEngine() const
{
return d_ptr->paintEngine();
}
QWindowSurface::WindowSurfaceFeatures QVGWindowSurface::features() const
{
WindowSurfaceFeatures features = PartialUpdates | PreservedContents;
if (d_ptr->supportsStaticContents())
features |= StaticContents;
return features;
}
int QVGWindowSurface::metric(PaintDeviceMetric met) const
{
return qt_paint_device_metric(window(), met);
}
QT_END_NAMESPACE
#endif

View File

@ -1,94 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef QWINDOWSURFACE_VG_P_H
#define QWINDOWSURFACE_VG_P_H
//
// W A R N I N G
// -------------
//
// This file is not part of the Qt API. It exists purely as an
// implementation detail. This header file may change from version to
// version without notice, or even be removed.
//
// We mean it.
//
#include <QtGui/private/qwindowsurface_p.h>
QT_BEGIN_NAMESPACE
#if !defined(QT_NO_EGL)
class QVGEGLWindowSurfacePrivate;
class Q_OPENVG_EXPORT QVGWindowSurface : public QWindowSurface, public QPaintDevice
{
public:
QVGWindowSurface(QWidget *window);
QVGWindowSurface(QWidget *window, QVGEGLWindowSurfacePrivate *d);
~QVGWindowSurface();
QPaintDevice *paintDevice();
void flush(QWidget *widget, const QRegion &region, const QPoint &offset);
void setGeometry(const QRect &rect);
bool scroll(const QRegion &area, int dx, int dy);
void beginPaint(const QRegion &region);
void endPaint(const QRegion &region);
QPaintEngine *paintEngine() const;
WindowSurfaceFeatures features() const;
protected:
int metric(PaintDeviceMetric metric) const;
private:
QVGEGLWindowSurfacePrivate *d_ptr;
};
#endif
QT_END_NAMESPACE
#endif // QWINDOWSURFACE_VG_P_H

View File

@ -1,782 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#include "qwindowsurface_vgegl_p.h"
#include "qpaintengine_vg_p.h"
#include "qpixmapdata_vg_p.h"
#include "qvgimagepool_p.h"
#include "qvg_p.h"
#if !defined(QT_NO_EGL)
QT_BEGIN_NAMESPACE
// Turn off "direct to window" rendering if EGL cannot support it.
#if !defined(EGL_RENDER_BUFFER) || !defined(EGL_SINGLE_BUFFER)
#if defined(QVG_DIRECT_TO_WINDOW)
#undef QVG_DIRECT_TO_WINDOW
#endif
#endif
// Determine if preserved window contents should be used.
#if !defined(EGL_SWAP_BEHAVIOR) || !defined(EGL_BUFFER_PRESERVED)
#if !defined(QVG_NO_PRESERVED_SWAP)
#define QVG_NO_PRESERVED_SWAP 1
#endif
#endif
VGImageFormat qt_vg_config_to_vg_format(QEglContext *context)
{
return qt_vg_image_to_vg_format
(qt_vg_config_to_image_format(context));
}
QImage::Format qt_vg_config_to_image_format(QEglContext *context)
{
EGLint red = context->configAttrib(EGL_RED_SIZE);
EGLint green = context->configAttrib(EGL_GREEN_SIZE);
EGLint blue = context->configAttrib(EGL_BLUE_SIZE);
EGLint alpha = context->configAttrib(EGL_ALPHA_SIZE);
QImage::Format argbFormat;
#ifdef EGL_VG_ALPHA_FORMAT_PRE_BIT
EGLint type = context->configAttrib(EGL_SURFACE_TYPE);
if ((type & EGL_VG_ALPHA_FORMAT_PRE_BIT) != 0)
argbFormat = QImage::Format_ARGB32_Premultiplied;
else
argbFormat = QImage::Format_ARGB32;
#else
argbFormat = QImage::Format_ARGB32;
#endif
if (red == 8 && green == 8 && blue == 8 && alpha == 8)
return argbFormat;
else if (red == 8 && green == 8 && blue == 8 && alpha == 0)
return QImage::Format_RGB32;
else if (red == 5 && green == 6 && blue == 5 && alpha == 0)
return QImage::Format_RGB16;
else if (red == 4 && green == 4 && blue == 4 && alpha == 4)
return QImage::Format_ARGB4444_Premultiplied;
else
return argbFormat; // XXX
}
#if !defined(QVG_NO_SINGLE_CONTEXT)
class QVGSharedContext
{
public:
QVGSharedContext();
~QVGSharedContext();
QEglContext *context;
int refCount;
int widgetRefCount;
QVGPaintEngine *engine;
EGLSurface surface;
QVGPixmapData *firstPixmap;
};
QVGSharedContext::QVGSharedContext()
: context(0)
, refCount(0)
, widgetRefCount(0)
, engine(0)
, surface(EGL_NO_SURFACE)
, firstPixmap(0)
{
}
QVGSharedContext::~QVGSharedContext()
{
// Don't accidentally destroy the QEglContext if the reference
// count falls to zero while deleting the paint engine.
++refCount;
if (context)
context->makeCurrent(qt_vg_shared_surface());
delete engine;
if (context)
context->doneCurrent();
if (context && surface != EGL_NO_SURFACE)
context->destroySurface(surface);
delete context;
}
Q_GLOBAL_STATIC(QVGSharedContext, sharedContext);
QVGPaintEngine *qt_vg_create_paint_engine(void)
{
QVGSharedContext *shared = sharedContext();
if (!shared->engine)
shared->engine = new QVGPaintEngine();
return shared->engine;
}
void qt_vg_destroy_paint_engine(QVGPaintEngine *engine)
{
Q_UNUSED(engine);
}
void qt_vg_register_pixmap(QVGPixmapData *pd)
{
QVGSharedContext *shared = sharedContext();
pd->next = shared->firstPixmap;
pd->prev = 0;
if (shared->firstPixmap)
shared->firstPixmap->prev = pd;
shared->firstPixmap = pd;
}
void qt_vg_unregister_pixmap(QVGPixmapData *pd)
{
if (pd->next)
pd->next->prev = pd->prev;
if (pd->prev) {
pd->prev->next = pd->next;
} else {
QVGSharedContext *shared = sharedContext();
if (shared)
shared->firstPixmap = pd->next;
}
}
#else
QVGPaintEngine *qt_vg_create_paint_engine(void)
{
return new QVGPaintEngine();
}
void qt_vg_destroy_paint_engine(QVGPaintEngine *engine)
{
delete engine;
}
void qt_vg_register_pixmap(QVGPixmapData *pd)
{
Q_UNUSED(pd);
}
void qt_vg_unregister_pixmap(QVGPixmapData *pd)
{
Q_UNUSED(pd);
}
#endif
#ifdef EGL_VG_ALPHA_FORMAT_PRE_BIT
static bool isPremultipliedContext(const QEglContext *context)
{
return context->configAttrib(EGL_SURFACE_TYPE) & EGL_VG_ALPHA_FORMAT_PRE_BIT;
}
#endif
static QEglContext *createContext(QPaintDevice *device)
{
QEglContext *context;
// Create the context object and open the display.
context = new QEglContext();
context->setApi(QEgl::OpenVG);
// Set the swap interval for the display.
QByteArray interval = qgetenv("QT_VG_SWAP_INTERVAL");
if (!interval.isEmpty())
eglSwapInterval(QEgl::display(), interval.toInt());
else
eglSwapInterval(QEgl::display(), 1);
#ifdef EGL_RENDERABLE_TYPE
// Has the user specified an explicit EGL configuration to use?
QByteArray configId = qgetenv("QT_VG_EGL_CONFIG");
if (!configId.isEmpty()) {
EGLint cfgId = configId.toInt();
EGLint properties[] = {
EGL_CONFIG_ID, cfgId,
EGL_NONE
};
EGLint matching = 0;
EGLConfig cfg;
if (eglChooseConfig
(QEgl::display(), properties, &cfg, 1, &matching) &&
matching > 0) {
// Check that the selected configuration actually supports OpenVG
// and then create the context with it.
EGLint id = 0;
EGLint type = 0;
eglGetConfigAttrib
(QEgl::display(), cfg, EGL_CONFIG_ID, &id);
eglGetConfigAttrib
(QEgl::display(), cfg, EGL_RENDERABLE_TYPE, &type);
if (cfgId == id && (type & EGL_OPENVG_BIT) != 0) {
context->setConfig(cfg);
if (!context->createContext()) {
delete context;
return 0;
}
return context;
} else {
qWarning("QT_VG_EGL_CONFIG: %d is not a valid OpenVG configuration", int(cfgId));
}
}
}
#endif
// Choose an appropriate configuration for rendering into the device.
QEglProperties configProps;
configProps.setPaintDeviceFormat(device);
int redSize = configProps.value(EGL_RED_SIZE);
if (redSize == EGL_DONT_CARE || redSize == 0)
configProps.setPixelFormat(QImage::Format_ARGB32); // XXX
configProps.setValue(EGL_ALPHA_MASK_SIZE, 1);
#ifdef EGL_VG_ALPHA_FORMAT_PRE_BIT
configProps.setValue(EGL_SURFACE_TYPE, EGL_WINDOW_BIT |
EGL_VG_ALPHA_FORMAT_PRE_BIT);
configProps.setRenderableType(QEgl::OpenVG);
if (!context->chooseConfig(configProps)) {
// Try again without the "pre" bit.
configProps.setValue(EGL_SURFACE_TYPE, EGL_WINDOW_BIT);
if (!context->chooseConfig(configProps)) {
delete context;
return 0;
}
}
#else
configProps.setValue(EGL_SURFACE_TYPE, EGL_WINDOW_BIT);
configProps.setRenderableType(QEgl::OpenVG);
if (!context->chooseConfig(configProps)) {
delete context;
return 0;
}
#endif
// Construct a new EGL context for the selected configuration.
if (!context->createContext()) {
delete context;
return 0;
}
return context;
}
#if !defined(QVG_NO_SINGLE_CONTEXT)
QEglContext *qt_vg_create_context(QPaintDevice *device, int devType)
{
QVGSharedContext *shared = sharedContext();
if (devType == QInternal::Widget)
++(shared->widgetRefCount);
if (shared->context) {
++(shared->refCount);
return shared->context;
} else {
shared->context = createContext(device);
shared->refCount = 1;
return shared->context;
}
}
static void qt_vg_destroy_shared_context(QVGSharedContext *shared)
{
shared->context->makeCurrent(qt_vg_shared_surface());
delete shared->engine;
shared->engine = 0;
shared->context->doneCurrent();
if (shared->surface != EGL_NO_SURFACE) {
eglDestroySurface(QEgl::display(), shared->surface);
shared->surface = EGL_NO_SURFACE;
}
delete shared->context;
shared->context = 0;
}
void qt_vg_hibernate_pixmaps(QVGSharedContext *shared)
{
// Artificially increase the reference count to prevent the
// context from being destroyed until after we have finished
// the hibernation process.
++(shared->refCount);
// We need a context current to hibernate the VGImage objects.
shared->context->makeCurrent(qt_vg_shared_surface());
// Scan all QVGPixmapData objects in the system and hibernate them.
QVGPixmapData *pd = shared->firstPixmap;
while (pd != 0) {
pd->hibernate();
pd = pd->next;
}
// Hibernate any remaining VGImage's in the image pool.
QVGImagePool::instance()->hibernate();
// Don't need the current context any more.
shared->context->lazyDoneCurrent();
// Decrease the reference count and destroy the context if necessary.
if (--(shared->refCount) <= 0)
qt_vg_destroy_shared_context(shared);
}
void qt_vg_destroy_context(QEglContext *context, int devType)
{
QVGSharedContext *shared = sharedContext();
if (shared->context != context) {
// This is not the shared context. Shouldn't happen!
delete context;
return;
}
if (devType == QInternal::Widget)
--(shared->widgetRefCount);
if (--(shared->refCount) <= 0) {
qt_vg_destroy_shared_context(shared);
} else if (shared->widgetRefCount <= 0 && devType == QInternal::Widget) {
// All of the widget window surfaces have been destroyed
// but we still have VG pixmaps active. Ask them to hibernate
// to free up GPU resources until a widget is shown again.
// This may eventually cause the EGLContext to be destroyed
// because nothing in the system needs a context, which will
// free up even more GPU resources.
qt_vg_hibernate_pixmaps(shared);
}
}
EGLSurface qt_vg_shared_surface(void)
{
QVGSharedContext *shared = sharedContext();
if (shared->surface == EGL_NO_SURFACE) {
EGLint attribs[7];
attribs[0] = EGL_WIDTH;
attribs[1] = 16;
attribs[2] = EGL_HEIGHT;
attribs[3] = 16;
#ifdef EGL_VG_ALPHA_FORMAT_PRE_BIT
if (isPremultipliedContext(shared->context)) {
attribs[4] = EGL_VG_ALPHA_FORMAT;
attribs[5] = EGL_VG_ALPHA_FORMAT_PRE;
attribs[6] = EGL_NONE;
} else
#endif
{
attribs[4] = EGL_NONE;
}
shared->surface = eglCreatePbufferSurface
(QEgl::display(), shared->context->config(), attribs);
}
return shared->surface;
}
#else
QEglContext *qt_vg_create_context(QPaintDevice *device, int devType)
{
Q_UNUSED(devType);
return createContext(device);
}
void qt_vg_destroy_context(QEglContext *context, int devType)
{
Q_UNUSED(devType);
delete context;
}
EGLSurface qt_vg_shared_surface(void)
{
return EGL_NO_SURFACE;
}
#endif
QVGEGLWindowSurfacePrivate::QVGEGLWindowSurfacePrivate(QWindowSurface *win)
{
winSurface = win;
engine = 0;
}
QVGEGLWindowSurfacePrivate::~QVGEGLWindowSurfacePrivate()
{
// Destroy the paint engine if it hasn't been destroyed already.
destroyPaintEngine();
}
QVGPaintEngine *QVGEGLWindowSurfacePrivate::paintEngine()
{
if (!engine)
engine = qt_vg_create_paint_engine();
return engine;
}
VGImage QVGEGLWindowSurfacePrivate::surfaceImage() const
{
return VG_INVALID_HANDLE;
}
void QVGEGLWindowSurfacePrivate::destroyPaintEngine()
{
if (engine) {
qt_vg_destroy_paint_engine(engine);
engine = 0;
}
}
QSize QVGEGLWindowSurfacePrivate::windowSurfaceSize(QWidget *widget) const
{
Q_UNUSED(widget);
QRect rect = winSurface->geometry();
QSize newSize = rect.size();
#if defined(Q_WS_QWS)
// Account for the widget mask, if any.
if (widget && !widget->mask().isEmpty()) {
const QRegion region = widget->mask()
& rect.translated(-widget->geometry().topLeft());
newSize = region.boundingRect().size();
}
#endif
return newSize;
}
#if defined(QVG_VGIMAGE_BACKBUFFERS)
QVGEGLWindowSurfaceVGImage::QVGEGLWindowSurfaceVGImage(QWindowSurface *win)
: QVGEGLWindowSurfacePrivate(win)
, context(0)
, backBuffer(VG_INVALID_HANDLE)
, backBufferSurface(EGL_NO_SURFACE)
, recreateBackBuffer(false)
, isPaintingActive(false)
, windowSurface(EGL_NO_SURFACE)
{
}
QVGEGLWindowSurfaceVGImage::~QVGEGLWindowSurfaceVGImage()
{
destroyPaintEngine();
if (context) {
if (backBufferSurface != EGL_NO_SURFACE) {
// We need a current context to be able to destroy the image.
// We use the shared surface because the native window handle
// associated with "windowSurface" may have been destroyed already.
context->makeCurrent(qt_vg_shared_surface());
context->destroySurface(backBufferSurface);
vgDestroyImage(backBuffer);
context->doneCurrent();
}
if (windowSurface != EGL_NO_SURFACE)
context->destroySurface(windowSurface);
qt_vg_destroy_context(context, QInternal::Widget);
}
}
QEglContext *QVGEGLWindowSurfaceVGImage::ensureContext(QWidget *widget)
{
QSize newSize = windowSurfaceSize(widget);
if (context && size != newSize) {
// The surface size has changed, so we need to recreate
// the back buffer. Keep the same context and paint engine.
size = newSize;
if (isPaintingActive)
context->doneCurrent();
isPaintingActive = false;
recreateBackBuffer = true;
}
if (!context) {
// Create a new EGL context. We create the surface in beginPaint().
size = newSize;
context = qt_vg_create_context(widget, QInternal::Widget);
if (!context)
return 0;
isPaintingActive = false;
}
return context;
}
void QVGEGLWindowSurfaceVGImage::beginPaint(QWidget *widget)
{
QEglContext *context = ensureContext(widget);
if (context) {
if (recreateBackBuffer || backBufferSurface == EGL_NO_SURFACE) {
// Create a VGImage object to act as the back buffer
// for this window. We have to create the VGImage with a
// current context, so activate the main surface for the window.
context->makeCurrent(mainSurface());
recreateBackBuffer = false;
if (backBufferSurface != EGL_NO_SURFACE) {
eglDestroySurface(QEgl::display(), backBufferSurface);
backBufferSurface = EGL_NO_SURFACE;
}
if (backBuffer != VG_INVALID_HANDLE) {
vgDestroyImage(backBuffer);
}
VGImageFormat format = qt_vg_config_to_vg_format(context);
backBuffer = vgCreateImage
(format, size.width(), size.height(),
VG_IMAGE_QUALITY_FASTER);
if (backBuffer != VG_INVALID_HANDLE) {
// Create an EGL surface for rendering into the VGImage.
backBufferSurface = eglCreatePbufferFromClientBuffer
(QEgl::display(), EGL_OPENVG_IMAGE,
(EGLClientBuffer)(backBuffer),
context->config(), NULL);
if (backBufferSurface == EGL_NO_SURFACE) {
vgDestroyImage(backBuffer);
backBuffer = VG_INVALID_HANDLE;
}
}
}
if (backBufferSurface != EGL_NO_SURFACE)
context->makeCurrent(backBufferSurface);
else
context->makeCurrent(mainSurface());
isPaintingActive = true;
}
}
void QVGEGLWindowSurfaceVGImage::endPaint
(QWidget *widget, const QRegion& region, QImage *image)
{
Q_UNUSED(region);
Q_UNUSED(image);
QEglContext *context = ensureContext(widget);
if (context) {
if (backBufferSurface != EGL_NO_SURFACE) {
if (isPaintingActive)
vgFlush();
context->lazyDoneCurrent();
}
isPaintingActive = false;
}
}
VGImage QVGEGLWindowSurfaceVGImage::surfaceImage() const
{
return backBuffer;
}
EGLSurface QVGEGLWindowSurfaceVGImage::mainSurface() const
{
if (windowSurface != EGL_NO_SURFACE)
return windowSurface;
else
return qt_vg_shared_surface();
}
#endif // QVG_VGIMAGE_BACKBUFFERS
QVGEGLWindowSurfaceDirect::QVGEGLWindowSurfaceDirect(QWindowSurface *win)
: QVGEGLWindowSurfacePrivate(win)
, context(0)
, isPaintingActive(false)
, needToSwap(false)
, windowSurface(EGL_NO_SURFACE)
{
}
QVGEGLWindowSurfaceDirect::~QVGEGLWindowSurfaceDirect()
{
destroyPaintEngine();
if (context) {
if (windowSurface != EGL_NO_SURFACE)
context->destroySurface(windowSurface);
qt_vg_destroy_context(context, QInternal::Widget);
}
}
QEglContext *QVGEGLWindowSurfaceDirect::ensureContext(QWidget *widget)
{
QSize newSize = windowSurfaceSize(widget);
QEglProperties surfaceProps;
#if defined(QVG_RECREATE_ON_SIZE_CHANGE)
#if !defined(QVG_NO_SINGLE_CONTEXT)
if (context && size != newSize) {
// The surface size has changed, so we need to recreate it.
// We can keep the same context and paint engine.
size = newSize;
if (isPaintingActive)
context->doneCurrent();
context->destroySurface(windowSurface);
#if defined(EGL_VG_ALPHA_FORMAT_PRE_BIT)
if (isPremultipliedContext(context)) {
surfaceProps.setValue
(EGL_VG_ALPHA_FORMAT, EGL_VG_ALPHA_FORMAT_PRE);
} else {
surfaceProps.removeValue(EGL_VG_ALPHA_FORMAT);
}
#endif
windowSurface = context->createSurface(widget, &surfaceProps);
isPaintingActive = false;
needToSwap = true;
}
#else
if (context && size != newSize) {
// The surface size has changed, so we need to recreate
// the EGL context for the widget. We also need to recreate
// the surface's paint engine if context sharing is not
// enabled because we cannot reuse the existing paint objects
// in the new context.
qt_vg_destroy_paint_engine(engine);
engine = 0;
context->destroySurface(windowSurface);
qt_vg_destroy_context(context, QInternal::Widget);
context = 0;
windowSurface = EGL_NO_SURFACE;
}
#endif
#endif
if (!context) {
// Create a new EGL context and bind it to the widget surface.
size = newSize;
context = qt_vg_create_context(widget, QInternal::Widget);
if (!context)
return 0;
// We want a direct to window rendering surface if possible.
#if defined(QVG_DIRECT_TO_WINDOW)
surfaceProps.setValue(EGL_RENDER_BUFFER, EGL_SINGLE_BUFFER);
#endif
#if defined(EGL_VG_ALPHA_FORMAT_PRE_BIT)
if (isPremultipliedContext(context)) {
surfaceProps.setValue
(EGL_VG_ALPHA_FORMAT, EGL_VG_ALPHA_FORMAT_PRE);
} else {
surfaceProps.removeValue(EGL_VG_ALPHA_FORMAT);
}
#endif
EGLSurface surface = context->createSurface(widget, &surfaceProps);
if (surface == EGL_NO_SURFACE) {
qt_vg_destroy_context(context, QInternal::Widget);
context = 0;
return 0;
}
needToSwap = true;
#if defined(QVG_DIRECT_TO_WINDOW)
// Did we get a direct to window rendering surface?
EGLint buffer = 0;
if (eglQueryContext(QEgl::display(), context->context(),
EGL_RENDER_BUFFER, &buffer) &&
buffer == EGL_SINGLE_BUFFER) {
needToSwap = false;
}
#endif
windowSurface = surface;
isPaintingActive = false;
}
#if !defined(QVG_NO_PRESERVED_SWAP)
// Try to force the surface back buffer to preserve its contents.
if (needToSwap) {
bool succeeded = eglSurfaceAttrib(QEgl::display(), windowSurface,
EGL_SWAP_BEHAVIOR, EGL_BUFFER_PRESERVED);
if (!succeeded && eglGetError() != EGL_SUCCESS) {
qWarning("QVG: could not enable preserved swap");
}
}
#endif
return context;
}
void QVGEGLWindowSurfaceDirect::beginPaint(QWidget *widget)
{
QEglContext *context = ensureContext(widget);
if (context) {
context->makeCurrent(windowSurface);
isPaintingActive = true;
}
}
void QVGEGLWindowSurfaceDirect::endPaint
(QWidget *widget, const QRegion& region, QImage *image)
{
Q_UNUSED(region);
Q_UNUSED(image);
QEglContext *context = ensureContext(widget);
if (context) {
if (needToSwap) {
if (!isPaintingActive)
context->makeCurrent(windowSurface);
context->swapBuffers(windowSurface);
context->lazyDoneCurrent();
} else if (isPaintingActive) {
vgFlush();
context->lazyDoneCurrent();
}
isPaintingActive = false;
}
}
bool QVGEGLWindowSurfaceDirect::supportsStaticContents() const
{
#if defined(QVG_BUFFER_SCROLLING) && !defined(QVG_NO_PRESERVED_SWAP)
return true;
#else
return QVGEGLWindowSurfacePrivate::supportsStaticContents();
#endif
}
bool QVGEGLWindowSurfaceDirect::scroll(QWidget *widget, const QRegion& area, int dx, int dy)
{
#ifdef QVG_BUFFER_SCROLLING
QEglContext *context = ensureContext(widget);
if (context) {
context->makeCurrent(windowSurface);
QRect scrollRect = area.boundingRect();
int sx = scrollRect.x();
int sy = size.height() - scrollRect.y() - scrollRect.height();
vgSeti(VG_SCISSORING, VG_FALSE);
vgCopyPixels(sx + dx, sy - dy, sx, sy, scrollRect.width(), scrollRect.height());
context->lazyDoneCurrent();
return true;
}
#else
Q_UNUSED(widget);
Q_UNUSED(area);
Q_UNUSED(dx);
Q_UNUSED(dy);
#endif
return false;
}
QT_END_NAMESPACE
#endif

View File

@ -1,148 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the QtOpenVG module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef QWINDOWSURFACE_VGEGL_P_H
#define QWINDOWSURFACE_VGEGL_P_H
//
// W A R N I N G
// -------------
//
// This file is not part of the Qt API. It exists for the convenience
// of the QLibrary class. This header file may change from
// version to version without notice, or even be removed.
//
// We mean it.
//
#include <QtGui/private/qwindowsurface_p.h>
#include "qvg_p.h"
#if !defined(QT_NO_EGL)
#include <QtGui/private/qeglcontext_p.h>
QT_BEGIN_NAMESPACE
class QWindowSurface;
class Q_OPENVG_EXPORT QVGEGLWindowSurfacePrivate
{
public:
QVGEGLWindowSurfacePrivate(QWindowSurface *win);
virtual ~QVGEGLWindowSurfacePrivate();
QVGPaintEngine *paintEngine();
virtual QEglContext *ensureContext(QWidget *widget) = 0;
virtual void beginPaint(QWidget *widget) = 0;
virtual void endPaint
(QWidget *widget, const QRegion& region, QImage *image = 0) = 0;
virtual VGImage surfaceImage() const;
virtual QSize surfaceSize() const = 0;
virtual bool supportsStaticContents() const { return false; }
virtual bool scroll(QWidget *, const QRegion&, int, int) { return false; }
private:
QVGPaintEngine *engine;
protected:
QWindowSurface *winSurface;
void destroyPaintEngine();
QSize windowSurfaceSize(QWidget *widget) const;
};
#if defined(EGL_OPENVG_IMAGE) && !defined(QVG_NO_SINGLE_CONTEXT)
#define QVG_VGIMAGE_BACKBUFFERS 1
class Q_OPENVG_EXPORT QVGEGLWindowSurfaceVGImage : public QVGEGLWindowSurfacePrivate
{
public:
QVGEGLWindowSurfaceVGImage(QWindowSurface *win);
virtual ~QVGEGLWindowSurfaceVGImage();
QEglContext *ensureContext(QWidget *widget);
void beginPaint(QWidget *widget);
void endPaint(QWidget *widget, const QRegion& region, QImage *image);
VGImage surfaceImage() const;
QSize surfaceSize() const { return size; }
protected:
QEglContext *context;
VGImage backBuffer;
EGLSurface backBufferSurface;
bool recreateBackBuffer;
bool isPaintingActive;
QSize size;
EGLSurface windowSurface;
EGLSurface mainSurface() const;
};
#endif // EGL_OPENVG_IMAGE
class Q_OPENVG_EXPORT QVGEGLWindowSurfaceDirect : public QVGEGLWindowSurfacePrivate
{
public:
QVGEGLWindowSurfaceDirect(QWindowSurface *win);
virtual ~QVGEGLWindowSurfaceDirect();
QEglContext *ensureContext(QWidget *widget);
void beginPaint(QWidget *widget);
void endPaint(QWidget *widget, const QRegion& region, QImage *image);
QSize surfaceSize() const { return size; }
bool supportsStaticContents() const;
bool scroll(QWidget *widget, const QRegion& area, int dx, int dy);
protected:
QEglContext *context;
QSize size;
bool isPaintingActive;
bool needToSwap;
EGLSurface windowSurface;
};
QT_END_NAMESPACE
#endif // !QT_NO_EGL
#endif // QWINDOWSURFACE_VGEGL_P_H