騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

開端

最近遇到了一個需求,就是對圖片進行色彩風格轉換,讓一個物體可以以各種不同的色彩來呈現。

比如一個紅色的蘋果,我想把它轉化成綠色,這可怎麼辦呢?本來想的解決方案是先識別邊界,然後對邊界內區域進行色彩替換或者填充,這樣整個流程就分成了兩步,首先需要進行邊界判斷,有了邊界之後才能對某些區域顏色進行替換填充,填充的區域還是不規則的,填充的顏色也需要根據實際的情況來變化,同時還要兼顧陰影、高光等等的處理,想想真是頭大。

然後我就突然想到了之前學 PS 的時候,曾經做過對某一張圖片進行色調替換,我還記得當時調的內容是「色相」,通過調節這個值可以實現各種色調的轉換。這之後我就心想,能不能用程序來做這件事呢?

於是我就開始了對圖像色彩的一些研究,研究完了之後就實現了用 Python 來更換圖片色調的功能,將這篇文章順便記錄下來。

先給大家看看效果吧,就比如我從百度上隨便搜一張圖,比如熱氣球吧,是這樣子

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

原圖

我把它轉成紅色、黃色、藍色、紫色,基本就是這個樣子:

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

紅色風格

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

黃色風格

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

綠色風格

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

藍色風格

這裡的圖片都是經過 Python 自動轉換算法實現的,主要調節的就是色相。其實代碼實現是比較簡單的,但在實現之前需要了解一些圖像色彩知識。瞭解了這些之後我們再實現才會更加遊刃有餘。

下面我們就首先來了解一下圖像色彩的基本知識,然後用 Python 實現色調轉換算法吧。

RGB

首先讓我們來了解下顏色的三原色,RGB。

RGB,其實就是三種顏色,分別代表紅色(Red)、綠色(Green)、藍色(Blue),用這三種原色顏色混合可以表示任意的顏色。RGB 是根據顏色發光的原理來設計的,比如這裡有紅綠藍三道光,當三束光混合在一起的時候,其呈現的最終的光效顏色就取決於這三種原色光的強弱了。

• 比如說紅光最強,綠光和藍光幾乎沒有,那麼最後結果肯定呈現為紅光了。 • 如果藍光很弱,紅光和綠光非常強,那麼結果就是紅光和綠光的混合光,也就黃光。 • 如果紅綠藍三種光都非常強,那麼就會呈現三種光的混合光,也就是白光。 • 如果三種光都非常弱,那就幾乎沒有光,自然就是黑色了。

如果大家瞭解過 RGB 的一些知識的話,想必也見過這張混合光圖:

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

但是這僅僅是一張平面圖,並不能很好地體現三原色的混合關係,大家可以看這張圖:

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

實際上可以對 RGB 色值建立一個三維座標系,座標原點就在上圖中所看不見的那個正方體頂點,像左延伸為 R 紅色軸,向右延伸為 B 藍色軸,向上延伸為 G 綠色軸。

RGB 在進行色彩表示時使用了 256 階,也就是從 0-255,可以由一個字節來表示。數值越大,RGB 三個軸,每個軸對應的數值越大,就代表其亮度越高,最亮就對應著 255,最暗就對應著 0。三個軸上的三個數字聯合起來可以用來表示一個顏色。

例如:

• (255, 255, 255) 就代表 RGB 都是滿的,組成白色。 • (255, 255, 0) 就代表 R 紅色是滿的,G 綠色是滿的,B 藍色是沒有的,紅色和綠色混合為黃色,所以它就表示黃色。 • (0, 0, 0) 就代表 RGB 都是沒有的,呈現黑色。

因此,通過這三個數值,我們就可以實現任何顏色的表示了。

HSV

但瞭解了 RGB 顯然不能應對我們的需求,它和色相也沒有什麼關係,所以這裡我們還需要研究另外一個顏色模型,叫做 HSV。

HSV,又叫做 HSB,其實也是三個參數,分別是色調(Hue)、飽和度(Saturation)、明度(Brightness),在 HSV 中 V 代表 Value,也是明度的意思。通過這三個值,我們同樣可以表示任意的顏色。

首先我們看看 HSV (HSB) 顏色模型的座標軸圖吧,它可以用這麼一個錐形的座標來表示:

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

色調,Hue,它是一種角度度量,就是圖中 Hue 所示的角度,繞圓錐體一週。它的值是從紅色開始逆時針方向計算的,紅色是 0,綠色是 120,藍色為 240,形成一個紅綠藍三原色組成的色帶。

飽和度,Saturation,它是圖中 Saturation 所示的方向,由最上面圓的圓心向外擴散。它表示顏色接近光譜色的程度。一種顏色,可以看成是某種光譜色與白色混合的結果。其中光譜色所佔的比例愈大,顏色接近光譜色的程度就愈高,顏色的飽和度也就愈高。飽和度高,顏色則深而豔。光譜色的白光成分為 0,飽和度達到最高。通常取值範圍為 0-100,值越大,顏色越飽和。也就是說圖中,圓心處飽和度為 0,越靠近邊,飽和度越高,最高達到 100。

明度,Brightness,它表示顏色明亮的程度,對於光源色,明度值與發光體的光亮度有關,對於物體色,此值和物體的透射比或反射比有關。通常取值範圍為 0-100,0 對應黑色,100 對應白色。

另外大家如果用到取色板的話,它是這樣子的:

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

你可以看到左邊有個大的矩形,右邊有個豎直的彩虹帶。 由於剛才所說的圓錐座標不好表示,在調色板裡面就把圓錐座標拆成了兩部分。

• 右邊的彩虹帶就可以選擇色調 Hue,拖動彩虹帶的箭頭位置就可以調整 Hue 的值。 • 左邊的正方形就和飽和度 Saturation、明度 Brightness 有關,橫座標表示飽和度 Saturation,縱座標表示 Brightness,從左到右,飽和度 Saturation 變高,從下到上,明度 Brightness 變高。 • 左下角,由於飽和度 Saturation 和明度 Brightness 都為 0,就呈現黑色。 • 左上角,由於飽和度 Saturation 為 0,所以相當於沒有顏色,顏色最淺,但是它的明度 Brightness 達到了最高,所以它就顯示沒有顏色的明度最高的色,即白色。 • 右上角,由於飽和度 Saturation 和明度 Brightness 都為最高,那就顯示最純的 Hue 值。

這也就是 HSB 顏色模型的原理。

同樣地,我們可以用 HSB 的三個值來表示任意的顏色,因此 HSB 也成為表示顏色的基本標準之一。

HSB 和 RGB 的轉換

HSB 和 RGB 都能表示一個顏色,它們之間也是可以相互轉換的,可以一一對應。

他們之間的轉換邏輯這裡就不再專門對其公式展開詳解了,公式總結如下:

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

RGB to HSB

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

HSV to RGB

大家如果感興趣想要研究的話也可以去:https://www.rapidtables.com/convert/color/hsv-to-rgb.html 來了解一下詳情,這裡還有詳細的轉換表格以及實時轉換實現。

另外對於它們之間的轉換算法,很多庫都已經封裝好了。我們可以直接調用,比如 Python 中的 colorsys 模塊,就實現了 rgb_to_hsv 和 hsv_to_rgb 算法,我們也可以直接使用。

色調轉換

瞭解了以上內容之後,我們就可以使用程序來實現色調轉換了。相比我們已經知道應該改什麼內容了,那就是修改 HSV 中的 H 值,通過不同的 H 值我們就可以將圖片轉換為不同的色調了。

具體思路是怎樣的呢:

• 首先獲取圖像每個像素的的 RGB 色值。 • 將 RGB 色值轉化為 HSV 色值。 • 調整 HSV 色值中的 H。 • 將 HSV 色值轉回 RGB 色值。 • 輸出圖像。

一共就是這麼五步,這裡的兩個轉換色值的操作我們就可以藉助於 colorsys 模塊。另外需要安裝一個 pillow 模塊:

pip3 install pillow

安裝完畢之後,我們準備任意一張圖片,然後實現上面的五個步驟。

最終的代碼實現如下:

import
 colorsys
from PIL 
import
Image
# 輸入文件
filename = 'input.jpg'
# 目標色值
target_hue = 0
# 讀入圖片,轉化為 RGB 色值
image = Image.open(filename).convert('
RGB
')
# 將 RGB 色值分離
image.load()
r, g, b = image.split()
result_r, result_g, result_b = [], [], []
# 依次對每個像素點進行處理
for pixel_r, pixel_g, pixel_b in zip(r.getdata(), g.getdata(), b.getdata()):
 # 轉為 HSV 色值
 h, s, v = colorsys.rgb_to_hsv(pixel_r / 255., pixel_b / 255., pixel_g / 255.)
 # 轉回 RGB 色系
 rgb = colorsys.hsv_to_rgb(target_hue, s, v)
 pixel_r, pixel_g, pixel_b = [int(x * 255.) for x in rgb]
 # 每個像素點結果保存
 result_r.append(pixel_r)
 result_g.append(pixel_g)
 result_b.append(pixel_b)
r.putdata(result_r)
g.putdata(result_g)
b.putdata(result_b)
# 合併圖片
image = Image.merge('
RGB
', (r, g, b))
# 輸出圖片
image.save('output.png')

具體的實現在代碼註釋裡面已經很清楚了。

在這裡我們將 target_hue 定義為 0。通過前文我們知道,Hue 為 0 代表紅色,120 代表綠色,240 代表藍色。我們可以自定義 0-355 這 360 個數值,實現不同的色調轉換。

如果想輸出其他顏色的圖片,就把 target_hue 這個值改一下就好了。

看看最後的運行效果,輸入是一張原圖:

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

所以最後的輸出效果就是如下的結果:

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

如果將代碼中的 target_hue 值進行更改,就會呈現不同的顏色風格了,就像文中開頭所示的一樣。

比如把飛豬的 Logo 由黃色變為紅色,都是可以做到的:

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

處理透明像素

上面的算法僅僅考慮了 RGB,如果有些圖包含了透明像素,上面的程序對於透明像素是無法處理的,最後輸出的結果會帶有某種顏色的背景。

對於透明像素的處理,我們可以增加一個維度的值,就是 A,即 Alpha 透明度。

所以使用 RGBA 和 HSV 的轉換我們就可以實現透明像素的處理了,代碼實現如下:

	import colorsys
	from PIL import Image
	
	# 輸入文件
	filename = 'input.png'
	# 目標色值
	target_hue = 0
	
	# 讀入圖片,轉化為 RGB 色值
	image = Image.open(filename).convert('RGBA')
	
	# 將 RGB 色值分離
	image.load()
	r, g, b, a = image.split()
	result_r, result_g, result_b, result_a = [], [], [], []
	# 依次對每個像素點進行處理
	for pixel_r, pixel_g, pixel_b, pixel_a in zip(r.getdata(), g.getdata(), b.getdata(), a.getdata()):
	 # 轉為 HSV 色值
	 h, s, v = colorsys.rgb_to_hsv(pixel_r / 255., pixel_b / 255., pixel_g / 255.)
	 # 轉回 RGB 色系
	 rgb = colorsys.hsv_to_rgb(target_hue, s, v)
	 pixel_r, pixel_g, pixel_b = [int(x * 255.) for x in rgb]
	 # 每個像素點結果保存
	 result_r.append(pixel_r)
	 result_g.append(pixel_g)
	 result_b.append(pixel_b)
	 result_a.append(pixel_a)
	
	r.putdata(result_r)
	g.putdata(result_g)
	b.putdata(result_b)
	a.putdata(result_a)
	
	# 合併圖片
	image = Image.merge('RGBA', (r, g, b, a))
	# 輸出圖片
	image.save('output.png')

在這裡就是增加了對透明像素的處理,在圖像 convert 和 merge 的時候都使用 RGBA 模式,就可以保留原有圖片中的透明像素了。

以上便是使用 Python 程序自動調整色調的實現。

其他應用

另外對於圖像調色的應用還有很多,比如我們可以不直接指定 Hue 的值,而是將 Hue 的值在原來的基礎上增加或減少,則可以實現彩虹變色,如:

原圖是這樣子:

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

經過處理之後我們可以得到這樣的效果:

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

這樣我們使用程序處理出各種風格的好看的照片了,是不是很有意思呢?

大家如果覺得有意思,就快來試試吧~

圖片來源於互聯網公開內容,如有圖片侵權,請聯繫我刪除,謝謝。

喜歡這篇文章的小夥伴可以點贊+收藏+轉發哦~

贈送三本Python機器學習基礎書籍

Python機器學習經典實例—Python語言描述

內容介紹:

在如今這個處處以數據驅動的世界中,機器學習正變得越來越大眾化。它已經被廣泛地應用於不同領域, 如搜索引擎、機器人、無人駕駛汽車等。本書首先通過實用的案例介紹機器學習的基礎知識,然後介紹一 些稍微複雜的機器學習算法,例如支持向量機、極端隨機森林、隱馬爾可夫模型、條件隨機場、深度神經 網絡,等等。

本書是為想用機器學習算法開發應用程序的 Python 程序員準備的。它適合 Python 初學者閱讀,不過熟 悉 Python 編程方法對體驗示例代碼大有裨益。

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

騷操作,小白一眼就能學會的操作,怎麼用Python 給圖片換色

獲取方式

關注小編

私信小編:回覆 Python 即可領取書籍

頭條怎麼私信

點擊頭條,點擊右下角“我的”

在個人界面點擊關注,如果你關注了,點擊“浪小久”就可以了

回覆:pyhon 就可以了 但是你要先關注我哦~


分享到:


相關文章: