Basic high-dpi "retina" support for Qt 5.
Bring Qt 5 on par with Qt 4, prepare for more comprehensive support later on. Introduce device independent pixels (dips), device pixels, and devicePixelRatio. Add high-dpi support to QPainter, QGLWidget, the cocoa platform plugin, mac and fusion styles. Dips are similar to CSS pixels, Apple points and Android density-independent pixels. Device pixels are pixels in the backing store/physical pixels on screen. devicePixelRatio is the ratio between them, which is 1.0 on standard displays and 2.0 on "retina" displays. New API: QImage::devicePixelRatio() and setDevicePixelRatio() QPixmap::devicePixelRatio() and setDevicePixelRatio() QWindow::devicePixelRatio() QScreen::devicePixelRatio() QGuiApplicaiton::devicePixelRatio() Change-Id: If98c3ca9bfdf0e1bdbcf7574cd5b912c9ff63856 Reviewed-by: Morten Johan Sørvig <morten.sorvig@digia.com> Reviewed-by: Gunnar Sletta <gunnar.sletta@digia.com>
This commit is contained in:
parent
c8dc41bacd
commit
5e61bbe586
@ -95,10 +95,12 @@ static QImage rotated270(const QImage &src);
|
||||
QBasicAtomicInt qimage_serial_number = Q_BASIC_ATOMIC_INITIALIZER(1);
|
||||
|
||||
QImageData::QImageData()
|
||||
: ref(0), width(0), height(0), depth(0), nbytes(0), data(0),
|
||||
: ref(0), width(0), height(0), depth(0), nbytes(0), devicePixelRatio(1.0), data(0),
|
||||
format(QImage::Format_ARGB32), bytes_per_line(0),
|
||||
ser_no(qimage_serial_number.fetchAndAddRelaxed(1)),
|
||||
detach_no(0),
|
||||
ldpmx(qt_defaultDpiX() * 100 / qreal(2.54)),
|
||||
ldpmy(qt_defaultDpiY() * 100 / qreal(2.54)),
|
||||
dpmx(qt_defaultDpiX() * 100 / qreal(2.54)),
|
||||
dpmy(qt_defaultDpiY() * 100 / qreal(2.54)),
|
||||
offset(0, 0), own_data(true), ro_data(false), has_alpha_clut(false),
|
||||
@ -1216,6 +1218,7 @@ QImage QImage::copy(const QRect& r) const
|
||||
|
||||
image.d->dpmx = dotsPerMeterX();
|
||||
image.d->dpmy = dotsPerMeterY();
|
||||
image.d->devicePixelRatio = devicePixelRatio();
|
||||
image.d->offset = offset();
|
||||
image.d->has_alpha_clut = d->has_alpha_clut;
|
||||
image.d->text = d->text;
|
||||
@ -1369,6 +1372,52 @@ QVector<QRgb> QImage::colorTable() const
|
||||
return d ? d->colortable : QVector<QRgb>();
|
||||
}
|
||||
|
||||
/*!
|
||||
Returns the device pixel ratio for the image. This is the
|
||||
ratio between image pixels and device-independent pixels.
|
||||
|
||||
Use this function when calculating layout geometry based on
|
||||
the image size: QSize layoutSize = image.size() / image.devicePixelRatio()
|
||||
|
||||
The default value is 1.0.
|
||||
|
||||
\sa setDevicePixelRatio()
|
||||
*/
|
||||
qreal QImage::devicePixelRatio() const
|
||||
{
|
||||
if (!d)
|
||||
return 1.0;
|
||||
return d->devicePixelRatio;
|
||||
}
|
||||
|
||||
/*!
|
||||
Sets the the device pixel ratio for the image. This is the
|
||||
ratio between image pixels and device-independent pixels.
|
||||
|
||||
The default value is 1.0. Setting it to something else has
|
||||
two effects:
|
||||
|
||||
QPainters that are opened on the image will be scaled. For
|
||||
example, painting on a 200x200 image if with a ratio of 2.0
|
||||
will result in effective (device-independent) painting bounds
|
||||
of 100x100.
|
||||
|
||||
Code paths in Qt that calculate layout geometry based on the
|
||||
image size will take the ratio into account:
|
||||
QSize layoutSize = image.size() / image.devicePixelRatio()
|
||||
The net effect of this is that the image is displayed as
|
||||
high-dpi image rather than a large image.
|
||||
|
||||
\sa devicePixelRatio()
|
||||
*/
|
||||
void QImage::setDevicePixelRatio(qreal scaleFactor)
|
||||
{
|
||||
if (!d)
|
||||
return;
|
||||
detach();
|
||||
d->devicePixelRatio = scaleFactor;
|
||||
}
|
||||
|
||||
/*!
|
||||
\since 4.6
|
||||
Returns the number of bytes occupied by the image data.
|
||||
@ -3359,6 +3408,7 @@ QImage QImage::convertToFormat(Format format, Qt::ImageConversionFlags flags) co
|
||||
|
||||
image.setDotsPerMeterY(dotsPerMeterY());
|
||||
image.setDotsPerMeterX(dotsPerMeterX());
|
||||
image.setDevicePixelRatio(devicePixelRatio());
|
||||
|
||||
image.d->text = d->text;
|
||||
|
||||
@ -3479,6 +3529,7 @@ QImage QImage::convertToFormat(Format format, const QVector<QRgb> &colorTable, Q
|
||||
|
||||
QImage image(d->width, d->height, format);
|
||||
QIMAGE_SANITYCHECK_MEMORY(image);
|
||||
image.setDevicePixelRatio(devicePixelRatio());
|
||||
|
||||
image.d->text = d->text;
|
||||
|
||||
@ -4932,17 +4983,20 @@ int QImage::metric(PaintDeviceMetric metric) const
|
||||
return d->depth;
|
||||
|
||||
case PdmDpiX:
|
||||
return qRound(d->dpmx * 0.0254);
|
||||
return qRound(d->ldpmx * 0.0254);
|
||||
break;
|
||||
|
||||
case PdmDpiY:
|
||||
return qRound(d->dpmy * 0.0254);
|
||||
return qRound(d->ldpmy * 0.0254);
|
||||
break;
|
||||
|
||||
case PdmPhysicalDpiX:
|
||||
return qRound(d->dpmx * 0.0254);
|
||||
return qRound(d->dpmx * 0.0254 * d->devicePixelRatio);
|
||||
break;
|
||||
|
||||
case PdmPhysicalDpiY:
|
||||
return qRound(d->dpmy * 0.0254);
|
||||
|
||||
return qRound(d->dpmy * 0.0254 * d->devicePixelRatio);
|
||||
break;
|
||||
default:
|
||||
qWarning("QImage::metric(): Unhandled metric type %d", metric);
|
||||
break;
|
||||
@ -5641,6 +5695,7 @@ QImage QImage::transformed(const QTransform &matrix, Qt::TransformationMode mode
|
||||
|
||||
dImage.d->dpmx = dotsPerMeterX();
|
||||
dImage.d->dpmy = dotsPerMeterY();
|
||||
dImage.d->devicePixelRatio = devicePixelRatio();
|
||||
|
||||
switch (bpp) {
|
||||
// initizialize the data
|
||||
|
@ -211,6 +211,9 @@ public:
|
||||
QVector<QRgb> colorTable() const;
|
||||
void setColorTable(const QVector<QRgb> colors);
|
||||
|
||||
qreal devicePixelRatio() const;
|
||||
void setDevicePixelRatio(qreal scaleFactor);
|
||||
|
||||
void fill(uint pixel);
|
||||
void fill(const QColor &color);
|
||||
void fill(Qt::GlobalColor color);
|
||||
|
@ -74,6 +74,7 @@ struct Q_GUI_EXPORT QImageData { // internal image data
|
||||
int height;
|
||||
int depth;
|
||||
int nbytes; // number of bytes data
|
||||
qreal devicePixelRatio;
|
||||
QVector<QRgb> colortable;
|
||||
uchar *data;
|
||||
QImage::Format format;
|
||||
@ -81,8 +82,10 @@ struct Q_GUI_EXPORT QImageData { // internal image data
|
||||
int ser_no; // serial number
|
||||
int detach_no;
|
||||
|
||||
qreal dpmx; // dots per meter X (or 0)
|
||||
qreal dpmy; // dots per meter Y (or 0)
|
||||
qreal ldpmx; // logical dots per meter X (or 0)
|
||||
qreal ldpmy; // logical dots per meter Y (or 0)
|
||||
qreal dpmx; // device dots per meter X (or 0)
|
||||
qreal dpmy; // device dots per meter Y (or 0)
|
||||
QPoint offset; // offset in pixels
|
||||
|
||||
uint own_data : 1;
|
||||
|
@ -1234,6 +1234,11 @@ bool QImageReader::read(QImage *image)
|
||||
}
|
||||
}
|
||||
|
||||
// successful read; check for "@2x" file name suffix and set device pixel ratio.
|
||||
if (QFileInfo(fileName()).baseName().endsWith("@2x")) {
|
||||
image->setDevicePixelRatio(2.0);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -638,6 +638,50 @@ void QPixmap::setMask(const QBitmap &mask)
|
||||
data->fromImage(image, Qt::AutoColor);
|
||||
}
|
||||
|
||||
/*!
|
||||
Returns the device pixel ratio for the pixmap. This is the
|
||||
ratio between pixmap pixels and device-independent pixels.
|
||||
|
||||
Use this function when calculating layout geometry based on
|
||||
the pixmap size: QSize layoutSize = image.size() / image.devicePixelRatio()
|
||||
|
||||
The default value is 1.0.
|
||||
|
||||
\sa setDevicePixelRatio()
|
||||
*/
|
||||
qreal QPixmap::devicePixelRatio() const
|
||||
{
|
||||
if (!data)
|
||||
return qreal(1.0);
|
||||
return data->devicePixelRatio();
|
||||
}
|
||||
|
||||
/*!
|
||||
Sets the the device pixel ratio for the pixmap. This is the
|
||||
ratio between image pixels and device-independent pixels.
|
||||
|
||||
The default value is 1.0. Setting it to something else has
|
||||
two effects:
|
||||
|
||||
QPainters that are opened on the pixmap will be scaled. For
|
||||
example, painting on a 200x200 image if with a ratio of 2.0
|
||||
will result in effective (device-independent) painting bounds
|
||||
of 100x100.
|
||||
|
||||
Code paths in Qt that calculate layout geometry based on the
|
||||
pixmap size will take the ratio into account:
|
||||
QSize layoutSize = pixmap.size() / pixmap.devicePixelRatio()
|
||||
The net effect of this is that the pixmap is displayed as
|
||||
high-dpi pixmap rather than a large pixmap.
|
||||
|
||||
\sa devicePixelRatio()
|
||||
*/
|
||||
void QPixmap::setDevicePixelRatio(qreal scaleFactor)
|
||||
{
|
||||
detach();
|
||||
data->setDevicePixelRatio(scaleFactor);
|
||||
}
|
||||
|
||||
#ifndef QT_NO_IMAGE_HEURISTIC_MASK
|
||||
/*!
|
||||
Creates and returns a heuristic mask for this pixmap.
|
||||
|
@ -102,6 +102,9 @@ public:
|
||||
QBitmap mask() const;
|
||||
void setMask(const QBitmap &);
|
||||
|
||||
qreal devicePixelRatio() const;
|
||||
void setDevicePixelRatio(qreal scaleFactor);
|
||||
|
||||
bool hasAlpha() const;
|
||||
bool hasAlphaChannel() const;
|
||||
|
||||
|
@ -195,6 +195,16 @@ void QBlittablePlatformPixmap::fromImage(const QImage &image,
|
||||
}
|
||||
}
|
||||
|
||||
qreal QBlittablePlatformPixmap::devicePixelRatio() const
|
||||
{
|
||||
return m_devicePixelRatio;
|
||||
}
|
||||
|
||||
void QBlittablePlatformPixmap::setDevicePixelRatio(qreal scaleFactor)
|
||||
{
|
||||
m_devicePixelRatio = scaleFactor;
|
||||
}
|
||||
|
||||
QPaintEngine *QBlittablePlatformPixmap::paintEngine() const
|
||||
{
|
||||
if (!m_engine) {
|
||||
|
@ -66,6 +66,8 @@ public:
|
||||
QImage toImage() const;
|
||||
bool hasAlphaChannel() const;
|
||||
void fromImage(const QImage &image, Qt::ImageConversionFlags flags);
|
||||
qreal devicePixelRatio() const;
|
||||
void setDevicePixelRatio(qreal scaleFactor);
|
||||
|
||||
QPaintEngine *paintEngine() const;
|
||||
|
||||
@ -89,6 +91,7 @@ protected:
|
||||
QScopedPointer<QBlitterPaintEngine> m_engine;
|
||||
QScopedPointer<QBlittable> m_blittable;
|
||||
bool m_alpha;
|
||||
qreal m_devicePixelRatio;
|
||||
|
||||
#ifdef QT_BLITTER_RASTEROVERLAY
|
||||
QImage *m_rasterOverlay;
|
||||
|
@ -272,12 +272,14 @@ int QRasterPlatformPixmap::metric(QPaintDevice::PaintDeviceMetric metric) const
|
||||
return d->colortable.size();
|
||||
case QPaintDevice::PdmDepth:
|
||||
return this->d;
|
||||
case QPaintDevice::PdmDpiX: // fall-through
|
||||
case QPaintDevice::PdmPhysicalDpiX:
|
||||
case QPaintDevice::PdmDpiX:
|
||||
return qt_defaultDpiX();
|
||||
case QPaintDevice::PdmPhysicalDpiX:
|
||||
return qt_defaultDpiX() * image.devicePixelRatio();
|
||||
case QPaintDevice::PdmDpiY:
|
||||
return qt_defaultDpiX();
|
||||
case QPaintDevice::PdmDpiY: // fall-through
|
||||
case QPaintDevice::PdmPhysicalDpiY:
|
||||
return qt_defaultDpiY();
|
||||
return qt_defaultDpiY() * image.devicePixelRatio();
|
||||
default:
|
||||
qWarning("QRasterPlatformPixmap::metric(): Unhandled metric type %d", metric);
|
||||
break;
|
||||
@ -350,6 +352,7 @@ void QRasterPlatformPixmap::createPixmapForImage(QImage &sourceImage, Qt::ImageC
|
||||
}
|
||||
is_null = (w <= 0 || h <= 0);
|
||||
|
||||
image.d->devicePixelRatio = sourceImage.devicePixelRatio();
|
||||
setSerialNumber(image.cacheKey() >> 32);
|
||||
}
|
||||
|
||||
@ -358,4 +361,14 @@ QImage* QRasterPlatformPixmap::buffer()
|
||||
return ℑ
|
||||
}
|
||||
|
||||
qreal QRasterPlatformPixmap::devicePixelRatio() const
|
||||
{
|
||||
return image.devicePixelRatio();
|
||||
}
|
||||
|
||||
void QRasterPlatformPixmap::setDevicePixelRatio(qreal scaleFactor)
|
||||
{
|
||||
image.setDevicePixelRatio(scaleFactor);
|
||||
}
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
@ -79,6 +79,9 @@ public:
|
||||
QImage toImage(const QRect &rect) const;
|
||||
QPaintEngine* paintEngine() const;
|
||||
QImage* buffer();
|
||||
qreal devicePixelRatio() const;
|
||||
void setDevicePixelRatio(qreal scaleFactor);
|
||||
|
||||
|
||||
protected:
|
||||
int metric(QPaintDevice::PaintDeviceMetric metric) const;
|
||||
|
@ -108,6 +108,9 @@ public:
|
||||
inline PixelType pixelType() const { return type; }
|
||||
inline ClassId classId() const { return static_cast<ClassId>(id); }
|
||||
|
||||
virtual qreal devicePixelRatio() const = 0;
|
||||
virtual void setDevicePixelRatio(qreal scaleFactor) = 0;
|
||||
|
||||
virtual QImage* buffer();
|
||||
|
||||
inline int width() const { return w; }
|
||||
|
@ -703,7 +703,34 @@ QList<QScreen *> QGuiApplication::screens()
|
||||
|
||||
|
||||
/*!
|
||||
Returns the top level window at the given position \a pos, if any.
|
||||
Returns the highest screen device pixel ratio found on
|
||||
the system. This is the ratio between physical pixels and
|
||||
device-independent pixels.
|
||||
|
||||
Use this function only when you don't know which window you are targeting.
|
||||
If you do know the target window use QWindow::devicePixelRatio() instead.
|
||||
|
||||
\sa QWindow::devicePixelRatio();
|
||||
\sa QGuiApplicaiton::devicePixelRatio();
|
||||
*/
|
||||
qreal QGuiApplication::devicePixelRatio() const
|
||||
{
|
||||
// Cache topDevicePixelRatio, iterate through the screen list once only.
|
||||
static qreal topDevicePixelRatio = 0.0;
|
||||
if (!qFuzzyIsNull(topDevicePixelRatio)) {
|
||||
return topDevicePixelRatio;
|
||||
}
|
||||
|
||||
topDevicePixelRatio = 1.0; // make sure we never return 0.
|
||||
foreach (QScreen *screen, QGuiApplicationPrivate::screen_list) {
|
||||
topDevicePixelRatio = qMax(topDevicePixelRatio, screen->devicePixelRatio());
|
||||
}
|
||||
|
||||
return topDevicePixelRatio;
|
||||
}
|
||||
|
||||
/*!
|
||||
Returns the top level window at the given position, if any.
|
||||
*/
|
||||
QWindow *QGuiApplication::topLevelAt(const QPoint &pos)
|
||||
{
|
||||
|
@ -104,6 +104,7 @@ public:
|
||||
|
||||
static QScreen *primaryScreen();
|
||||
static QList<QScreen *> screens();
|
||||
qreal devicePixelRatio() const;
|
||||
|
||||
#ifndef QT_NO_CURSOR
|
||||
static QCursor *overrideCursor();
|
||||
|
@ -160,6 +160,18 @@ QDpi QPlatformScreen::logicalDpi() const
|
||||
25.4 * s.height() / ps.height());
|
||||
}
|
||||
|
||||
/*!
|
||||
Reimplement this function in subclass to return the device pixel
|
||||
ratio for the screen. This is the ratio between physical pixels
|
||||
and device-independent pixels.
|
||||
|
||||
\sa QPlatformWindow::devicePixelRatio();
|
||||
*/
|
||||
qreal QPlatformScreen::devicePixelRatio() const
|
||||
{
|
||||
return 1.0;
|
||||
}
|
||||
|
||||
/*!
|
||||
Reimplement this function in subclass to return the vertical refresh rate
|
||||
of the screen, in Hz.
|
||||
|
@ -98,6 +98,7 @@ public:
|
||||
|
||||
virtual QSizeF physicalSize() const;
|
||||
virtual QDpi logicalDpi() const;
|
||||
virtual qreal devicePixelRatio() const;
|
||||
|
||||
virtual qreal refreshRate() const;
|
||||
|
||||
|
@ -355,6 +355,18 @@ Qt::ScreenOrientation QPlatformWindow::requestWindowOrientation(Qt::ScreenOrient
|
||||
return Qt::PrimaryOrientation;
|
||||
}
|
||||
|
||||
/*!
|
||||
Reimplement this function in subclass to return the device pixel ratio
|
||||
for the window. This is the ratio between physical pixels
|
||||
and device-independent pixels.
|
||||
|
||||
\sa QPlatformWindow::devicePixelRatio();
|
||||
*/
|
||||
qreal QPlatformWindow::devicePixelRatio() const
|
||||
{
|
||||
return 1.0;
|
||||
}
|
||||
|
||||
bool QPlatformWindow::setKeyboardGrabEnabled(bool grab)
|
||||
{
|
||||
Q_UNUSED(grab);
|
||||
|
@ -117,6 +117,8 @@ public:
|
||||
virtual void handleContentOrientationChange(Qt::ScreenOrientation orientation);
|
||||
virtual Qt::ScreenOrientation requestWindowOrientation(Qt::ScreenOrientation orientation);
|
||||
|
||||
virtual qreal devicePixelRatio() const;
|
||||
|
||||
virtual bool setKeyboardGrabEnabled(bool grab);
|
||||
virtual bool setMouseGrabEnabled(bool grab);
|
||||
|
||||
|
@ -214,6 +214,20 @@ qreal QScreen::logicalDotsPerInch() const
|
||||
return (dpi.first + dpi.second) * qreal(0.5);
|
||||
}
|
||||
|
||||
/*
|
||||
Returns the ratio between physical pixels and device-independent pixels for the screen.
|
||||
|
||||
Common values are 1.0 on normal displays and 2.0 on Apple retina displays.
|
||||
|
||||
\sa QWindow::devicePixelRatio();
|
||||
\sa QGuiApplicaiton::devicePixelRatio();
|
||||
*/
|
||||
qreal QScreen::devicePixelRatio() const
|
||||
{
|
||||
Q_D(const QScreen);
|
||||
return d->platformScreen->devicePixelRatio();
|
||||
}
|
||||
|
||||
/*!
|
||||
\property QScreen::physicalSize
|
||||
\brief the screen's physical size (in millimeters)
|
||||
|
@ -109,6 +109,8 @@ public:
|
||||
qreal logicalDotsPerInchY() const;
|
||||
qreal logicalDotsPerInch() const;
|
||||
|
||||
qreal devicePixelRatio() const;
|
||||
|
||||
QSize availableSize() const;
|
||||
QRect availableGeometry() const;
|
||||
|
||||
|
@ -805,6 +805,24 @@ Qt::ScreenOrientation QWindow::orientation() const
|
||||
return d->windowOrientation;
|
||||
}
|
||||
|
||||
/*!
|
||||
Returns the ratio between physical pixels and device-independent pixels
|
||||
for the window. This value is dependent on the screen the window is on,
|
||||
and may change when the window is moved.
|
||||
|
||||
Common values are 1.0 on normal displays and 2.0 on Apple "retina" displays.
|
||||
|
||||
\sa QWindow::devicePixelRatio();
|
||||
\sa QGuiApplicaiton::devicePixelRatio();
|
||||
*/
|
||||
qreal QWindow::devicePixelRatio() const
|
||||
{
|
||||
Q_D(const QWindow);
|
||||
if (!d->platformWindow)
|
||||
return 1.0;
|
||||
return d->platformWindow->devicePixelRatio();
|
||||
}
|
||||
|
||||
/*!
|
||||
\brief set the screen-occupation state of the window
|
||||
|
||||
|
@ -184,6 +184,8 @@ public:
|
||||
void reportContentOrientationChange(Qt::ScreenOrientation orientation);
|
||||
Qt::ScreenOrientation contentOrientation() const;
|
||||
|
||||
qreal devicePixelRatio() const;
|
||||
|
||||
bool requestOrientation(Qt::ScreenOrientation orientation);
|
||||
Qt::ScreenOrientation orientation() const;
|
||||
|
||||
|
@ -1072,9 +1072,11 @@ void QRasterPaintEnginePrivate::systemStateChanged()
|
||||
exDeviceRect = deviceRect;
|
||||
|
||||
Q_Q(QRasterPaintEngine);
|
||||
q->state()->strokeFlags |= QPaintEngine::DirtyClipRegion;
|
||||
q->state()->fillFlags |= QPaintEngine::DirtyClipRegion;
|
||||
q->state()->pixmapFlags |= QPaintEngine::DirtyClipRegion;
|
||||
if (q->state()) {
|
||||
q->state()->strokeFlags |= QPaintEngine::DirtyClipRegion;
|
||||
q->state()->fillFlags |= QPaintEngine::DirtyClipRegion;
|
||||
q->state()->pixmapFlags |= QPaintEngine::DirtyClipRegion;
|
||||
}
|
||||
}
|
||||
|
||||
void QRasterPaintEnginePrivate::updateMatrixData(QSpanData *spanData, const QBrush &b, const QTransform &m)
|
||||
@ -2143,9 +2145,10 @@ void QRasterPaintEngine::drawImage(const QPointF &p, const QImage &img)
|
||||
|
||||
Q_D(QRasterPaintEngine);
|
||||
QRasterPaintEngineState *s = state();
|
||||
qreal scale = img.devicePixelRatio();
|
||||
|
||||
if (s->matrix.type() > QTransform::TxTranslate) {
|
||||
drawImage(QRectF(p.x(), p.y(), img.width(), img.height()),
|
||||
if (scale > 1.0 || s->matrix.type() > QTransform::TxTranslate) {
|
||||
drawImage(QRectF(p.x(), p.y(), img.width() / scale, img.height() / scale),
|
||||
img,
|
||||
QRectF(0, 0, img.width(), img.height()));
|
||||
} else {
|
||||
@ -2349,6 +2352,22 @@ void QRasterPaintEngine::drawImage(const QRectF &r, const QImage &img, const QRe
|
||||
return;
|
||||
}
|
||||
} else {
|
||||
// Test for optimized high-dpi case: 2x source on 2x target. (Could be generalized to nX.)
|
||||
bool sourceRect2x = r.width() * 2 == sr.width() && r.height() * 2 == sr.height();
|
||||
bool scale2x = (s->matrix.m11() == qreal(2)) && (s->matrix.m22() == qreal(2));
|
||||
if (s->matrix.type() == QTransform::TxScale && sourceRect2x && scale2x) {
|
||||
SrcOverBlendFunc func = qBlendFunctions[d->rasterBuffer->format][img.format()];
|
||||
if (func) {
|
||||
QPointF pt(r.x() * 2 + s->matrix.dx(), r.y() * 2 + s->matrix.dy());
|
||||
if (!clip) {
|
||||
d->drawImage(pt, img, func, d->deviceRect, s->intOpacity, sr.toRect());
|
||||
return;
|
||||
} else if (clip->hasRectClip) {
|
||||
d->drawImage(pt, img, func, clip->clipRect, s->intOpacity, sr.toRect());
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
SrcOverScaleFunc func = qScaleFunctions[d->rasterBuffer->format][img.format()];
|
||||
if (func && (!clip || clip->hasRectClip)) {
|
||||
func(d->rasterBuffer->buffer(), d->rasterBuffer->bytesPerLine(),
|
||||
|
@ -939,12 +939,12 @@ void QPaintEngineEx::drawPolygon(const QPoint *points, int pointCount, PolygonDr
|
||||
|
||||
void QPaintEngineEx::drawPixmap(const QPointF &pos, const QPixmap &pm)
|
||||
{
|
||||
drawPixmap(QRectF(pos, pm.size()), pm, pm.rect());
|
||||
drawPixmap(QRectF(pos, pm.size() / pm.devicePixelRatio()), pm, pm.rect());
|
||||
}
|
||||
|
||||
void QPaintEngineEx::drawImage(const QPointF &pos, const QImage &image)
|
||||
{
|
||||
drawImage(QRectF(pos, image.size()), image, image.rect());
|
||||
drawImage(QRectF(pos, image.size() / image.devicePixelRatio()), image, image.rect());
|
||||
}
|
||||
|
||||
void QPaintEngineEx::drawTiledPixmap(const QRectF &r, const QPixmap &pixmap, const QPointF &s)
|
||||
|
@ -225,6 +225,18 @@ QTransform QPainterPrivate::viewTransform() const
|
||||
return QTransform();
|
||||
}
|
||||
|
||||
QTransform QPainterPrivate::hidpiScaleTransform() const
|
||||
{
|
||||
#ifdef Q_OS_MAC
|
||||
// Limited feature introduction for Qt 5.0.0, remove ifdef in a later release.
|
||||
if (device->physicalDpiX() == 0 || device->logicalDpiX() == 0)
|
||||
return QTransform();
|
||||
const qreal deviceScale = (device->physicalDpiX() / device->logicalDpiX());
|
||||
if (deviceScale > 1.0)
|
||||
return QTransform::fromScale(deviceScale, deviceScale);
|
||||
#endif
|
||||
return QTransform();
|
||||
}
|
||||
|
||||
/*
|
||||
\internal
|
||||
@ -641,6 +653,8 @@ void QPainterPrivate::updateMatrix()
|
||||
else
|
||||
state->dirtyFlags |= QPaintEngine::DirtyTransform;
|
||||
|
||||
state->matrix *= hidpiScaleTransform();
|
||||
|
||||
// printf("VxF=%d, WxF=%d\n", state->VxF, state->WxF);
|
||||
// qDebug() << " --- using matrix" << state->matrix << redirection_offset;
|
||||
}
|
||||
@ -1827,7 +1841,14 @@ bool QPainter::begin(QPaintDevice *pd)
|
||||
|
||||
Q_ASSERT(d->engine->isActive());
|
||||
|
||||
if (!d->state->redirectionMatrix.isIdentity())
|
||||
#ifdef Q_OS_MAC
|
||||
// Limited feature introduction for Qt 5.0.0, remove ifdef in a later release.
|
||||
const bool isHighDpi = (d->device->physicalDpiX() == 0 || d->device->logicalDpiX() == 0) ?
|
||||
false : (d->device->physicalDpiX() / d->device->logicalDpiX() > 1);
|
||||
#else
|
||||
const bool isHighDpi = false;
|
||||
#endif
|
||||
if (!d->state->redirectionMatrix.isIdentity() || isHighDpi)
|
||||
d->updateMatrix();
|
||||
|
||||
Q_ASSERT(d->engine->isActive());
|
||||
@ -5092,7 +5113,8 @@ void QPainter::drawPixmap(const QPointF &p, const QPixmap &pm)
|
||||
x += d->state->matrix.dx();
|
||||
y += d->state->matrix.dy();
|
||||
}
|
||||
d->engine->drawPixmap(QRectF(x, y, w, h), pm, QRectF(0, 0, w, h));
|
||||
int scale = pm.devicePixelRatio();
|
||||
d->engine->drawPixmap(QRectF(x, y, w / scale, h / scale), pm, QRectF(0, 0, w, h));
|
||||
}
|
||||
}
|
||||
|
||||
@ -5122,6 +5144,11 @@ void QPainter::drawPixmap(const QRectF &r, const QPixmap &pm, const QRectF &sr)
|
||||
qreal sw = sr.width();
|
||||
qreal sh = sr.height();
|
||||
|
||||
// Get pixmap scale. Use it when calculating the target
|
||||
// rect size from pixmap size. For example, a 2X 64x64 pixel
|
||||
// pixmap should result in a 32x32 point target rect.
|
||||
const qreal pmscale = pm.devicePixelRatio();
|
||||
|
||||
// Sanity-check clipping
|
||||
if (sw <= 0)
|
||||
sw = pm.width() - sx;
|
||||
@ -5130,9 +5157,9 @@ void QPainter::drawPixmap(const QRectF &r, const QPixmap &pm, const QRectF &sr)
|
||||
sh = pm.height() - sy;
|
||||
|
||||
if (w < 0)
|
||||
w = sw;
|
||||
w = sw / pmscale;
|
||||
if (h < 0)
|
||||
h = sh;
|
||||
h = sh / pmscale;
|
||||
|
||||
if (sx < 0) {
|
||||
qreal w_ratio = sx * w/sw;
|
||||
@ -5345,6 +5372,7 @@ void QPainter::drawImage(const QPointF &p, const QImage &image)
|
||||
|
||||
int w = image.width();
|
||||
int h = image.height();
|
||||
qreal scale = image.devicePixelRatio();
|
||||
|
||||
d->updateState(d->state);
|
||||
|
||||
@ -5368,8 +5396,7 @@ void QPainter::drawImage(const QPointF &p, const QImage &image)
|
||||
setBrush(brush);
|
||||
setPen(Qt::NoPen);
|
||||
setBrushOrigin(QPointF(0, 0));
|
||||
|
||||
drawRect(image.rect());
|
||||
drawRect(QRect(QPoint(0, 0), image.size() / scale));
|
||||
restore();
|
||||
return;
|
||||
}
|
||||
@ -5380,7 +5407,7 @@ void QPainter::drawImage(const QPointF &p, const QImage &image)
|
||||
y += d->state->matrix.dy();
|
||||
}
|
||||
|
||||
d->engine->drawImage(QRectF(x, y, w, h), image, QRectF(0, 0, w, h), Qt::AutoColor);
|
||||
d->engine->drawImage(QRectF(x, y, w / scale, h / scale), image, QRectF(0, 0, w, h), Qt::AutoColor);
|
||||
}
|
||||
|
||||
void QPainter::drawImage(const QRectF &targetRect, const QImage &image, const QRectF &sourceRect,
|
||||
@ -5399,6 +5426,7 @@ void QPainter::drawImage(const QRectF &targetRect, const QImage &image, const QR
|
||||
qreal sy = sourceRect.y();
|
||||
qreal sw = sourceRect.width();
|
||||
qreal sh = sourceRect.height();
|
||||
qreal imageScale = image.devicePixelRatio();
|
||||
|
||||
// Sanity-check clipping
|
||||
if (sw <= 0)
|
||||
@ -5408,9 +5436,9 @@ void QPainter::drawImage(const QRectF &targetRect, const QImage &image, const QR
|
||||
sh = image.height() - sy;
|
||||
|
||||
if (w < 0)
|
||||
w = sw;
|
||||
w = sw / imageScale;
|
||||
if (h < 0)
|
||||
h = sh;
|
||||
h = sh / imageScale;
|
||||
|
||||
if (sx < 0) {
|
||||
qreal w_ratio = sx * w/sw;
|
||||
@ -8235,7 +8263,7 @@ QTransform QPainter::combinedTransform() const
|
||||
qWarning("QPainter::combinedTransform: Painter not active");
|
||||
return QTransform();
|
||||
}
|
||||
return d->state->worldMatrix * d->viewTransform();
|
||||
return d->state->worldMatrix * d->viewTransform() * d->hidpiScaleTransform();
|
||||
}
|
||||
|
||||
/*!
|
||||
|
@ -249,6 +249,7 @@ public:
|
||||
}
|
||||
|
||||
QTransform viewTransform() const;
|
||||
QTransform hidpiScaleTransform() const;
|
||||
static bool attachPainterPrivate(QPainter *q, QPaintDevice *pdev);
|
||||
void detachPainterPrivate(QPainter *q);
|
||||
|
||||
|
@ -4100,7 +4100,9 @@ void QGLWidget::glDraw()
|
||||
#endif
|
||||
if (!d->glcx->initialized()) {
|
||||
glInit();
|
||||
resizeGL(d->glcx->device()->width(), d->glcx->device()->height()); // New context needs this "resize"
|
||||
const qreal scaleFactor = (window() && window()->windowHandle()) ?
|
||||
window()->windowHandle()->devicePixelRatio() : 1.0;
|
||||
resizeGL(d->glcx->device()->width() * scaleFactor, d->glcx->device()->height() * scaleFactor); // New context needs this "resize"
|
||||
}
|
||||
paintGL();
|
||||
if (doubleBuffer()) {
|
||||
|
@ -370,7 +370,10 @@ void QGLWidget::resizeEvent(QResizeEvent *e)
|
||||
makeCurrent();
|
||||
if (!d->glcx->initialized())
|
||||
glInit();
|
||||
resizeGL(width(), height());
|
||||
const qreal scaleFactor = (window() && window()->windowHandle()) ?
|
||||
window()->windowHandle()->devicePixelRatio() : 1.0;
|
||||
|
||||
resizeGL(width() * scaleFactor, height() * scaleFactor);
|
||||
}
|
||||
|
||||
|
||||
|
@ -62,6 +62,7 @@ public:
|
||||
void resize (const QSize &size, const QRegion &);
|
||||
bool scroll(const QRegion &area, int dx, int dy);
|
||||
CGImageRef getBackingStoreCGImage();
|
||||
qreal getBackingStoreDevicePixelRatio();
|
||||
|
||||
private:
|
||||
QImage m_qImage;
|
||||
|
@ -59,10 +59,22 @@ QCocoaBackingStore::~QCocoaBackingStore()
|
||||
|
||||
QPaintDevice *QCocoaBackingStore::paintDevice()
|
||||
{
|
||||
if (m_qImage.size() != m_requestedSize) {
|
||||
if (m_qImage.size() / m_qImage.devicePixelRatio() != m_requestedSize) {
|
||||
CGImageRelease(m_cgImage);
|
||||
m_cgImage = 0;
|
||||
m_qImage = QImage(m_requestedSize, QImage::Format_ARGB32_Premultiplied);
|
||||
|
||||
int scaleFactor = 1;
|
||||
#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_7
|
||||
if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_7) {
|
||||
QCocoaWindow *cocoaWindow = static_cast<QCocoaWindow *>(window()->handle());
|
||||
if (cocoaWindow && cocoaWindow->m_contentView) {
|
||||
scaleFactor = int([[cocoaWindow->m_contentView window] backingScaleFactor]);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
m_qImage = QImage(m_requestedSize * scaleFactor, QImage::Format_ARGB32_Premultiplied);
|
||||
m_qImage.setDevicePixelRatio(scaleFactor);
|
||||
}
|
||||
return &m_qImage;
|
||||
}
|
||||
@ -90,10 +102,11 @@ void QCocoaBackingStore::resize(const QSize &size, const QRegion &)
|
||||
bool QCocoaBackingStore::scroll(const QRegion &area, int dx, int dy)
|
||||
{
|
||||
extern void qt_scrollRectInImage(QImage &img, const QRect &rect, const QPoint &offset);
|
||||
QPoint qpoint(dx, dy);
|
||||
const qreal devicePixelRatio = m_qImage.devicePixelRatio();
|
||||
QPoint qpoint(dx * devicePixelRatio, dy * devicePixelRatio);
|
||||
const QVector<QRect> qrects = area.rects();
|
||||
for (int i = 0; i < qrects.count(); ++i) {
|
||||
const QRect &qrect = qrects.at(i);
|
||||
const QRect &qrect = QRect(qrects.at(i).topLeft() * devicePixelRatio, qrects.at(i).size() * devicePixelRatio);
|
||||
qt_scrollRectInImage(m_qImage, qrect, qpoint);
|
||||
}
|
||||
return true;
|
||||
@ -110,4 +123,9 @@ CGImageRef QCocoaBackingStore::getBackingStoreCGImage()
|
||||
return m_cgImage;
|
||||
}
|
||||
|
||||
qreal QCocoaBackingStore::getBackingStoreDevicePixelRatio()
|
||||
{
|
||||
return m_qImage.devicePixelRatio();
|
||||
}
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
@ -114,6 +114,18 @@ void QCocoaGLContext::setActiveWindow(QWindow *window)
|
||||
cocoaWindow->setCurrentContext(this);
|
||||
|
||||
[(QNSView *) cocoaWindow->contentView() setQCocoaGLContext:this];
|
||||
|
||||
// Enable high-dpi OpenGL for retina displays. Enabling has the side
|
||||
// effect that Cooca will start calling glViewport(0, 0, width, height),
|
||||
// overriding any glViewport calls in application code. This is usually not a
|
||||
// problem, except if the applcation wants to have a "custom" viewport.
|
||||
// (like the hellogl example)
|
||||
#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_7
|
||||
if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_7) {
|
||||
if (cocoaWindow->devicePixelRatio() > 1)
|
||||
[cocoaWindow->contentView() setWantsBestResolutionOpenGLSurface:YES];
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void QCocoaGLContext::doneCurrent()
|
||||
|
@ -68,6 +68,7 @@ public:
|
||||
QRect availableGeometry() const { return m_availableGeometry; }
|
||||
int depth() const { return m_depth; }
|
||||
QImage::Format format() const { return m_format; }
|
||||
qreal devicePixelRatio() const;
|
||||
QSizeF physicalSize() const { return m_physicalSize; }
|
||||
QDpi logicalDpi() const { return m_logicalDpi; }
|
||||
qreal refreshRate() const { return m_refreshRate; }
|
||||
|
@ -115,6 +115,18 @@ void QCocoaScreen::updateGeometry()
|
||||
QWindowSystemInterface::handleScreenAvailableGeometryChange(screen(), availableGeometry());
|
||||
}
|
||||
|
||||
qreal QCocoaScreen::devicePixelRatio() const
|
||||
{
|
||||
#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_7
|
||||
if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_7) {
|
||||
return qreal([m_screen backingScaleFactor]);
|
||||
} else
|
||||
#endif
|
||||
{
|
||||
return 1.0;
|
||||
}
|
||||
}
|
||||
|
||||
extern CGContextRef qt_mac_cg_context(const QPaintDevice *pdev);
|
||||
|
||||
QPixmap QCocoaScreen::grabWindow(WId window, int x, int y, int width, int height) const
|
||||
|
@ -140,6 +140,8 @@ public:
|
||||
|
||||
void setMenubar(QCocoaMenuBar *mb);
|
||||
QCocoaMenuBar *menubar() const;
|
||||
|
||||
qreal devicePixelRatio() const;
|
||||
protected:
|
||||
// NSWindow handling. The QCocoaWindow/QNSView can either be displayed
|
||||
// in an existing NSWindow or in one created by Qt.
|
||||
|
@ -39,6 +39,7 @@
|
||||
**
|
||||
****************************************************************************/
|
||||
#include "qcocoawindow.h"
|
||||
#include "qcocoaintegration.h"
|
||||
#include "qnswindowdelegate.h"
|
||||
#include "qcocoaautoreleasepool.h"
|
||||
#include "qcocoaeventdispatcher.h"
|
||||
@ -820,6 +821,20 @@ QCocoaMenuBar *QCocoaWindow::menubar() const
|
||||
return m_menubar;
|
||||
}
|
||||
|
||||
qreal QCocoaWindow::devicePixelRatio() const
|
||||
{
|
||||
if (!m_nsWindow)
|
||||
return 1.0;
|
||||
#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_7
|
||||
if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_7) {
|
||||
return qreal([m_nsWindow backingScaleFactor]);
|
||||
} else
|
||||
#endif
|
||||
{
|
||||
return 1.0;
|
||||
}
|
||||
}
|
||||
|
||||
QMargins QCocoaWindow::frameMargins() const
|
||||
{
|
||||
NSRect frameW = [m_nsWindow frame];
|
||||
|
@ -244,7 +244,7 @@ static QTouchDevice *touchDevice = 0;
|
||||
- (void) flushBackingStore:(QCocoaBackingStore *)backingStore region:(const QRegion &)region offset:(QPoint)offset
|
||||
{
|
||||
m_backingStore = backingStore;
|
||||
m_backingStoreOffset = offset;
|
||||
m_backingStoreOffset = offset * m_backingStore->getBackingStoreDevicePixelRatio();
|
||||
QRect br = region.boundingRect();
|
||||
[self setNeedsDisplayInRect:NSMakeRect(br.x(), br.y(), br.width(), br.height())];
|
||||
}
|
||||
@ -275,33 +275,44 @@ static QTouchDevice *touchDevice = 0;
|
||||
if (!m_backingStore)
|
||||
return;
|
||||
|
||||
CGRect dirtyCGRect = NSRectToCGRect(dirtyRect);
|
||||
// Calculate source and target rects. The target rect is the dirtyRect:
|
||||
CGRect dirtyWindowRect = NSRectToCGRect(dirtyRect);
|
||||
|
||||
// The backing store source rect will be larger on retina displays.
|
||||
// Scale dirtyRect by the device pixel ratio:
|
||||
const qreal devicePixelRatio = m_backingStore->getBackingStoreDevicePixelRatio();
|
||||
CGRect dirtyBackingRect = CGRectMake(dirtyRect.origin.x * devicePixelRatio,
|
||||
dirtyRect.origin.y * devicePixelRatio,
|
||||
dirtyRect.size.width * devicePixelRatio,
|
||||
dirtyRect.size.height * devicePixelRatio);
|
||||
|
||||
NSGraphicsContext *nsGraphicsContext = [NSGraphicsContext currentContext];
|
||||
CGContextRef cgContext = (CGContextRef) [nsGraphicsContext graphicsPort];
|
||||
|
||||
// Translate coordiate system from CoreGraphics (bottom-left) to NSView (top-left):
|
||||
CGContextSaveGState(cgContext);
|
||||
int dy = dirtyCGRect.origin.y + CGRectGetMaxY(dirtyCGRect);
|
||||
int dy = dirtyWindowRect.origin.y + CGRectGetMaxY(dirtyWindowRect);
|
||||
|
||||
CGContextTranslateCTM(cgContext, 0, dy);
|
||||
CGContextScaleCTM(cgContext, 1, -1);
|
||||
|
||||
// If a mask is set, modify the sub image accordingly:
|
||||
CGImageRef subMask = 0;
|
||||
if (m_maskImage) {
|
||||
subMask = CGImageCreateWithImageInRect(m_maskImage, dirtyCGRect);
|
||||
CGContextClipToMask(cgContext, dirtyCGRect, subMask);
|
||||
subMask = CGImageCreateWithImageInRect(m_maskImage, dirtyWindowRect);
|
||||
CGContextClipToMask(cgContext, dirtyWindowRect, subMask);
|
||||
}
|
||||
|
||||
// Clip out and draw the correct sub image from the (shared) backingstore:
|
||||
CGRect backingStoreRect = CGRectMake(
|
||||
dirtyRect.origin.x + m_backingStoreOffset.x(),
|
||||
dirtyRect.origin.y + m_backingStoreOffset.y(),
|
||||
dirtyRect.size.width,
|
||||
dirtyRect.size.height
|
||||
dirtyBackingRect.origin.x + m_backingStoreOffset.x(),
|
||||
dirtyBackingRect.origin.y + m_backingStoreOffset.y(),
|
||||
dirtyBackingRect.size.width,
|
||||
dirtyBackingRect.size.height
|
||||
);
|
||||
CGImageRef bsCGImage = m_backingStore->getBackingStoreCGImage();
|
||||
CGImageRef cleanImg = CGImageCreateWithImageInRect(bsCGImage, backingStoreRect);
|
||||
CGContextDrawImage(cgContext, dirtyCGRect, cleanImg);
|
||||
CGContextDrawImage(cgContext, dirtyWindowRect, cleanImg);
|
||||
|
||||
// Clean-up:
|
||||
CGContextRestoreGState(cgContext);
|
||||
|
@ -1060,10 +1060,12 @@ QRect QItemDelegate::rect(const QStyleOptionViewItem &option,
|
||||
switch (value.type()) {
|
||||
case QVariant::Invalid:
|
||||
break;
|
||||
case QVariant::Pixmap:
|
||||
return QRect(QPoint(0, 0), qvariant_cast<QPixmap>(value).size());
|
||||
case QVariant::Image:
|
||||
return QRect(QPoint(0, 0), qvariant_cast<QImage>(value).size());
|
||||
case QVariant::Pixmap: {
|
||||
const QPixmap &pixmap = qvariant_cast<QPixmap>(value);
|
||||
return QRect(QPoint(0, 0), pixmap.size() / pixmap.devicePixelRatio() ); }
|
||||
case QVariant::Image: {
|
||||
const QImage &image = qvariant_cast<QImage>(value);
|
||||
return QRect(QPoint(0, 0), image.size() / image.devicePixelRatio() ); }
|
||||
case QVariant::Icon: {
|
||||
QIcon::Mode mode = d->iconMode(option.state);
|
||||
QIcon::State state = d->iconState(option.state);
|
||||
|
@ -1794,6 +1794,23 @@ QRegion QWidgetPrivate::clipRegion() const
|
||||
return r;
|
||||
}
|
||||
|
||||
void QWidgetPrivate::setSystemClip(QPaintDevice *paintDevice, const QRegion ®ion)
|
||||
{
|
||||
// Transform the system clip region from device-independent pixels to device pixels
|
||||
// Qt 5.0.0: This is a Mac-only code path for now, can be made cross-platform once
|
||||
// it has been tested.
|
||||
QPaintEngine *paintEngine = paintDevice->paintEngine();
|
||||
#ifdef Q_OS_MAC
|
||||
const qreal devicePixelRatio = (paintDevice->physicalDpiX() == 0 || paintDevice->logicalDpiX() == 0) ?
|
||||
1.0 : (paintDevice->physicalDpiX() / paintDevice->logicalDpiX());
|
||||
QTransform scaleTransform;
|
||||
scaleTransform.scale(devicePixelRatio, devicePixelRatio);
|
||||
paintEngine->d_func()->systemClip = scaleTransform.map(region);
|
||||
#else
|
||||
paintEngine->d_func()->systemClip = region;
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifndef QT_NO_GRAPHICSEFFECT
|
||||
void QWidgetPrivate::invalidateGraphicsEffectsRecursively()
|
||||
{
|
||||
@ -4998,13 +5015,12 @@ void QWidgetPrivate::drawWidget(QPaintDevice *pdev, const QRegion &rgn, const QP
|
||||
QWidgetPaintContext context(pdev, rgn, offset, flags, sharedPainter, backingStore);
|
||||
sourced->context = &context;
|
||||
if (!sharedPainter) {
|
||||
QPaintEngine *paintEngine = pdev->paintEngine();
|
||||
paintEngine->d_func()->systemClip = rgn.translated(offset);
|
||||
setSystemClip(pdev, rgn.translated(offset));
|
||||
QPainter p(pdev);
|
||||
p.translate(offset);
|
||||
context.painter = &p;
|
||||
graphicsEffect->draw(&p);
|
||||
paintEngine->d_func()->systemClip = QRegion();
|
||||
setSystemClip(pdev, QRegion());
|
||||
} else {
|
||||
context.painter = sharedPainter;
|
||||
if (sharedPainter->worldTransform() != sourced->lastEffectTransform) {
|
||||
@ -5061,7 +5077,7 @@ void QWidgetPrivate::drawWidget(QPaintDevice *pdev, const QRegion &rgn, const QP
|
||||
|
||||
#endif
|
||||
if (sharedPainter)
|
||||
paintEngine->d_func()->systemClip = toBePainted;
|
||||
setSystemClip(pdev, toBePainted);
|
||||
else
|
||||
paintEngine->d_func()->systemRect = q->data->crect;
|
||||
|
||||
@ -5073,7 +5089,7 @@ void QWidgetPrivate::drawWidget(QPaintDevice *pdev, const QRegion &rgn, const QP
|
||||
}
|
||||
|
||||
if (!sharedPainter)
|
||||
paintEngine->d_func()->systemClip = toBePainted.translated(offset);
|
||||
setSystemClip(pdev, toBePainted.translated(offset));
|
||||
|
||||
if (!onScreen && !asRoot && !isOpaque && q->testAttribute(Qt::WA_TintedBackground)) {
|
||||
QPainter p(q);
|
||||
@ -5108,7 +5124,8 @@ void QWidgetPrivate::drawWidget(QPaintDevice *pdev, const QRegion &rgn, const QP
|
||||
paintEngine->d_func()->systemRect = QRect();
|
||||
else
|
||||
paintEngine->d_func()->currentClipDevice = 0;
|
||||
paintEngine->d_func()->systemClip = QRegion();
|
||||
|
||||
setSystemClip(pdev, QRegion());
|
||||
}
|
||||
q->setAttribute(Qt::WA_WState_InPaintEvent, false);
|
||||
if (q->paintingActive())
|
||||
|
@ -402,6 +402,7 @@ public:
|
||||
|
||||
QRect clipRect() const;
|
||||
QRegion clipRegion() const;
|
||||
void setSystemClip(QPaintDevice *paintDevice, const QRegion ®ion);
|
||||
void subtractOpaqueChildren(QRegion &rgn, const QRect &clipRect) const;
|
||||
void subtractOpaqueSiblings(QRegion &source, bool *hasDirtySiblingsAbove = 0,
|
||||
bool alsoNonOpaque = false) const;
|
||||
|
@ -303,7 +303,7 @@ static void qt_fusion_draw_mdibutton(QPainter *painter, const QStyleOptionTitleB
|
||||
gradient.setColorAt(1, mdiButtonGradientStopColor);
|
||||
QColor mdiButtonBorderColor(active ? option->palette.highlight().color().darker(180): dark.darker(110));
|
||||
|
||||
painter->setPen(QPen(mdiButtonBorderColor, 1));
|
||||
painter->setPen(QPen(mdiButtonBorderColor));
|
||||
const QLine lines[4] = {
|
||||
QLine(tmp.left() + 2, tmp.top(), tmp.right() - 2, tmp.top()),
|
||||
QLine(tmp.left() + 2, tmp.bottom(), tmp.right() - 2, tmp.bottom()),
|
||||
@ -457,7 +457,7 @@ void QFusionStyle::drawPrimitive(PrimitiveElement elem,
|
||||
if (const QStyleOptionTabBarBase *tbb
|
||||
= qstyleoption_cast<const QStyleOptionTabBarBase *>(option)) {
|
||||
painter->save();
|
||||
painter->setPen(QPen(outline.lighter(110), 0));
|
||||
painter->setPen(QPen(outline.lighter(110)));
|
||||
switch (tbb->shape) {
|
||||
case QTabBar::RoundedNorth: {
|
||||
QRegion region(tbb->rect);
|
||||
@ -603,7 +603,7 @@ void QFusionStyle::drawPrimitive(PrimitiveElement elem,
|
||||
}
|
||||
}
|
||||
break;
|
||||
case PE_Frame:
|
||||
case PE_Frame: {
|
||||
if (widget && widget->inherits("QComboBoxPrivateContainer")){
|
||||
QStyleOption copy = *option;
|
||||
copy.state |= State_Raised;
|
||||
@ -611,14 +611,16 @@ void QFusionStyle::drawPrimitive(PrimitiveElement elem,
|
||||
break;
|
||||
}
|
||||
painter->save();
|
||||
painter->setPen(outline.lighter(108));
|
||||
QPen thePen(outline.lighter(108));
|
||||
thePen.setCosmetic(false);
|
||||
painter->setPen(thePen);
|
||||
painter->drawRect(option->rect.adjusted(0, 0, -1, -1));
|
||||
painter->restore();
|
||||
painter->restore(); }
|
||||
break;
|
||||
case PE_FrameMenu:
|
||||
painter->save();
|
||||
{
|
||||
painter->setPen(QPen(outline, 1));
|
||||
painter->setPen(QPen(outline));
|
||||
painter->drawRect(option->rect.adjusted(0, 0, -1, -1));
|
||||
QColor frameLight = option->palette.background().color().lighter(160);
|
||||
QColor frameShadow = option->palette.background().color().darker(110);
|
||||
@ -644,9 +646,9 @@ void QFusionStyle::drawPrimitive(PrimitiveElement elem,
|
||||
QRect rect= option->rect;
|
||||
painter->setPen(softshadow);
|
||||
painter->drawRect(option->rect.adjusted(0, 0, -1, -1));
|
||||
painter->setPen(QPen(option->palette.light(), 0));
|
||||
painter->setPen(QPen(option->palette.light(), 1));
|
||||
painter->drawLine(QPoint(rect.left() + 1, rect.top() + 1), QPoint(rect.left() + 1, rect.bottom() - 1));
|
||||
painter->setPen(QPen(option->palette.background().color().darker(120), 0));
|
||||
painter->setPen(QPen(option->palette.background().color().darker(120)));
|
||||
painter->drawLine(QPoint(rect.left() + 1, rect.bottom() - 1), QPoint(rect.right() - 2, rect.bottom() - 1));
|
||||
painter->drawLine(QPoint(rect.right() - 1, rect.top() + 1), QPoint(rect.right() - 1, rect.bottom() - 1));
|
||||
|
||||
@ -680,12 +682,12 @@ void QFusionStyle::drawPrimitive(PrimitiveElement elem,
|
||||
painter->save();
|
||||
{
|
||||
QRect rect= option->rect;
|
||||
painter->setPen(QPen(outline.darker(150), 0));
|
||||
painter->setPen(QPen(outline.darker(150)));
|
||||
painter->drawRect(option->rect.adjusted(0, 0, -1, -1));
|
||||
painter->setPen(QPen(option->palette.light(), 0));
|
||||
painter->setPen(QPen(option->palette.light(), 1));
|
||||
painter->drawLine(QPoint(rect.left() + 1, rect.top() + 1),
|
||||
QPoint(rect.left() + 1, rect.bottom() - 1));
|
||||
painter->setPen(QPen(option->palette.background().color().darker(120), 0));
|
||||
painter->setPen(QPen(option->palette.background().color().darker(120)));
|
||||
painter->drawLine(QPoint(rect.left() + 1, rect.bottom() - 1),
|
||||
QPoint(rect.right() - 2, rect.bottom() - 1));
|
||||
painter->drawLine(QPoint(rect.right() - 1, rect.top() + 1),
|
||||
@ -705,7 +707,7 @@ void QFusionStyle::drawPrimitive(PrimitiveElement elem,
|
||||
painter->translate(0.5, 0.5);
|
||||
|
||||
// Draw Outline
|
||||
painter->setPen( QPen(hasFocus ? highlightedOutline : outline, 0));
|
||||
painter->setPen( QPen(hasFocus ? highlightedOutline : outline));
|
||||
painter->setBrush(option->palette.base());
|
||||
painter->drawRoundedRect(r.adjusted(0, 0, -1, -1), 2, 2);
|
||||
|
||||
@ -740,10 +742,10 @@ void QFusionStyle::drawPrimitive(PrimitiveElement elem,
|
||||
gradient.setColorAt(1, (state & State_Sunken) ? pressedColor : option->palette.base().color());
|
||||
|
||||
painter->setBrush((state & State_Sunken) ? QBrush(pressedColor) : gradient);
|
||||
painter->setPen(QPen(outline.lighter(110), 1));
|
||||
painter->setPen(QPen(outline.lighter(110)));
|
||||
|
||||
if (option->state & State_HasFocus && option->state & State_KeyboardFocusChange)
|
||||
painter->setPen(QPen(highlightedOutline, 1));
|
||||
painter->setPen(QPen(highlightedOutline));
|
||||
painter->drawRect(rect);
|
||||
|
||||
QColor checkMarkColor = option->palette.text().color().darker(120);
|
||||
@ -785,9 +787,9 @@ void QFusionStyle::drawPrimitive(PrimitiveElement elem,
|
||||
painter->setRenderHint(QPainter::Antialiasing, true);
|
||||
QPainterPath circle;
|
||||
circle.addEllipse(rect.center() + QPoint(1.0, 1.0), 6.5, 6.5);
|
||||
painter->setPen(QPen(option->palette.background().color().darker(150), 1));
|
||||
painter->setPen(QPen(option->palette.background().color().darker(150)));
|
||||
if (option->state & State_HasFocus && option->state & State_KeyboardFocusChange)
|
||||
painter->setPen(QPen(highlightedOutline, 1));
|
||||
painter->setPen(QPen(highlightedOutline));
|
||||
painter->drawPath(circle);
|
||||
|
||||
if (state & (State_On )) {
|
||||
@ -862,7 +864,7 @@ void QFusionStyle::drawPrimitive(PrimitiveElement elem,
|
||||
if (isFlat && !isDown) {
|
||||
if (isDefault) {
|
||||
r = option->rect.adjusted(0, 1, 0, -1);
|
||||
painter->setPen(QPen(Qt::black, 0));
|
||||
painter->setPen(QPen(Qt::black));
|
||||
const QLine lines[4] = {
|
||||
QLine(QPoint(r.left() + 2, r.top()),
|
||||
QPoint(r.right() - 2, r.top())),
|
||||
@ -910,7 +912,7 @@ void QFusionStyle::drawPrimitive(PrimitiveElement elem,
|
||||
p->setBrush(Qt::NoBrush);
|
||||
|
||||
// Outline
|
||||
p->setPen(!isEnabled ? QPen(darkOutline.lighter(115)) : QPen(darkOutline, 1));
|
||||
p->setPen(!isEnabled ? QPen(darkOutline.lighter(115)) : QPen(darkOutline));
|
||||
p->drawRoundedRect(r, 2.0, 2.0);
|
||||
|
||||
p->setPen(d->innerContrastLine());
|
||||
@ -1300,7 +1302,7 @@ void QFusionStyle::drawControl(ControlElement element, const QStyleOption *optio
|
||||
painter->drawLine(rect.topLeft() - QPoint(0, 1), rect.topRight() - QPoint(0, 1));
|
||||
|
||||
painter->setBrush(option->palette.base());
|
||||
painter->setPen(QPen(outline, 0));
|
||||
painter->setPen(QPen(outline));
|
||||
painter->drawRoundedRect(rect.adjusted(0, 0, -1, -1), 2, 2);
|
||||
|
||||
// Inner shadow
|
||||
@ -1359,14 +1361,14 @@ void QFusionStyle::drawControl(ControlElement element, const QStyleOption *optio
|
||||
progressBar.setRect(rect.left(), rect.top(), width - 1, rect.height() - 1);
|
||||
if (!complete) {
|
||||
painter->drawLine(progressBar.topRight() + QPoint(2, 1), progressBar.bottomRight() + QPoint(2, 0));
|
||||
painter->setPen(QPen(highlight.darker(140), 0));
|
||||
painter->setPen(QPen(highlight.darker(140)));
|
||||
painter->drawLine(progressBar.topRight() + QPoint(1, 1), progressBar.bottomRight() + QPoint(1, 0));
|
||||
}
|
||||
} else {
|
||||
progressBar.setRect(rect.right() - width - 1, rect.top(), width + 2, rect.height() - 1);
|
||||
if (!complete) {
|
||||
painter->drawLine(progressBar.topLeft() + QPoint(-2, 1), progressBar.bottomLeft() + QPoint(-2, 0));
|
||||
painter->setPen(QPen(highlight.darker(140), 0));
|
||||
painter->setPen(QPen(highlight.darker(140)));
|
||||
painter->drawLine(progressBar.topLeft() + QPoint(-1, 1), progressBar.bottomLeft() + QPoint(-1, 0));
|
||||
}
|
||||
}
|
||||
@ -1376,7 +1378,7 @@ void QFusionStyle::drawControl(ControlElement element, const QStyleOption *optio
|
||||
|
||||
if (indeterminate || bar->progress > bar->minimum) {
|
||||
|
||||
painter->setPen(QPen(outline, 0));
|
||||
painter->setPen(QPen(outline));
|
||||
|
||||
QColor highlightedGradientStartColor = highlight.lighter(120);
|
||||
QColor highlightedGradientStopColor = highlight;
|
||||
@ -1471,7 +1473,7 @@ void QFusionStyle::drawControl(ControlElement element, const QStyleOption *optio
|
||||
QRect r = option->rect;
|
||||
if (act) {
|
||||
painter->setBrush(option->palette.highlight().color());
|
||||
painter->setPen(QPen(highlightOutline, 0));
|
||||
painter->setPen(QPen(highlightOutline));
|
||||
painter->drawRect(r.adjusted(0, 0, -1, -1));
|
||||
|
||||
// painter->drawRoundedRect(r.adjusted(1, 1, -1, -1), 2, 2);
|
||||
@ -1518,7 +1520,7 @@ void QFusionStyle::drawControl(ControlElement element, const QStyleOption *optio
|
||||
if (selected) {
|
||||
QRect r = option->rect;
|
||||
painter->fillRect(r, highlight);
|
||||
painter->setPen(QPen(highlightOutline, 0));
|
||||
painter->setPen(QPen(highlightOutline));
|
||||
const QLine lines[4] = {
|
||||
QLine(QPoint(r.left() + 1, r.bottom()), QPoint(r.right() - 1, r.bottom())),
|
||||
QLine(QPoint(r.left() + 1, r.top()), QPoint(r.right() - 1, r.top())),
|
||||
@ -2141,15 +2143,18 @@ void QFusionStyle::drawComplexControl(ComplexControl control, const QStyleOption
|
||||
QPixmap upArrow = colorizedImage(QLatin1String(":/qt-project.org/styles/commonstyle/images/fusion_arrow.png"),
|
||||
(spinBox->stepEnabled & QAbstractSpinBox::StepUpEnabled) ? arrowColor : disabledColor);
|
||||
|
||||
cachePainter.drawPixmap(QRect(upRect.center().x() - upArrow.width() / 4 + 1,
|
||||
upRect.center().y() - upArrow.height() / 4 + 1,
|
||||
upArrow.width()/2, upArrow.height()/2), upArrow);
|
||||
QRectF upArrowRect = QRectF(upRect.center().x() - upArrow.width() / 4.0 + 1.0,
|
||||
upRect.center().y() - upArrow.height() / 4.0 + 1.0,
|
||||
upArrow.width() / 2.0, upArrow.height() / 2.0);
|
||||
|
||||
cachePainter.drawPixmap(upArrowRect, upArrow, QRectF(QPointF(0.0, 0.0), upArrow.size()));
|
||||
|
||||
QPixmap downArrow = colorizedImage(QLatin1String(":/qt-project.org/styles/commonstyle/images/fusion_arrow.png"),
|
||||
(spinBox->stepEnabled & QAbstractSpinBox::StepDownEnabled) ? arrowColor : disabledColor, 180);
|
||||
cachePainter.drawPixmap(QRect(downRect.center().x() - downArrow.width() / 4 + 1,
|
||||
downRect.center().y() - downArrow.height() / 4 + 1,
|
||||
downArrow.width()/2, downArrow.height()/2), downArrow);
|
||||
QRectF downArrowRect = QRectF(downRect.center().x() - downArrow.width() / 4.0 + 1.0,
|
||||
downRect.center().y() - downArrow.height() / 4.0 + 1.0,
|
||||
downArrow.width() / 2.0, downArrow.height() / 2.0);
|
||||
cachePainter.drawPixmap(downArrowRect, downArrow, QRectF(QPointF(0.0, 0.0), downArrow.size()));
|
||||
}
|
||||
|
||||
cachePainter.end();
|
||||
@ -2486,7 +2491,7 @@ void QFusionStyle::drawComplexControl(ComplexControl control, const QStyleOption
|
||||
// Paint slider
|
||||
if (scrollBar->subControls & SC_ScrollBarSlider) {
|
||||
QRect pixmapRect = scrollBarSlider;
|
||||
painter->setPen(QPen(alphaOutline, 0));
|
||||
painter->setPen(QPen(alphaOutline));
|
||||
if (option->state & State_Sunken && scrollBar->activeSubControls & SC_ScrollBarSlider)
|
||||
painter->setBrush(midColor2);
|
||||
else if (option->state & State_MouseOver && scrollBar->activeSubControls & SC_ScrollBarSlider)
|
||||
@ -2521,7 +2526,7 @@ void QFusionStyle::drawComplexControl(ComplexControl control, const QStyleOption
|
||||
|
||||
painter->setPen(Qt::NoPen);
|
||||
painter->drawRect(scrollBarSubLine.adjusted(horizontal ? 0 : 1, horizontal ? 1 : 0, 0, 0));
|
||||
painter->setPen(QPen(alphaOutline, 1));
|
||||
painter->setPen(QPen(alphaOutline));
|
||||
if (option->state & State_Horizontal) {
|
||||
if (option->direction == Qt::RightToLeft) {
|
||||
pixmapRect.setLeft(scrollBarSubLine.left());
|
||||
@ -2545,9 +2550,10 @@ void QFusionStyle::drawComplexControl(ComplexControl control, const QStyleOption
|
||||
rotation = option->direction == Qt::LeftToRight ? -90 : 90;
|
||||
QRect upRect = scrollBarSubLine.translated(horizontal ? -2 : -1, 0);
|
||||
QPixmap arrowPixmap = colorizedImage(QLatin1String(":/qt-project.org/styles/commonstyle/images/fusion_arrow.png"), arrowColor, rotation);
|
||||
painter->drawPixmap(QRect(upRect.center().x() - arrowPixmap.width() / 4 + 2,
|
||||
upRect.center().y() - arrowPixmap.height() / 4 + 1,
|
||||
arrowPixmap.width()/2, arrowPixmap.height()/2), arrowPixmap);
|
||||
painter->drawPixmap(QRectF(upRect.center().x() - arrowPixmap.width() / 4.0 + 2.0,
|
||||
upRect.center().y() - arrowPixmap.height() / 4.0 + 1.0,
|
||||
arrowPixmap.width() / 2.0, arrowPixmap.height() / 2.0),
|
||||
arrowPixmap, QRectF(QPoint(0.0, 0.0), arrowPixmap.size()));
|
||||
}
|
||||
|
||||
// The AddLine (down/right) button
|
||||
@ -2584,9 +2590,10 @@ void QFusionStyle::drawComplexControl(ComplexControl control, const QStyleOption
|
||||
rotation = option->direction == Qt::LeftToRight ? 90 : -90;
|
||||
QRect downRect = scrollBarAddLine.translated(-1, 1);
|
||||
QPixmap arrowPixmap = colorizedImage(QLatin1String(":/qt-project.org/styles/commonstyle/images/fusion_arrow.png"), arrowColor, rotation);
|
||||
painter->drawPixmap(QRect(downRect.center().x() - arrowPixmap.width() / 4 + 2,
|
||||
downRect.center().y() - arrowPixmap.height() / 4,
|
||||
arrowPixmap.width()/2, arrowPixmap.height()/2), arrowPixmap);
|
||||
painter->drawPixmap(QRectF(downRect.center().x() - arrowPixmap.width() / 4.0 + 2.0,
|
||||
downRect.center().y() - arrowPixmap.height() / 4.0,
|
||||
arrowPixmap.width() / 2.0, arrowPixmap.height() / 2.0),
|
||||
arrowPixmap, QRectF(QPoint(0.0, 0.0), arrowPixmap.size()));
|
||||
}
|
||||
|
||||
}
|
||||
@ -2640,7 +2647,7 @@ void QFusionStyle::drawComplexControl(ComplexControl control, const QStyleOption
|
||||
downArrowRect.left() - 6: downArrowRect.right() + 6);
|
||||
proxy()->drawPrimitive(PE_PanelButtonCommand, &buttonOption, &cachePainter, widget);
|
||||
cachePainter.restore();
|
||||
cachePainter.setPen( QPen(hasFocus ? option->palette.highlight() : outline.lighter(110), 0));
|
||||
cachePainter.setPen( QPen(hasFocus ? option->palette.highlight() : outline.lighter(110), 1));
|
||||
|
||||
if (!sunken) {
|
||||
int borderSize = 1;
|
||||
@ -2677,9 +2684,10 @@ void QFusionStyle::drawComplexControl(ComplexControl control, const QStyleOption
|
||||
QColor arrowColor = option->palette.buttonText().color();
|
||||
arrowColor.setAlpha(220);
|
||||
QPixmap downArrow = colorizedImage(QLatin1String(":/qt-project.org/styles/commonstyle/images/fusion_arrow.png"), arrowColor, 180);
|
||||
cachePainter.drawPixmap(QRect(downArrowRect.center().x() - downArrow.width() / 4 + 1,
|
||||
downArrowRect.center().y() - downArrow.height() / 4 + 1,
|
||||
downArrow.width()/2, downArrow.height()/2), downArrow);
|
||||
cachePainter.drawPixmap(QRectF(downArrowRect.center().x() - downArrow.width() / 4.0 + 1.0,
|
||||
downArrowRect.center().y() - downArrow.height() / 4.0 + 1.0,
|
||||
downArrow.width() / 2.0, downArrow.height() / 2.0),
|
||||
downArrow, QRectF(QPointF(0.0, 0.0), downArrow.size()));
|
||||
}
|
||||
cachePainter.end();
|
||||
QPixmapCache::insert(pixmapName, cache);
|
||||
@ -2730,7 +2738,7 @@ void QFusionStyle::drawComplexControl(ComplexControl control, const QStyleOption
|
||||
gradient.setStart(pixmapRect.left(), pixmapRect.center().y());
|
||||
gradient.setFinalStop(pixmapRect.right(), pixmapRect.center().y());
|
||||
}
|
||||
groovePainter.setPen(QPen(outline, 0));
|
||||
groovePainter.setPen(QPen(outline));
|
||||
gradient.setColorAt(0, grooveColor.darker(110));
|
||||
gradient.setColorAt(1, grooveColor.lighter(110));//palette.button().color().darker(115));
|
||||
groovePainter.setBrush(gradient);
|
||||
@ -2764,7 +2772,7 @@ void QFusionStyle::drawComplexControl(ComplexControl control, const QStyleOption
|
||||
|
||||
groovePainter.setRenderHint(QPainter::Antialiasing, true);
|
||||
groovePainter.translate(0.5, 0.5);
|
||||
groovePainter.setPen(QPen(outline, 0));
|
||||
groovePainter.setPen(QPen(outline));
|
||||
gradient.setColorAt(0, activeHighlight);
|
||||
gradient.setColorAt(1, activeHighlight.lighter(130));
|
||||
groovePainter.setBrush(gradient);
|
||||
@ -2813,9 +2821,9 @@ void QFusionStyle::drawComplexControl(ComplexControl control, const QStyleOption
|
||||
handlePainter.setBrush(QColor(0, 0, 0, 40));
|
||||
handlePainter.drawRect(r.adjusted(-1, 2, 1, -2));
|
||||
|
||||
handlePainter.setPen(QPen(d->outline(option->palette), 1));
|
||||
handlePainter.setPen(QPen(d->outline(option->palette)));
|
||||
if (option->state & State_HasFocus && option->state & State_KeyboardFocusChange)
|
||||
handlePainter.setPen(QPen(d->highlightedOutline(option->palette), 1));
|
||||
handlePainter.setPen(QPen(d->highlightedOutline(option->palette)));
|
||||
|
||||
handlePainter.setBrush(gradient);
|
||||
handlePainter.drawRoundedRect(r, 2, 2);
|
||||
|
@ -462,7 +462,7 @@ class QMacCGContext
|
||||
{
|
||||
CGContextRef context;
|
||||
public:
|
||||
QMacCGContext(QPainter *p); //qpaintengine_mac.cpp
|
||||
QMacCGContext(QPainter *p);
|
||||
inline QMacCGContext() { context = 0; }
|
||||
inline QMacCGContext(const QPaintDevice *pdev) {
|
||||
extern CGContextRef qt_mac_cg_context(const QPaintDevice *);
|
||||
@ -6476,6 +6476,18 @@ void qt_mac_clip_cg(CGContextRef hd, const QRegion &rgn, CGAffineTransform *orig
|
||||
}
|
||||
}
|
||||
|
||||
// move to QRegion?
|
||||
void qt_mac_scale_region(QRegion *region, qreal scaleFactor)
|
||||
{
|
||||
QVector<QRect> scaledRects;
|
||||
scaledRects.reserve(region->rects().count());
|
||||
|
||||
foreach (const QRect &rect, region->rects()) {
|
||||
scaledRects.append(QRect(rect.topLeft(), rect.size() * scaleFactor));
|
||||
}
|
||||
region->setRects(&scaledRects[0], scaledRects.count());
|
||||
}
|
||||
|
||||
QMacCGContext::QMacCGContext(QPainter *p)
|
||||
{
|
||||
QPaintEngine *pe = p->paintEngine();
|
||||
@ -6502,20 +6514,28 @@ QMacCGContext::QMacCGContext(QPainter *p)
|
||||
CGContextScaleCTM(context, 1, -1);
|
||||
|
||||
if (devType == QInternal::Widget) {
|
||||
QRegion clip = p->paintEngine()->systemClip();
|
||||
QTransform native = p->deviceTransform();
|
||||
// Set the clip rect which is an intersection of the system clip
|
||||
// and the painter clip. To make matters more interesting these
|
||||
// are in device pixels and device-independent pixels, respectively.
|
||||
const qreal devicePixelRatio = image->devicePixelRatio();
|
||||
|
||||
QRegion clip = p->paintEngine()->systemClip(); // get system clip in device pixels
|
||||
QTransform native = p->deviceTransform(); // get device transform. dx/dy is in device pixels
|
||||
|
||||
if (p->hasClipping()) {
|
||||
QRegion r = p->clipRegion();
|
||||
QRegion r = p->clipRegion(); // get painter clip, which is in device-independent pixels
|
||||
qt_mac_scale_region(&r, devicePixelRatio); // scale painter clip to device pixels
|
||||
r.translate(native.dx(), native.dy());
|
||||
if (clip.isEmpty())
|
||||
clip = r;
|
||||
else
|
||||
clip &= r;
|
||||
}
|
||||
qt_mac_clip_cg(context, clip, 0);
|
||||
qt_mac_clip_cg(context, clip, 0); // clip in device pixels
|
||||
|
||||
CGContextTranslateCTM(context, native.dx(), native.dy());
|
||||
// Scale the context so that painting happens in device-independet pixels.
|
||||
CGContextScaleCTM(context, devicePixelRatio, devicePixelRatio);
|
||||
CGContextTranslateCTM(context, native.dx() / devicePixelRatio, native.dy() / devicePixelRatio);
|
||||
}
|
||||
} else {
|
||||
qDebug() << "QMacCGContext:: Unsupported painter devtype type" << devType;
|
||||
|
@ -618,10 +618,11 @@ void QStyle::drawItemText(QPainter *painter, const QRect &rect, int alignment, c
|
||||
void QStyle::drawItemPixmap(QPainter *painter, const QRect &rect, int alignment,
|
||||
const QPixmap &pixmap) const
|
||||
{
|
||||
QRect aligned = alignedRect(QApplication::layoutDirection(), QFlag(alignment), pixmap.size(), rect);
|
||||
int scale = pixmap.devicePixelRatio();
|
||||
QRect aligned = alignedRect(QApplication::layoutDirection(), QFlag(alignment), pixmap.size() / scale, rect);
|
||||
QRect inter = aligned.intersected(rect);
|
||||
|
||||
painter->drawPixmap(inter.x(), inter.y(), pixmap, inter.x() - aligned.x(), inter.y() - aligned.y(), inter.width(), inter.height());
|
||||
painter->drawPixmap(inter.x(), inter.y(), pixmap, inter.x() - aligned.x(), inter.y() - aligned.y(), inter.width() * scale, inter.height() *scale);
|
||||
}
|
||||
|
||||
/*!
|
||||
|
@ -43,6 +43,7 @@
|
||||
#define QSTYLE_P_H
|
||||
|
||||
#include "private/qobject_p.h"
|
||||
#include <QtGui/qguiapplication.h>
|
||||
#include <QtWidgets/qstyle.h>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
@ -74,12 +75,18 @@ public:
|
||||
|
||||
inline QImage styleCacheImage(const QSize &size)
|
||||
{
|
||||
return QImage(size, QImage::Format_ARGB32_Premultiplied);
|
||||
const qreal pixelRatio = qApp->devicePixelRatio();
|
||||
QImage cacheImage = QImage(size * pixelRatio, QImage::Format_ARGB32_Premultiplied);
|
||||
cacheImage.setDevicePixelRatio(pixelRatio);
|
||||
return cacheImage;
|
||||
}
|
||||
|
||||
inline QPixmap styleCachePixmap(const QSize &size)
|
||||
{
|
||||
return QPixmap(size);
|
||||
const qreal pixelRatio = qApp->devicePixelRatio();
|
||||
QPixmap cachePixmap = QPixmap(size * pixelRatio);
|
||||
cachePixmap.setDevicePixelRatio(pixelRatio);
|
||||
return cachePixmap;
|
||||
}
|
||||
|
||||
#define BEGIN_STYLE_PIXMAPCACHE(a) \
|
||||
|
@ -562,17 +562,18 @@ QSize QLabelPrivate::sizeForWidth(int w) const
|
||||
int vextra = hextra;
|
||||
QFontMetrics fm = q->fontMetrics();
|
||||
|
||||
if (pixmap && !pixmap->isNull())
|
||||
if (pixmap && !pixmap->isNull()) {
|
||||
br = pixmap->rect();
|
||||
br.setSize(br.size() / pixmap->devicePixelRatio());
|
||||
#ifndef QT_NO_PICTURE
|
||||
else if (picture && !picture->isNull())
|
||||
} else if (picture && !picture->isNull()) {
|
||||
br = picture->boundingRect();
|
||||
#endif
|
||||
#ifndef QT_NO_MOVIE
|
||||
else if (movie && !movie->currentPixmap().isNull())
|
||||
} else if (movie && !movie->currentPixmap().isNull()) {
|
||||
br = movie->currentPixmap().rect();
|
||||
#endif
|
||||
else if (isTextLabel) {
|
||||
} else if (isTextLabel) {
|
||||
int align = QStyle::visualAlignment(textDirection(), QFlag(this->align));
|
||||
// Add indentation
|
||||
int m = indent;
|
||||
|
12
tests/manual/highdpi/highdpi.pro
Normal file
12
tests/manual/highdpi/highdpi.pro
Normal file
@ -0,0 +1,12 @@
|
||||
TEMPLATE = app
|
||||
TARGET = highdpi
|
||||
DEPENDPATH += .
|
||||
INCLUDEPATH += .
|
||||
QT += widgets
|
||||
|
||||
# Input
|
||||
SOURCES += main.cpp
|
||||
|
||||
RESOURCES += \
|
||||
highdpi.qrc
|
||||
|
7
tests/manual/highdpi/highdpi.qrc
Normal file
7
tests/manual/highdpi/highdpi.qrc
Normal file
@ -0,0 +1,7 @@
|
||||
<RCC>
|
||||
<qresource prefix="/">
|
||||
<file>qticon.png</file>
|
||||
<file>qticon@2x.png</file>
|
||||
<file>qticon_large.png</file>
|
||||
</qresource>
|
||||
</RCC>
|
366
tests/manual/highdpi/main.cpp
Normal file
366
tests/manual/highdpi/main.cpp
Normal file
@ -0,0 +1,366 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2012 Digia Plc and/or its subsidiary(-ies).
|
||||
** Contact: http://www.qt-project.org/legal
|
||||
**
|
||||
** This file is part of the QtGui module of the Qt Toolkit.
|
||||
**
|
||||
** $QT_BEGIN_LICENSE:LGPL$
|
||||
** Commercial License Usage
|
||||
** Licensees holding valid commercial Qt licenses may use this file in
|
||||
** accordance with the commercial license agreement provided with the
|
||||
** Software or, alternatively, in accordance with the terms contained in
|
||||
** a written agreement between you and Digia. For licensing terms and
|
||||
** conditions see http://qt.digia.com/licensing. For further information
|
||||
** use the contact form at http://qt.digia.com/contact-us.
|
||||
**
|
||||
** 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, Digia gives you certain additional
|
||||
** rights. These rights are described in the Digia Qt LGPL Exception
|
||||
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
|
||||
**
|
||||
** GNU General Public License Usage
|
||||
** Alternatively, this file may be used under the terms of the GNU
|
||||
** General Public License version 3.0 as published by the Free Software
|
||||
** Foundation and appearing in the file LICENSE.GPL included in the
|
||||
** packaging of this file. Please review the following information to
|
||||
** ensure the GNU General Public License version 3.0 requirements will be
|
||||
** met: http://www.gnu.org/copyleft/gpl.html.
|
||||
**
|
||||
**
|
||||
** $QT_END_LICENSE$
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#include <QtCore>
|
||||
#include <QtGui>
|
||||
#include <QtWidgets>
|
||||
|
||||
|
||||
class PixmapPainter : public QWidget
|
||||
{
|
||||
public:
|
||||
PixmapPainter();
|
||||
void paintEvent(QPaintEvent *event);
|
||||
|
||||
QPixmap pixmap1X;
|
||||
QPixmap pixmap2X;
|
||||
QPixmap pixmapLarge;
|
||||
QImage image1X;
|
||||
QImage image2X;
|
||||
QImage imageLarge;
|
||||
QIcon qtIcon;
|
||||
};
|
||||
|
||||
|
||||
PixmapPainter::PixmapPainter()
|
||||
{
|
||||
pixmap1X = QPixmap(":/qticon.png");
|
||||
pixmap2X = QPixmap(":/qticon@2x.png");
|
||||
pixmapLarge = QPixmap(":/qticon_large.png");
|
||||
|
||||
image1X = QImage(":/qticon.png");
|
||||
image2X = QImage(":/qticon@2x.png");
|
||||
imageLarge = QImage(":/qticon_large.png");
|
||||
|
||||
qtIcon.addFile(":/qticon.png");
|
||||
qtIcon.addFile(":/qticon@2x.png");
|
||||
}
|
||||
|
||||
void PixmapPainter::paintEvent(QPaintEvent *event)
|
||||
{
|
||||
QPainter p(this);
|
||||
p.fillRect(QRect(QPoint(0, 0), size()), QBrush(Qt::gray));
|
||||
|
||||
int pixmapPointSize = 64;
|
||||
int y = 30;
|
||||
int dy = 150;
|
||||
|
||||
int x = 10;
|
||||
int dx = 80;
|
||||
// draw at point
|
||||
// qDebug() << "paint pixmap" << pixmap1X.devicePixelRatio();
|
||||
p.drawPixmap(x, y, pixmap1X);
|
||||
x+=dx;p.drawPixmap(x, y, pixmap2X);
|
||||
x+=dx;p.drawPixmap(x, y, pixmapLarge);
|
||||
x+=dx*2;p.drawPixmap(x, y, qtIcon.pixmap(QSize(pixmapPointSize, pixmapPointSize)));
|
||||
x+=dx;p.drawImage(x, y, image1X);
|
||||
x+=dx;p.drawImage(x, y, image2X);
|
||||
x+=dx;p.drawImage(x, y, imageLarge);
|
||||
|
||||
// draw at 64x64 rect
|
||||
y+=dy;
|
||||
x = 10;
|
||||
p.drawPixmap(QRect(x, y, pixmapPointSize, pixmapPointSize), pixmap1X);
|
||||
x+=dx;p.drawPixmap(QRect(x, y, pixmapPointSize, pixmapPointSize), pixmap2X);
|
||||
x+=dx;p.drawPixmap(QRect(x, y, pixmapPointSize, pixmapPointSize), pixmapLarge);
|
||||
x+=dx;p.drawPixmap(QRect(x, y, pixmapPointSize, pixmapPointSize), qtIcon.pixmap(QSize(pixmapPointSize, pixmapPointSize)));
|
||||
x+=dx;p.drawImage(QRect(x, y, pixmapPointSize, pixmapPointSize), image1X);
|
||||
x+=dx;p.drawImage(QRect(x, y, pixmapPointSize, pixmapPointSize), image2X);
|
||||
x+=dx;p.drawImage(QRect(x, y, pixmapPointSize, pixmapPointSize), imageLarge);
|
||||
|
||||
|
||||
// draw at 128x128 rect
|
||||
y+=dy - 50;
|
||||
x = 10;
|
||||
p.drawPixmap(QRect(x, y, pixmapPointSize * 2, pixmapPointSize * 2), pixmap1X);
|
||||
x+=dx * 2; p.drawPixmap(QRect(x, y, pixmapPointSize * 2, pixmapPointSize * 2), pixmap2X);
|
||||
x+=dx * 2; p.drawPixmap(QRect(x, y, pixmapPointSize * 2, pixmapPointSize * 2), pixmapLarge);
|
||||
x+=dx * 2; p.drawPixmap(QRect(x, y, pixmapPointSize * 2, pixmapPointSize * 2), qtIcon.pixmap(QSize(pixmapPointSize, pixmapPointSize)));
|
||||
x+=dx * 2; p.drawImage(QRect(x, y, pixmapPointSize * 2, pixmapPointSize * 2), image1X);
|
||||
x+=dx * 2; p.drawImage(QRect(x, y, pixmapPointSize * 2, pixmapPointSize * 2), image2X);
|
||||
x+=dx * 2; p.drawImage(QRect(x, y, pixmapPointSize * 2, pixmapPointSize * 2), imageLarge);
|
||||
}
|
||||
|
||||
class Labels : public QWidget
|
||||
{
|
||||
public:
|
||||
Labels();
|
||||
|
||||
QPixmap pixmap1X;
|
||||
QPixmap pixmap2X;
|
||||
QPixmap pixmapLarge;
|
||||
QIcon qtIcon;
|
||||
};
|
||||
|
||||
Labels::Labels()
|
||||
{
|
||||
pixmap1X = QPixmap(":/qticon.png");
|
||||
pixmap2X = QPixmap(":/qticon@2x.png");
|
||||
pixmapLarge = QPixmap(":/qticon_large.png");
|
||||
|
||||
qtIcon.addFile(":/qticon.png");
|
||||
qtIcon.addFile(":/qticon@2x.png");
|
||||
setWindowIcon(qtIcon);
|
||||
setWindowTitle("Labels");
|
||||
|
||||
QLabel *label1x = new QLabel();
|
||||
label1x->setPixmap(pixmap1X);
|
||||
QLabel *label2x = new QLabel();
|
||||
label2x->setPixmap(pixmap2X);
|
||||
QLabel *labelIcon = new QLabel();
|
||||
labelIcon->setPixmap(qtIcon.pixmap(QSize(64,64)));
|
||||
QLabel *labelLarge = new QLabel();
|
||||
labelLarge->setPixmap(pixmapLarge);
|
||||
|
||||
QHBoxLayout *layout = new QHBoxLayout(this);
|
||||
// layout->addWidget(label1x); //expected low-res on high-dpi displays
|
||||
layout->addWidget(label2x);
|
||||
// layout->addWidget(labelIcon);
|
||||
// layout->addWidget(labelLarge); // expected large size and low-res
|
||||
setLayout(layout);
|
||||
}
|
||||
|
||||
class MainWindow : public QMainWindow
|
||||
{
|
||||
public:
|
||||
MainWindow();
|
||||
|
||||
QIcon qtIcon;
|
||||
QIcon qtIcon1x;
|
||||
QIcon qtIcon2x;
|
||||
|
||||
QToolBar *fileToolBar;
|
||||
};
|
||||
|
||||
MainWindow::MainWindow()
|
||||
{
|
||||
qtIcon.addFile(":/qticon.png");
|
||||
qtIcon.addFile(":/qticon@2x.png");
|
||||
qtIcon1x.addFile(":/qticon.png");
|
||||
qtIcon2x.addFile(":/qticon@2x.png");
|
||||
setWindowIcon(qtIcon);
|
||||
setWindowTitle("MainWindow");
|
||||
|
||||
fileToolBar = addToolBar(tr("File"));
|
||||
// fileToolBar->setToolButtonStyle(Qt::ToolButtonTextUnderIcon);
|
||||
fileToolBar->addAction(new QAction(qtIcon, QString("1x and 2x"), this));
|
||||
fileToolBar->addAction(new QAction(qtIcon1x, QString("1x"), this));
|
||||
fileToolBar->addAction(new QAction(qtIcon2x, QString("2x"), this));
|
||||
}
|
||||
|
||||
class StandardIcons : public QWidget
|
||||
{
|
||||
public:
|
||||
void paintEvent(QPaintEvent *event)
|
||||
{
|
||||
int x = 10;
|
||||
int y = 10;
|
||||
int dx = 50;
|
||||
int dy = 50;
|
||||
int maxX = 500;
|
||||
|
||||
for (int iconIndex = QStyle::SP_TitleBarMenuButton; iconIndex < QStyle::SP_MediaVolumeMuted; ++iconIndex) {
|
||||
QIcon icon = qApp->style()->standardIcon(QStyle::StandardPixmap(iconIndex));
|
||||
QPainter p(this);
|
||||
p.drawPixmap(x, y, icon.pixmap(dx - 5, dy - 5));
|
||||
if (x + dx > maxX)
|
||||
y+=dy;
|
||||
x = ((x + dx) % maxX);
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
class Caching : public QWidget
|
||||
{
|
||||
public:
|
||||
void paintEvent(QPaintEvent *event)
|
||||
{
|
||||
QSize layoutSize(75, 75);
|
||||
|
||||
QPainter widgetPainter(this);
|
||||
widgetPainter.fillRect(QRect(QPoint(0, 0), this->size()), Qt::gray);
|
||||
|
||||
{
|
||||
const qreal devicePixelRatio = this->windowHandle()->devicePixelRatio();
|
||||
QPixmap cache(layoutSize * devicePixelRatio);
|
||||
cache.setDevicePixelRatio(devicePixelRatio);
|
||||
|
||||
QPainter cachedPainter(&cache);
|
||||
cachedPainter.fillRect(QRect(0,0, 75, 75), Qt::blue);
|
||||
cachedPainter.fillRect(QRect(10,10, 55, 55), Qt::red);
|
||||
cachedPainter.drawEllipse(QRect(10,10, 55, 55));
|
||||
|
||||
QPainter widgetPainter(this);
|
||||
widgetPainter.drawPixmap(QPoint(10, 10), cache);
|
||||
}
|
||||
|
||||
{
|
||||
const qreal devicePixelRatio = this->windowHandle()->devicePixelRatio();
|
||||
QImage cache = QImage(layoutSize * devicePixelRatio, QImage::QImage::Format_ARGB32_Premultiplied);
|
||||
cache.setDevicePixelRatio(devicePixelRatio);
|
||||
|
||||
QPainter cachedPainter(&cache);
|
||||
cachedPainter.fillRect(QRect(0,0, 75, 75), Qt::blue);
|
||||
cachedPainter.fillRect(QRect(10,10, 55, 55), Qt::red);
|
||||
cachedPainter.drawEllipse(QRect(10,10, 55, 55));
|
||||
|
||||
QPainter widgetPainter(this);
|
||||
widgetPainter.drawImage(QPoint(95, 10), cache);
|
||||
}
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
class Style : public QWidget {
|
||||
public:
|
||||
QPushButton *button;
|
||||
QLineEdit *lineEdit;
|
||||
QSlider *slider;
|
||||
QHBoxLayout *row1;
|
||||
|
||||
Style() {
|
||||
row1 = new QHBoxLayout();
|
||||
setLayout(row1);
|
||||
|
||||
button = new QPushButton();
|
||||
button->setText("Test Button");
|
||||
row1->addWidget(button);
|
||||
|
||||
lineEdit = new QLineEdit();
|
||||
lineEdit->setText("Test Lineedit");
|
||||
row1->addWidget(lineEdit);
|
||||
|
||||
slider = new QSlider();
|
||||
row1->addWidget(slider);
|
||||
|
||||
row1->addWidget(new QSpinBox);
|
||||
row1->addWidget(new QScrollBar);
|
||||
|
||||
QTabBar *tab = new QTabBar();
|
||||
tab->addTab("Foo");
|
||||
tab->addTab("Bar");
|
||||
row1->addWidget(tab);
|
||||
}
|
||||
};
|
||||
|
||||
class Fonts : public QWidget
|
||||
{
|
||||
public:
|
||||
void paintEvent(QPaintEvent *event)
|
||||
{
|
||||
QPainter painter(this);
|
||||
int y = 40;
|
||||
for (int fontSize = 2; fontSize < 18; fontSize += 2) {
|
||||
QFont font;
|
||||
font.setPointSize(fontSize);
|
||||
QString string = QString(QStringLiteral("%1 The quick brown fox jumped over the lazy Doug.")).arg(fontSize);
|
||||
painter.setFont(font);
|
||||
painter.drawText(10, y, string);
|
||||
y += (fontSize * 2.5);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
template <typename T>
|
||||
void apiTestdevicePixelRatioGetter()
|
||||
{
|
||||
if (0) {
|
||||
T *t = 0;
|
||||
t->devicePixelRatio();
|
||||
}
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
void apiTestdevicePixelRatioSetter()
|
||||
{
|
||||
if (0) {
|
||||
T *t = 0;
|
||||
t->setDevicePixelRatio(2.0);
|
||||
}
|
||||
}
|
||||
|
||||
void apiTest()
|
||||
{
|
||||
// compile call to devicePixelRatio getter and setter (verify spelling)
|
||||
apiTestdevicePixelRatioGetter<QWindow>();
|
||||
apiTestdevicePixelRatioGetter<QScreen>();
|
||||
apiTestdevicePixelRatioGetter<QGuiApplication>();
|
||||
|
||||
apiTestdevicePixelRatioGetter<QImage>();
|
||||
apiTestdevicePixelRatioSetter<QImage>();
|
||||
apiTestdevicePixelRatioGetter<QPixmap>();
|
||||
apiTestdevicePixelRatioSetter<QPixmap>();
|
||||
}
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
qputenv("QT_HIGHDPI_AWARE", "1");
|
||||
QApplication app(argc, argv);
|
||||
|
||||
PixmapPainter pixmapPainter;
|
||||
|
||||
// Enable for lots of pixmap drawing
|
||||
pixmapPainter.show();
|
||||
|
||||
Labels label;
|
||||
label.resize(200, 200);
|
||||
label.show();
|
||||
|
||||
MainWindow mainWindow;
|
||||
mainWindow.show();
|
||||
|
||||
StandardIcons icons;
|
||||
icons.resize(510, 510);
|
||||
icons.show();
|
||||
|
||||
Caching caching;
|
||||
caching.resize(300, 300);
|
||||
caching.show();
|
||||
|
||||
Style style;
|
||||
style.show();
|
||||
|
||||
Fonts fonts;
|
||||
fonts.show();
|
||||
|
||||
return app.exec();
|
||||
}
|
BIN
tests/manual/highdpi/qticon.png
Normal file
BIN
tests/manual/highdpi/qticon.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 6.3 KiB |
BIN
tests/manual/highdpi/qticon@2x.png
Normal file
BIN
tests/manual/highdpi/qticon@2x.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 17 KiB |
BIN
tests/manual/highdpi/qticon_large.png
Normal file
BIN
tests/manual/highdpi/qticon_large.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 17 KiB |
@ -121,6 +121,7 @@ static void printHelp()
|
||||
" -commands Displays all available commands\n"
|
||||
" -w Width of the paintdevice\n"
|
||||
" -h Height of the paintdevice\n"
|
||||
" -scalefactor Scale factor (device pixel ratio) of the paintdevice\n"
|
||||
" -cmp Show the reference picture\n"
|
||||
" -bg-white No checkers background\n");
|
||||
}
|
||||
@ -238,6 +239,8 @@ int main(int argc, char **argv)
|
||||
bool highres = false;
|
||||
bool show_cmp = false;
|
||||
int width = 800, height = 800;
|
||||
int scaledWidth = width, scaledHeight = height;
|
||||
qreal scalefactor = 1.0;
|
||||
bool verboseMode = false;
|
||||
|
||||
#ifndef QT_NO_OPENGL
|
||||
@ -328,6 +331,9 @@ int main(int argc, char **argv)
|
||||
} else if (option == "h") {
|
||||
Q_ASSERT_X(i + 1 < argc, "main", "-h must be followed by a value");
|
||||
height = atoi(argv[++i]);
|
||||
} else if (option == "scalefactor") {
|
||||
Q_ASSERT_X(i + 1 < argc, "main", "-scalefactor must be followed by a value");
|
||||
scalefactor = atof(argv[++i]);
|
||||
} else if (option == "cmp") {
|
||||
show_cmp = true;
|
||||
} else if (option == "bg-white") {
|
||||
@ -350,6 +356,8 @@ int main(int argc, char **argv)
|
||||
#endif
|
||||
}
|
||||
}
|
||||
scaledWidth = width * scalefactor;
|
||||
scaledHeight = height * scalefactor;
|
||||
|
||||
PaintCommands pcmd(QStringList(), 800, 800);
|
||||
pcmd.setVerboseMode(verboseMode);
|
||||
@ -514,7 +522,8 @@ int main(int argc, char **argv)
|
||||
#endif
|
||||
case PixmapType:
|
||||
{
|
||||
QPixmap pixmap(width, height);
|
||||
QPixmap pixmap(scaledWidth, scaledHeight);
|
||||
pixmap.setDevicePixelRatio(scalefactor);
|
||||
pixmap.fill(Qt::white);
|
||||
QPainter pt(&pixmap);
|
||||
pcmd.setPainter(&pt);
|
||||
@ -527,7 +536,8 @@ int main(int argc, char **argv)
|
||||
|
||||
case BitmapType:
|
||||
{
|
||||
QBitmap bitmap(width, height);
|
||||
QBitmap bitmap(scaledWidth, scaledHeight);
|
||||
bitmap.setDevicePixelRatio(scalefactor);
|
||||
QPainter pt(&bitmap);
|
||||
pcmd.setPainter(&pt);
|
||||
pcmd.setFilePath(fileinfo.absolutePath());
|
||||
@ -547,9 +557,10 @@ int main(int argc, char **argv)
|
||||
case ImageType:
|
||||
{
|
||||
qDebug() << "Creating image";
|
||||
QImage image(width, height, type == ImageMonoType
|
||||
QImage image(scaledWidth, scaledHeight, type == ImageMonoType
|
||||
? QImage::Format_MonoLSB
|
||||
: imageFormat);
|
||||
image.setDevicePixelRatio(scalefactor);
|
||||
image.fill(0);
|
||||
QPainter pt(&image);
|
||||
pcmd.setPainter(&pt);
|
||||
@ -557,6 +568,7 @@ int main(int argc, char **argv)
|
||||
pcmd.runCommands();
|
||||
pt.end();
|
||||
image.convertToFormat(QImage::Format_ARGB32).save("output_image.png", "PNG");
|
||||
image.setDevicePixelRatio(1.0); // reset scale factor: display "large" image.
|
||||
#ifndef CONSOLE_APPLICATION
|
||||
QLabel *label = createLabel();
|
||||
label->setPixmap(QPixmap::fromImage(image));
|
||||
|
Loading…
Reference in New Issue
Block a user