Darken or lighten a color in matplotlib

前端 未结 3 947
闹比i
闹比i 2021-02-02 08:38

Say I have a color in Matplotlib. Maybe it\'s a string (\'k\') or an rgb tuple ((0.5, 0.1, 0.8)) or even some hex (#05FA2B). Is there a

3条回答
  •  广开言路
    2021-02-02 08:55

    Using only colorsys which is part of the python standard library it is possible to scale the lighntess with just two lines of code

    If you still want the option to pass non rgb values like colornames or HEX you can simply use matplotlib.colors.ColorConverter.to_rgb("#ff0000").

    This method scales the lightness of an rgb color

    import colorsys
    
    def scale_lightness(rgb, scale_l):
        # convert rgb to hls
        h, l, s = colorsys.rgb_to_hls(*rgb)
        # manipulate h, l, s values and return as rgb
        return colorsys.hls_to_rgb(h, min(1, l * scale_l), s = s)
    

    A simple demonstration. For more details have a look at the old example.

    import matplotlib
    import seaborn as sns
    
    color = matplotlib.colors.ColorConverter.to_rgb("navy")
    rgbs = [scale_lightness(color, scale) for scale in [0, .5, 1, 1.5, 2]]
    sns.palplot(rgbs)
    


    Old Answer

    There is a Seaborn method, that easily lets you manipulate the lightness. seaborn.set_hls_values() takes a color as RGB-Tuple, HEX or HTML-name and lets you manipulate the hue, lightness and saturation.

    The scaled lightness should be between 0 and 1, where 1 < scale increases the lightness and 0 ≤ scale < 1 darkens the color.

    from colorsys import rgb_to_hls
    import seaborn as sns
    
    color = (1.0, 0.0, 0.0)     # RGB
    
    print(f"Input color:    \t Lightness:  {rgb_to_hls(*color)[1]: .2g}\t RGB:  {color}")
    
    rgbs = []
    for scale in [0, .5, 1, 1.5, 2]:
    
        # scale the lightness (The values should be between 0 and 1)
        lightness = min(1, rgb_to_hls(*color)[1] * scale)
    
        # manipulate h, l, s channel of a rgb color
        rgb = sns.set_hls_values(color = color, h = None, l = lightness, s = None)
    
        print(f"Scale factor: {scale: .2g}\t Lightness:  {lightness: .2g}  \t RGB:  {rgb}")
        rgbs.append(rgb)
    
    sns.palplot(rgbs)
    

    In case you want to use other than RGB codes you need to convert your color to RGB. You could use the following command.

    color = "red"               # HTML name
    color = "#ff0000"           # HEX
    color = matplotlib.colors.ColorConverter.to_rgb(color)
    

    The returned values are RGB-Tuples:

    Input color:        Lightness:   0.5    RGB:  (1.0, 0.0, 0.0)
    
    Scale factor:  0    Lightness:   0      RGB:  (0.0, 0.0, 0.0)  # Black
    Scale factor:  0.5  Lightness:   0.25   RGB:  (0.5, 0.0, 0.0)
    Scale factor:  1    Lightness:   0.5    RGB:  (1.0, 0.0, 0.0)  # Unchanged
    Scale factor:  1.5  Lightness:   0.75   RGB:  (1.0, 0.5, 0.5)
    Scale factor:  2    Lightness:   1      RGB:  (1.0, 1.0, 1.0)  # White
    

    EDIT:

    Thanks @fhgd! I changed the code to actually scale the lightness and not just set it.

提交回复
热议问题