PDA

View Full Version : QAbstractTableModel for continuous pixel stream



Vikram.Saralaya
30th July 2015, 15:16
I have a
QList< Qvector<uint> > structure to store pixel values of an image. There is a very fast image generator which continuously generates these images pixel by pixel. I need to display the pixels of the last generated image in my GUI.

So I created a QAbstractTableModel which will reference to the last generated image. I attached a QTableView to this. A QAbstractItemDelegate is delegated to paint the individual items in the QTableView.


void PixelDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const
{
if (option.state)
{
QColor color = index.model()->data(index, Qt::DisplayRole).value<QColor>();
painter->fillRect(option.rect, color);
}
}

Basically I am using QTableView to display an image! I also add this QTableView to a graphicsScene to zoom in and out of image etc. So I need to resize my QTableView everytime the size of the generated image changes to avoid scrollbars.

Question:
Looks like I am complicating things way too much for no reason?! Any suggestion would be useful.

Regards
Vikram :)

anda_skoa
30th July 2015, 22:10
Why not just write into a QImage and display that?

Cheers,
_

Vikram.Saralaya
31st July 2015, 09:49
Thanks @anda_skoa.

But why doesn't Qt suppor something like a "QImageView"!!
I mean I wanted to use Qt's Model-View architecture for displaying pixel data from the data model to the GUI. I now decided to just send a signal from the data model to the GUI at fixed intervals (slower than the data being written by my fast Image Generator!). The GUI then maps these pixel values to QImage and then sets the pixmap of a QGraphicsPixmapItem that I have placed in my graphics scene.

The processing in the GUI takes about 5-7 milliseconds depending on the size of the image since each pixel value is mapped to RGB:


QList< QVector<uint> > dataModelImage;
int minPixVal; // say 0.. depends on the image
int maxPixVal; // say 65535.. depends on the image

QImage newImg(dataModelImage[0].size(), dataModelImage.size(), QImage::Format_RGB16);

// For each row
for(int i=0; i<dataModelImage.size(); ++i)
{
// For each column
for(int j=0; j<dataModelImage[i].size(); ++j)
{
double ratio = (double)(dataModelImage[i][j] - minPixVal) / (maxPixVal - minPixVal);
int rgbVal = ratio*255;
newImg.setPixel(j, i, qRgb(rgbVal,rgbVal,rgbVal));
}
}

m_pixmapItem->setPixmap(QPixmap::fromImage(newImg));

I can live with 5-7 milliseconds for now. But isn't it way too much?

Regards
Vikram :)

anda_skoa
31st July 2015, 12:32
But why doesn't Qt suppor something like a "QImageView"!!

There are many classes that can be a "QImageView", e.g. QLabel, QPixmapItem in a QGraphicsView, any custom widget using QPainter, etc.



I mean I wanted to use Qt's Model-View architecture for displaying pixel data from the data model to the GUI.

Why, which of the model/view features do you need?



The processing in the GUI takes about 5-7 milliseconds depending on the size of the image since each pixel value is mapped to RGB:

Just some ideas:
- you seem to allocate a new image every time
- you are using two nested loops instead of scanline() or bits() for direct data access
- if you use the same value for red/green/blue, isn't that a grayscale image? In which case an image with a color table might be faster

Cheers,
_