图像手绘效果的实现
图像的数组表示
图像一般使用RGB色彩模式,即每个像素点的颜色由红( R)、绿(G)、蓝(B)组成。
RGB三个颜色通道的变化和叠加得到各种颜色,其中
- R 红色,取值范围,0‐255
- G 绿色,取值范围,0‐255
- B 蓝色,取值范围,0‐255
RGB形成的颜色包括了人类视力所能感知的所有颜色。
PIL库是一个具有强大图像处理能力的第三方库
在命令行下的安装方法: pip install pillow
from PIL import Image
Image是PIL库中代表一个图像的类(对象)
In [1]: from PIL import Image
In [2]: import numpy as np
In [3]: im = np.array(Image.open('d:/ylde.png'))
In [4]: print(im.shape,im.dtype)
(1080, 1920, 3) uint8
图像是一个三维数组,维度分别是高度、宽度和像素RGB值
图像的变换
图像RGB3通道补值(负片)(最大值255 - 原值):
In [6]: b = [255,255,255] - im
In [7]: im1 = Image.fromarray(b.astype('uint8'))
In [8]: im1.save('d:/ylde1.png')
convert('L')
将彩色图变为灰度值图,RGB变为灰度值(二维):
In [8]: im1.save('d:/ylde1.png')
In [9]: c = np.array(Image.open('d:/ylde.png').convert('L'))
In [10]: d = 255 - c # 底片
In [11]: im = Image.fromarray(d.astype('uint8'))
In [12]: im.save('d:/ylde2.png')
灰度值进行区间压缩:
In [13]: e = (100/255)*c + 150 # 区间变换
In [14]: im = Image.fromarray(e.astype('uint8'))
In [15]: im.save('d:/ylde3.png')
像素平方:
In [16]: f = 255*(c/255)**2 # 像素平方
In [17]: im = Image.fromarray(f.astype('uint8'))
In [18]: im.save('d:/ylde4.png')
图像的手绘效果
灰度即图像的明暗变化,梯度值grad
表示灰度的变化率,故可以通过调整像素梯度值改变其明暗变化。
立体效果由添加虚拟深度值depth
实现。可通过调节depth
改变手绘深浅。
模拟虚拟光源,计算角度
from PIL import Image
import numpy as np
a = np.asarray(Image.open('d:/ylde.png').convert('L')).astype('float')
depth = 10. # (0-100)
grad = np.gradient(a) #取图像灰度的梯度值
grad_x, grad_y = grad #grad是数据对,将其分别赋给gradx,grady(分别取横纵图像梯度值)
grad_x = grad_x*depth/100. # 添加深度对于灰度的影响,归一化
grad_y = grad_y*depth/100.
A = np.sqrt(grad_x**2 + grad_y**2 + 1.)
uni_x = grad_x/A
uni_y = grad_y/A
uni_z = 1./A
vec_el = np.pi/2.2 # 光源的俯视角度,弧度值
vec_az = np.pi/4. # 光源的方位角度,弧度值
dx = np.cos(vec_el)*np.cos(vec_az) #光源对x 轴的影响
dy = np.cos(vec_el)*np.sin(vec_az) #光源对y 轴的影响
dz = np.sin(vec_el) #光源对z 轴的影响
b = 255*(dx*uni_x + dy*uni_y + dz*uni_z) #光源归一化
b = b.clip(0,255) # 避免越界
im = Image.fromarray(b.astype('uint8')) #重构图像
im.save('d:/ylde_fin.png')