前两天看到篇介绍英伟达StyleGAN生成逼真假脸的文章,其源码正是通过Python和Tensorflow实现的,利用AI生成并不存在的头像图,来感受下:
而提到假脸,各位老司机们的第一反应想必是诸多小片中的人工智能明星换脸,比如:
声明:上图是文章写作为目的,某Pxxxhub所得
那么今天,我们就用Python自己手动搞一个换脸代码,先定个小目标,能达到下图这个水平就OK了:
再次声明:只截了这两张图,再无其他
在琢磨Python换脸代码时,很容易就溯源到一份2015年在GitHub上开源的faceswap代码,试运行之后效果只能说还可以,不如预期,这里我们并不采用。
当然,不采用此份代码的最主要原因,还是它涉及的算法太复杂,看不懂!所以理直气壮,一定要自己写一份换脸的代码,通俗易懂地来把这事儿办了。
思路
还是先利用之前提过的Python面部识别模块dlib,识别并获取目标的脸部图像信息,之后通过opencv这个计算机视觉库,来进行图像处理和计算机视觉方面的调整。
为求思路简单直接,我们就用长方形截取眼睛区域,将其缩放贴图到对应新脸上,如图:
那么接下来就是解决新脸上颜色和融合效果。在一步步试验中,最终我选择了将眼睛区域继续拆分成左眼、右眼区,由于鼻子实在不好处理,忽略掉,再额外加上嘴巴区域进行换脸。
以下是效果图:
互换眼睛和嘴巴后:
有点惨不忍睹,全靠二位颜值支撑。。。暂且把这份代码定义为1.0版本吧,后续继续改进更新,毕竟学艺不精。。。
获取脸部信息
运行代码时,要将后缀为.dat文件置于代码文件夹内,该文件是dlib用于面部识别的必要文件:
img = cv2.imread(f"{img_src}.jpg") gray = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY) detector = dlib.get_frontal_face_detector() predictor = dlib.shape_predictor("shape_predictor_68_face_landmarks.dat") faces = detector(gray)
之后根据dlib面部识别的点位图:
将左右眼和嘴巴按矩形区域划分截取:
#右眼睛区域左上角点(x,y),右下角点(x0,y0) x, y, x0, y0 = landmarks.part(42).x - 5, min(landmarks.part(43).y, landmarks.part(44).y) - 5, landmarks.part(45).x 5, max(landmarks.part(46).y, landmarks.part(47).y) 5 #左眼睛区域左上角点(x1,y1),右下角点(x2,y2) x1,y1,x2,y2 = landmarks.part(36).x-5,min(landmarks.part(37).y,landmarks.part(38).y)-5,landmarks.part(39).x 5,max(landmarks.part(40).y,landmarks.part(41).y) 5 # 嘴巴区域左上角点(x3,y3),右下角点(x4,y4) x3, y3, x4, y4 = landmarks.part(48).x-5, min(landmarks.part(50).y,landmarks.part(52).y)-5, landmarks.part(54).x 5,landmarks.part(57).y 5
对要换脸的两张人物图片同时处理,获取到其眼睛、嘴巴的局部信息和尺寸数据,接下来,进行无缝融合。
脸部融合拼接
都说Python简单、强大,体现在哪呢?体现在只用opencv的一行命令即可实现融合效果:
normal_clone = cv2.seamlessClone(obj, im, mask, center, cv2.NORMAL_CLONE)
这里用到的是opencv中图像融合相关的seamlessClone泊松融合函数。是为了解决最初眼睛贴图后肤色不一致、有明显矩形边界等问题,特地搜索来的神奇函数。
有了脸部融合的简易算法,余下就是生产新图片等基础问题了。
回顾
说起来虽然简单,真实施还是有些繁琐的,涉及到许多图片信息问题,我也是能避就避,留作之后深入研究。
而我的代码思路也由最初改造源码,发现难以下手后,改成了用矩形截取面部局部,根据融合效果,继续将区域分割成较容易处理的眼睛和嘴巴,相应地进行脸部局部融合。虽然最终效果远不及预期,但能完整地完成计划的要求这一点还是挺满足的。
最后再放两张用GitHub上开源代码faceswap做的换脸图,男主仍是胡歌,女主大家可以猜一下:
女主:
代码下载
后台回复 换脸 获取代码下载,除自写代码外也包含文中提到的GitHub开源faceswap代码,已做过修改可直接执行测试~
如果觉着还不错,点个好看呗,这将是对我最大的肯定,感谢!