Python

Pythonで色の階調のカラーコードを計算する

実行した環境

Ubuntu Stdio 18.04LTS
Python 3.6.5

Pythonで世界地図-14(都道府県を着色する)
https://qiita.com/ty21ky/items/097e0c362586109b8ca2
で各都道府県毎に違う色で着色し、なおかつ色の違いがわかる色にしたいと思いましたが、色の階調をどのようにすればよいかわかりませんでした。

ネットで探したら同じようなことをやっているコードがあるのですが、私のオツムでは何をやっているのかわかりません。もちろん、エラーがでて動きません。

ネットで検索してもなかなか見つかりませんし、自分で考えても色のことがよくわかっていないので、???

サーモグラフィ風の色変化をシグモイド関数で再現する
https://qiita.com/masato_ka/items/c178a53c51364703d70b
で、それらしいことが書かれていました。
でも、私が考えているのと少し違う。

image.png

このグラフを見て大体わかってきました。

image.png

私のレベルでできそうな、上図でコーディングしました。
見苦しいコードですみません。
コメント欄で素晴らしいコードを教えていただきました。下のコードは見ないでコメント欄のコードを見てください。

#!/usr/bin/python3
# coding: UTF-8

def rgb2hex(r,g,b): #RGB配列からHTMLなどに使われる16進数表現へ
    # r , g , b = 0 〜 255 # int型
    color = (r, g , b)
    html_color = '#%02X%02X%02X' % (color[0],color[1],color[2])
    return html_color

def make_color_code(n,n1,gray = False):
    #nは3の倍数とする。(3,6,9,12・・・)
    #引数:n=色数、n1=色番号、gray=False(白黒を使用しない),True(使用する)
    #n1=0とn1=nは赤色なので、n1=nは赤として使用しない。gray=Trueの時は白とする。

    if n % 3 != 0:
        return 'Error:nが3の倍数では無い'

    area1 = n/3   #0 〜 n/3
    area2 = 2/3*n #n/3 < 〜 2/3*n
    area3 = n     #2/3*n < 〜 n

    if n1 == 0:
        return '#FF0000' #赤

    elif n1 < area1:
        y1r = 255*(-3/n*n1+1)
        y1g = 255*3*n1/n
        y1b = 0
        return rgb2hex(int(y1r),int(y1g),int(y1b))

    elif n1 == n/3:
        return '#00FF00' #緑

    elif n1 < area2:
        y2r = 0
        y2g = 255*(-3*n1/n+2)
        y2b = 255*(3*n1/n-1)
        return rgb2hex(int(y2r),int(y2g),int(y2b))

    elif n1 == 2 * n / 3:
        return '#0000FF' #青

    elif n1 < area3:
        y3r = 255*(3*n1/n-2)
        y3g = 0
        y3b = 255*(-3*n1/n+3)
        return rgb2hex(int(y3r),int(y3g),int(y3b))

    elif gray: #白黒を使用する
        if n == n1:
            return '#FFFFFF' #白
        elif n+1 == n1:
            return '#F5F5F5' #whitesmoke
        elif n+2 == n1:
            return '#DCDCDC' #gainsboro
        elif n+3 == n1:
            return '#D3D3D3' #lightgray
        elif n+4 == n1:
            return '#C0C0C0' #silver
        elif n+5 == n1:
            return '#A9A9A9' #darkgray
        elif n+6 == n1:
            return '#808080' #gray
        elif n+7 == n1:
            return '#696969' #dimgray
        elif n+8 == n1:
            return '#000000' #black

    else:
        return 'Error' #エラー
#----
if __name__ == '__main__':
    #print(make_color_code(6,1,gray = False))
    for i in range(12):
        print(make_color_code(12,i,gray = False)) #色の数=12
$ ./color変化4.py
#FF0000
#BF3F00
#7F7F00
#3FBF00
#00FF00
#00BF3F
#007F7F
#003FBF
#0000FF
#3F00BF
#7F007F
#BF003F

image.png

RGB配列からHTMLなどに使われる16進数表現へ変換する関数は、
カラーコードの変換
http://code.tiblab.net/python/color_code_transform
のコードをそのまま使用させていただきました。

グレースケールのカラーコードは、ネットで見つけたものをそのまま使用しました。URL等は控えるのを忘れたのでわかりません。

使い方

make_color_code(色の数(int),色の番号(int),gray = False)


make_color_code(12,i,gray = False)
・色の数は、必ず3の倍数で指定します。(あまり大きくすると、隣の色と違いがわからないようになる。)
・色の番号は、0 - 赤色
から、12まで(例の場合)ありますが、12は赤色になるので使用しません。
グレースケールを使用する時に、12(例の場合)は白色として使用します。
・gray = Falseはグレースケールを使用しません。
 gray = Trueはグレースケール(9色)を使用します。