[Kde-games-devel] [Patch] Fix QPainter usage

Christian Ehrlicher Ch.Ehrlicher at gmx.de
Wed Dec 26 19:28:12 CET 2007


Ian Wadham schrieb:
> On Mon, 24 Dec 2007 11:14 pm, Christian Ehrlicher wrote:
>> I just added a few QPainter::end().
>>
> Oops!  Looks like you were way ahead of me in getting to
> this list, Christian.  And you have patched so many games
> too.  Please disregard my post a few minutes ago, to KDE
> Windows list.  It's Christmas morning here in Australia and
> I am just waking up.
> 
> Everybody, when rendering SVG elements, please double-check
> that QPainter::end() is called or the QPainter is "destructed"
> (with auto end()), *before* you convert your QImage to a
> QPixmap.  Otherwise your graphics will fail in Windows.
> 
I now found the place where I've my information about QPainter::end()
from. Looks like it's outdated:
http://doc.trolltech.com/3.3/qpainter.html#end
see also QPainter::flush(). I've also looked through the Qt examples and
demos and there QPainter::end() is used every time before accessing the
QImage. So it's good practice :)

Now to the problem why it does not work in a loop. See the following code:

QImage img (10, 10, QImage::Format_ARGB32_Premultiplied);
QPainter p(&img);
QList<QPixmap> elements;
for(int i = 0; i < 10; i++) {
  img.fill(0);
  p.doSomething();
  elements.append(QPixmap::fromImage(img));
}

QPainter paints on img. img.fill() does a detach:

void QImage::fill(uint pixel)
{
    if (!d)
        return;

    detach();
    ...
}

Now QPixmap::fromImage() works different on windows than on linux. On
linux the pixmap data is created from scratch, on windows the qimage
data is simply copied -> the ref counter is inceased and detach() does a
deep copy later:

QPixmap QPixmap::fromImage(const QImage &image, Qt::ImageConversionFlags
flags )
{
 ...
    case QImage::Format_ARGB32_Premultiplied:
    case QImage::Format_RGB16:
        pixmap.data->image = image;
        break;
 ...
}

I'll ask tt what they think about the issue. For now it's important to
call QPainter::begin() and end() for every new QImage.


Christian


More information about the kde-games-devel mailing list