RGB颜色值相互转换
不同进制RGB颜色值互相转换
本脚本支持整数[0 - 255]、浮点数[0.0 - 1.0]和16进制RGB值相互转换
使用语言为Python 3.7.
用来造轮子,练手用的代码.
本博客地址: https://mp.csdn.net/mdeditor/101625635
#!-*- coding:utf-8 -*-
# @author: dwcai
# @contact: dwcai.17b@gmail.com
# @software: PyCharm
# @file: color.py
# @time: 2019-09-27 21:56
# @desc: 颜色转换器, 16进制-10进制-小数 RGB 颜色值互相转换.
class RGB:
"""
RGB 类可以实现不同颜色表达方式的互转.
1. 可以输入单个颜色值, 如 '0f', '0E', 255, 122, 0.12, 0.8等;
2. 可以输入 RGB 顺次排列的16进制字符串, 10进制列表(元组), 如:
'FFEE08', '8f4a2c', [255, 100, 50], (0.1, 0.5, 0.8).
"""
def __init__(self, value, auto=False, test=False):
self.__hex = [str(i) for i in range(10)] + ['a', 'b', 'c', 'd', 'e', 'f']
self.__int = [i for i in range(16)]
self.__hex2int__ = {k: v for k, v in zip(self.__hex, self.__int)}
self.__int2hex__ = {k: v for k, v in zip(self.__int, self.__hex)}
self.__auto = auto # 是否自动输出转换的颜色值.
self.__test = test # 是否运行测试
if self.__auto:
self.__test = False # 如果自动输出用户结果, 则不输出测试用例.
if isinstance(value, str):
self.value = value.replace(' ', '')
else:
self.value = value
self.dtype = "<class 'RGB'>"
self.type = type(value)
self.to_decimal = self.__to_decimal()
self.to_hex = self.__to_hex()
self.to_int = self.__to_int()
if self.__auto:
print("-----------------------------用户实例-----------------------------------")
print(""">> from rgb\t\t%s\n>> to int\t\t%s\n>> to hex\t\t%s\n>> to decimal\t%s
""" % (str(self.value), str(self.to_int), str(self.to_hex), str(self.to_decimal)))
print("-----------------------------用户实例-----------------------------------")
if self.__test:
self.__run_test()
@staticmethod
def __run_test():
tc1 = RGB([255, 'ff', 1.0])
tc2 = RGB(['ff', 0.5])
tc3 = RGB('ff ff ff')
print("-----------------------------测试用例-----------------------------------")
print(""">> from rgb\t\t%s\n>> to int\t\t%s\n>> to hex\t\t%s\n>> to decimal\t%s
""" % (str(tc1.value), str(tc1.to_int), str(tc1.to_hex), str(tc1.to_decimal)))
print(""">> from rgb\t\t%s\n>> to int\t\t%s\n>> to hex\t\t%s\n>> to decimal\t%s
""" % (str(tc2.value), str(tc2.to_int), str(tc2.to_hex), str(tc2.to_decimal)))
print(""">> from rgb\t\t%s\n>> to int\t\t%s\n>> to hex\t\t%s\n>> to decimal\t%s
""" % (str(tc3.value), str(tc3.to_int), str(tc3.to_hex), str(tc3.to_decimal)))
print("-----------------------------测试结束-----------------------------------")
def __to_decimal(self): # 转换为小数
return self.__all2decimal(self.value)
def __to_hex(self): # 转换为16进制
return self.__all2hex(self.value)
def __to_int(self): # 转换为10进制
return self.__all2int(self.value)
def __all2decimal(self, hx):
__all2decimal = {'str': self.__hex2decimal(hx),
'int': self.__int2decimal(hx),
'float': self.__decimal2decimal(hx),
'iterable': self.__handle_iterable(hx, 'float')}
return __all2decimal[self.__return_type(hx)]
def __all2int(self, hx):
__all2int = {'str': self.__hex2int(hx),
'int': self.__int2int(hx),
'float': self.__decimal2int(hx),
'iterable': self.__handle_iterable(hx, 'int')}
return __all2int[self.__return_type(hx)]
def __all2hex(self, hx):
__all2hex = {'str': self.__hex2hex(hx),
'int': self.__int2hex(hx),
'float': self.__decimal2hex(hx),
'iterable': self.__handle_iterable(hx, 'hex')}
return __all2hex[self.__return_type(hx)]
def __hex2int(self, hx):
if self.__condition(hx) is 'str':
if len(hx) == 2:
return self.__hex2int__[hx[0].lower()] * 16 + self.__hex2int__[hx[1].lower()]
else:
out = []
for i in range(0, len(hx), 2):
out.append(self.__hex2int__[hx[i].lower()] * 16 + self.__hex2int__[hx[i+1].lower()])
return out
def __hex2decimal(self, hx):
if self.__condition(hx) is 'str':
if len(hx) == 2:
return round(self.__int2decimal(self.__hex2int(hx)), 2)
else:
out = []
for i in range(0, len(hx), 2):
out.append(round(self.__int2decimal(self.__hex2int(hx[i:i+2])), 2))
return out
def __hex2hex(self, hx):
if self.__condition(hx) is 'str':
return hx
def __decimal2int(self, hx):
if self.__condition(hx) is 'float':
return int(hx * 255)
def __decimal2hex(self, hx):
if self.__condition(hx) is 'float':
return self.__int2hex(self.__decimal2int(hx))
def __decimal2decimal(self, hx):
if self.__condition(hx) is 'float':
return round(hx, 2)
def __int2decimal(self, hx):
if self.__condition(hx) is 'int':
return round(hx / 255, 2)
def __int2int(self, hx):
if self.__condition(hx) is 'int':
return hx
def __int2hex(self, hx):
if self.__condition(hx) is 'int':
return self.__int2hex__[hx // 16] + self.__int2hex__[hx % 16]
def __handle_iterable(self, hx, flag):
if self.__condition(hx) is 'iterable':
try:
if flag is 'hex':
out = ''
for h in hx:
out += self.__all2hex(h)
elif flag is 'int':
out = []
for h in hx:
out.append(self.__all2int(h))
elif flag is 'float':
out = []
for h in hx:
out.append(self.__all2decimal(h))
else:
out = hx
return out
except TypeError:
return hx
def __condition(self, hx):
if isinstance(hx, int):
if 0 <= hx <= 255:
if not isinstance(hx, float):
return 'int'
elif isinstance(hx, float):
if 0 <= hx <= 1:
return 'float'
elif isinstance(hx, str):
for i in hx:
if len(hx) % 2 != 0:
exit("Condition: 输入的16进制数必须为偶数位, 否则出错!")
if i.lower() not in self.__hex2int__.keys():
exit("condition: 请输入合法的16进制数[0-9, a-f]!")
return 'str'
elif isinstance(hx, list):
return 'iterable'
elif isinstance(hx, tuple):
return 'iterable'
else:
return False
@staticmethod
def __check_iterable_dtype(hx):
if isinstance(hx, int):
return 'int'
elif isinstance(hx, float):
print('float', hx)
elif isinstance(hx, str):
return 'str'
else:
return False
@staticmethod
def __return_type(hx):
if str(type(hx)) == str(type('')):
return 'str'
elif str(type(hx)) == str(type(1)):
return 'int'
elif str(type(hx)) == str(type(0.1)):
return 'float'
elif str(type(hx)) == str(type([])):
return 'iterable'
elif str(type(hx)) == str(type(tuple())):
return 'iterable'
def get_info(self):
color_dict = {"int to hex dict": self.__int2hex__, 'hex to int dict': self.__hex2int__}
return color_dict
if __name__ == '__main__':
vec = ['ef', 'ff', 1.0]
color = RGB(vec, auto=True, test=True)