[數(shù)字圖像處理] 濾鏡算法整理

灰度變換

將顏色的RGB設(shè)置為相同的值即可使得圖片為灰色在抛,一般處理方法有:
1满着、取三種顏色的平均值
2蟹地、取三種顏色的最大值(最小值) 3授翻、加權(quán)平均值:0.3R + 0.59G + 0.11*B
人眼對綠色最為敏感

黑白濾鏡

計算RGB的平均值arg或悲,arg>=100,r=g=b=255堪唐,否則均為0

去色濾鏡

RGB取三種顏色的最大值和最小值的平均值

單色濾鏡

只保留一個通道巡语,其他設(shè)為0

高斯模糊

根據(jù)正態(tài)分布為每個像素點周圍的像素點分配權(quán)重,將各個權(quán)重(各個權(quán)重值和為1)與對應(yīng)的色值相乘淮菠,所得結(jié)果求和作為中心像素點新的色值
G(x,y) = \frac{1}{2\pi\sigma^2}e^{-\frac{x^2+y^2}{2\sigma^2}}

function gaussBlur(imgData, radius, sigma) {
    var pixes = imgData.data,
        height = imgData.height,
        width = imgData.width,
        radius = radius || 5;
        sigma = sigma || radius / 3;
    
    var gaussEdge = radius * 2 + 1;

    var gaussMatrix = [],
        gaussSum = 0,
        a = 1 / (2 * sigma * sigma * Math.PI),
        b = -a * Math.PI;
    
    for(var i = -radius; i <= radius; i++) {
        for(var j = -radius; j <= radius; j++) {
            var gxy = a * Math.exp((i * i + j * j) * b);
            gaussMatrix.push(gxy);
            gaussSum += gxy;
        }
    }
    var gaussNum = (radius + 1) * (radius + 1);
    for(var i = 0; i < gaussNum; i++) {
        gaussMatrix[i] /= gaussSum;
    }

    for(var x = 0; x < width; x++) {
        for(var y = 0; y < height; y++) {
            var r = g = b = 0;
            for(var i = -radius; i<=radius; i++) {
                var m = handleEdge(i, x, width);
                for(var j = -radius; j <= radius; j++) {
                    var mm = handleEdge(j, y, height);
                    var currentPixId = (mm * width + m) * 4;
                    var jj = j + radius;
                    var ii = i + radius;
                    r += pixes[currentPixId] * gaussMatrix[jj * gaussEdge + ii];
                    g += pixes[currentPixId + 1] * gaussMatrix[jj * gaussEdge + ii];
                    b += pixes[currentPixId + 2] * gaussMatrix[jj * gaussEdge + ii];
                }
            }
            var pixId = (y * width + x) * 4;

            pixes[pixId] = ~~r;
            pixes[pixId + 1] = ~~g;
            pixes[pixId + 2] = ~~b;
        }
    }
    imgData.data = pixes;
    return imgData;
}

function handleEdge(i, x, w) {
    var m = x + I;
    if(m < 0) {
        m = -m;
    } else if(m >= w) {
        m = w + i -x;
    }
    return m;
}
懷舊濾鏡

R = (0.393 * r + 0.769 * g + 0.189 * b)
G = (0.349 * r + 0.686 * g + 0.168 * b)
B = (0.272 * r + 0.534 * g + 0.131 * b)
注意更新RGB值需要對0~255范圍之外的值進行判斷處理

連環(huán)畫濾鏡

R = |g – b + g + r| * r / 256
G = |b – g + b + r| * r / 256
B = |b – g + b + r| * g / 256

對比度增強和亮度增強
private static byte ContrastModify(int degree, byte basePixel)
 {
     if (degree < -100) degree = -100;
     if (degree > 100) degree = 100;
     double contrast = (100.0 + degree) / 100.0;
     contrast *= contrast;
     double pixel = ((basePixel / 255.0 - 0.5) * contrast + 0.5) * 255;
     if (pixel < 0) pixel = 0;
     if (pixel > 255) pixel = 255;
     return (byte)pixel;
 }

 private static byte BrightModify(int degree, byte basePixel)
 {
     if (degree < -255) degree = -255;
     if (degree > 255) degree = 255;
     int pixel = basePixel + degree;
     if (pixel < 0) pixel = 0;
     if (pixel > 255) pixel = 255;
     return (byte)pixel;
}
LOMO濾鏡

特點:色彩濃郁男公、高飽和度、可能伴隨晃動兜材、照片暗角

  1. 將原圖與原圖進行“柔光”圖層混合得到圖B
    柔光圖層混合
    根據(jù)混合色的通道數(shù)值選擇不同公式計算:數(shù)值大于128的時候理澎,結(jié)果色就比基色稍亮;數(shù)值小于或等于128曙寡,結(jié)果色就比基色稍暗。
    柔光模式是以基色為主導(dǎo)执隧,混合色只相應(yīng)改變局部明暗。其中混合色為黑色镀琉,結(jié)果色不會為黑色峦嗤,只比結(jié)果色稍暗,混合色為中性色屋摔,結(jié)果色跟基色一樣。
    計算公式:
    C=\begin{cases} A + (2 *B - 255) * (A -A *A / 255) / 255 \;\; if\; B <=128 \\ A + (2 *B - 255) * (Sqrt(A/255)*255 -A)/255 \;otherwise \end{cases}
  2. 圖B與一種自己設(shè)定的風(fēng)格色(比如藍色:R-200,G-37,B-11)進行“排除”圖層混合装黑,設(shè)定40%透明度,得到圖C
    差值&排除圖層混合
    差值圖層混合用基色減去混合色或用混合色減去基色從基色亮度中減去混合色弓熏,如果產(chǎn)生負值取正進行反相恋谭,白色與任何顏色混合得到反相色,黑色與任何顏色混合顏色不變疚颊。
    排除圖層混合與差值類似信认,但對比度更低,白色與基色混合得到基色補色母截,黑色與任何顏色混合顏色不變橄教。
    計算公式:
    C = (B + A) -B*A / 128
  3. 選擇一種暗角模板,與圖C進行“疊加”圖層混合
    疊加圖層混合
    根據(jù)基色通道的數(shù)值選擇不同公式計算护蝶,對顏色進行正片疊加或濾色混合持灰,結(jié)果色保留基色的明暗對比,以基色為主導(dǎo)堤魁。
    計算公式:
    C= \begin{cases} B*A / 128 \;\; if \; A < = 128 \\ 255 - (255 -B)* (255 -A) / 128 \; otherwise \end{cases}
暗角生成

暗角特效在Vignette類中實現(xiàn)妥泉,主要的算法實現(xiàn)原理是首先建立兩個以圖像中心為中心的橢圓邊界將圖像劃分為Zone A,Zone B和Zone C三個區(qū)域蝇率,然后根據(jù)圖像中各像素點在橢圓邊界內(nèi)外的判斷對像素點進行操作:Zone A保持原始圖像的像素值,Zone C完全使用純黑色的邊角顏色本慕,Zone B則進行暗角和原圖的融合疊加。為了實現(xiàn)融合區(qū)域的漸變效果监氢,Zone B建立了一系列以圖像中心為中心的橢圓藤违,各個相鄰橢圓間的區(qū)域根據(jù)其邊界的坐標(biāo)距離使用不同的融合權(quán)重系數(shù)以實現(xiàn)中間亮到四個角漸暗的暗角效果,具體的融合公式如下所示:
P=l_1*w_1+l_2*w_2
w_1 = 1/2(1+\cos(\pi s/d)), w_2 = 1/2(1-\cos(\pi s/d)),
關(guān)于漸變暗角的融合權(quán)重系數(shù)的代碼具體實現(xiàn)如下:

List<double> aVals; //融合區(qū)域系列橢圓的寬向坐標(biāo)          
 List<double> bVals; //融合區(qū)域系列橢圓的高向坐標(biāo)          
 List<double> aValsMidPoints; 
 List<double> bValsMidPoints; 
 List<double> imageWeight;    // 原圖融合權(quán)重系數(shù) 
 List<double> vignetteWeight; // 暗角融合權(quán)重系數(shù) 

 double a0 = vignetteWidthHalf - bandPixelsHalf; //融合區(qū)域系列橢圓寬向起始坐標(biāo) 
 double b0 = vignetteHeightHalf - bandPixelsHalf; //融合區(qū)域系列橢圓高向起始坐標(biāo) 

 //計算融合區(qū)域系列橢圓的坐標(biāo)數(shù)組 
 for (int i = 0; i <= numberSteps; ++i) 
 { 
?     aEll = a0 + stepSize * i; 
?     bEll = b0 + stepSize * i; 
?     aVals.Add(aEll); 
?     bVals.Add(bEll); 
 } 
 for (int i = 0; i < numberSteps; ++i) 
 { 
?     aEll = a0 + stepSize * (i + 0.5); 
?     bEll = b0 + stepSize * (i + 0.5); 
?     aValsMidPoints.Add(aEll); 
?     bValsMidPoints.Add(bEll); 
 } 

 // 計算融合權(quán)重 
 double weight1, weight2, arg, argCosVal; 
 double arguFactor = Math.PI / bandPixels; 
 for (int i = 0; i < numberSteps; ++i) 
 { 
?     arg = arguFactor * (aValsMidPoints[i] - a0); 
?     argCosVal = Math.Cos(arg); 
?     weight1 = 0.5 * (1.0 + argCosVal); 
?     weight2 = 0.5 * (1.0 - argCosVal); 
?     imageWeight.Add(weight1); 
?     vignetteWeight.Add(weight2); 
 }

效果如下:


晶格化濾鏡

超像素分割SLIC(simple linear iterative clustering)+塊內(nèi)平均
SLIC算法使用k-means聚類實現(xiàn)骡男,首先根據(jù)用戶界面設(shè)置的聚類中心個數(shù)的超參數(shù)初始化k個聚類中心隔盛,也即超像素中心,將其均勻分布到圖像的像素點上吮炕。
初始化label數(shù)組保存每一個像素點所屬的超像素標(biāo)簽,初始化lengths數(shù)組保存各個像素點到所屬的超像素中心的距離陕凹。

如果圖片包含N個像素鳄炉,要分割成K個超像素,那么每個超像素的大小是N/K 佑女,超像素之間的距離S=\sqrt{N/K}谈竿。為了將算法復(fù)雜度降低為O(n),在聚類時將搜索區(qū)域限制在2S*2S范圍內(nèi)嚎花。聚類的目標(biāo)是使各個像素到所屬的超像素中心的距離之和最小劫恒。實現(xiàn)時首先將圖像的RGB顏色轉(zhuǎn)換為LAB顏色空間轿腺,使得計算距離時能夠同時考慮LAB顏色信息和XY距離信息丛楚,并可以通過用戶界面設(shè)置的M值調(diào)整顏色和距離的比重。

對每一個超像素中心x仿荆,搜索它2S*2S范圍內(nèi)的點:如果點到超像素中心x的5維信息的距離小于這個點到它原來所屬的超像素中心的距離坏平,那么說明這個點屬于超像素x,更新lengths數(shù)組和label數(shù)組令境,然后對每個聚類中心顾瞪,找到所有l(wèi)abel值為該聚類中心的點,求他們的平均值從而更新得到k個新的聚類中心惕橙。上述過程迭代十次钉跷,該部分核心實現(xiàn)代碼如下所示:

//計算每個超像素分割區(qū)域的面積 
 double S = Math.Sqrt((w * h) / numberOfCenters); 
 //生成聚類中心 
 Center[] centers = createCenters(w, h, lband, aband, labbband, numberOfCenters, S); 
 //生成聚類標(biāo)簽 
 double[,] labels = new double[h, w]; 
 for (int i = 0; i < h; i++) 
 { 
?     for (int j = 0; j < w; j++) 
?     { 
?         labels[i, j] = -1; 
?     } 
 } 

 for (int iteration = 0; iteration < 10; iteration++) 
 { 
?     double[,] lengths = new double[h, w]; 
?     for (int ii = 0; ii < h; ii++) 
?     { 
?         for (int j = 0; j < w; j++) 
?         { 
?             lengths[ii, j] = Double.MaxValue; 
?         } 
?     } 

?     int i = 0; 
?     foreach (Center center in centers) 
?     { 
?         for (int k = (int)Math.Round(center.X - S); k < (int)Math.Round(center.X + S); k++) 
?             for (int l = (int)Math.Round(center.Y - S); l < (int)Math.Round(center.Y + S); l++) 
?                 if (k >= 0 && k < h && l >= 0 && l < w) 
?                 { 
?                     double L = lband[k, l]; 
?                     double A = aband[k, l]; 
?                     double B = labbband[k, l]; 

?                     double Dc = Math.Sqrt(Math.Pow(L - center.L, 2) + Math.Pow(A - center.A, 2) + Math.Pow(B - center.B, 2)); 
?                     double Ds = Math.Sqrt(Math.Pow(l - center.Y, 2) + Math.Pow(k - center.X, 2)); 
?                     double length = Math.Sqrt(Math.Pow(Dc, 2) + Math.Pow(Ds / 2, 2) * Math.Pow(m, 2)); 

?                     if (length < lengths[k, l]) 
?                     { 
?                         lengths[k, l] = length; 
?                         labels[k, l] = i; 
?                     } 
?                 } 
?         i++; 
?     } 
?     centers = calculateNewCenters(lband, aband, labbband, w, h, centers, labels); 
 } 

效果如下:


參考:

  1. 圖像處理的簡單濾鏡算法
  2. 看云文檔圖像濾鏡匯總
  3. 微像素
  4. 圖層混合模式計算公式
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末彬坏,一起剝皮案震驚了整個濱河市膝晾,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌混滔,老刑警劉巖歹颓,帶你破解...
    沈念sama閱讀 222,252評論 6 516
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件巍扛,死亡現(xiàn)場離奇詭異,居然都是意外死亡撤奸,警方通過查閱死者的電腦和手機喊括,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,886評論 3 399
  • 文/潘曉璐 我一進店門郑什,熙熙樓的掌柜王于貴愁眉苦臉地迎上來蒲肋,“玉大人,你說我怎么就攤上這事申窘】字幔” “怎么了?”我有些...
    開封第一講書人閱讀 168,814評論 0 361
  • 文/不壞的土叔 我叫張陵玄窝,是天一觀的道長悍引。 經(jīng)常有香客問我帽氓,道長,這世上最難降的妖魔是什么浓领? 我笑而不...
    開封第一講書人閱讀 59,869評論 1 299
  • 正文 為了忘掉前任势腮,我火速辦了婚禮,結(jié)果婚禮上泪幌,老公的妹妹穿的比我還像新娘署照。我一直安慰自己,他們只是感情好没隘,可當(dāng)我...
    茶點故事閱讀 68,888評論 6 398
  • 文/花漫 我一把揭開白布禁荸。 她就那樣靜靜地躺著阀湿,像睡著了一般瑰妄。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上罩旋,一...
    開封第一講書人閱讀 52,475評論 1 312
  • 那天眶诈,我揣著相機與錄音逝撬,去河邊找鬼。 笑死宪潮,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的梯轻。 我是一名探鬼主播尽棕,決...
    沈念sama閱讀 41,010評論 3 422
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼伊诵!你這毒婦竟也來了逸寓?” 一聲冷哼從身側(cè)響起揪利,我...
    開封第一講書人閱讀 39,924評論 0 277
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎苔巨,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體资厉,經(jīng)...
    沈念sama閱讀 46,469評論 1 319
  • 正文 獨居荒郊野嶺守林人離奇死亡宴偿,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 38,552評論 3 342
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了窥妇。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片娩践。...
    茶點故事閱讀 40,680評論 1 353
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖材泄,靈堂內(nèi)的尸體忽然破棺而出吨岭,到底是詐尸還是另有隱情,我是刑警寧澤辣辫,帶...
    沈念sama閱讀 36,362評論 5 351
  • 正文 年R本政府宣布急灭,位于F島的核電站,受9級特大地震影響葬馋,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 42,037評論 3 335
  • 文/蒙蒙 一掠廓、第九天 我趴在偏房一處隱蔽的房頂上張望甩恼。 院中可真熱鬧,春花似錦悦污、人聲如沸钉蒲。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,519評論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至茵瀑,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間竞帽,已是汗流浹背鸿捧。 一陣腳步聲響...
    開封第一講書人閱讀 33,621評論 1 274
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留抱虐,地道東北人饥脑。 一個月前我還...
    沈念sama閱讀 49,099評論 3 378
  • 正文 我出身青樓,卻偏偏與公主長得像谣沸,于是被迫代替她去往敵國和親笋颤。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 45,691評論 2 361

推薦閱讀更多精彩內(nèi)容