使用Python PIL 给图片添加水印
我们做网站,做公众号经常会使用到很多图片,很多图片是我们自己原创的。为了不让人盗图,我们常做的操作是加水印。当然公众号可以打官方的水印,wordpress网站可以用一些插件来实现打水印的目的。如果不使用这两种方式,我们可能会使用PS等图片编辑软件来添加水印,但是感觉为了打个水印打开这些软件似乎让人心累(谁让咱这么懒呢~),所以这里给大家用Python实现这个功能,下来也就20行代码不到。先来看看水印的效果:
这里水印分成文字水印和图片水印,这里首先介绍文字水印。当然完成这一切的前提是你安装了Python的PIL库(或者Pillow也是可以的)。
1.文字水印
话不多说,直接上代码:
from PIL import Image,ImageDraw,ImageFont
image = Image.open('lifeistoshort.jpg')
# 打开要加水印的图片
text=input('输入你的水印文字:\n')
# 提示要打水印的文字
font=ImageFont.truetype('C:\Windows\Fonts\simhei.ttf',64)
# 获得一个字体,你也可以自己下载相应字体,第二个值是字体大小
layer=image.convert('RGBA')
# 将图片转换为RGBA图片
text_overlay=Image.new('RGBA',layer.size)
# 依照目标图片大小生成一张新的图片 参数[模式,尺寸,颜色(默认为0)]
image_draw=ImageDraw.Draw(text_overlay)
# 画图
text_size_x,text_size_y=image_draw.textsize(text,font=font)
# 获得字体大小,textsize(text, font=None)
text_xy=(layer.size[0]-text_size_x,layer.size[1]-text_size_y)
# 设置文本位置 此处是右下角显示
image_draw.text(text_xy, text, font=font, fill=(0, 0, 0, 85))
# 设置文字,位置,字体,颜色和透明度
marked_img=Image.alpha_composite(layer,text_overlay)
# 将水印打到原图片上生成新的图片
marked_img.save('qingwei_after.png')
# 保存图片
marked_img.show()
# 显示图片(这里是生成一个临时文件,必须关闭图片 这段py代码才算结束)
对于水印的字体、颜色、文字等设置相信你看了注释也知道在哪里调整,例如对于位置的调节:
text_xy=(layer.size[0]-text_size_x,layer.size[1]-text_size_y) # 设置文本位置 此处是右下角显示 text_xy = (layer.size[0]//2-text_size_x//2, layer.size[1]-text_size_y) # 设置文本位置 此处是下方居中显示 text_xy = (0, layer.size[1]-text_size_y) # 设置文本位置 此处是左下角下角显示 text_xy=(layer.size[0]-text_size_x,0) # 设置文本位置 此处是右上角显示 text_xy=(0,0) # 设置文本位置 此处是左上角角显示 text_xy = (layer.size[0]//2-text_size_x//2, layer.size[1]//2-text_size_y//2) # 设置文本位置 此处是居中显示
当然,我们可以改进下,可以循环获得指定目录下所有图片文件,然后批量添加水印,下面是简单改进版代码:
from PIL import Image,ImageDraw,ImageFont import os def watermark(text,filename,savepath): ''' 给图片加文字水印 text 水印文字 String filename 图片名称 String savepath 保存路径 String ''' if not os.path.exists(savepath): os.makedirs(savepath) # 检查保存文件夹是否存在,如果不存在则生成一个 image = Image.open(filename) # 打开要加水印的图片 font=ImageFont.truetype('C:\Windows\Fonts\simhei.ttf',64) # 获得一个字体,你也可以自己下载相应字体,第二个值是字体大小 layer=image.convert('RGBA') # 将图片转换为RGBA text_overlay=Image.new('RGBA',layer.size) # 依照目标图片大小生成一张新的图片 参数[模式,尺寸,颜色(默认为0)] image_draw=ImageDraw.Draw(text_overlay) # 画图 text_size_x,text_size_y=image_draw.textsize(text,font=font) # 获得字体大小,textsize(text, font=None) text_xy=(layer.size[0]-text_size_x,layer.size[1]-text_size_y) # 设置文本位置 此处是右下角显示 image_draw.text(text_xy, text, font=font, fill=(0, 0, 0, 85)) # 设置文字,位置,字体,颜色和透明度 marked_img=Image.alpha_composite(layer,text_overlay) # 将水印打到原图片上生成新的图片 marked_img.save(savepath+'\\'+filename[filename.rfind("\\")+1:filename.rfind(".")]+".png") # 保存图片 def all_path(dirname, filters): ''' 获取路径下所有文件名称(完整路径) dirname 路径名 String filters 过滤文件类型 Array ''' result = [] # 所有的文件 for maindir, subdir, file_name_list in os.walk(dirname): # maindir 当前主目录 # subdir 当前主目录下的所有目录 # file_name_list 当前主目录下的所有文件 for filename in file_name_list: apath = os.path.join(maindir, filename) # 合并成一个完整路径 ext = os.path.splitext(apath)[1] # 获取文件后缀 [0]获取的是除了文件名以外的内容 if ext in filters: result.append(apath) return result filters = [".jpg", ".jpeg", ".png"] # 设置过滤后的文件类型 path = all_path("D:\mytest", filters) text = input('输入你的水印文字:\n') for name in path: watermark(text,name, "D:\\watermark") print('Done!')
2.图片水印
这个就更简单了,也就十行代码左右,代码如下:
from PIL import Image image = Image.open('lifeistoshort.jpg') # 打开等待加水印的图片 watermark = Image.open('qrcode.jpg') # 打开水印图片 factor = 0.5 # 如果觉得水印图片太大,可以缩放,这里缩放比例为50% watermark = watermark.resize( tuple(map(lambda x: int(x * factor), watermark.size))) # 缩放图片 layer=Image.new('RGBA',image.size) # 生成一个新的layer layer.paste(watermark,(image.size[0]-watermark.size[0], image.size[1]-watermark.size[1])) # 把水印打到新的layer上去,后面参数是水印位置,此处是右下角 marked_img=Image.composite(layer,image,layer) # 添加水印 # marked_img.show()# 打开生成的图片(缓存图片) marked_img.save('maked_lifeistoshort_1.jpg') # 保存图片
当然,我们依旧来一个批量打水印的版本,代码如下:
from PIL import Image import os def watermark(mark, path, savepath): ''' 给图片加文字水印 mark 水印文字 String path 图片名称 String savepath 保存路径 String ''' image = Image.open(path) # 打开等待加水印的图片 watermark = Image.open(mark) # 打开水印图片 factor = 0.5 # 如果觉得水印图片太大,可以缩放,这里缩放比例为50% watermark = watermark.resize( tuple(map(lambda x: int(x * factor), watermark.size))) # 缩放图片 layer=Image.new('RGBA',image.size) # 生成一个新的layer layer.paste(watermark,(image.size[0]-watermark.size[0], image.size[1]-watermark.size[1])) # 把水印打到新的layer上去,后面参数是水印位置,此处是右下角 # 更多位置参考上面的代码 marked_img=Image.composite(layer,image,layer) # 添加水印 # marked_img.show()# 打开生成的图片(缓存图片) marked_img.save(savepath+'\\'+path[path.rfind("\\")+ 1:]) # 保存图片 def all_path(dirname, filters): ''' 获取路径下所有文件名称(完整路径) dirname 路径名 String filters 过滤文件类型 Array ''' result = [] # 所有的文件 for maindir, subdir, file_name_list in os.walk(dirname): # maindir 当前主目录 # subdir 当前主目录下的所有目录 # file_name_list 当前主目录下的所有文件 for filename in file_name_list: apath = os.path.join(maindir, filename) # 合并成一个完整路径 ext = os.path.splitext(apath)[1] # 获取文件后缀 [0]获取的是除了文件名以外的内容 if ext in filters: result.append(apath) return result filters = [".jpg", ".jpeg", ".png"] # 设置过滤后的文件类型 path = all_path("D:\mytest", filters) mark='qrcode.jpg' for name in path: watermark(mark, name, "D:\\watermark") print('Done!')
有了这些代码你要做的只是把图片和水印放到相应位置,让后打开你的命令行,Python 一下,水印就轻松打上了,是不是很爽。水平有限,请多多指教~
人生苦短,我用Python 。
喜欢这篇文章的话可以扫描下方二维码支持我
版权声明:
作者:Kiwi
链接:https://www.qingwei.tech/programe-develops/1154.html
来源:清渭技术小站
文章版权归作者所有,未经允许请勿转载。
取昵称好麻烦
可以,如果加上图形界面就更好了 :biggrin: