问题
I have my own image class containing an unsigned char array with RGB values. I would like to show images stored in this class, without copying them, in a QGraphicsScene. I can make an QImage with
QImage image(data, width, height, width * 3, QImage::Format_RGB888);
without copying my image. How can I show image in a QGraphicsScene without a deep copy of data?
回答1:
With the default, raster paint engine/backend, the top-level widget's contents are stored as a QImage
. Drawing a QImage
(and a QPixmap
, too) on it is quick and doesn't involve copies. The QPixmap
, with the raster backend, is simply internally a QImage
that has the same format as that of the backing store. The pixmap generally doesn't represent any native resource handle - since you are using a raster backend unless you ask for something else explicitly.
So what you would wish to do is to directly drawImage
from your source image, within a QGraphicsItem::paint
implementation. What really happens behind the scenes is the paint
gets executed on the backing store - a QImage
, and that's fast and efficient. The QPainter
that you use operates on a QImage
!
All you have to do is to implement a QGraphicsImageItem
akin to QGraphicsPixmapItem
. No copying and no format conversion will be involved as long as your source image has the same format as the image backing the top-level window. And how would you know that? Just ask the backing store about what format it's in.
QImage::Format backingStoreFormat(QWidget * widget) {
auto store = dynamic_cast<QImage*>(widget->backingStore()->paintDevice())
return store ? store->format() : QImage::Format_Invalid;
}
I leave the implementation of QGraphicsImageItem
to the reader :)
回答2:
For displaying images QPixmap is a proper class. QGraphicsScene pdovides a method only for a QPixmap.
QGraphicsPixmapItem * QGraphicsScene::addPixmap(const QPixmap & pixmap)
However, QPixmap is an optimized class for displaying images, so it can't be created with existing block of memory. So if you intend to display your memory data as an image in QGraphicsScene, it seems to be not possible (with reasonable effort).
Why do you concern about copying a data from your class into QPixmap? Is there a prove, that it will be a performance bottle-neck?
If not, either you convert your class directly to a QPixmap or use QPixmap::fromImage(). Add yout image with e.g.:
myScene->addPixmap( QPixmap::fromImage(myImage) );
来源:https://stackoverflow.com/questions/32101556/how-to-show-a-qimage-without-copying-in-qgraphicsscene