使用Python转换图片中的颜色

说明:最近在看梵高的画册,我手上的这本画册(《文森特·梵高》杨建飞 主编)书中说,梵高用的颜料里有不耐久的合成颜料,原本的紫色褪成了我们现在所看到的灰蓝色。于是我想,能不能用程序将画中的颜色还原成原本的紫色。


盛开的桃花,1888年

盛开的桃花

生成图片

首先,写一段代码,用来读取图片,生成一个副本,代码如下:

from PIL import Image, ImageDraw
import numpy as np# 生成转换后的画
def generate_img(in_path, out_path):# 打开图片im = Image.open(in_path)# 生成后的图片大小,使用im.size[0],im.size[1],即原图大小new_im_size = np.array([im.size[0], im.size[1]]).astype(int)# 生成图片的背景颜色bg_color = "black"# 生成图片im_out = Image.new("RGB", tuple(new_im_size), bg_color)# 获取图片的颜色im_color = np.array(im)# 生成图片draw = ImageDraw.Draw(im_out)# 用于统计进度count = 0total_pixels = im.size[0] * im.size[1]# 遍历图片的每个像素点,将颜色填充到新图片中for i in range(im.size[0]):for j in range(im.size[1]):color = tuple(im_color[j, i])draw.point((i, j), fill=color)count += 1print('生成进度:%d%%' % ((count / total_pixels) * 100))# 保存图片im_out.save(out_path)if __name__ == "__main__":in_path = r'C:\Users\10765\Desktop\1.jpg'out_path = r'C:\Users\10765\Desktop\2.jpg'# 读取图片,并将图片中的颜色转换generate_img(in_path, out_path)

运行

在这里插入图片描述

可在桌面上生成一张几乎一模一样大小的图片;

在这里插入图片描述

颜色转换

接着,我们就是对颜色进行处理,也就是上面for循环里的这行代码;

            color = tuple(im_color[j, i])

我们要写一个方法,对这里面的色值进行转换,我的思路是这样的,首先找到紫色和灰蓝色的RGB色值范围,然后对图片中的色值进行判断,如果是在灰蓝色的色值范围内,则对该RGB色值进行映射,映射到紫色的RGB色值范围内。通过问GPT,可知两种颜色的色值范围如下:

  • 紫色:128-255,0-20,128-255;

  • 灰蓝色:100-180,120-200,150-230;

代码如下:

# 色值转换,灰蓝色 => 紫色
def convert_color(gray_blue_rgb):# 灰蓝色范围gray_blue_range = [(100, 180), (120, 200), (150, 230)]# 紫色范围violet_range = [(128, 255), (0, 20), (128, 255)]# 检查输入的 RGB 值是否在灰蓝色范围内for i in range(3):if not (gray_blue_range[i][0] <= gray_blue_rgb[i] <= gray_blue_range[i][1]):return tuple(gray_blue_rgb)# 根据灰蓝色范围的值转换到紫色范围violet_color = []for i in range(3):gray_blue_min, gray_blue_max = gray_blue_range[i]violet_min, violet_max = violet_range[i]# 灰蓝色范围内的值映射到紫色范围violet_val = int((gray_blue_rgb[i] - gray_blue_min)/ (gray_blue_max - gray_blue_min)* (violet_max - violet_min)+ violet_min)violet_color.append(violet_val)return tuple(violet_color)

为了方便理解,举个例子。如果一个A色值区间是 [20,100],另一个B色值区间是[100,180],现在一个A色值是80,需要转为B色值,过程如下:

  • (80 - 20)/ (100 - 20) * (180 - 100) + 100 = 160

  • (当前色值 - A色值范围的最低值) / (A色值的区间长度,即 100 - 20) * (B色值的区间长度,即 180 - 100) + B色值范围的最低值

160,就是A色值在B色值中的值;

代码写好了,在将颜色填充到图片前做一层转换即可,如下:

    # 遍历图片的每个像素点,将颜色填充到新图片中for i in range(im.size[0]):for j in range(im.size[1]):# 将颜色转换,然后填充到新图片中color = tuple(convert_color(im_color[j, i]))draw.point((i, j), fill=color)count += 1print('生成进度:%d%%' % ((count / total_pixels) * 100))

启动,看下效果,有点妖娆,色值范围没控制好;

在这里插入图片描述

我之前选的色值如下:

  • 紫色:80-150,100-180,120-200;

  • 灰蓝色:150-220,0-80,150-220;

转换后的效果如下:

在这里插入图片描述

完整代码

from PIL import Image, ImageDraw
import numpy as np# 生成转换后的画
def generate_img(in_path, out_path):# 打开图片im = Image.open(in_path)# 生成后的图片大小,使用im.size[0],im.size[1],即原图大小new_im_size = np.array([im.size[0], im.size[1]]).astype(int)# 生成图片的背景颜色bg_color = "black"# 生成图片im_out = Image.new("RGB", tuple(new_im_size), bg_color)# 获取图片的颜色im_color = np.array(im)# 生成图片draw = ImageDraw.Draw(im_out)# 用于统计进度count = 0total_pixels = im.size[0] * im.size[1]# 遍历图片的每个像素点,将颜色填充到新图片中for i in range(im.size[0]):for j in range(im.size[1]):# 将颜色转换,然后填充到新图片中color = tuple(convert_color(im_color[j, i]))draw.point((i, j), fill=color)count += 1print('生成进度:%d%%' % ((count / total_pixels) * 100))# 保存图片im_out.save(out_path)# 色值转换,灰蓝色 => 紫色
def convert_color(gray_blue_rgb):# 灰蓝色范围gray_blue_range = [(100, 180), (120, 200), (150, 230)]# 紫色范围violet_range = [(128, 255), (0, 20), (128, 255)]# 检查输入的 RGB 值是否在灰蓝色范围内for i in range(3):if not (gray_blue_range[i][0] <= gray_blue_rgb[i] <= gray_blue_range[i][1]):return tuple(gray_blue_rgb)# 根据灰蓝色范围的值转换到紫色范围violet_color = []for i in range(3):gray_blue_min, gray_blue_max = gray_blue_range[i]violet_min, violet_max = violet_range[i]# 灰蓝色范围内的值映射到紫色范围violet_val = int((gray_blue_rgb[i] - gray_blue_min)/ (gray_blue_max - gray_blue_min)* (violet_max - violet_min)+ violet_min)violet_color.append(violet_val)return tuple(violet_color)if __name__ == "__main__":# 输入图片路径in_path = r'C:\Users\10765\Desktop\1.png'# 输出图片路径out_path = r'C:\Users\10765\Desktop\2.png'# 读取图片,并将图片中的颜色转换generate_img(in_path, out_path)

总结

本文介绍了如何使用Python程序对图片中的颜色进行转换

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/794990.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

单链表的排序

目录 题目来源&#xff1a; 题目描述&#xff1a; 初始代码&#xff1a; 思路&#xff1a; 具体做法&#xff1a; 我的代码&#xff1a; 优化代码&#xff1a; 对比&#xff1a; 复习&#xff1a;List 基本介绍 常用方法 遍历方式 题目来源&#xff1a; 单链表的排…

MySQL常见锁探究

MySQL常见锁探究 1. 各种锁类型1.1 全局锁1.2 表级锁1.2.1 表锁1.2.2 元数据锁&#xff08;MDL&#xff09;1.2.3 意向锁1.2.4 AUTO-INC 锁 1.3 行级锁1.3.1 Record Lock1.3.2 Gap Lock1.3.3 Next-Key Lock 2. MySQL是如何加锁的&#xff1f;2.1 什么 SQL 语句会加行级锁&#…

Win10 下 Vision Mamba(Vim-main)的环境配置(libcuda.so文件无法找到,windows系统运行失败)

目录 1、下载NVIDIA 驱动程序、cuda11.8、cudnn8.6.0 2、在Anaconda中创建环境并激活 3、下载gpu版本的torch 4、配置环境所需要的包 5、安装causal_conv1d和mamba-1p1p1 安装causal_conv1d 安装mamba-1p1p1 6、运行main.py失败 请直接拉到最后查看运行失败的原因&am…

Pandas:sort_index、sort_values方法的使用

sort_index和sort_values既是Series类型数据自带的方法&#xff0c;也是DataFrame数据自带的方法。本篇博客以DataFrame为例进行讲述。 1 概览 sort_index和sort_values可以将DataFrame中的数据按照索引及值的大小进行排序。这两个方法所包含的参数及其作用都基本一致。如下表…

重读Java设计模式: 桥接模式详解

引言 在软件开发中&#xff0c;经常会遇到需要在抽象与实现之间建立连接的情况。当系统需要支持多个维度的变化时&#xff0c;使用传统的继承方式往往会导致类爆炸和耦合度增加的问题。为了解决这一问题&#xff0c;我们可以使用桥接模式。桥接模式是一种结构型设计模式&#…

【windows】--- nginx 超详细安装并配置教程

目录 一、下载 nginx二、安装三、查看是否安装成功四、配置五、关闭 nginx六 负载均衡七 配置静态资源1. 根目录下的子目录(root)2.完全匹配(alias) 刷新配置&#xff08;不必重启nginx&#xff09;八、后端鉴权 一、下载 nginx 打开 nginx 的官网&#xff1a;nginx.org/ &…

2024.4.3-[作业记录]-day08-CSS 盒子模型(溢出显示、伪元素)

个人主页&#xff1a;学习前端的小z 个人专栏&#xff1a;HTML5和CSS3悦读 本专栏旨在分享记录每日学习的前端知识和学习笔记的归纳总结&#xff0c;欢迎大家在评论区交流讨论&#xff01; 文章目录 作业 2024.4.3-学习笔记css溢出显示单行文本溢出显示省略号多行文本溢出显示省…

Linux基础篇:Linux网络yum源——以配置阿里云yum源为例

Linux网络yum源——以阿里云为例 一、网络yum源介绍 Linux中的YUM&#xff08;Yellowdog Updater, Modified&#xff09;源是一个软件包管理器&#xff0c;它可以自动处理依赖关系并安装、更新、卸载软件包。YUM源是一个包含软件包的远程仓库&#xff0c;它可以让用户轻松地安…

苹果cmsV10 MXProV4.5自适应PC手机影视站主题模板苹果cms模板mxone pro

演示站&#xff1a;http://a.88531.cn:8016 MXPro 模板主题(又名&#xff1a;mxonepro)是一款基于苹果 cms程序的一款全新的简洁好看 UI 的影视站模板类似于西瓜视频&#xff0c;不过同对比 MxoneV10 魔改模板来说功能没有那么多,也没有那么大气&#xff0c;但是比较且可视化功…

服务器硬件构成与性能要点:CPU、内存、硬盘、RAID、网络接口卡等关键组件的基础知识总结

文章目录 服务器硬件基础知识CPU&#xff08;中央处理器&#xff09;内存&#xff08;RAM&#xff09;硬盘RAID&#xff08;磁盘阵列&#xff09;网络接口卡&#xff08;NIC&#xff09;电源散热器主板显卡光驱 服务器硬件基础知识 服务器是一种高性能计算机&#xff0c;用于在…

thinkphp6入门(21)-- 如何删除图片、文件

假设文件的位置在 /*** 删除文件* $file_name avatar/20240208/d71d108bc1086b498df5191f9f925db3.jpg*/ function deleteFile($file_name) {// 要删除的文件路径$file app()->getRootPath() . public/uploads/ . $file_name; $result [];if (is_file($file)) {if (unlin…

论文笔记:Large Language Models as Analogical Reasoners

iclr 2024 reviewer打分5558 1 intro 基于CoT prompt的大模型能够更好地解决复杂推理问题 然而传统CoT需要提供相关的例子作为指导&#xff0c;这就增加了人工标注的成本——>Zero-shot CoT避免了人工标注来引导推理 但是对于一些复杂的任务难以完成推理&#xff0c;例如c…

Type-c转USBA3.0芯片 USBA3.0转Type-c芯片(USB3.1GEN2 多路切换Switch芯片) VL162

VL162具有CC功能的USB Type-C数据开关USB 3.1 Gen2 (10Gbps) VL162 带CC功能的USB Type-C数据开关 支持最高10Gbps 2差分通道&#xff0c;2:1 MUX/DeMUX 兼容10Gbps USB3.1 Gen2 低功耗&#xff0c;6mW在设备模式下有效 高直流共模电压&#xff0c;支持2.0V 28针QFN 3.5 x 4.5m…

人工智能数据分析Python常用库 04 matplotlib库

文章目录 一、matplotlib库的作用与环境配置1、环境配置示例2、改变绘图风格3、保存图片 二、绘制二维图形1、折线图&#xff08;1&#xff09;示例&#xff08;2&#xff09;调整线条颜色&#xff1a;&#xff08;3&#xff09;调整线条风格&#xff08;4&#xff09;调整线宽…

【C语言】_文件内容操作:随机读写

目录 1. fseek 1.1 随机读文件 1.2 随机写文件 2. ftell 3. rewind 当以读方式打开一个存在且存有内容的文件时&#xff0c;文件指针会默认指向第一个元素。以在test4.txt文件中存储abcdef为例&#xff1a; int main() {//打开文件FILE* pf fopen("E:\\C_文件操作…

关系型数据库与非关系型数据库、Redis数据库

相比于其他的内存/缓存数据库&#xff0c;redis可以方便的实现持久化的功能&#xff08;保存至磁盘中&#xff09; 一、关系数据库与非关系型数据库 1.1 关系型数据库 一个结构化的数据库&#xff0c;创建在关系模型基础上一般面向于记录 SQL语句 (标准数据查询语言) 就是一种…

LNMP环境:揭秘负载均衡与高可用性设计

lb1: 192.168.8.5 lb2: 192.168.8.6 web1:192.168.8.7 web2:192.168.8.8 php-fpm: 192.168.8.9 mysql: 192.168.8.10 nfs:192.168.8.11 分别插入镜像 8.5-8.8 分别安装nginx,并设置启动 8.9 安装php 8.10 安装mysql 先配置一台web服务器然后同步 设置网站根目录 cp -…

【00】【solidity最新教程】-简介

Solidity 是一门面向合约的、为实现智能合约而创建的高级编程语言。这门语言受到了 C&#xff0c;Python 和 Javascript 语言的影响&#xff0c;设计的目的是能在以太坊虚拟机&#xff08;EVM&#xff09;上运行。 Solidity 是静态类型语言&#xff0c;支持继承、库和复杂的用…

java -网络编程socket-聊天室-02

完整版代码 java -聊天室的代码: 用于存放聊天室的项目的代码和思路导图https://gitee.com/to-uphold-justice-for-others/java---code-for-chat-rooms.git 先引入线程的正统解释 线程&#xff08;Thread&#xff09;是程序执行流的最小单元。线程是操作系统分配CPU时间片的基…

【数据分析面试】10. 计算平均通勤时间(SQL:timestampdiff() 和datediff()区别)

题目 假设你在Uber工作。rides表包含了关于Uber用户在美国各地的行程信息。 编写一个查询&#xff0c;以获取纽约&#xff08;NY&#xff09;每位通勤者的平均通勤时间&#xff08;以分钟为单位&#xff09;&#xff0c;以及纽约所有通勤者的平均通勤时间&#xff08;以分钟为…