├── LICENSE.txt ├── README.md ├── images ├── 1989.png ├── evermore.png ├── evermore_shifted.png ├── fearless_tv.png ├── folklore.png ├── lightness_cmaps_re_recordings.png ├── lightness_swift_as_cmaps.png ├── lover.png ├── maps.png ├── midnights.png ├── midnights_uniformity.png ├── red.png ├── red_tv.jpg ├── reputation.png ├── speak_now_tv.jpg ├── speak_now_tv_uniformity.png └── uniformity.png ├── setup.py ├── swiftascmaps ├── __init__.py ├── __version__.py ├── colors.py └── make_cmap.py └── test_maps.py /LICENSE.txt: -------------------------------------------------------------------------------- 1 | GNU LESSER GENERAL PUBLIC LICENSE 2 | Version 3, 29 June 2007 3 | 4 | Copyright (C) 2007 Free Software Foundation, Inc. 5 | Everyone is permitted to copy and distribute verbatim copies 6 | of this license document, but changing it is not allowed. 7 | 8 | 9 | This version of the GNU Lesser General Public License incorporates 10 | the terms and conditions of version 3 of the GNU General Public 11 | License, supplemented by the additional permissions listed below. 12 | 13 | 0. Additional Definitions. 14 | 15 | As used herein, "this License" refers to version 3 of the GNU Lesser 16 | General Public License, and the "GNU GPL" refers to version 3 of the GNU 17 | General Public License. 18 | 19 | "The Library" refers to a covered work governed by this License, 20 | other than an Application or a Combined Work as defined below. 21 | 22 | An "Application" is any work that makes use of an interface provided 23 | by the Library, but which is not otherwise based on the Library. 24 | Defining a subclass of a class defined by the Library is deemed a mode 25 | of using an interface provided by the Library. 26 | 27 | A "Combined Work" is a work produced by combining or linking an 28 | Application with the Library. The particular version of the Library 29 | with which the Combined Work was made is also called the "Linked 30 | Version". 31 | 32 | The "Minimal Corresponding Source" for a Combined Work means the 33 | Corresponding Source for the Combined Work, excluding any source code 34 | for portions of the Combined Work that, considered in isolation, are 35 | based on the Application, and not on the Linked Version. 36 | 37 | The "Corresponding Application Code" for a Combined Work means the 38 | object code and/or source code for the Application, including any data 39 | and utility programs needed for reproducing the Combined Work from the 40 | Application, but excluding the System Libraries of the Combined Work. 41 | 42 | 1. Exception to Section 3 of the GNU GPL. 43 | 44 | You may convey a covered work under sections 3 and 4 of this License 45 | without being bound by section 3 of the GNU GPL. 46 | 47 | 2. Conveying Modified Versions. 48 | 49 | If you modify a copy of the Library, and, in your modifications, a 50 | facility refers to a function or data to be supplied by an Application 51 | that uses the facility (other than as an argument passed when the 52 | facility is invoked), then you may convey a copy of the modified 53 | version: 54 | 55 | a) under this License, provided that you make a good faith effort to 56 | ensure that, in the event an Application does not supply the 57 | function or data, the facility still operates, and performs 58 | whatever part of its purpose remains meaningful, or 59 | 60 | b) under the GNU GPL, with none of the additional permissions of 61 | this License applicable to that copy. 62 | 63 | 3. Object Code Incorporating Material from Library Header Files. 64 | 65 | The object code form of an Application may incorporate material from 66 | a header file that is part of the Library. You may convey such object 67 | code under terms of your choice, provided that, if the incorporated 68 | material is not limited to numerical parameters, data structure 69 | layouts and accessors, or small macros, inline functions and templates 70 | (ten or fewer lines in length), you do both of the following: 71 | 72 | a) Give prominent notice with each copy of the object code that the 73 | Library is used in it and that the Library and its use are 74 | covered by this License. 75 | 76 | b) Accompany the object code with a copy of the GNU GPL and this license 77 | document. 78 | 79 | 4. Combined Works. 80 | 81 | You may convey a Combined Work under terms of your choice that, 82 | taken together, effectively do not restrict modification of the 83 | portions of the Library contained in the Combined Work and reverse 84 | engineering for debugging such modifications, if you also do each of 85 | the following: 86 | 87 | a) Give prominent notice with each copy of the Combined Work that 88 | the Library is used in it and that the Library and its use are 89 | covered by this License. 90 | 91 | b) Accompany the Combined Work with a copy of the GNU GPL and this license 92 | document. 93 | 94 | c) For a Combined Work that displays copyright notices during 95 | execution, include the copyright notice for the Library among 96 | these notices, as well as a reference directing the user to the 97 | copies of the GNU GPL and this license document. 98 | 99 | d) Do one of the following: 100 | 101 | 0) Convey the Minimal Corresponding Source under the terms of this 102 | License, and the Corresponding Application Code in a form 103 | suitable for, and under terms that permit, the user to 104 | recombine or relink the Application with a modified version of 105 | the Linked Version to produce a modified Combined Work, in the 106 | manner specified by section 6 of the GNU GPL for conveying 107 | Corresponding Source. 108 | 109 | 1) Use a suitable shared library mechanism for linking with the 110 | Library. A suitable mechanism is one that (a) uses at run time 111 | a copy of the Library already present on the user's computer 112 | system, and (b) will operate properly with a modified version 113 | of the Library that is interface-compatible with the Linked 114 | Version. 115 | 116 | e) Provide Installation Information, but only if you would otherwise 117 | be required to provide such information under section 6 of the 118 | GNU GPL, and only to the extent that such information is 119 | necessary to install and execute a modified version of the 120 | Combined Work produced by recombining or relinking the 121 | Application with a modified version of the Linked Version. (If 122 | you use option 4d0, the Installation Information must accompany 123 | the Minimal Corresponding Source and Corresponding Application 124 | Code. If you use option 4d1, you must provide the Installation 125 | Information in the manner specified by section 6 of the GNU GPL 126 | for conveying Corresponding Source.) 127 | 128 | 5. Combined Libraries. 129 | 130 | You may place library facilities that are a work based on the 131 | Library side by side in a single library together with other library 132 | facilities that are not Applications and are not covered by this 133 | License, and convey such a combined library under terms of your 134 | choice, if you do both of the following: 135 | 136 | a) Accompany the combined library with a copy of the same work based 137 | on the Library, uncombined with any other library facilities, 138 | conveyed under the terms of this License. 139 | 140 | b) Give prominent notice with the combined library that part of it 141 | is a work based on the Library, and explaining where to find the 142 | accompanying uncombined form of the same work. 143 | 144 | 6. Revised Versions of the GNU Lesser General Public License. 145 | 146 | The Free Software Foundation may publish revised and/or new versions 147 | of the GNU Lesser General Public License from time to time. Such new 148 | versions will be similar in spirit to the present version, but may 149 | differ in detail to address new problems or concerns. 150 | 151 | Each version is given a distinguishing version number. If the 152 | Library as you received it specifies that a certain numbered version 153 | of the GNU Lesser General Public License "or any later version" 154 | applies to it, you have the option of following the terms and 155 | conditions either of that published version or of any later version 156 | published by the Free Software Foundation. If the Library as you 157 | received it does not specify a version number of the GNU Lesser 158 | General Public License, you may choose any version of the GNU Lesser 159 | General Public License ever published by the Free Software Foundation. 160 | 161 | If the Library as you received it specifies that a proxy can decide 162 | whether future versions of the GNU Lesser General Public License shall 163 | apply, that proxy's public statement of acceptance of any version is 164 | permanent authorization for you to choose that version for the 165 | Library. -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ## Taylor Swift color map collection. 2 | 3 | [![DOI](https://zenodo.org/badge/DOI/10.5281/zenodo.5649259.svg)](https://doi.org/10.5281/zenodo.5649259) 4 | 5 | Quick start: `pip install swiftascmaps` 6 | 7 | Includes color maps based on the following albums: 8 | 9 | + Red (`red`, `red_r`) 10 | + 1989 (`nineteen_eighty_nine`, `nineteen_eighty_nine_r`) 11 | + Reputation (`reputation`, `reputation_r`) 12 | + Lover (`lover`, `lover_r`) 13 | + Folklore (`folklore`, `folklore_r`) 14 | + Evermore (`evermore`, `evermore_r`, `evermore_shifted`, `evermore_shifted_r`) 15 | + Fearless: Taylor's Version (`fearless_tv`, `fearless_tv_r`) 16 | + Red: Taylor's Version (`red_tv`, `red_tv_r`) 17 | + Midnights (`midnights`, `midnights_r`) 18 | + Speak Now: Taylor's Version (`speak_now_tv`, `speak_now_tv_r`) 19 | + 1989: Taylor's Version (nineteen_eighty_nine_tv, nineteen_eighty_nine_tv_r) 20 | 21 | License: LGPLv3 22 | Author: Josh Borrow (josh@joshborrow.com) 23 | 24 | If you prefer to use `R`, there is an alternative package 25 | maintained as [taloRswift](https://github.com/asteves/tayloRswift). 26 | 27 | Usage 28 | ----- 29 | 30 | To use these, you can import them and use them 31 | with matplotlib as you would with any other color map. 32 | 33 | ```python 34 | from swiftascmaps import red 35 | from matplotlib.pyplot import imshow 36 | from numpy import random 37 | 38 | imshow(random.rand(128, 128), cmap=red) 39 | ``` 40 | 41 | The color maps can also be accessed in matplotlib using strings 42 | by prefixing `swift`, e.g. 43 | 44 | ```python 45 | import swiftascmaps 46 | 47 | imshow(random.rand(128, 128), cmap="swift.red") 48 | ``` 49 | 50 | Examples 51 | -------- 52 | 53 | ![](images/maps.png) 54 | 55 | Note 56 | ---- 57 | 58 | Of course, these aren't necessarily designed to be colorblind 59 | friendly, or perceptually uniform, so use them with caution. 60 | They are quite pretty though. To underline how much you should 61 | _not_ use these in a real scientific publication (apart from 62 | perhaps qualitative imaging), the lightness values are shown 63 | below. 64 | 65 | ![](images/uniformity.png) 66 | 67 | For quantitative comparisons, please ensure that you use a 68 | perceptually uniform colour map (see e.g. those available 69 | directly through [matplotlib](https://matplotlib.org/3.1.0/tutorials/colors/colormaps.html)). 70 | -------------------------------------------------------------------------------- /images/1989.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/1989.png -------------------------------------------------------------------------------- /images/evermore.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/evermore.png -------------------------------------------------------------------------------- /images/evermore_shifted.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/evermore_shifted.png -------------------------------------------------------------------------------- /images/fearless_tv.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/fearless_tv.png -------------------------------------------------------------------------------- /images/folklore.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/folklore.png -------------------------------------------------------------------------------- /images/lightness_cmaps_re_recordings.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/lightness_cmaps_re_recordings.png -------------------------------------------------------------------------------- /images/lightness_swift_as_cmaps.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/lightness_swift_as_cmaps.png -------------------------------------------------------------------------------- /images/lover.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/lover.png -------------------------------------------------------------------------------- /images/maps.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/maps.png -------------------------------------------------------------------------------- /images/midnights.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/midnights.png -------------------------------------------------------------------------------- /images/midnights_uniformity.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/midnights_uniformity.png -------------------------------------------------------------------------------- /images/red.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/red.png -------------------------------------------------------------------------------- /images/red_tv.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/red_tv.jpg -------------------------------------------------------------------------------- /images/reputation.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/reputation.png -------------------------------------------------------------------------------- /images/speak_now_tv.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/speak_now_tv.jpg -------------------------------------------------------------------------------- /images/speak_now_tv_uniformity.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/speak_now_tv_uniformity.png -------------------------------------------------------------------------------- /images/uniformity.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/JBorrow/swiftascmaps/10f283e6d6c5e9bad748aefcf27ac8c5e9ceb4ba/images/uniformity.png -------------------------------------------------------------------------------- /setup.py: -------------------------------------------------------------------------------- 1 | import setuptools 2 | 3 | version = {} 4 | 5 | with open("./swiftascmaps/__version__.py", "r") as fh: 6 | exec(fh.read(), version) 7 | 8 | with open("README.md", "r") as fh: 9 | long_description = fh.read() 10 | 11 | setuptools.setup( 12 | name="swiftascmaps", 13 | version=version["__version__"], 14 | description="Taylor Swift inspired Matplotlib colormaps.", 15 | url="https://github.com/jborrow/swiftascmaps", 16 | author="Josh Borrow", 17 | author_email="joshua.borrow@durham.ac.uk", 18 | packages=setuptools.find_packages(), 19 | long_description=long_description, 20 | long_description_content_type="text/markdown", 21 | zip_safe=False, 22 | classifiers=[ 23 | "Programming Language :: Python :: 3.6", 24 | "Programming Language :: Python :: 3.7", 25 | "License :: OSI Approved :: GNU Lesser General Public License v3 or later (LGPLv3+)", 26 | "Operating System :: OS Independent", 27 | ], 28 | install_requires=[ 29 | "matplotlib", 30 | ], 31 | ) 32 | -------------------------------------------------------------------------------- /swiftascmaps/__init__.py: -------------------------------------------------------------------------------- 1 | """ 2 | Taylor Swift color map collection. 3 | 4 | Includes color maps based on the following albums: 5 | 6 | + Red (red, red_r) 7 | + 1989 (nineteen_eighty_nine, nineteen_eighty_nine_r) 8 | + Reputation (reputation, reputation_r) 9 | + Lover (lover, lover_r) 10 | + Folklore (folklore, folklore_r) 11 | + Evermore (evermore, evermore_r, evermore_shifted, evermore_shifted_r) 12 | + Fearless: Taylor's Version (fearless_tv, fearless_tv_r) 13 | + Midnights (midnights, midnights_r) 14 | + Speak Now: Taylor's Version (speak_now_tv, speak_now_rv_r) 15 | + 1989: Taylor's Version (nineteen_eighty_nine_tv, nineteen_eighty_nine_tv_r) 16 | 17 | License: LGPLv3 18 | Author: Josh Borrow (josh.borrow@gmail.com) 19 | 20 | Usage 21 | ----- 22 | 23 | To use these, you can import them and use them 24 | with matplotlib as you would with any other color map. 25 | 26 | .. code-block:: python 27 | 28 | from swiftascmaps import red 29 | from matplotlib.pyplot import imshow 30 | from numpy import random 31 | 32 | imshow(random.rand(128, 128), cmap=red) 33 | 34 | """ 35 | 36 | import swiftascmaps.colors as colors 37 | from swiftascmaps.make_cmap import make_custom_cmap 38 | from swiftascmaps.__version__ import __version__ 39 | 40 | red, red_r = make_custom_cmap("red", colors.red) 41 | nineteen_eighty_nine, nineteen_eighty_nine_r = make_custom_cmap( 42 | "nineteen_eighty_nine", colors.nineteen_eighty_nine 43 | ) 44 | reputation, reputation_r = make_custom_cmap("reputation", colors.reputation) 45 | lover, lover_r = make_custom_cmap("lover", colors.lover) 46 | folklore, folklore_r = make_custom_cmap("folklore", colors.folklore) 47 | evermore, evermore_r = make_custom_cmap("evermore", colors.evermore) 48 | evermore_shifted, evermore_shifted_r = make_custom_cmap( 49 | "evermore_shifted", colors.evermore_shifted 50 | ) 51 | fearless_tv, fearless_tv_r = make_custom_cmap("fearless_tv", colors.fearless_tv) 52 | red_tv, red_tv_r = make_custom_cmap("red_tv", colors.red_tv) 53 | midnights, midnights_r = make_custom_cmap("midnights", colors.midnights) 54 | speak_now_tv, speak_now_tv_r = make_custom_cmap("speak_now_tv", colors.speak_now_tv) 55 | nineteen_eighty_nine_tv, nineteen_eighty_nine_tv_r = make_custom_cmap( 56 | "nineteen_eighty_nine_tv", colors.nineteen_eighty_nine_tv 57 | ) 58 | -------------------------------------------------------------------------------- /swiftascmaps/__version__.py: -------------------------------------------------------------------------------- 1 | __version__ = "1.4.0" 2 | -------------------------------------------------------------------------------- /swiftascmaps/colors.py: -------------------------------------------------------------------------------- 1 | """ 2 | Colors (defined as RGB values) for the Taylor Swift albums. 3 | """ 4 | 5 | from swiftascmaps.make_cmap import hex_to_rgb 6 | 7 | red = [ 8 | [40, 37, 62], 9 | [175, 30, 73], 10 | [235, 233, 220], 11 | ] 12 | 13 | nineteen_eighty_nine = [ 14 | [58, 64, 84], 15 | [139, 112, 156], 16 | [203, 152, 123], 17 | [215, 197, 162], 18 | [229, 231, 220], 19 | ] 20 | 21 | reputation = [ 22 | [26, 26, 26], 23 | [140, 140, 140], 24 | [230, 230, 230], 25 | [255, 255, 255], 26 | ] 27 | 28 | lover = [ 29 | [93, 174, 218], 30 | [254, 166, 184], 31 | [255, 244, 208], 32 | ] 33 | 34 | folklore = [ 35 | [69, 60, 46], 36 | [106, 103, 88], 37 | [158, 134, 108], 38 | [223, 222, 220], 39 | ] 40 | 41 | evermore = [ 42 | [241, 149, 91], 43 | [142, 52, 38], 44 | [33, 21, 49], 45 | [154, 112, 82], 46 | [241, 149, 91], 47 | ] 48 | 49 | evermore_shifted = [ 50 | [33, 21, 49], 51 | [154, 112, 82], 52 | [241, 149, 91], 53 | [142, 52, 38], 54 | [33, 21, 49], 55 | ] 56 | 57 | fearless_tv = [ 58 | [77, 51, 33], 59 | [132, 99, 60], 60 | # [117, 84, 45], 61 | # [202, 165, 98], 62 | [186, 151, 88], 63 | [232, 206, 148], 64 | [250, 241, 200], 65 | ] 66 | 67 | red_tv = hex_to_rgb( 68 | reversed( 69 | [ 70 | "#E7DDD5", 71 | "#C5AD9A", 72 | "#BA704B", 73 | "#8F4C3A", 74 | "#6F2019", 75 | "#480200", 76 | ] 77 | ) 78 | ) 79 | 80 | midnights = hex_to_rgb( 81 | [ 82 | "#2A1828", 83 | "#4F5D87", 84 | "#83A5BA", 85 | "#E8E7E3", 86 | ] 87 | ) 88 | 89 | speak_now_tv = hex_to_rgb( 90 | [ 91 | "#0E0E0E", 92 | "#693C83", 93 | "#B58CB5", 94 | "#EEE6DC", 95 | ] 96 | ) 97 | 98 | nineteen_eighty_nine_tv = hex_to_rgb( 99 | ["#3A1F16", "#C13C25", "#D7AB8A", "#FBFAF8", "#7EA7C5", "#446D8D", "#1F2D3B"] 100 | ) 101 | -------------------------------------------------------------------------------- /swiftascmaps/make_cmap.py: -------------------------------------------------------------------------------- 1 | """ 2 | Wrapper function for making color maps from lists 3 | of colors. 4 | """ 5 | 6 | from matplotlib.cm import register_cmap 7 | from matplotlib.colors import LinearSegmentedColormap 8 | from typing import List, Tuple 9 | 10 | 11 | def hex_to_rgb(colors: List[str]) -> List[List[int]]: 12 | """ 13 | Converts colors from hex codes to 8-bit integer RGB values. 14 | 15 | Parameters 16 | ---------- 17 | 18 | colors: List[str] 19 | Your hex codes, e.g. ["#000000"] 20 | 21 | Returns 22 | ------- 23 | 24 | rgb_colors: List[List[int]] 25 | List of colors formatted as rgb [[0, 0, 0]] 26 | """ 27 | 28 | rgb_colors = [] 29 | 30 | for color in colors: 31 | rgb_colors.append(list(int(color[1:][i : i + 2], 16) for i in (0, 2, 4))) 32 | 33 | return rgb_colors 34 | 35 | 36 | def make_custom_cmap(name: str, colors: List) -> Tuple[LinearSegmentedColormap]: 37 | """ 38 | Makes a custom color map from your set of colors, and returns 39 | it along with a 'reversed' version. 40 | 41 | Parameters 42 | ---------- 43 | 44 | name: str 45 | Base name for your color map. 46 | 47 | colors: List[List[int]] 48 | List of colors (from bottom to top) as 8-bit integers. Max is 49 | 255, so: 50 | 51 | .. code-block:: python 52 | 53 | colors = [ 54 | [0, 0, 0], 55 | [255, 255, 255] 56 | ] 57 | 58 | would produce a color map from black to white. 59 | 60 | 61 | Returns 62 | ------- 63 | 64 | cmap: LinearSegmentedColormap 65 | Base colour map, made from your colors. 66 | 67 | cmap_r: LinearSegmentedColormap 68 | Reversed version of your color map. 69 | """ 70 | 71 | float_colors = [[x / 255 for x in color] for color in colors] 72 | 73 | cmap = LinearSegmentedColormap.from_list(f"swift.{name}", float_colors, N=1024) 74 | 75 | cmap_r = LinearSegmentedColormap.from_list( 76 | f"swift.{name}_r", list(reversed(float_colors)), N=1024 77 | ) 78 | 79 | register_cmap(cmap=cmap) 80 | register_cmap(cmap=cmap_r) 81 | 82 | return cmap, cmap_r 83 | -------------------------------------------------------------------------------- /test_maps.py: -------------------------------------------------------------------------------- 1 | from colorspacious import cspace_converter 2 | 3 | import matplotlib.pyplot as plt 4 | import numpy as np 5 | 6 | import matplotlib as mpl 7 | 8 | import swiftascmaps 9 | 10 | cmaps = {} 11 | 12 | gradient = np.linspace(0, 1, 256) 13 | gradient = np.vstack((gradient, gradient)) 14 | 15 | 16 | def plot_color_gradients(category, cmap_list): 17 | # Create figure and adjust figure height to number of colormaps 18 | nrows = len(cmap_list) 19 | figh = 0.35 + 0.15 + (nrows + (nrows - 1) * 0.1) * 0.22 20 | fig, axs = plt.subplots(nrows=nrows + 1, figsize=(6.4, figh)) 21 | fig.subplots_adjust(top=1 - 0.35 / figh, bottom=0.15 / figh, 22 | left=0.3, right=0.99) 23 | axs[0].set_title(f'{category} colormaps', fontsize=14) 24 | 25 | for ax, name in zip(axs, cmap_list): 26 | ax.imshow(gradient, aspect='auto', cmap=mpl.colormaps[name]) 27 | ax.text(-0.01, 0.5, name.split(".")[-1], va='center', ha='right', fontsize=10, 28 | transform=ax.transAxes) 29 | 30 | # Turn off *all* ticks & spines, not just the ones with colormaps. 31 | for ax in axs: 32 | ax.set_axis_off() 33 | 34 | # Save colormap list for later. 35 | cmaps[category] = cmap_list 36 | 37 | plot_color_gradients("Matplotlib: Taylor's Color Maps", 38 | [ 39 | "swift.red", 40 | "swift.nineteen_eighty_nine", 41 | "swift.reputation", 42 | "swift.lover", 43 | "swift.folklore", 44 | "swift.evermore", 45 | "swift.fearless_tv", 46 | "swift.midnights", 47 | "swift.speak_now_tv", 48 | "swift.nineteen_eighty_nine_tv" 49 | ] 50 | ) 51 | 52 | plt.savefig("images/maps.png") 53 | 54 | mpl.rcParams.update({'font.size': 12}) 55 | 56 | # Number of colormap per subplot for particular cmap categories 57 | _DSUBS = {"Matplotlib: Taylor's Color Maps": 4} 58 | 59 | # Spacing between the colormaps of a subplot 60 | _DC = {"Matplotlib: Taylor's Color Maps": 1.4} 61 | 62 | # Indices to step through colormap 63 | x = np.linspace(0.0, 1.0, 100) 64 | 65 | # Do plot 66 | for cmap_category, cmap_list in cmaps.items(): 67 | 68 | # Do subplots so that colormaps have enough space. 69 | # Default is 6 colormaps per subplot. 70 | dsub = _DSUBS.get(cmap_category, 6) 71 | nsubplots = int(np.ceil(len(cmap_list) / dsub)) 72 | 73 | # squeeze=False to handle similarly the case of a single subplot 74 | fig, axs = plt.subplots(nrows=nsubplots, squeeze=False, 75 | figsize=(7, 2.6*nsubplots)) 76 | 77 | for i, ax in enumerate(axs.flat): 78 | 79 | locs = [] # locations for text labels 80 | 81 | for j, cmap in enumerate(cmap_list[i*dsub:(i+1)*dsub]): 82 | 83 | # Get RGB values for colormap and convert the colormap in 84 | # CAM02-UCS colorspace. lab[0, :, 0] is the lightness. 85 | rgb = mpl.colormaps[cmap](x)[np.newaxis, :, :3] 86 | lab = cspace_converter("sRGB1", "CAM02-UCS")(rgb) 87 | 88 | # Plot colormap L values. Do separately for each category 89 | # so each plot can be pretty. To make scatter markers change 90 | # color along plot: 91 | # https://stackoverflow.com/q/8202605/ 92 | 93 | if cmap_category == 'Sequential': 94 | # These colormaps all start at high lightness, but we want them 95 | # reversed to look nice in the plot, so reverse the order. 96 | y_ = lab[0, ::-1, 0] 97 | c_ = x[::-1] 98 | else: 99 | y_ = lab[0, :, 0] 100 | c_ = x 101 | 102 | dc = _DC.get(cmap_category, 1.4) # cmaps horizontal spacing 103 | ax.scatter(x + j*dc, y_, c=c_, cmap=cmap, s=300, linewidths=0.0) 104 | 105 | # Store locations for colormap labels 106 | if cmap_category in ('Perceptually Uniform Sequential', 107 | 'Sequential'): 108 | locs.append(x[-1] + j*dc) 109 | elif cmap_category in ('Diverging', 'Qualitative', 'Cyclic', 110 | 'Miscellaneous', 'Sequential (2)'): 111 | locs.append(x[int(x.size/2.)] + j*dc) 112 | 113 | # Set up the axis limits: 114 | # * the 1st subplot is used as a reference for the x-axis limits 115 | # * lightness values goes from 0 to 100 (y-axis limits) 116 | ax.set_xlim(axs[0, 0].get_xlim()) 117 | ax.set_ylim(0.0, 100.0) 118 | 119 | # Set up labels for colormaps 120 | ax.xaxis.set_ticks_position('top') 121 | ticker = mpl.ticker.FixedLocator(locs) 122 | ax.xaxis.set_major_locator(ticker) 123 | formatter = mpl.ticker.FixedFormatter(cmap_list[i*dsub:(i+1)*dsub]) 124 | ax.xaxis.set_major_formatter(formatter) 125 | ax.xaxis.set_tick_params(rotation=50) 126 | ax.set_ylabel('Lightness $L^*$', fontsize=12) 127 | 128 | ax.set_xlabel(cmap_category + ' colormaps', fontsize=14) 129 | 130 | fig.tight_layout(h_pad=0.0, pad=1.5) 131 | plt.savefig("images/uniformity.png") --------------------------------------------------------------------------------