~oif-team/ubuntu/natty/qt4-x11/xi2.1

« back to all changes in this revision

Viewing changes to src/gui/image/qpixmap.cpp

  • Committer: Bazaar Package Importer
  • Author(s): Adam Conrad
  • Date: 2005-08-24 04:09:09 UTC
  • Revision ID: james.westby@ubuntu.com-20050824040909-xmxe9jfr4a0w5671
Tags: upstream-4.0.0
ImportĀ upstreamĀ versionĀ 4.0.0

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/****************************************************************************
 
2
**
 
3
** Copyright (C) 1992-2005 Trolltech AS. All rights reserved.
 
4
**
 
5
** This file is part of the painting module of the Qt Toolkit.
 
6
**
 
7
** This file may be distributed under the terms of the Q Public License
 
8
** as defined by Trolltech AS of Norway and appearing in the file
 
9
** LICENSE.QPL included in the packaging of this file.
 
10
**
 
11
** This file may be distributed and/or modified under the terms of the
 
12
** GNU General Public License version 2 as published by the Free Software
 
13
** Foundation and appearing in the file LICENSE.GPL included in the
 
14
** packaging of this file.
 
15
**
 
16
** See http://www.trolltech.com/pricing.html or email sales@trolltech.com for
 
17
**   information about Qt Commercial License Agreements.
 
18
** See http://www.trolltech.com/qpl/ for QPL licensing information.
 
19
** See http://www.trolltech.com/gpl/ for GPL licensing information.
 
20
**
 
21
** Contact info@trolltech.com if any conditions of this licensing are
 
22
** not clear to you.
 
23
**
 
24
** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
 
25
** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
 
26
**
 
27
****************************************************************************/
 
28
 
 
29
 
 
30
#include <qglobal.h>
 
31
 
 
32
#include "qpixmap.h"
 
33
#include "qpixmap_p.h"
 
34
 
 
35
#include "qbitmap.h"
 
36
#include "qimage.h"
 
37
#include "qwidget.h"
 
38
#include "qpainter.h"
 
39
#include "qdatastream.h"
 
40
#include "qbuffer.h"
 
41
#include "qapplication.h"
 
42
#include <private/qinternal_p.h>
 
43
#include "qevent.h"
 
44
#include "qfile.h"
 
45
#include "qfileinfo.h"
 
46
#include "qpixmapcache.h"
 
47
#include "qdatetime.h"
 
48
#include "qimagereader.h"
 
49
#include "qimagewriter.h"
 
50
 
 
51
#if defined(Q_WS_X11)
 
52
#include "qx11info_x11.h"
 
53
#include <private/qt_x11_p.h>
 
54
#endif
 
55
 
 
56
/*!
 
57
    \enum QPixmap::ColorMode
 
58
 
 
59
    \compat
 
60
 
 
61
    This enum type defines the color modes that exist for converting
 
62
    QImage objects to QPixmap.
 
63
 
 
64
    \value Auto  Select \c Color or \c Mono on a case-by-case basis.
 
65
    \value Color Always create colored pixmaps.
 
66
    \value Mono  Always create bitmaps.
 
67
*/
 
68
 
 
69
/*!
 
70
    Constructs a null pixmap.
 
71
 
 
72
    \sa isNull()
 
73
*/
 
74
 
 
75
QPixmap::QPixmap()
 
76
    : QPaintDevice()
 
77
{
 
78
    init(0, 0);
 
79
}
 
80
 
 
81
/*!
 
82
    Constructs a pixmap with \a w width, \a h height.
 
83
 
 
84
    The content of the pixmap is uninitialized.
 
85
 
 
86
    If either \a w or \a h is zero, a null pixmap is constructed.
 
87
 
 
88
    \sa isNull()
 
89
*/
 
90
 
 
91
QPixmap::QPixmap(int w, int h)
 
92
    : QPaintDevice()
 
93
{
 
94
    init(w, h);
 
95
}
 
96
 
 
97
/*!
 
98
    \overload
 
99
 
 
100
    Constructs a pixmap of size \a size.
 
101
*/
 
102
 
 
103
QPixmap::QPixmap(const QSize &size)
 
104
    : QPaintDevice()
 
105
{
 
106
    init(size.width(), size.height());
 
107
}
 
108
 
 
109
/*!
 
110
  \internal
 
111
*/
 
112
QPixmap::QPixmap(const QSize &s, Type type)
 
113
{
 
114
    init(s.width(), s.height(), type);
 
115
}
 
116
 
 
117
#ifndef QT_NO_IMAGEIO
 
118
/*!
 
119
    Constructs a pixmap from the file with the given \a fileName. If the
 
120
    file does not exist or is of an unknown format, the pixmap becomes a
 
121
    null pixmap.
 
122
 
 
123
    The \a fileName, \a format and \a flags parameters are
 
124
    passed on to load(). This means that the data in \a fileName is
 
125
    not compiled into the binary. If \a fileName contains a relative
 
126
    path (e.g. the filename only) the relevant file must be found
 
127
    relative to the runtime working directory.
 
128
 
 
129
    The file name can either refer to an actual file on disk or to
 
130
    one of the application's embedded resources. See the
 
131
    \l{resources.html}{Resource System} overview for details on how
 
132
    to embed images and other resource files in the application's
 
133
    executable.
 
134
 
 
135
    If the image needs to be modified to fit in a lower-resolution
 
136
    result (e.g. converting from 32-bit to 8-bit), use the \a
 
137
    flags to specify how you'd prefer this to happen.
 
138
 
 
139
    \sa Qt::ImageConversionFlags, isNull(), load(), loadFromData(), save(),
 
140
    QImageReader::imageFormat()
 
141
*/
 
142
 
 
143
QPixmap::QPixmap(const QString& fileName, const char *format, Qt::ImageConversionFlags flags)
 
144
    : QPaintDevice()
 
145
{
 
146
    init(0, 0);
 
147
    load(fileName, format, flags);
 
148
}
 
149
#endif //QT_NO_IMAGEIO
 
150
 
 
151
/*!
 
152
    Constructs a pixmap that is a copy of \a pixmap.
 
153
*/
 
154
 
 
155
QPixmap::QPixmap(const QPixmap &pixmap)
 
156
    : QPaintDevice()
 
157
{
 
158
    if (pixmap.paintingActive()) {                // make a deep copy
 
159
        data = 0;
 
160
        operator=(pixmap.copy());
 
161
    } else {
 
162
        data = pixmap.data;
 
163
        data->ref();
 
164
    }
 
165
}
 
166
 
 
167
/*!
 
168
    Constructs a pixmap from \a xpm, which must be a valid XPM image.
 
169
 
 
170
    Errors are silently ignored.
 
171
 
 
172
    Note that it's possible to squeeze the XPM variable a little bit
 
173
    by using an unusual declaration:
 
174
 
 
175
    \code
 
176
        static const char * const start_xpm[]={
 
177
            "16 15 8 1",
 
178
            "a c #cec6bd",
 
179
        ....
 
180
    \endcode
 
181
 
 
182
    The extra \c const makes the entire definition read-only, which is
 
183
    slightly more efficient (for example, when the code is in a shared
 
184
    library) and ROMable when the application is to be stored in ROM.
 
185
*/
 
186
 
 
187
QPixmap::QPixmap(const char * const xpm[])
 
188
    : QPaintDevice()
 
189
{
 
190
    init(0, 0);
 
191
 
 
192
    QImage image(xpm);
 
193
    if (!image.isNull()) {
 
194
        if (data->type == BitmapType)
 
195
            *this =  QBitmap::fromImage(image);
 
196
        else
 
197
            *this = fromImage(image);
 
198
    }
 
199
}
 
200
 
 
201
 
 
202
 
 
203
/*!
 
204
    Destroys the pixmap.
 
205
*/
 
206
 
 
207
QPixmap::~QPixmap()
 
208
{
 
209
    deref();
 
210
}
 
211
 
 
212
/*!
 
213
  \internal
 
214
*/
 
215
int QPixmap::devType() const
 
216
{
 
217
    return QInternal::Pixmap;
 
218
}
 
219
 
 
220
/*!
 
221
    \fn QPixmap QPixmap::copy(int x, int y, int w, int h) const
 
222
 
 
223
    \overload
 
224
 
 
225
    Returns a \link shclass.html deep copy\endlink of the subpart of
 
226
    the pixmap that is specified by the rectangle \a x, \a y, \a w \a
 
227
    h.
 
228
 
 
229
    If the rectangle is empty, the whole image is copied.
 
230
*/
 
231
 
 
232
/*!
 
233
    Returns a \link shclass.html deep copy\endlink of the subpart of
 
234
    the pixmap that is specified by \a rect.
 
235
 
 
236
    If \a rect is empty, the whole image is copied.
 
237
 
 
238
    \sa operator=()
 
239
*/
 
240
 
 
241
QPixmap QPixmap::copy(const QRect &rect) const
 
242
{
 
243
    // ### This could be sped up by platform specific implementation.
 
244
    QPixmap pm;
 
245
    if (data->type == BitmapType)
 
246
        pm = QBitmap::fromImage(toImage().copy(rect));
 
247
    else
 
248
        pm = fromImage(toImage().copy(rect));
 
249
    return pm;
 
250
}
 
251
 
 
252
 
 
253
/*!
 
254
    Assigns the pixmap \a pixmap to this pixmap and returns a
 
255
    reference to this pixmap.
 
256
*/
 
257
 
 
258
QPixmap &QPixmap::operator=(const QPixmap &pixmap)
 
259
{
 
260
    if (paintingActive()) {
 
261
        qWarning("QPixmap::operator=: Cannot assign to pixmap during painting");
 
262
        return *this;
 
263
    }
 
264
    if (pixmap.paintingActive()) {                // make a deep copy
 
265
        *this = pixmap.copy();
 
266
    } else {
 
267
        pixmap.data->ref();                                // avoid 'x = x'
 
268
        deref();
 
269
        data = pixmap.data;
 
270
    }
 
271
    return *this;
 
272
}
 
273
 
 
274
/*!
 
275
   Returns the pixmap as a QVariant
 
276
*/
 
277
QPixmap::operator QVariant() const
 
278
{
 
279
    return QVariant(QVariant::Pixmap, this);
 
280
}
 
281
 
 
282
/*!
 
283
    \fn bool QPixmap::operator!() const
 
284
 
 
285
    Returns true if this is a null pixmap; otherwise returns false.
 
286
 
 
287
    \sa isNull()
 
288
*/
 
289
 
 
290
/*!
 
291
    \fn QPixmap::operator QImage() const
 
292
 
 
293
    Returns the pixmap as a QImage.
 
294
 
 
295
    This automatic conversion is disabled when \c QT3_SUPPORT is not
 
296
    defined. Use toImage() instead.
 
297
*/
 
298
 
 
299
/*!
 
300
    Returns the actual matrix used for transforming a pixmap with \a w
 
301
    width and \a h height and matrix \a m.
 
302
 
 
303
    When transforming a pixmap with transform(), the transformation matrix
 
304
    is internally adjusted to compensate for unwanted translation,
 
305
    i.e. transform() returns the smallest pixmap containing all
 
306
    transformed points of the original pixmap.
 
307
 
 
308
    This function returns the modified matrix, which maps points
 
309
    correctly from the original pixmap into the new pixmap.
 
310
 
 
311
    \sa transformed(), QMatrix
 
312
*/
 
313
#ifndef QT_NO_PIXMAP_TRANSFORMATION
 
314
QMatrix QPixmap::trueMatrix(const QMatrix &m, int w, int h)
 
315
{
 
316
    return QImage::trueMatrix(m, w, h);
 
317
}
 
318
#endif
 
319
 
 
320
/*!
 
321
    \fn bool QPixmap::isQBitmap() const
 
322
 
 
323
    Returns true if this is a QBitmap; otherwise returns false.
 
324
*/
 
325
 
 
326
/*!
 
327
    \fn bool QPixmap::isNull() const
 
328
 
 
329
    Returns true if this is a null pixmap; otherwise returns false.
 
330
 
 
331
    A null pixmap has zero width, zero height and no contents. You
 
332
    cannot draw in a null pixmap.
 
333
 
 
334
    Resizing an existing pixmap to (0, 0) makes a pixmap into a null
 
335
    pixmap.
 
336
 
 
337
    \sa resize()
 
338
*/
 
339
bool QPixmap::isNull() const
 
340
{
 
341
    return data->w == 0;
 
342
}
 
343
 
 
344
/*!
 
345
    \fn int QPixmap::width() const
 
346
 
 
347
    Returns the width of the pixmap.
 
348
 
 
349
    \sa height(), size(), rect()
 
350
*/
 
351
int QPixmap::width() const
 
352
{
 
353
    return data->w;
 
354
}
 
355
 
 
356
/*!
 
357
    \fn int QPixmap::height() const
 
358
 
 
359
    Returns the height of the pixmap.
 
360
 
 
361
    \sa width(), size(), rect()
 
362
*/
 
363
int QPixmap::height() const
 
364
{
 
365
    return data->h;
 
366
}
 
367
 
 
368
/*!
 
369
    \fn QSize QPixmap::size() const
 
370
 
 
371
    Returns the size of the pixmap.
 
372
 
 
373
    \sa width(), height(), rect()
 
374
*/
 
375
QSize QPixmap::size() const
 
376
{
 
377
    return QSize(data->w,data->h);
 
378
}
 
379
 
 
380
/*!
 
381
    \fn QRect QPixmap::rect() const
 
382
 
 
383
    Returns the enclosing rectangle (0,0,width(),height()) of the pixmap.
 
384
 
 
385
    \sa width(), height(), size()
 
386
*/
 
387
QRect QPixmap::rect() const
 
388
{
 
389
    return QRect(0,0,data->w,data->h);
 
390
}
 
391
 
 
392
/*!
 
393
    \fn int QPixmap::depth() const
 
394
 
 
395
    Returns the depth of the pixmap.
 
396
 
 
397
    The pixmap depth is also called bits per pixel (bpp) or bit planes
 
398
    of a pixmap. A null pixmap has depth 0.
 
399
 
 
400
    \sa defaultDepth(), isNull(), QImage::convertDepth()
 
401
*/
 
402
int QPixmap::depth() const
 
403
{
 
404
    return data->d;
 
405
}
 
406
 
 
407
/*!
 
408
    \fn void QPixmap::resize(const QSize &size)
 
409
    \overload
 
410
 
 
411
    Resizes the pixmap to size \a size.
 
412
*/
 
413
#ifdef QT3_SUPPORT
 
414
void QPixmap::resize_helper(const QSize &s)
 
415
{
 
416
    int w = s.width();
 
417
    int h = s.height();
 
418
    if (w < 1 || h < 1) {
 
419
        *this = QPixmap();
 
420
        return;
 
421
    }
 
422
 
 
423
    int d = data->d;
 
424
    // Create new pixmap
 
425
    QPixmap pm(QSize(w, h), d == 1 ? BitmapType : PixmapType);
 
426
#ifdef Q_WS_X11
 
427
    pm.x11SetScreen(data->xinfo.screen());
 
428
#endif // Q_WS_X11
 
429
    if (!data->uninit && !isNull()) {                // has existing pixmap
 
430
        // Copy old pixmap
 
431
        QPainter p(&pm);
 
432
        p.drawPixmap(0, 0, *this, 0, 0, qMin(width(), w), qMin(height(), h));
 
433
    }
 
434
#if defined(Q_WS_MAC)
 
435
    if(data->qd_alpha) {
 
436
        data->macQDUpdateAlpha();
 
437
    } else
 
438
#endif // Q_WS_X11
 
439
#ifdef Q_WS_X11
 
440
        if (data->x11_mask) {
 
441
            pm.data->x11_mask = (Qt::HANDLE)XCreatePixmap(X11->display, RootWindow(data->xinfo.display(), data->xinfo.screen()),
 
442
                                                          w, h, 1);
 
443
            GC gc = XCreateGC(X11->display, pm.data->x11_mask, 0, 0);
 
444
            XCopyArea(X11->display, data->x11_mask, pm.data->x11_mask, gc, 0, 0, qMin(width(), w), qMin(height(), h), 0, 0);
 
445
            XFreeGC(X11->display, gc);
 
446
        }
 
447
#elif !defined(Q_WS_MAC)
 
448
    if (data->mask) {
 
449
        QBitmap m = *data->mask;
 
450
        m.resize(w, h);
 
451
        pm.setMask(m);
 
452
    }
 
453
#endif
 
454
    *this = pm;
 
455
}
 
456
#endif
 
457
 
 
458
/*!
 
459
  \fn void QPixmap::resize(int w, int h)
 
460
 
 
461
    Resizes the pixmap to \a w width and \a h height. If either \a w
 
462
    or \a h is 0, the pixmap becomes a null pixmap.
 
463
 
 
464
    If both \a w and \a h are greater than 0, a valid pixmap is
 
465
    created. New pixels will be uninitialized (random) if the pixmap
 
466
    is expanded.
 
467
*/
 
468
 
 
469
/*!
 
470
    \fn bool QPixmap::selfMask() const
 
471
 
 
472
    \obsolete
 
473
*/
 
474
 
 
475
#ifndef QT_NO_IMAGE_HEURISTIC_MASK
 
476
/*!
 
477
    Creates and returns a heuristic mask for this pixmap. It works by
 
478
    selecting a color from one of the corners and then chipping away
 
479
    pixels of that color, starting at all the edges.
 
480
 
 
481
    The mask may not be perfect but it should be reasonable, so you
 
482
    can do things such as the following:
 
483
    \code
 
484
    pm->setMask(pm->createHeuristicMask());
 
485
    \endcode
 
486
 
 
487
    This function is slow because it involves transformation to a
 
488
    QImage, non-trivial computations and a transformation back to a
 
489
    QBitmap.
 
490
 
 
491
    If \a clipTight is true (the default) the mask is just large enough to cover the
 
492
    pixels; otherwise, the mask is larger than the data pixels.
 
493
 
 
494
    \sa QImage::createHeuristicMask()
 
495
*/
 
496
QBitmap QPixmap::createHeuristicMask(bool clipTight) const
 
497
{
 
498
    QBitmap m = QBitmap::fromImage(toImage().createHeuristicMask(clipTight));
 
499
    return m;
 
500
}
 
501
#endif
 
502
 
 
503
/*!
 
504
    Creates and returns a mask for this pixmap based on \a maskColor.
 
505
 
 
506
    This function is slow because it involves transformation to a
 
507
    QImage and a transformation back to a QBitmap.
 
508
 
 
509
    \sa createHeuristicMask()
 
510
*/
 
511
QBitmap QPixmap::createMaskFromColor(const QColor &maskColor) const
 
512
{
 
513
    QImage maskImage(size(), QImage::Format_MonoLSB);
 
514
    QImage image = toImage();
 
515
    QRgb mColor = maskColor.rgba();
 
516
    for (int w = 0; w < width(); w++) {
 
517
        for (int h = 0; h < height(); h++) {
 
518
            if (image.pixel(w, h) == mColor)
 
519
                maskImage.setPixel(w, h, Qt::color1);
 
520
            else
 
521
                maskImage.setPixel(w, h, Qt::color0);
 
522
        }
 
523
    }
 
524
    QBitmap m = QBitmap::fromImage(maskImage);
 
525
    return m;
 
526
}
 
527
 
 
528
#ifndef QT_NO_IMAGEIO
 
529
/*!
 
530
    Loads a pixmap from the file \a fileName at runtime. Returns true
 
531
    if successful; otherwise returns false.
 
532
 
 
533
    If \a format is specified, the loader attempts to read the pixmap
 
534
    using the specified format. If \a format is not specified
 
535
    (default), the loader reads a few bytes from the header to guess
 
536
    the file's format.
 
537
 
 
538
    If the data needs to be modified to fit in a lower-resolution
 
539
    result (e.g. converting from 32-bit to 8-bit), use the \a
 
540
    flags to specify how you'd prefer this to happen.
 
541
 
 
542
    The QImageReader documentation lists the supported image formats and
 
543
    explains how to add extra formats.
 
544
 
 
545
    The file name can either refer to an actual file on disk or to
 
546
    one of the application's embedded resources. See the
 
547
    \l{resources.html}{Resource System} overview for details on how
 
548
    to embed images and other resource files in the application's
 
549
    executable.
 
550
 
 
551
    \sa loadFromData(), save(), QImageReader::imageFormat(), QImage::load(), fromImage()
 
552
    QImageReader
 
553
*/
 
554
 
 
555
bool QPixmap::load(const QString &fileName, const char *format, Qt::ImageConversionFlags flags)
 
556
{
 
557
    QFileInfo info(fileName);
 
558
    QString key = QLatin1String("qt_pixmap_") + info.absoluteFilePath() + QLatin1Char('_') + info.lastModified().toString()
 
559
                  + QString::number(data->type);
 
560
 
 
561
    if (QPixmapCache::find(key, *this))
 
562
            return true;
 
563
    QImage image = QImageReader(fileName, format).read();
 
564
    if (image.isNull())
 
565
        return false;
 
566
    QPixmap pm;
 
567
    if (data->type == BitmapType)
 
568
        pm = QBitmap::fromImage(image, flags);
 
569
    else
 
570
        pm = fromImage(image, flags);
 
571
    if (!pm.isNull()) {
 
572
        *this = pm;
 
573
        QPixmapCache::insert(key, *this);
 
574
        return true;
 
575
    }
 
576
    return false;
 
577
}
 
578
 
 
579
/*!
 
580
    Loads a pixmap from the binary data in \a buf (\a len bytes).
 
581
    Returns true if successful; otherwise returns false.
 
582
 
 
583
    If \a format is specified, the loader attempts to read the pixmap
 
584
    using the specified format. If \a format is not specified
 
585
    (default), the loader reads a few bytes from the header to guess
 
586
    the file's format.
 
587
 
 
588
    If the data needs to be modified to fit in a lower-resolution
 
589
    result (e.g. converting from 32-bit to 8-bit), use the \a
 
590
    flags to specify how you'd prefer this to happen.
 
591
 
 
592
    The QImageReader documentation lists the supported image formats and
 
593
    explains how to add extra formats.
 
594
 
 
595
    \sa load(), save(), QImageReader::imageFormat(), QImage::loadFromData(), fromImage(),
 
596
    QImageReader
 
597
*/
 
598
 
 
599
bool QPixmap::loadFromData(const uchar *buf, uint len, const char *format, Qt::ImageConversionFlags flags)
 
600
{
 
601
    QByteArray a = QByteArray::fromRawData(reinterpret_cast<const char *>(buf), len);
 
602
    QBuffer b(&a);
 
603
    b.open(QIODevice::ReadOnly);
 
604
 
 
605
    QImage image = QImageReader(&b, format).read();
 
606
    QPixmap pm;
 
607
    if (data->type == BitmapType)
 
608
        pm = QBitmap::fromImage(image, flags);
 
609
    else
 
610
        pm = fromImage(image, flags);
 
611
    if (!pm.isNull()) {
 
612
        *this = pm;
 
613
        return true;
 
614
    }
 
615
    return false;
 
616
}
 
617
 
 
618
/*!
 
619
  \fn bool QPixmap::loadFromData(const QByteArray &buf, const char *format, Qt::ImageConversionFlags flags)
 
620
    \overload
 
621
 
 
622
    Loads a pixmap from the binary data \a buf.
 
623
 
 
624
    If \a format is specified, the loader attempts to read the pixmap
 
625
    using the specified format. If \a format is not specified
 
626
    (default), the loader reads a few bytes from the header to guess
 
627
    the file's format.
 
628
 
 
629
    If the data needs to be modified to fit in a lower-resolution
 
630
    result (e.g. converting from 32-bit to 8-bit), use the \a
 
631
    flags to specify how you'd prefer this to happen.
 
632
*/
 
633
 
 
634
 
 
635
/*!
 
636
    Saves the pixmap to the file \a fileName using the image file
 
637
    format \a format and a quality factor \a quality. \a quality must
 
638
    be in the range [0,100] or -1. Specify 0 to obtain small
 
639
    compressed files, 100 for large uncompressed files, and -1 to use
 
640
    the default settings. Returns true if successful; otherwise
 
641
    returns false.
 
642
 
 
643
    \sa load(), loadFromData(), QImageReader::imageFormat(), QImage::save(),
 
644
    QImageReader
 
645
*/
 
646
 
 
647
bool QPixmap::save(const QString &fileName, const char *format, int quality) const
 
648
{
 
649
    if (isNull())
 
650
        return false;                                // nothing to save
 
651
    QImageWriter writer(fileName, format);
 
652
    return doImageIO(&writer, quality);
 
653
}
 
654
 
 
655
/*!
 
656
    \overload
 
657
 
 
658
    This function writes a QPixmap to the QIODevice, \a device using the image
 
659
    file format \a format. This can be used, for example, to save a pixmap
 
660
    directly into a QByteArray:
 
661
    \quotefromfile snippets/image/image.cpp
 
662
    \skipto PIX SAVE
 
663
    \skipto QPixmap
 
664
    \printuntil save
 
665
 
 
666
    The \a quality parameter is a quality factor \a quality. \a quality must
 
667
    be in the range [0,100] or -1. Specify 0 to obtain small
 
668
    compressed files, 100 for large uncompressed files, and -1 to use
 
669
    the default settings.
 
670
*/
 
671
 
 
672
bool QPixmap::save(QIODevice* device, const char* format, int quality) const
 
673
{
 
674
    if (isNull())
 
675
        return false;                                // nothing to save
 
676
    QImageWriter writer(device, format);
 
677
    return doImageIO(&writer, quality);
 
678
}
 
679
 
 
680
/*! \internal
 
681
*/
 
682
 
 
683
bool QPixmap::doImageIO(QImageWriter *writer, int quality) const
 
684
{
 
685
    if (quality > 100  || quality < -1)
 
686
        qWarning("QPixmap::save: quality out of range [-1,100]");
 
687
    if (quality >= 0)
 
688
        writer->setQuality(qMin(quality,100));
 
689
    return writer->write(toImage());
 
690
}
 
691
 
 
692
#endif //QT_NO_IMAGEIO
 
693
 
 
694
 
 
695
// The implementation of QPixmap::fill(const QWidget *, const QPoint &)
 
696
// is in qwidget.cpp
 
697
/*!
 
698
 \fn void QPixmap::fill(const QWidget *widget, int xoff, int yoff)
 
699
 
 
700
 \overload
 
701
 
 
702
    Fills the pixmap with the \a widget's background color or pixmap.
 
703
    \a xoff, \a yoff is an offset in the widget.
 
704
*/
 
705
 
 
706
 
 
707
/*!
 
708
    \fn int QPixmap::serialNumber() const
 
709
 
 
710
    Returns a number that uniquely identifies the contents of this
 
711
    QPixmap object. This means that multiple QPixmap objects can have
 
712
    the same serial number as long as they refer to the same contents.
 
713
 
 
714
    A null pixmap always have a serial number of 0.
 
715
 
 
716
    An example of where this is useful is for caching QPixmaps.
 
717
 
 
718
    \sa QPixmapCache
 
719
*/
 
720
int QPixmap::serialNumber() const
 
721
{
 
722
    if (isNull())
 
723
        return 0;
 
724
    else
 
725
        return data->ser_no;
 
726
}
 
727
 
 
728
/*
 
729
  Fills \a buf with \a r in \a widget. Then blits \a buf on \a res at
 
730
  position \a offset
 
731
 */
 
732
static void grabWidget_helper(QWidget *widget, QPixmap &res, QPixmap &buf,
 
733
                              const QRect &r, const QPoint &offset)
 
734
{
 
735
    buf.fill(widget, r.topLeft());
 
736
    QPainter::setRedirected(widget, &buf, r.topLeft());
 
737
    QPaintEvent e(r & widget->rect());
 
738
    QApplication::sendEvent(widget, &e);
 
739
    QPainter::restoreRedirected(widget);
 
740
    {
 
741
        QPainter pt(&res);
 
742
        pt.drawPixmap(offset.x(), offset.y(), buf, 0, 0, r.width(), r.height());
 
743
    }
 
744
 
 
745
    const QObjectList children = widget->children();
 
746
    for (int i = 0; i < children.size(); ++i) {
 
747
        QWidget *child = static_cast<QWidget*>(children.at(i));
 
748
        if (!child->isWidgetType() || child->isWindow()
 
749
            || child->isHidden() || !child->geometry().intersects(r))
 
750
            continue;
 
751
        QRect cr = r & child->geometry();
 
752
        cr.translate(-child->pos());
 
753
        grabWidget_helper(child, res, buf, cr, offset + child->pos());
 
754
    }
 
755
}
 
756
 
 
757
/*!
 
758
    \overload
 
759
 
 
760
    Creates a pixmap and paints \a widget in it. If the \a widget
 
761
    has any children, then they are also painted in the appropriate
 
762
    positions.
 
763
 
 
764
    If \a rect is a valid rectangle, only the rectangle you specify
 
765
    is painted.
 
766
 
 
767
    grabWidget(), QRect::isValid()
 
768
*/
 
769
 
 
770
QPixmap QPixmap::grabWidget(QWidget * widget, const QRect &rect)
 
771
{
 
772
 
 
773
    if (!widget)
 
774
        return QPixmap();
 
775
 
 
776
    QRect r(rect);
 
777
    if (r.width() < 0)
 
778
        r.setWidth(widget->width() - rect.x());
 
779
    if (r.height() < 0)
 
780
        r.setHeight(widget->height() - rect.y());
 
781
 
 
782
    if (!r.intersects(widget->rect()))
 
783
        return QPixmap();
 
784
 
 
785
    QPixmap res(r.size());
 
786
    QPixmap buf(r.size());
 
787
    if(res.isNull() || buf.isNull())
 
788
        return res;
 
789
 
 
790
    grabWidget_helper(widget, res, buf, r, QPoint());
 
791
    return res;
 
792
}
 
793
 
 
794
/*!
 
795
    \fn QPixmap QPixmap::grabWidget(QWidget *widget, int x, int y, int w, int h)
 
796
 
 
797
    Creates a pixmap and paints \a widget in it.
 
798
 
 
799
    If the \a widget has any children, then they are also painted in
 
800
    the appropriate positions.
 
801
 
 
802
    If you specify \a x, \a y, \a w or \a h, only the rectangle you
 
803
    specify is painted. The defaults are 0, 0 (top-left corner) and
 
804
    -1,-1 (which means the entire widget).
 
805
 
 
806
    (If \a w is negative, the function copies everything to the right
 
807
    border of the window. If \a h is negative, the function copies
 
808
    everything to the bottom of the window.)
 
809
 
 
810
    If \a widget is 0, or if the rectangle defined by \a x, \a y, the
 
811
    modified \a w and the modified \a h does not overlap the \a
 
812
    {widget}->rect(), this function will return a null QPixmap.
 
813
 
 
814
    This function actually asks \a widget to paint itself (and its
 
815
    children to paint themselves). QPixmap::grabWindow() grabs pixels
 
816
    off the screen, which is a bit faster and picks up \e exactly
 
817
    what's on-screen. This function works by calling paintEvent() with
 
818
    painter redirection turned on. If there are overlaying windows,
 
819
    grabWindow() will see them, but not this function.
 
820
 
 
821
    If there is overlap, it returns a pixmap of the size you want,
 
822
    containing a rendering of \a widget. If the rectangle you ask for
 
823
    is a superset of \a widget, the areas outside \a widget are
 
824
    covered with the widget's background.
 
825
 
 
826
    If an error occurs when trying to grab the widget, such as the
 
827
    size of the widget being too large to fit in memory, an isNull()
 
828
    pixmap is returned.
 
829
 
 
830
    \sa grabWindow() QWidget::paintEvent()
 
831
*/
 
832
 
 
833
 
 
834
#if !defined(Q_WS_WIN) && !defined(Q_WS_MAC)
 
835
/*!
 
836
    Returns the pixmap's handle to the device context.
 
837
 
 
838
    \warning This function is Windows-specific; using it is
 
839
    non-portable.
 
840
*/
 
841
 
 
842
Qt::HANDLE QPixmap::handle() const
 
843
{
 
844
    return data->hd;
 
845
}
 
846
#endif
 
847
 
 
848
 
 
849
#ifdef QT3_SUPPORT
 
850
#ifndef QT_NO_IMAGEIO
 
851
static Qt::ImageConversionFlags colorModeToFlags(QPixmap::ColorMode mode)
 
852
{
 
853
    Qt::ImageConversionFlags flags = Qt::AutoColor;
 
854
    switch (mode) {
 
855
      case QPixmap::Color:
 
856
        flags |= Qt::ColorOnly;
 
857
        break;
 
858
      case QPixmap::Mono:
 
859
        flags |= Qt::MonoOnly;
 
860
        break;
 
861
      default:
 
862
        break;// Nothing.
 
863
    }
 
864
    return flags;
 
865
}
 
866
 
 
867
/*!
 
868
    Use the constructor that takes a Qt::ImageConversionFlag instead.
 
869
 
 
870
    \sa ColorMode, Qt::ImageConversionFlag
 
871
*/
 
872
 
 
873
QPixmap::QPixmap(const QString& fileName, const char *format, ColorMode mode)
 
874
    : QPaintDevice()
 
875
{
 
876
    init(0, 0);
 
877
    load(fileName, format, colorModeToFlags(mode));
 
878
}
 
879
 
 
880
/*!
 
881
    Constructs a pixmap from the QImage \a image.
 
882
 
 
883
    \sa fromImage()
 
884
*/
 
885
 
 
886
QPixmap::QPixmap(const QImage& image)
 
887
    : QPaintDevice()
 
888
{
 
889
    init(0, 0);
 
890
    if (data->type == BitmapType)
 
891
        *this = QBitmap::fromImage(image);
 
892
    else
 
893
        *this = fromImage(image);
 
894
}
 
895
 
 
896
/*!
 
897
    \overload
 
898
 
 
899
    Converts the image \a image to a pixmap that is assigned to this
 
900
    pixmap. Returns a reference to the pixmap.
 
901
 
 
902
    \sa fromImage()
 
903
*/
 
904
 
 
905
QPixmap &QPixmap::operator=(const QImage &image)
 
906
{
 
907
    if (data->type == BitmapType)
 
908
        *this = QBitmap::fromImage(image);
 
909
    else
 
910
        *this = fromImage(image);
 
911
    return *this;
 
912
}
 
913
 
 
914
/*!
 
915
    Use the load() function that takes a Qt::ImageConversionFlag instead.
 
916
 
 
917
    \sa ColorMode, Qt::ImageConversionFlag
 
918
*/
 
919
 
 
920
bool QPixmap::load(const QString &fileName, const char *format, ColorMode mode)
 
921
{
 
922
    return load(fileName, format, colorModeToFlags(mode));
 
923
}
 
924
 
 
925
/*!
 
926
    Use the loadFromData() function that takes a Qt::ImageConversionFlag instead.
 
927
 
 
928
    \sa ColorMode, Qt::ImageConversionFlag
 
929
*/
 
930
 
 
931
bool QPixmap::loadFromData(const uchar *buf, uint len, const char *format, ColorMode mode)
 
932
{
 
933
    return loadFromData(buf, len, format, colorModeToFlags(mode));
 
934
}
 
935
#endif
 
936
 
 
937
/*!
 
938
    Use fromImage() instead.
 
939
*/
 
940
bool QPixmap::convertFromImage(const QImage &image, ColorMode mode)
 
941
{
 
942
    if (data->type == BitmapType)
 
943
        *this = QBitmap::fromImage(image, colorModeToFlags(mode));
 
944
    else
 
945
        *this = fromImage(image, colorModeToFlags(mode));
 
946
    return !isNull();
 
947
}
 
948
 
 
949
#endif
 
950
 
 
951
/*****************************************************************************
 
952
  QPixmap stream functions
 
953
 *****************************************************************************/
 
954
#if !defined(QT_NO_DATASTREAM) && !defined(QT_NO_IMAGEIO)
 
955
/*!
 
956
    \relates QPixmap
 
957
 
 
958
    Writes the pixmap \a pixmap to the stream \a s as a PNG image.
 
959
 
 
960
    Note that writing the stream to a file will not produce a valid image file.
 
961
 
 
962
    \sa QPixmap::save()
 
963
    \link datastreamformat.html Format of the QDataStream operators \endlink
 
964
*/
 
965
 
 
966
QDataStream &operator<<(QDataStream &s, const QPixmap &pixmap)
 
967
{
 
968
    s << pixmap.toImage();
 
969
    return s;
 
970
}
 
971
 
 
972
/*!
 
973
    \relates QPixmap
 
974
 
 
975
    Reads a pixmap from the stream \a s into the pixmap \a pixmap.
 
976
 
 
977
    \sa QPixmap::load()
 
978
    \link datastreamformat.html Format of the QDataStream operators \endlink
 
979
*/
 
980
 
 
981
QDataStream &operator>>(QDataStream &s, QPixmap &pixmap)
 
982
{
 
983
    QImage img;
 
984
    s >> img;
 
985
    if (pixmap.data->type == QPixmap::BitmapType)
 
986
        pixmap = QBitmap::fromImage(img);
 
987
    else
 
988
        pixmap = QPixmap::fromImage(img);
 
989
    return s;
 
990
}
 
991
 
 
992
#endif //QT_NO_DATASTREAM
 
993
 
 
994
#ifdef QT3_SUPPORT
 
995
Q_GUI_EXPORT void copyBlt(QPixmap *dst, int dx, int dy,
 
996
                          const QPixmap *src, int sx, int sy, int sw, int sh)
 
997
{
 
998
    Q_ASSERT_X(dst, "::copyBlt", "Destination pixmap must be non null");
 
999
    Q_ASSERT_X(src, "::copyBlt", "Source pixmap must be non null");
 
1000
 
 
1001
    QImage image = dst->toImage();
 
1002
    QPainter p(&image);
 
1003
    p.setCompositionMode(QPainter::CompositionMode_Source);
 
1004
    p.drawPixmap(dx, dy, *src, sx, sy, sw, sh);
 
1005
    *dst = QPixmap::fromImage(image);
 
1006
}
 
1007
#endif
 
1008
 
 
1009
/*!
 
1010
    \internal
 
1011
*/
 
1012
 
 
1013
bool QPixmap::isDetached() const
 
1014
{
 
1015
    return data->count == 1;
 
1016
}
 
1017
 
 
1018
void QPixmap::deref()
 
1019
{
 
1020
    if(data && data->deref()) { // Destroy image if last ref
 
1021
        delete data;
 
1022
        data = 0;
 
1023
    }
 
1024
}
 
1025
 
 
1026
/*!
 
1027
    \fn QImage QPixmap::convertToImage() const
 
1028
 
 
1029
    Use toImage() instead.
 
1030
*/
 
1031
 
 
1032
/*!
 
1033
    \fn bool QPixmap::convertFromImage(const QImage &image, Qt::ImageConversionFlags flags)
 
1034
 
 
1035
    Use fromImage() instead.
 
1036
*/
 
1037
 
 
1038
/*!
 
1039
    \fn QPixmap QPixmap::xForm(const QMatrix &matrix) const
 
1040
 
 
1041
    Use transform() instead.
 
1042
*/
 
1043
 
 
1044
/*!
 
1045
    \fn QPixmap QPixmap::scaled(int w, int h, Qt::AspectRatioMode aspectRatioMode, Qt::TransformationMode transformMode) const
 
1046
 
 
1047
    Returns a copy of the pixmap scaled to a rectangle of width \a w
 
1048
    and height \a h according to \a aspectRatioMode and \a transformMode.
 
1049
 
 
1050
    \list
 
1051
    \i If \a aspectRatioMode is \c Qt::IgnoreAspectRatio, the pixmap
 
1052
       is scaled to (\a w, \a h).
 
1053
    \i If \a aspectRatioMode is \c Qt::KeepAspectRatio, the pixmap is
 
1054
       scaled to a rectangle as large as possible inside (\a w, \a
 
1055
       h), preserving the aspect ratio.
 
1056
    \i If \a aspectRatioMode is \c Qt::KeepAspectRatioByExpanding,
 
1057
       the pixmap is scaled to a rectangle as small as possible
 
1058
       outside (\a w, \a h), preserving the aspect ratio.
 
1059
    \endlist
 
1060
 
 
1061
    If either the width \a w or the height \a h is zero or negative,
 
1062
    this function returns a \l{isNull()}{null} pixmap.
 
1063
 
 
1064
    \sa scaledToWidth(), scaledToHeight(), transformed()
 
1065
*/
 
1066
 
 
1067
/*!
 
1068
    \fn QPixmap QPixmap::scaled(const QSize &size, Qt::AspectRatioMode aspectMode, Qt::TransformationMode transformMode) const
 
1069
 
 
1070
    \overload
 
1071
 
 
1072
    Scales the pixmap to the given \a size, using the aspect ratio and
 
1073
    transformation modes specified by \a aspectMode and \a transformMode.
 
1074
*/
 
1075
QPixmap QPixmap::scaled(const QSize& s, Qt::AspectRatioMode aspectMode, Qt::TransformationMode mode) const
 
1076
{
 
1077
    if (isNull()) {
 
1078
        qWarning("QPixmap::scaled: Pixmap is a null pixmap");
 
1079
        return copy();
 
1080
    }
 
1081
    if (s.isEmpty())
 
1082
        return QPixmap();
 
1083
 
 
1084
    QSize newSize = size();
 
1085
    newSize.scale(s, aspectMode);
 
1086
    if (newSize == size())
 
1087
        return copy();
 
1088
 
 
1089
    QPixmap pix;
 
1090
    QMatrix wm;
 
1091
    wm.scale((double)newSize.width() / width(), (double)newSize.height() / height());
 
1092
    pix = transformed(wm, mode);
 
1093
    return pix;
 
1094
}
 
1095
 
 
1096
/*!
 
1097
    Returns a scaled copy of the pixmap using a transformation specified
 
1098
    by \a mode. The returned pixmap has a width of \a w pixels. This
 
1099
    function automatically calculates the height of the pixmap so that the
 
1100
    ratio of the pixmap is preserved.
 
1101
 
 
1102
    If \a w is 0 or negative a \link isNull() null\endlink pixmap is
 
1103
    returned.
 
1104
 
 
1105
    \sa scaled(), scaledToHeight(), transformed()
 
1106
*/
 
1107
QPixmap QPixmap::scaledToWidth(int w, Qt::TransformationMode mode) const
 
1108
{
 
1109
    if (isNull()) {
 
1110
        qWarning("QPixmap::scaleWidth: Pixmap is a null pixmap");
 
1111
        return copy();
 
1112
    }
 
1113
    if (w <= 0)
 
1114
        return QPixmap();
 
1115
 
 
1116
    QMatrix wm;
 
1117
    double factor = (double) w / width();
 
1118
    wm.scale(factor, factor);
 
1119
    return transformed(wm, mode);
 
1120
}
 
1121
 
 
1122
/*!
 
1123
    Returns a scaled copy of the pixmap using a transformation specified
 
1124
    by \a mode. The returned pixmap has a height of \a h pixels. This
 
1125
    function automatically calculates the width of the pixmap so that the
 
1126
    ratio of the pixmap is preserved.
 
1127
 
 
1128
    If \a h is 0 or negative a \link isNull() null\endlink pixmap is
 
1129
    returned.
 
1130
 
 
1131
    \sa scaled(), scaledToWidth(), transformed()
 
1132
*/
 
1133
QPixmap QPixmap::scaledToHeight(int h, Qt::TransformationMode mode) const
 
1134
{
 
1135
    if (isNull()) {
 
1136
        qWarning("QPixmap::scaleHeight: Pixmap is a null pixmap");
 
1137
        return copy();
 
1138
    }
 
1139
    if (h <= 0)
 
1140
        return QPixmap();
 
1141
 
 
1142
    QMatrix wm;
 
1143
    double factor = (double) h / height();
 
1144
    wm.scale(factor, factor);
 
1145
    return transformed(wm, mode);
 
1146
}
 
1147
 
 
1148
/*!
 
1149
    \class QPixmap
 
1150
    \brief The QPixmap class is an off-screen, pixel-based paint device.
 
1151
 
 
1152
    \ingroup multimedia
 
1153
    \ingroup shared
 
1154
    \mainclass
 
1155
 
 
1156
    QPixmap is one of the three classes Qt provides for dealing with
 
1157
    images, the others being QImage and QPicture. QPixmap is designed
 
1158
    and optimized for drawing on screen; QImage is designed for I/O
 
1159
    and for direct pixel access; QPicture provides a scalable,
 
1160
    vectorial picture. There are (slow) functions to convert between
 
1161
    QImage and QPixmap: toImage() and fromImage(). There's also a
 
1162
    QIcon class that stores various versions of an icon.
 
1163
 
 
1164
    A common way to create a pixmap is to use the constructor that
 
1165
    takes a file name. For example:
 
1166
 
 
1167
    \code
 
1168
        label->setPixmap(QPixmap("paste.png"));
 
1169
    \endcode
 
1170
 
 
1171
    The file name can either refer to an actual file on disk or to
 
1172
    one of the application's embedded resources. See the
 
1173
    \l{Resource System} overview for details on how
 
1174
    to embed images and other resource files in the application's
 
1175
    executable.
 
1176
 
 
1177
    Pixel data in a pixmap is internal and is managed by the
 
1178
    underlying window system. Pixels can be accessed only through
 
1179
    QPainter functions or by converting the QPixmap to a QImage.
 
1180
 
 
1181
    You can easily display a QPixmap on the screen using QLabel or
 
1182
    one of QAbstractButton's subclasses (such as QPushButton and
 
1183
    QToolButton). QLabel has a \l{QLabel::pixmap}{pixmap} property,
 
1184
    whereas QAbstractButton has an \l{QAbstractButton::icon}{icon}
 
1185
    property.
 
1186
 
 
1187
    The QPixmap class uses \l{shclass.html}{implicit sharing}, so you
 
1188
    can pass QPixmap objects around by value.
 
1189
 
 
1190
    You can retrieve the width(), height(), depth(), and size() of a
 
1191
    pixmap. The enclosing rectangle can be determined with rect().
 
1192
    Pixmaps can be filled with fill() and resized with resize(). You
 
1193
    can create and set a mask with createHeuristicMask() and setMask().
 
1194
    Use selfMask() to see if the pixmap is identical to its mask.
 
1195
 
 
1196
    In addition to loading a pixmap from file using load() you can
 
1197
    also loadFromData(). You can obtain a transformed version of the
 
1198
    pixmap using transform().
 
1199
 
 
1200
    \sa QBitmap, QImage, QImageReader, {shclass.html}{Shared Classes}
 
1201
*/