summaryrefslogtreecommitdiffstats
path: root/src/gui/painting
diff options
context:
space:
mode:
Diffstat (limited to 'src/gui/painting')
-rw-r--r--src/gui/painting/qdrawhelper.cpp11
-rw-r--r--src/gui/painting/qpaintbuffer.cpp101
-rw-r--r--src/gui/painting/qpaintbuffer_p.h8
-rw-r--r--src/gui/painting/qpaintengine_mac.cpp8
-rw-r--r--src/gui/painting/qpaintengine_raster_p.h12
-rw-r--r--src/gui/painting/qpainter.cpp68
-rw-r--r--src/gui/painting/qprinter.cpp17
-rw-r--r--src/gui/painting/qprinter.h2
-rw-r--r--src/gui/painting/qrasterizer_p.h6
9 files changed, 176 insertions, 57 deletions
diff --git a/src/gui/painting/qdrawhelper.cpp b/src/gui/painting/qdrawhelper.cpp
index ab192c5..e9b1bd3 100644
--- a/src/gui/painting/qdrawhelper.cpp
+++ b/src/gui/painting/qdrawhelper.cpp
@@ -4953,15 +4953,18 @@ Q_STATIC_TEMPLATE_FUNCTION void blendTiled(int count, const QSpan *spans, void *
if (modeSource && coverage == 255) {
// Copy the first texture block
- length = image_width;
+ length = qMin(image_width,length);
+ int tx = x;
while (length) {
int l = qMin(image_width - sx, length);
if (buffer_size < l)
l = buffer_size;
- DST *dest = ((DST*)data->rasterBuffer->scanLine(spans->y)) + x;
+ DST *dest = ((DST*)data->rasterBuffer->scanLine(spans->y)) + tx;
const SRC *src = (SRC*)data->texture.scanLine(sy) + sx;
+
qt_memconvert<DST, SRC>(dest, src, l);
length -= l;
+ tx += l;
sx = 0;
}
@@ -4971,8 +4974,8 @@ Q_STATIC_TEMPLATE_FUNCTION void blendTiled(int count, const QSpan *spans, void *
// We are dealing with one block of data
// - More likely to fit in the cache
// - can use memcpy
- int copy_image_width = image_width;
- length = spans->len - image_width;
+ int copy_image_width = qMin(image_width, int(spans->len));
+ length = spans->len - copy_image_width;
DST *src = ((DST*)data->rasterBuffer->scanLine(spans->y)) + x;
DST *dest = src + copy_image_width;
while (copy_image_width < length) {
diff --git a/src/gui/painting/qpaintbuffer.cpp b/src/gui/painting/qpaintbuffer.cpp
index 04ddd7d..4d8b8c9 100644
--- a/src/gui/painting/qpaintbuffer.cpp
+++ b/src/gui/painting/qpaintbuffer.cpp
@@ -239,7 +239,7 @@ bool QPaintBuffer::isEmpty() const
-void QPaintBuffer::draw(QPainter *painter) const
+void QPaintBuffer::draw(QPainter *painter, int frame) const
{
#ifdef QPAINTBUFFER_DEBUG_DRAW
qDebug() << "QPaintBuffer::draw() --------------------------------";
@@ -270,10 +270,10 @@ void QPaintBuffer::draw(QPainter *painter) const
? (QPaintEngineEx *) painter->paintEngine() : 0;
if (xengine) {
QPaintEngineExReplayer player;
- player.draw(*this, painter);
+ player.draw(*this, painter, frame);
} else {
QPainterReplayer player;
- player.draw(*this, painter);
+ player.draw(*this, painter, frame);
}
#ifdef QPAINTBUFFER_DEBUG_DRAW
@@ -1035,17 +1035,31 @@ void QPainterReplayer::setupTransform(QPainter *_painter)
painter->setTransform(m_world_matrix);
}
-void QPainterReplayer::draw(const QPaintBuffer &buffer, QPainter *_painter)
+void QPainterReplayer::draw(const QPaintBuffer &buffer, QPainter *_painter, int frame)
{
d = buffer.d_ptr;
setupTransform(_painter);
- for (int cmdIndex=0; cmdIndex<d->commands.size(); ++cmdIndex) {
+ int frameStart = (frame == 0) ? 0 : d->frames.at(frame-1);
+ int frameEnd = (frame == d->frames.size()) ? d->commands.size() : d->frames.at(frame);
+
+ for (int cmdIndex=frameStart; cmdIndex<frameEnd; ++cmdIndex) {
const QPaintBufferCommand &cmd = d->commands.at(cmdIndex);
process(cmd);
}
}
+void QPaintBuffer::beginNewFrame()
+{
+ if (!d_ptr->commands.isEmpty())
+ d_ptr->frames << d_ptr->commands.size();
+}
+
+int QPaintBuffer::numFrames() const
+{
+ return d_ptr->frames.size() + 1;
+}
+
void QPainterReplayer::process(const QPaintBufferCommand &cmd)
{
switch (cmd.id) {
@@ -1721,24 +1735,99 @@ QDataStream &operator>>(QDataStream &stream, QPaintBufferCommand &command)
return stream;
}
+struct QPaintBufferCacheEntry
+{
+ QVariant::Type type;
+ quint64 cacheKey;
+};
+Q_DECLARE_METATYPE(QPaintBufferCacheEntry);
+
+QDataStream &operator<<(QDataStream &stream, const QPaintBufferCacheEntry &entry)
+{
+ return stream << entry.type << entry.cacheKey;
+}
+
+QDataStream &operator>>(QDataStream &stream, QPaintBufferCacheEntry &entry)
+{
+ return stream >> entry.type >> entry.cacheKey;
+}
+
+static int qRegisterPaintBufferMetaTypes()
+{
+ qRegisterMetaType<QPaintBufferCacheEntry>();
+ qRegisterMetaTypeStreamOperators<QPaintBufferCacheEntry>("QPaintBufferCacheEntry");
+
+ return 0; // something
+}
+
+Q_CONSTRUCTOR_FUNCTION(qRegisterPaintBufferMetaTypes)
+
QDataStream &operator<<(QDataStream &stream, const QPaintBuffer &buffer)
{
+ QHash<qint64, QPixmap> pixmaps;
+ QHash<qint64, QImage> images;
+
+ QVector<QVariant> variants = buffer.d_ptr->variants;
+ for (int i = 0; i < variants.size(); ++i) {
+ const QVariant &v = variants.at(i);
+ if (v.type() == QVariant::Image) {
+ const QImage image(v.value<QImage>());
+ images[image.cacheKey()] = image;
+
+ QPaintBufferCacheEntry entry;
+ entry.type = QVariant::Image;
+ entry.cacheKey = image.cacheKey();
+ variants[i] = QVariant::fromValue(entry);
+ } else if (v.type() == QVariant::Pixmap) {
+ const QPixmap pixmap(v.value<QPixmap>());
+ pixmaps[pixmap.cacheKey()] = pixmap;
+
+ QPaintBufferCacheEntry entry;
+ entry.type = QVariant::Pixmap;
+ entry.cacheKey = pixmap.cacheKey();
+ variants[i] = QVariant::fromValue(entry);
+ }
+ }
+
+ stream << pixmaps;
+ stream << images;
+
stream << buffer.d_ptr->ints;
stream << buffer.d_ptr->floats;
- stream << buffer.d_ptr->variants;
+ stream << variants;
stream << buffer.d_ptr->commands;
stream << buffer.d_ptr->boundingRect;
+ stream << buffer.d_ptr->frames;
return stream;
}
QDataStream &operator>>(QDataStream &stream, QPaintBuffer &buffer)
{
+ QHash<qint64, QPixmap> pixmaps;
+ QHash<qint64, QImage> images;
+
+ stream >> pixmaps;
+ stream >> images;
+
stream >> buffer.d_ptr->ints;
stream >> buffer.d_ptr->floats;
stream >> buffer.d_ptr->variants;
stream >> buffer.d_ptr->commands;
stream >> buffer.d_ptr->boundingRect;
+ stream >> buffer.d_ptr->frames;
+
+ QVector<QVariant> &variants = buffer.d_ptr->variants;
+ for (int i = 0; i < variants.size(); ++i) {
+ const QVariant &v = variants.at(i);
+ if (v.canConvert<QPaintBufferCacheEntry>()) {
+ QPaintBufferCacheEntry entry = v.value<QPaintBufferCacheEntry>();
+ if (entry.type == QVariant::Image)
+ variants[i] = QVariant(images.value(entry.cacheKey));
+ else
+ variants[i] = QVariant(pixmaps.value(entry.cacheKey));
+ }
+ }
return stream;
}
diff --git a/src/gui/painting/qpaintbuffer_p.h b/src/gui/painting/qpaintbuffer_p.h
index b360279..2cb1d7c 100644
--- a/src/gui/painting/qpaintbuffer_p.h
+++ b/src/gui/painting/qpaintbuffer_p.h
@@ -71,7 +71,10 @@ public:
bool isEmpty() const;
- void draw(QPainter *painter) const;
+ void beginNewFrame();
+ int numFrames() const;
+
+ void draw(QPainter *painter, int frame = 0) const;
void setBoundingRect(const QRectF &rect);
QRectF boundingRect() const;
@@ -270,6 +273,7 @@ public:
QVector<QVariant> variants;
QVector<QPaintBufferCommand> commands;
+ QList<int> frames;
QPaintBufferEngine *engine;
QRectF boundingRect;
@@ -306,7 +310,7 @@ public:
void setupTransform(QPainter *painter);
void process(const QPaintBufferCommand &cmd);
- void draw(const QPaintBuffer &buffer, QPainter *painter);
+ void draw(const QPaintBuffer &buffer, QPainter *painter, int frame);
protected:
QPaintBufferPrivate *d;
diff --git a/src/gui/painting/qpaintengine_mac.cpp b/src/gui/painting/qpaintengine_mac.cpp
index 934b385..249bcfa 100644
--- a/src/gui/painting/qpaintengine_mac.cpp
+++ b/src/gui/painting/qpaintengine_mac.cpp
@@ -116,11 +116,15 @@ QMacCGContext::QMacCGContext(QPainter *p)
if (devType == QInternal::Widget) {
QRegion clip = p->paintEngine()->systemClip();
+ QTransform native = p->deviceTransform();
+ QTransform logical = p->combinedTransform();
if (p->hasClipping()) {
+ QRegion r = p->clipRegion();
+ r.translate(native.dx() - logical.dx(), native.dy() - logical.dy());
if (clip.isEmpty())
- clip = p->clipRegion();
+ clip = r;
else
- clip &= p->clipRegion();
+ clip &= r;
}
qt_mac_clip_cg(context, clip, 0);
diff --git a/src/gui/painting/qpaintengine_raster_p.h b/src/gui/painting/qpaintengine_raster_p.h
index c31a087..b13fb62 100644
--- a/src/gui/painting/qpaintengine_raster_p.h
+++ b/src/gui/painting/qpaintengine_raster_p.h
@@ -373,7 +373,11 @@ public:
};
-class Q_GUI_EXPORT QClipData {
+class
+#ifdef Q_WS_QWS
+Q_GUI_EXPORT
+#endif
+QClipData {
public:
QClipData(int height);
~QClipData();
@@ -480,7 +484,11 @@ private:
/*******************************************************************************
* QRasterBuffer
*/
-class Q_GUI_EXPORT QRasterBuffer
+class
+#ifdef Q_WS_QWS
+Q_GUI_EXPORT
+#endif
+QRasterBuffer
{
public:
QRasterBuffer() : m_width(0), m_height(0), m_buffer(0) { init(); }
diff --git a/src/gui/painting/qpainter.cpp b/src/gui/painting/qpainter.cpp
index a6bea76..263e53e 100644
--- a/src/gui/painting/qpainter.cpp
+++ b/src/gui/painting/qpainter.cpp
@@ -7545,10 +7545,9 @@ void qt_format_text(const QFont &fnt, const QRectF &_r,
if (!painter)
tf |= Qt::TextDontPrint;
- int maxUnderlines = 0;
+ uint maxUnderlines = 0;
int numUnderlines = 0;
- int underlinePositionStack[32];
- int *underlinePositions = underlinePositionStack;
+ QVarLengthArray<int, 32> underlinePositions(1);
QFontMetricsF fm(fnt);
QString text = str;
@@ -7557,54 +7556,46 @@ start_lengthVariant:
bool hasMoreLengthVariants = false;
// compatible behaviour to the old implementation. Replace
// tabs by spaces
- QChar *chr = text.data() + offset;
- QChar *end = text.data() + text.length();
bool has_tab = false;
- while (chr != end) {
- if (*chr == QLatin1Char('\r') || (singleline && *chr == QLatin1Char('\n'))) {
- *chr = QLatin1Char(' ');
- } else if (*chr == QLatin1Char('\n')) {
- *chr = QChar::LineSeparator;
- } else if (*chr == QLatin1Char('&')) {
+ int old_offset = offset;
+ for (; offset < text.length(); offset++) {
+ QChar chr = text.at(offset);
+ if (chr == QLatin1Char('\r') || (singleline && chr == QLatin1Char('\n'))) {
+ text[offset] = QLatin1Char(' ');
+ } else if (chr == QLatin1Char('\n')) {
+ text[offset] = QChar::LineSeparator;
+ } else if (chr == QLatin1Char('&')) {
++maxUnderlines;
- } else if (*chr == QLatin1Char('\t')) {
+ } else if (chr == QLatin1Char('\t')) {
+ if (!expandtabs) {
+ text[offset] = QLatin1Char(' ');
+ } else if (!tabarraylen && !tabstops) {
+ tabstops = qRound(fm.width(QLatin1Char('x'))*8);
+ }
has_tab = true;
- } else if (*chr == QChar(ushort(0x9c))) {
+ } else if (chr == QChar(ushort(0x9c))) {
// string with multiple length variants
- end = chr;
hasMoreLengthVariants = true;
break;
}
- ++chr;
- }
- if (has_tab) {
- if (!expandtabs) {
- chr = text.data() + offset;
- while (chr != end) {
- if (*chr == QLatin1Char('\t'))
- *chr = QLatin1Char(' ');
- ++chr;
- }
- } else if (!tabarraylen && !tabstops) {
- tabstops = qRound(fm.width(QLatin1Char('x'))*8);
- }
}
- QChar *cout = end;
- if (hidemnmemonic || showmnemonic) {
- if (maxUnderlines > 32)
- underlinePositions = new int[maxUnderlines];
- cout = text.data() + offset;
+ int length = offset - old_offset;
+ if ((hidemnmemonic || showmnemonic) && maxUnderlines > 0) {
+ underlinePositions.resize(maxUnderlines + 1);
+
+ QChar *cout = text.data() + old_offset;
QChar *cin = cout;
- int l = end - cout;
+ int l = length;
while (l) {
if (*cin == QLatin1Char('&')) {
++cin;
+ --length;
--l;
if (!l)
break;
if (*cin != QLatin1Char('&') && !hidemnmemonic)
- underlinePositions[numUnderlines++] = cout - text.unicode();
+ underlinePositions[numUnderlines++] = cout - text.data() - old_offset;
}
*cout = *cin;
++cout;
@@ -7621,7 +7612,7 @@ start_lengthVariant:
qreal height = 0;
qreal width = 0;
- QString finalText = text.mid(offset, cout - (text.data() + offset));
+ QString finalText = text.mid(old_offset, length);
QStackTextEngine engine(finalText, fnt);
if (option) {
engine.option = *option;
@@ -7640,7 +7631,7 @@ start_lengthVariant:
engine.forceJustification = true;
QTextLayout textLayout(&engine);
textLayout.setCacheEnabled(true);
- textLayout.engine()->underlinePositions = underlinePositions;
+ textLayout.engine()->underlinePositions = underlinePositions.data();
if (finalText.isEmpty()) {
height = fm.height();
@@ -7709,7 +7700,7 @@ start_lengthVariant:
QRectF bounds = QRectF(r.x() + xoff, r.y() + yoff, width, height);
if (hasMoreLengthVariants && !(tf & Qt::TextLongestVariant) && !r.contains(bounds)) {
- offset = end - text.data() + 1;
+ offset++;
goto start_lengthVariant;
}
if (brect)
@@ -7738,9 +7729,6 @@ start_lengthVariant:
painter->restore();
}
}
-
- if (underlinePositions != underlinePositionStack)
- delete [] underlinePositions;
}
/*!
diff --git a/src/gui/painting/qprinter.cpp b/src/gui/painting/qprinter.cpp
index 882e6bc..882f994 100644
--- a/src/gui/painting/qprinter.cpp
+++ b/src/gui/painting/qprinter.cpp
@@ -1286,6 +1286,23 @@ int QPrinter::numCopies() const
/*!
+ Returns the number of copies that will be printed. The default
+ value is 1.
+
+ This function always returns the actual value specified in the print
+ dialog or using setNumCopies().
+
+ \sa setNumCopies(), numCopies();
+*/
+int QPrinter::actualNumCopies() const
+{
+ Q_D(const QPrinter);
+ return qt_printerRealNumCopies(d->paintEngine);
+}
+
+
+
+/*!
Sets the number of copies to be printed to \a numCopies.
The printer driver reads this setting and prints the specified
diff --git a/src/gui/painting/qprinter.h b/src/gui/painting/qprinter.h
index 46419f4..16f2182 100644
--- a/src/gui/painting/qprinter.h
+++ b/src/gui/painting/qprinter.h
@@ -197,6 +197,8 @@ public:
void setNumCopies(int);
int numCopies() const;
+ int actualNumCopies() const;
+
void setPaperSource(PaperSource);
PaperSource paperSource() const;
diff --git a/src/gui/painting/qrasterizer_p.h b/src/gui/painting/qrasterizer_p.h
index 4cfdbbf..059d772 100644
--- a/src/gui/painting/qrasterizer_p.h
+++ b/src/gui/painting/qrasterizer_p.h
@@ -65,7 +65,11 @@ struct QSpanData;
class QRasterBuffer;
class QRasterizerPrivate;
-class Q_GUI_EXPORT QRasterizer
+class
+#ifdef Q_WS_QWS
+Q_GUI_EXPORT
+#endif
+QRasterizer
{
public:
QRasterizer();