IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 人工智能 -> OpenCV-Python实战(1) —— 给图片添加图片水印【利用 OpenCV 像素的读写原理实现】 -> 正文阅读

[人工智能]OpenCV-Python实战(1) —— 给图片添加图片水印【利用 OpenCV 像素的读写原理实现】

1. 需求分析

  1. 使用 OpenCV 图像像素读写操作原理,也就是 image[row][col] 获取和设值;
  2. 给图片添加水印:对应添加水印的位置,设置为水印图片的像素;
  3. 水印下能看到原图,也就是说水印必须是透明图片;
  4. 同时将水印透明位置像素(0,0,0)改变为同位置的图片的像素。

2. 直接将水印添加到图片

2.1 代码逻辑分析

  1. 读取水印logo图片;
  2. 读取需要添加水印的图片;
  3. 获取水印的宽高; 注意:此处水印使用的三通道读取,因此获取水印属性时需要加通道值。
  4. 利用图像像素读取设值原理,直接修改对应像素为水印像素;
  5. 注意:此处默认直接从坐标(0,0)开始直接修改【需要添加水印的图片】,如果其他位置,需要获取【需要添加水印的图片】的宽高等属性
  6. 显示添加水印后的图像。

2.2 代码实现

import cv2 as cv

def add_logo_to_img():
  # 水印logo图片
  logo = cv.imread('./images/opencv-logo-white.png')
  # 需要添加水印的图片
  img = cv.imread('./images/messi5.jpg')
  # 获取水印的宽高,注意此处水印使用的三通道读取,因此获取水印属性时需要加通道值
  h,w,c = logo.shape
  # 利用图像像素读取设值原理,直接修改对应像素为水印像素
  img[:h,:w] = logo
  # 显示添加水印后的图像
  cv.imshow('add_logo', img)
  cv.waitKey(0)
  cv.destroyAllWindows()

if __name__ == "__main__":
  add_logo_to_img()

2.3 实现结果

2.4 注意

  1. 此处水印使用的三通道读取,因此获取水印属性时需要加通道值。
  2. 注意:此处默认直接从坐标(0,0)开始直接修改。
  3. 此处的水印图片是透明的水印图片,因此加上水印后会看到水印周边很多黑色。
  4. 水印图片的宽高比原图尺寸小。

2.5 非透明水印添加代码

import cv2 as cv

def add_logo_to_img():
  # 水印logo图片
  logo = cv.imread('./images/butterfly-mall.jpg')
  # 需要添加水印的图片
  img = cv.imread('./images/messi5.jpg')
  # 获取水印的宽高,注意此处水印使用的三通道读取,因此获取水印属性时需要加通道值
  h,w,c = logo.shape
  # 利用图像像素读取设值原理,直接修改对应像素为水印像素
  img[:h,:w] = logo
  # 显示添加水印后的图像
  cv.imshow('add_logo', img)
  cv.waitKey(0)
  cv.destroyAllWindows()

if __name__ == "__main__":
  add_logo_to_img()

2.5 非透明水印添加结果

3. 遍历像素添加水印

3.1 代码逻辑分析

  1. 读取水印logo图片;
  2. 读取需要添加水印的图片;
  3. 获取水印的宽高; 注意:此处水印使用的三通道读取,因此获取水印属性时需要加通道值。
  4. 利用图像像素读取设值原理,直接修改对应像素为水印像素;
  5. 遍历 logo 的像素,发现像素值是黑色(0,0,0)就替换为对应的原图像素【反之就是logo像素不是黑色的位置直接赋值给原图】;
  6. 注意:此处默认直接从坐标(0,0)开始直接修改【需要添加水印的图片】,如果其他位置,需要获取【需要添加水印的图片】的宽高等属性
  7. 显示添加水印后的图像。

3.2 代码实现

def add_logo_to_img():
  # 水印logo图片
  logo = cv.imread('./images/opencv-logo-white.png')
  # 需要添加水印的图片
  img = cv.imread('./images/messi5.jpg')
  # 获取水印的宽高,注意此处水印使用的三通道读取,因此获取水印属性时需要加通道值
  h,w,c = logo.shape
  # 利用图像像素读取设值原理,直接修改对应像素为水印像素
  # 遍历 logo 的像素,发现像素值是黑色(0,0,0)就替换为对应的原图像素【反之就是logo像素不是黑色的位置直接赋值给原图】
  for row in range(h):
    for col in range(w):
      b,g,r = logo[row][col]
      if b != 0 or g != 0 or r != 0:
        img[row][col] = (b,g,r)
  
  # 显示添加水印后的图像
  cv.imshow('add_logo', img)
  cv.waitKey(0)
  cv.destroyAllWindows()

if __name__ == "__main__":
  add_logo_to_img()

3.3 实现结果

4. 改变水印的位置【居中】

4.1 代码逻辑分析

  1. 在原来的基础上【获取原图的宽高属性】;
  2. 计算水印居中时的其实坐标;
  3. 修改像素值时,加上起始坐标的值,才是改变对应原图的像素坐标。

4.2 代码实现

import cv2 as cv

def add_logo_to_img():
  # 水印logo图片
  logo = cv.imread('./images/opencv-logo-white.png')
  # 需要添加水印的图片
  img = cv.imread('./images/messi5.jpg')
  # 获取水印的宽高,注意此处水印使用的三通道读取,因此获取水印属性时需要加通道值
  h,w,c = logo.shape
  # 获取原图的宽高属性
  mh,mw,mc = img.shape
  # 计算水印居中时的其实坐标
  y = int((mh - h) / 2)
  x = int((mw - w) / 2)
  # 利用图像像素读取设值原理,直接修改对应像素为水印像素
  # 遍历 logo 的像素,发现像素值是黑色(0,0,0)就替换为对应的原图像素【反之就是logo像素不是黑色的位置直接赋值给原图】
  for row in range(h):
    for col in range(w):
      b,g,r = logo[row][col]
      if b != 0 or g != 0 or r != 0:
        img[row + y][col + x] = (b,g,r)
  
  # 显示添加水印后的图像
  cv.imshow('add_logo', img)
  cv.waitKey(0)
  cv.destroyAllWindows()

if __name__ == "__main__":
  add_logo_to_img()

4.3 实现结果

5. 使用整体法实现水印的位置的改变

5.1 代码逻辑分析

  1. 在第四步的基础上添加【截取添加水印位置和水印等大的图像】;
  2. 此时截取图像和水印图像大小一致;
  3. 直接使用第二步的方法,直接修改这个大小一致的截取图像,此处的方便在于不用遍历的时候每次都需要计算修改的位置
  4. 将修改后的截取图像还原回原图像;
  5. 实现添加水印效果。

5.2 实现代码

import cv2 as cv

def add_logo_to_img():
  # 水印logo图片
  logo = cv.imread('./images/opencv-logo-white.png')
  # 需要添加水印的图片
  img = cv.imread('./images/messi5.jpg')
  # 获取水印的宽高,注意此处水印使用的三通道读取,因此获取水印属性时需要加通道值
  h,w,c = logo.shape
  # 获取原图的宽高属性
  mh,mw,mc = img.shape
  # 计算水印居中时的其实坐标
  y = int((mh - h) / 2)
  x = int((mw - w) / 2)
  # 截取和水印大小等同的原图需要改变位置的图像
  change_img = img[y:y+h,x:x+w]
  # 显示添加水印位置的截取图像
  cv.imshow('change_img', change_img)
  # 修改截取图片
  # 利用图像像素读取设值原理,直接修改对应像素为水印像素
  # 遍历 logo 的像素,发现像素值是黑色(0,0,0)就替换为对应的原图像素【反之就是logo像素不是黑色的位置直接赋值给原图】
  for row in range(h):
    for col in range(w):
      b,g,r = logo[row][col]
      if b != 0 or g != 0 or r != 0:
        change_img[row][col] = (b,g,r)
  # 显示截取图像添加水印后的效果
  cv.imshow('change_img_add_logo', change_img)
  # 将截取的图片还原到截取位置
  img[y:y+h,x:x+w] = change_img
  # 显示添加水印后的图像
  cv.imshow('add_logo', img)
  cv.waitKey(0)
  cv.destroyAllWindows()

if __name__ == "__main__":
  add_logo_to_img()

5.3 实现结果

6. 总结

  1. 本篇文章是学习【图像像素读写操作】的实战实现;
  2. 文章还差水印文字的实现,水印图片大小的改变实现,在后续文章中学到了依旧会使用到开发实例中;
  3. 注意本文章都没有考虑图片的超出限制,如果是需要logo的部分等操作,需要另行操作;
  4. 注意本文章没有使用cv的其他二值处理等函数处理水印,所以水印最好是透明背景的图片,或者是纯色背景,方便获取背景的像素值。
  人工智能 最新文章
2022吴恩达机器学习课程——第二课(神经网
第十五章 规则学习
FixMatch: Simplifying Semi-Supervised Le
数据挖掘Java——Kmeans算法的实现
大脑皮层的分割方法
【翻译】GPT-3是如何工作的
论文笔记:TEACHTEXT: CrossModal Generaliz
python从零学(六)
详解Python 3.x 导入(import)
【答读者问27】backtrader不支持最新版本的
上一篇文章      下一篇文章      查看所有文章
加:2022-10-22 21:15:35  更:2022-10-22 21:15:51 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/25 20:30:58-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码