2014-08-28 48 views
0

我想要訪問QImage中的圖像顏色。從RGB32和索引類型的圖像獲取圖像顏色信息

,我發現在文檔大多數是基於掃描線功能的方法...

我試着和它的工作......在RGB32圖像。使用精確的方法獲取8位索引或單色圖像的顏色數據時,我出現了令人驚訝的不愉快結果。

這是我的代碼:

// note RGBTriple is a struct containing unsigned R, G, B 
// rgbImage.pixels is a RGBTriple* array 

RGBTriple* pTriple = rgbImage.pixels; 
for (int y = 0; y < source.height(); y++) 
{ 
    const unsigned char* pScanLine = source.scanLine(y); 
    for (int x = 0; x < source.width(); x++) 
    { 
     QRgb* color = (QRgb*)pScanLine; 
     pTriple->R = qRed(*color); 
     pTriple->G = qGreen(*color); 
     pTriple->B = qBlue(*color); 
     ++pTriple; 
     pScanLine += 4; 
    } 
} 

運行相同的代碼與8位圖像索引或單色,我在創造越來越顏色有誤差。該文件說scanline是32b的倍數 - 但由於這是8和2的倍數,我不認爲這會是一個問題。

一旦我發現,我沒有得到正確的結果,爲所有類型的輸入圖像,我把它改成

RGBTriple* pTriple = rgbImage.pixels; 
for (int y = 0; y < source.height(); y++) 
{ 
    for (int x = 0; x < source.width(); x++) 
    { 
     pTriple->R = qRed(source.pixel(x, y)); 
     pTriple->G = qGreen(source.pixel(x, y)); 
     pTriple->B = qBlue(source.pixel(x, y)); 
     ++pTriple; 
    } 
} 

完美的作品......我不知道它是較慢或將有其他意外的行爲?畢竟,我使用pixel()函數 - 即使是在索引圖像上 - 以獲取顏色信息,實際上應該以不同的方式存儲......看起來應該會失敗...

有沒有辦法讓第一個版本,使用掃描線,適用於其他圖像類型?

爲什麼看起來像使用scanline來獲取數據是首選方法?

+1

關於「慢」,至少調用'pixel'只有一次和存儲返回值的臨時變量... – hyde 2014-08-28 17:42:28

回答

1

我試過了,它在RGB32圖像上工作。當我使用確切的方法獲取位圖索引或單色圖像的顏色數據時,我出人意料地發現了令人不快的結果。

你不應該感到驚訝,因爲索引和單色圖像不同格式。您發佈的第一個代碼片段是基於如何將RGB32(和RGB32)鋪設在內存中的知識。

想一想。在單色圖像R=G=B。所以只有一個通道需要保存在內存中。

如果你的目標是獲得內部rgbImage.pixels使用QImage::convertToFormat() RGB圖像:

QImage source; 
QImage dest = source.convertToFormat(QImage::Format_RGB888); 
memcpy(rgbImage.pixels, dest.bits(),dest.byteCount()); 
+0

什麼將是rgbImage.pixels的內容?它會變成一個無符號字符數組*,每種顏色都有一個字符 - 所以字節數爲size的3倍? – Thalia 2014-08-28 16:42:39

+0

是的,它是一個arrawy rgbrgbrgb ....其中每種顏色都是無符號字符。 rgb24的dest.byteCount已經是3 * width *高度字節。我期望rgbImage.pixels是相同的大小。 – UmNyobe 2014-08-28 18:43:07