2016-02-08 68 views
1

我想模糊QImage alpha通道。我當前的實現使用不推薦使用的'alphaChannel'方法,並且工作緩慢。模糊QImage alpha通道

QImage blurImage(const QImage & image, double radius) 
{ 
    QImage newImage = image.convertToFormat(QImage::Format_ARGB32); 

    QImage alpha = newImage.alphaChannel(); 
    QImage blurredAlpha = alpha; 
    for (int x = 0; x < alpha.width(); x++) 
    { 
    for (int y = 0; y < alpha.height(); y++) 
    { 
     uint color = calculateAverageAlpha(x, y, alpha, radius); 
     blurredAlpha.setPixel(x, y, color); 
    } 
    } 
    newImage.setAlphaChannel(blurredAlpha); 

    return newImage; 
} 

我也試圖使用QGraphicsBlurEffect來實現它,但它不影響阿爾法。

模糊QImage alpha通道的正確方法是什麼?

+0

也許值得使用opencv進行圖像處理。 – UmNyobe

回答

0

我面臨一個similar question about pixel read\write access

  1. 倒置的循環。圖像作爲一連串的行被放置在內存中。所以你應該先訪問高度然後再訪問寬度
  2. 使用QImage::scanline來訪問數據,而不是昂貴的QImage::pixelQImage::setPixel。掃描中的像素(又名行)保證連續。

你的代碼如下:

for (int ii = 0; ii < image.height(); ii++) { 
    uchar* scan = image.scanLine(ii); 
    int depth =4; 
    for (int jj = 0; jj < image.width(); jj++) { 
     //it is in fact an rgba 
     QRgb* rgbpixel = reinterpret_cast<QRgb*>(scan + jj*depth); 
     QColor color(*rgbpixel); 
     int alpha = calculateAverageAlpha(ii, jj, color, image); 
     color.setAlpha(alpha); 

     //write 
     *rgbpixel = color.rgba(); 
    } 
} 

您可以進一步去優化阿爾法平均的計算。讓我們看看半徑像素的總和。在(x,y)半徑處的α值的總和是s(x,y)。當您向任一方向移動一個像素時,單條線被刪除,而單條線被刪除。可以說你水平移動。如果L(X,y)是長度2*radius的垂直線周圍(x,y)居中的總和,必須

s(x + 1, y) = s(x, y) + l(x + r + 1, y) - l(x - r, y) 

,讓你可以有效地計算總和的矩陣(然後平均,通過用數除像素)。

我懷疑這種優化已經在諸如opencv的庫中以更好的方式實現了。所以如果你想節省時間,我會鼓勵你使用現有的opencv函數。