OpenCV-Python實(shí)現(xiàn)懷舊濾鏡與連環(huán)畫(huà)濾鏡
懷舊濾鏡實(shí)現(xiàn)原理
不管是榮耀華為手機(jī)還是其他的手機(jī),我們都可以找到相機(jī)中的懷舊效果,這是手機(jī)中常用的一種濾鏡效果。
懷舊風(fēng)格的設(shè)計(jì)主要是在圖像的顏色空間進(jìn)行處理。以BGR為例,對(duì)B、G、R這3個(gè)通道的顏色數(shù)值進(jìn)行處理,讓圖像有一種泛黃的懷舊效果。設(shè)計(jì)的轉(zhuǎn)換公式如下:
B=0.272r+0.534g+0.131*b
G=0.349r+0.686g+0.168*b
R=0.393r+0.769g+0.189*b
計(jì)算公式中的小寫(xiě)的bgr是原圖像的RGB通道的顏色,結(jié)果BGR是懷舊變換后的值。需要注意的是,顏色值的范圍在[0,255],需要在程序中約束一下。
實(shí)現(xiàn)懷舊濾鏡
既然我們已經(jīng)了解了其實(shí)現(xiàn)的原理公式。下面我們直接上代碼實(shí)現(xiàn)該功能,具體代碼如下所示:
def cowboy_effect(img): new_img = img.copy() h, w, n = img.shape for i in range(w): for j in range(h): b = img[j, i, 0] g = img[j, i, 1] r = img[j, i, 2] B = int(0.272 * r + 0.534 * g + 0.131 * b) G = int(0.349 * r + 0.686 * g + 0.168 * b) R = int(0.393 * r + 0.769 * g + 0.189 * b) new_img[j, i, 0] = max(0, min(B, 255)) new_img[j, i, 1] = max(0, min(G, 255)) new_img[j, i, 2] = max(0, min(R, 255)) return new_img if __name__ == "__main__": img = cv2.imread("48.jpg") cv2.imshow("0", img) cv2.imshow("1", cowboy_effect(img)) cv2.waitKey() cv2.destroyAllWindows()
運(yùn)行之后,效果如下:
連環(huán)畫(huà)濾鏡原理
從懷舊濾鏡就可以看出來(lái),其實(shí)相機(jī)的各種濾鏡效果就是對(duì)RGB的顏色通道進(jìn)行計(jì)算處理。既然懷舊濾鏡有公式,那么肯定的連環(huán)畫(huà)濾鏡也有公式。它的具體公式如下:
R = |g – b + g + r| * r / 256
G = |b – g + b + r| * r / 256
B = |b – g + b + r| * g / 256
實(shí)現(xiàn)連環(huán)畫(huà)濾鏡
有了公式,下面直接套用公式即可。具體代碼如下所示:
# 連環(huán)畫(huà)濾鏡 def comics_effect(img): new_img = img.copy() h, w, n = img.shape for i in range(w): for j in range(h): b = img[j, i, 0] g = img[j, i, 1] r = img[j, i, 2] R = int(int(abs(g - b + g + r)) * r / 256) G = int(int(abs(b - g + b + r)) * r / 256) B = int(int(abs(b - g + b + r)) * g / 256) new_img[j, i, 0] = R new_img[j, i, 1] = G new_img[j, i, 2] = B return new_img if __name__ == "__main__": img = cv2.imread("48.jpg") cv2.imshow("0", img) cv2.imshow("1", comics_effect(img)) cv2.waitKey() cv2.destroyAllWindows()
運(yùn)行之后,效果如下:
綜上所述,基本上所有的基礎(chǔ)濾鏡都是通過(guò)對(duì)RGB通道的顏色值進(jìn)行公式計(jì)算得到的。當(dāng)然,要是數(shù)學(xué)很好,又對(duì)算法情有獨(dú)鐘的讀者,可以自己自研濾鏡算法豐富濾鏡的效果。
熔鑄算法
r = r*128/(g+b +1);
g = g*128/(r+b +1);
b = b*128/(g+r +1);
冰凍算法
r = (r-g-b)*3/2;
g = (g-r-b)*3/2;
b = (b-g-r)*3/2;
#include <math.h> #include <opencv/cv.h> #include <opencv/highgui.h> #define MAXSIZE (32768) using namespace cv; using namespace std; void casting(const Mat& src) { Mat img; src.copyTo(img); int width=src.cols; int heigh=src.rows; Mat dst(img.size(),CV_8UC3); for (int y=0;y<heigh;y++) { uchar* imgP=img.ptr<uchar>(y); uchar* dstP=dst.ptr<uchar>(y); for (int x=0;x<width;x++) { float b0=imgP[3*x]; float g0=imgP[3*x+1]; float r0=imgP[3*x+2]; float b = b0*255/(g0+r0+1); float g = g0*255/(b0+r0+1); float r = r0*255/(g0+b0+1); r = (r>255 ? 255 : (r<0? 0 : r)); g = (g>255 ? 255 : (g<0? 0 : g)); b = (b>255 ? 255 : (b<0? 0 : b)); dstP[3*x] = (uchar)b; dstP[3*x+1] = (uchar)g; dstP[3*x+2] = (uchar)r; } } imshow("熔鑄",dst); imwrite("D:/img/熔鑄.jpg",dst); } void freezing(const Mat& src) { Mat img; src.copyTo(img); int width=src.cols; int heigh=src.rows; Mat dst(img.size(),CV_8UC3); for (int y=0;y<heigh;y++) { uchar* imgP=img.ptr<uchar>(y); uchar* dstP=dst.ptr<uchar>(y); for (int x=0;x<width;x++) { float b0=imgP[3*x]; float g0=imgP[3*x+1]; float r0=imgP[3*x+2]; float b = (b0-g0-r0)*3/2; float g = (g0-b0-r0)*3/2; float r = (r0-g0-b0)*3/2; r = (r>255 ? 255 : (r<0? -r : r)); g = (g>255 ? 255 : (g<0? -g : g)); b = (b>255 ? 255 : (b<0? -b : b)); // r = (r>255 ? 255 : (r<0? 0 : r)); // g = (g>255 ? 255 : (g<0? 0 : g)); // b = (b>255 ? 255 : (b<0? 0 : b)); dstP[3*x] = (uchar)b; dstP[3*x+1] = (uchar)g; dstP[3*x+2] = (uchar)r; } } imwrite("D:/img/冰凍.jpg",dst); } int main() { Mat src = imread("D:/img/scene04.jpg",1); imshow("src",src); casting(src); freezing(src); waitKey(); }
到此這篇關(guān)于OpenCV-Python實(shí)現(xiàn)懷舊濾鏡與連環(huán)畫(huà)濾鏡的文章就介紹到這了,更多相關(guān)OpenCV 懷舊濾鏡與連環(huán)畫(huà)濾鏡內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
python中實(shí)現(xiàn)根據(jù)坐標(biāo)點(diǎn)位置求方位角
這篇文章主要介紹了python中實(shí)現(xiàn)根據(jù)坐標(biāo)點(diǎn)位置求方位角方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-08-08關(guān)于Python可視化Dash工具之plotly基本圖形示例詳解
這篇文章主要介紹了關(guān)于Python可視化Dash工具之plotly基本圖形示例詳解,需要的朋友可以參考下2021-03-03淺談python內(nèi)置變量-reversed(seq)
下面小編就為大家?guī)?lái)一篇淺談python內(nèi)置變量-reversed(seq)。小編覺(jué)得挺不錯(cuò)的?,F(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2017-06-06python GUI庫(kù)圖形界面開(kāi)發(fā)之PyQt5窗口布局控件QStackedWidget詳細(xì)使用方法
這篇文章主要介紹了python GUI庫(kù)圖形界面開(kāi)發(fā)之PyQt5窗口布局控件QStackedWidget詳細(xì)使用方法,需要的朋友可以參考下2020-02-02Python實(shí)現(xiàn)前端樣式尺寸單位轉(zhuǎn)換
在?Web?前端項(xiàng)目開(kāi)發(fā)時(shí),樣式尺寸都是以?rpx?為單位,可是?UI?設(shè)計(jì)師在看完開(kāi)發(fā)后的?UI?,卻要求都以?px?為單位,所以本文就和大家分享一個(gè)利用Python就能實(shí)現(xiàn)尺寸單位轉(zhuǎn)換的方法吧2023-06-06