QT QImage манипуляции с пикселями

Я создаю приложение QT GUI и использую QImage для открытия изображений. Моя проблема в том, что я не могу понять, как использовать методы bit () и scanline () QImage для получения доступа на уровне пикселей.

Я видел этот пост Проблемы с манипуляцией с пикселями Qt QImage, но это только для первого пиксель каждой строки. Это правильно или я все неправильно понял?

заранее спасибо


person theosem    schedule 19.01.2010    source источник
comment
oopps !! Извините! после публикации вопроса я нашел его на форумах QT qt.nokia.com/doc/ qq / qq17-imageio.html и ответ: for (quint32 y = 0; y ‹h; ++ y) {QRgb * scanLine = (QRgb *) img.scanLine (y); для (quint32 x = 0; x ‹w; ++ x) {pix = qBlue (scanLine [x]); }}   -  person theosem    schedule 19.01.2010


Ответы (3)


scanlines соответствуют высоте изображения, столбцы соответствуют в ширину изображения.

Согласно документации, прототип выглядит как uchar* QImage::scanline(int i) или аналогичная const версия.

Но, как отметил комментатор, поскольку данные зависят от архитектуры и образа компьютера, вам НЕ следует использовать uchar * напрямую. Вместо этого используйте что-то вроде следующего:

QRgb *rowData = (QRgb*)img.scanLine(row);
QRgb pixelData = rowData[col];
int red = qRed(pixelData);
person Kaleb Pederson    schedule 19.01.2010
comment
-1: Внимание! Поскольку этот ответ появляется в поиске Google еще до официального документа Qt-API, я подумал, что уместно сделать одно предупреждение. Вы НЕ МОЖЕТЕ использовать [row] [col] для доступа к данным пикселей, поскольку [col] выберет uchar, а данные пикселей очень зависят от формата бит на пиксель. См. Предупреждение в официальном документе. Вы не можете использовать указатель uchar * напрямую, потому что формат пикселей зависит от порядка байтов на базовой платформе. Используйте qRed (), qGreen (), qBlue () и qAlpha () для доступа к пикселям. qt-project.org/doc/qt-4.8/qimage.html# scanLine - person Valentin Heinitz; 03.05.2013
comment
Я обновил ответ, чтобы отразить правильный способ доступа к нему. - person Kaleb Pederson; 19.02.2014

Это может быть не сразу очевидно из сообщения Калеба, но для установки пикселя в изображении Format_RGB32 можно использовать следующие действия.

// Get the line we want
QRgb *line = (QRgb *)image->scanLine(row_index);

// Go to the pixel we want
line += col_index;

// Actually set the pixel
*line = qRgb(qRed(color), qGreen(color), qBlue(color));
person LeviX    schedule 23.05.2011

Ответ у меня не сработал. Похоже, что данные в моей системе не выровнены по 32 бита. Чтобы получить правильные данные, в моей системе мне пришлось сделать следующее:

for(uint32_t Y = 0; Y < mHeight; ++Y)
{
    uint8_t* pPixel = Image.scanLine(Y);

    for(uint32_t X = 0; X < mWidth; ++X)
    {
      const int Blue = *pPixel++;
      const int Green = *pPixel++;
      const int Red = *pPixel++;

      uint8_t GrayscalePixel = (0.21f * Red) + (0.72f * Green) + (0.07 * Blue);
    }
}
person MvHorssen    schedule 03.12.2016
comment
Выравнивание зависит от формата пикселей! Здесь у вас есть невыровненный формат пикселей RGB888 :) Всегда конвертируйте исходное изображение в формат, с которым хотите работать, например RGBA32 или ARGB32 или подобное - person Петър Петров; 21.03.2019