Source code for colour.plotting.temperature

"""
Colour Temperature & Correlated Colour Temperature Plotting
===========================================================

Define the colour temperature and correlated colour temperature plotting
objects:

-   :func:`colour.plotting.lines_daylight_locus`
-   :func:`colour.plotting.lines_planckian_locus`
-   :func:`colour.plotting.\
plot_planckian_locus_in_chromaticity_diagram_CIE1931`
-   :func:`colour.plotting.\
plot_planckian_locus_in_chromaticity_diagram_CIE1960UCS`
-   :func:`colour.plotting.\
plot_planckian_locus_in_chromaticity_diagram_CIE1976UCS`
"""

from __future__ import annotations

import numpy as np
from matplotlib.axes import Axes
from matplotlib.collections import LineCollection
from matplotlib.figure import Figure

from colour.algebra import normalise_maximum, normalise_vector
from colour.colorimetry import CCS_ILLUMINANTS, MSDS_CMFS
from colour.constants import DTYPE_FLOAT_DEFAULT
from colour.hints import (
    Any,
    ArrayLike,
    Callable,
    Dict,
    List,
    Literal,
    NDArray,
    Sequence,
    Tuple,
    cast,
)
from colour.models import (
    UCS_uv_to_xy,
    xy_to_XYZ,
)
from colour.plotting import (
    CONSTANTS_ARROW_STYLE,
    CONSTANTS_COLOUR_STYLE,
    METHODS_CHROMATICITY_DIAGRAM,
    XYZ_to_plotting_colourspace,
    artist,
    filter_passthrough,
    override_style,
    plot_chromaticity_diagram_CIE1931,
    plot_chromaticity_diagram_CIE1960UCS,
    plot_chromaticity_diagram_CIE1976UCS,
    render,
    update_settings_collection,
)
from colour.plotting.diagrams import plot_chromaticity_diagram
from colour.temperature import CCT_to_uv, CCT_to_xy_CIE_D, mired_to_CCT
from colour.utilities import (
    CanonicalMapping,
    as_float_array,
    as_float_scalar,
    as_int_scalar,
    full,
    optional,
    tstack,
    validate_method,
    zeros,
)

__author__ = "Colour Developers"
__copyright__ = "Copyright 2013 Colour Developers"
__license__ = "BSD-3-Clause - https://opensource.org/licenses/BSD-3-Clause"
__maintainer__ = "Colour Developers"
__email__ = "colour-developers@colour-science.org"
__status__ = "Production"

__all__ = [
    "lines_daylight_locus",
    "plot_daylight_locus",
    "LABELS_PLANCKIAN_LOCUS_DEFAULT",
    "lines_planckian_locus",
    "plot_planckian_locus",
    "plot_planckian_locus_in_chromaticity_diagram",
    "plot_planckian_locus_in_chromaticity_diagram_CIE1931",
    "plot_planckian_locus_in_chromaticity_diagram_CIE1960UCS",
    "plot_planckian_locus_in_chromaticity_diagram_CIE1976UCS",
]


[docs] def lines_daylight_locus( mireds: bool = False, method: (Literal["CIE 1931", "CIE 1960 UCS", "CIE 1976 UCS"] | str) = "CIE 1931", ) -> Tuple[NDArray]: """ Return the *Daylight Locus* line vertices, i.e., positions, normals and colours, according to given method. Parameters ---------- mireds Whether to use micro reciprocal degrees for the iso-temperature lines. method *Daylight Locus* method. Returns ------- :class:`tuple` Tuple of *Spectral Locus* vertices. Examples -------- >>> lines = lines_daylight_locus() >>> len(lines) 1 >>> lines[0].dtype dtype([('position', '<f8', (2,)), ('normal', '<f8', (2,)), \ ('colour', '<f8', (3,))]) """ method = validate_method(method, ("CIE 1931", "CIE 1960 UCS", "CIE 1976 UCS")) xy_to_ij = METHODS_CHROMATICITY_DIAGRAM[method]["xy_to_ij"] def CCT_to_plotting_colourspace(CCT): """ Convert given correlated colour temperature :math:`T_{cp}` to the default plotting colourspace. """ return normalise_maximum( XYZ_to_plotting_colourspace(xy_to_XYZ(CCT_to_xy_CIE_D(CCT))), axis=-1, ) start, end = (0, 1000) if mireds else (1e6 / 600, 1e6 / 10) CCT = np.arange(start, end + 100, 10) * 1.4388 / 1.4380 CCT = mired_to_CCT(CCT) if mireds else CCT ij_sl = np.reshape(xy_to_ij(CCT_to_xy_CIE_D(CCT)), (-1, 2)) colour_sl = np.reshape(CCT_to_plotting_colourspace(CCT), (-1, 3)) lines_sl = zeros( ij_sl.shape[0], [ ("position", DTYPE_FLOAT_DEFAULT, 2), ("normal", DTYPE_FLOAT_DEFAULT, 2), ("colour", DTYPE_FLOAT_DEFAULT, 3), ], # pyright: ignore ) lines_sl["position"] = ij_sl lines_sl["colour"] = colour_sl return (lines_sl,)
[docs] @override_style() def plot_daylight_locus( daylight_locus_colours: ArrayLike | str | None = None, daylight_locus_opacity: float = 1, daylight_locus_mireds: bool = False, method: (Literal["CIE 1931", "CIE 1960 UCS", "CIE 1976 UCS"] | str) = "CIE 1931", **kwargs: Any, ) -> Tuple[Figure, Axes]: """ Plot the *Daylight Locus* according to given method. Parameters ---------- daylight_locus_colours Colours of the *Daylight Locus*, if ``daylight_locus_colours`` is set to *RGB*, the colours will be computed according to the corresponding chromaticity coordinates. daylight_locus_opacity Opacity of the *Daylight Locus*. daylight_locus_mireds Whether to use micro reciprocal degrees for the iso-temperature lines. method *Chromaticity Diagram* method. Other Parameters ---------------- kwargs {:func:`colour.plotting.artist`, :func:`colour.plotting.render`}, See the documentation of the previously listed definitions. Returns ------- :class:`tuple` Current figure and axes. Examples -------- >>> plot_daylight_locus(daylight_locus_colours="RGB") ... # doctest: +ELLIPSIS (<Figure size ... with 1 Axes>, <...Axes...>) .. image:: ../_static/Plotting_Plot_Daylight_Locus.png :align: center :alt: plot_daylight_locus """ method = validate_method(method, ("CIE 1931", "CIE 1960 UCS", "CIE 1976 UCS")) use_RGB_daylight_locus_colours = str(daylight_locus_colours).upper() == "RGB" daylight_locus_colours = optional( daylight_locus_colours, CONSTANTS_COLOUR_STYLE.colour.dark ) settings: Dict[str, Any] = {"uniform": True} settings.update(kwargs) _figure, axes = artist(**settings) lines_sl, *_ = lines_daylight_locus(daylight_locus_mireds, method) line_collection = LineCollection( np.reshape( np.concatenate( [lines_sl["position"][:-1], lines_sl["position"][1:]], axis=1 ), (-1, 2, 2), ), # pyright: ignore colors=( lines_sl["colour"] if use_RGB_daylight_locus_colours else daylight_locus_colours ), alpha=daylight_locus_opacity, zorder=CONSTANTS_COLOUR_STYLE.zorder.foreground_line, ) axes.add_collection(line_collection) settings = {"axes": axes} settings.update(kwargs) return render(**settings)
LABELS_PLANCKIAN_LOCUS_DEFAULT: CanonicalMapping = CanonicalMapping( { "Default": (1e6 / 600, 2000, 2500, 3000, 4000, 6000, 1e6 / 100), "Mireds": (0, 100, 200, 300, 400, 500, 600, 700, 800, 900, 1000), } ) """*Planckian Locus* default labels."""
[docs] def lines_planckian_locus( labels: Sequence | None = None, mireds: bool = False, iso_temperature_lines_D_uv: float = 0.05, method: (Literal["CIE 1931", "CIE 1960 UCS", "CIE 1976 UCS"] | str) = "CIE 1931", ) -> Tuple[NDArray, NDArray]: """ Return the *Planckian Locus* line vertices, i.e., positions, normals and colours, according to given method. Parameters ---------- labels Array of labels used to customise which iso-temperature lines will be drawn along the *Planckian Locus*. Passing an empty array will result in no iso-temperature lines being drawn. mireds Whether to use micro reciprocal degrees for the iso-temperature lines. iso_temperature_lines_D_uv Iso-temperature lines :math:`\\Delta_{uv}` length on each side of the *Planckian Locus*. method *Planckian Locus* method. Returns ------- :class:`tuple` Tuple of *Planckian Locus* vertices and wavelength labels vertices. Examples -------- >>> lines = lines_planckian_locus() >>> len(lines) 2 >>> lines[0].dtype dtype([('position', '<f8', (2,)), ('normal', '<f8', (2,)), \ ('colour', '<f8', (3,))]) >>> lines[1].dtype dtype([('position', '<f8', (2,)), ('normal', '<f8', (2,)), \ ('colour', '<f8', (3,))]) """ method = validate_method(method, ("CIE 1931", "CIE 1960 UCS", "CIE 1976 UCS")) labels = cast( tuple, optional( labels, LABELS_PLANCKIAN_LOCUS_DEFAULT["Mireds" if mireds else "Default"], ), ) D_uv = iso_temperature_lines_D_uv uv_to_ij = METHODS_CHROMATICITY_DIAGRAM[method]["uv_to_ij"] def CCT_D_uv_to_plotting_colourspace(CCT_D_uv): """ Convert given correlated colour temperature :math:`T_{cp}` and :math:`\\Delta_{uv}` to the default plotting colourspace. """ return normalise_maximum( XYZ_to_plotting_colourspace( xy_to_XYZ(UCS_uv_to_xy(CCT_to_uv(CCT_D_uv, "Robertson 1968"))) ), axis=-1, ) # Planckian Locus start, end = (0, 1000) if mireds else (1e6 / 600, 1e6 / 10) CCT = np.arange(start, end + 100, 100) CCT = mired_to_CCT(CCT) if mireds else CCT CCT_D_uv = tstack([CCT, zeros(CCT.shape)]) ij_pl = uv_to_ij(CCT_to_uv(CCT_D_uv, "Robertson 1968")) colour_pl = CCT_D_uv_to_plotting_colourspace(CCT_D_uv) lines_pl = zeros( ij_pl.shape[0], [ ("position", DTYPE_FLOAT_DEFAULT, 2), ("normal", DTYPE_FLOAT_DEFAULT, 2), ("colour", DTYPE_FLOAT_DEFAULT, 3), ], # pyright: ignore ) lines_pl["position"] = ij_pl lines_pl["colour"] = colour_pl # Labels ij_itl, normal_itl, colour_itl = [], [], [] for label in labels: CCT_D_uv = tstack( [ full( 20, as_float_scalar(mired_to_CCT(label)) if mireds else label, ), np.linspace(-D_uv, D_uv, 20), ] ) ij = uv_to_ij(CCT_to_uv(CCT_D_uv, "Robertson 1968")) ij_itl.append(ij) normal_itl.append(np.tile(normalise_vector(ij[-1, ...] - ij[0, ...]), (20, 1))) colour_itl.append(CCT_D_uv_to_plotting_colourspace(CCT_D_uv)) ij_l = np.reshape(as_float_array(ij_itl), (-1, 2)) normal_l = np.reshape(as_float_array(normal_itl), (-1, 2)) colour_l = np.reshape(as_float_array(colour_itl), (-1, 3)) lines_l = zeros( ij_l.shape[0], [ ("position", DTYPE_FLOAT_DEFAULT, 2), ("normal", DTYPE_FLOAT_DEFAULT, 2), ("colour", DTYPE_FLOAT_DEFAULT, 3), ], # pyright: ignore ) lines_l["position"] = ij_l lines_l["normal"] = normal_l lines_l["colour"] = colour_l return lines_pl, lines_l
[docs] @override_style() def plot_planckian_locus( planckian_locus_colours: ArrayLike | str | None = None, planckian_locus_opacity: float = 1, planckian_locus_labels: Sequence | None = None, planckian_locus_mireds: bool = False, planckian_locus_iso_temperature_lines_D_uv: float = 0.05, method: (Literal["CIE 1931", "CIE 1960 UCS", "CIE 1976 UCS"] | str) = "CIE 1931", **kwargs: Any, ) -> Tuple[Figure, Axes]: """ Plot the *Planckian Locus* according to given method. Parameters ---------- planckian_locus_colours Colours of the *Planckian Locus*, if ``planckian_locus_colours`` is set to *RGB*, the colours will be computed according to the corresponding chromaticity coordinates. planckian_locus_opacity Opacity of the *Planckian Locus*. planckian_locus_labels Array of labels used to customise which iso-temperature lines will be drawn along the *Planckian Locus*. Passing an empty array will result in no iso-temperature lines being drawn. planckian_locus_mireds Whether to use micro reciprocal degrees for the iso-temperature lines. planckian_locus_iso_temperature_lines_D_uv Iso-temperature lines :math:`\\Delta_{uv}` length on each side of the *Planckian Locus*. method *Chromaticity Diagram* method. Other Parameters ---------------- kwargs {:func:`colour.plotting.artist`, :func:`colour.plotting.render`}, See the documentation of the previously listed definitions. Returns ------- :class:`tuple` Current figure and axes. Examples -------- >>> plot_planckian_locus(planckian_locus_colours="RGB") ... # doctest: +ELLIPSIS (<Figure size ... with 1 Axes>, <...Axes...>) .. image:: ../_static/Plotting_Plot_Planckian_Locus.png :align: center :alt: plot_planckian_locus """ planckian_locus_colours = optional( planckian_locus_colours, CONSTANTS_COLOUR_STYLE.colour.dark ) use_RGB_planckian_locus_colours = str(planckian_locus_colours).upper() == "RGB" labels = cast( tuple, optional( planckian_locus_labels, LABELS_PLANCKIAN_LOCUS_DEFAULT[ "Mireds" if planckian_locus_mireds else "Default" ], ), ) settings: Dict[str, Any] = {"uniform": True} settings.update(kwargs) _figure, axes = artist(**settings) lines_pl, lines_l = lines_planckian_locus( labels, planckian_locus_mireds, planckian_locus_iso_temperature_lines_D_uv, method, ) axes.add_collection( LineCollection( np.reshape( np.concatenate( [lines_pl["position"][:-1], lines_pl["position"][1:]], axis=1 ), (-1, 2, 2), ), # pyright: ignore colors=( lines_pl["colour"] if use_RGB_planckian_locus_colours else planckian_locus_colours ), alpha=planckian_locus_opacity, zorder=CONSTANTS_COLOUR_STYLE.zorder.foreground_line, ) ) lines_itl = np.reshape(lines_l["position"], (len(labels), 20, 2)) colours_itl = np.reshape(lines_l["colour"], (len(labels), 20, 3)) for i, label in enumerate(labels): axes.add_collection( LineCollection( np.reshape( np.concatenate( [lines_itl[i][:-1], lines_itl[i][1:]], # pyright: ignore axis=1, ), (-1, 2, 2), ), colors=( colours_itl[i] if use_RGB_planckian_locus_colours else planckian_locus_colours ), alpha=planckian_locus_opacity, zorder=CONSTANTS_COLOUR_STYLE.zorder.foreground_line, ) ) axes.text( lines_itl[i][-1, 0], lines_itl[i][-1, 1], f'{as_int_scalar(label)}{"M" if planckian_locus_mireds else "K"}', clip_on=True, ha="left", va="bottom", fontsize="x-small-colour-science", zorder=CONSTANTS_COLOUR_STYLE.zorder.foreground_label, ) settings = {"axes": axes} settings.update(kwargs) return render(**settings)
[docs] @override_style() def plot_planckian_locus_in_chromaticity_diagram( illuminants: str | Sequence[str] | None = None, chromaticity_diagram_callable: Callable = plot_chromaticity_diagram, method: (Literal["CIE 1931", "CIE 1960 UCS", "CIE 1976 UCS"] | str) = "CIE 1931", annotate_kwargs: dict | List[dict] | None = None, plot_kwargs: dict | List[dict] | None = None, **kwargs: Any, ) -> Tuple[Figure, Axes]: """ Plot the *Planckian Locus* and given illuminants in the *Chromaticity Diagram* according to given method. Parameters ---------- illuminants Illuminants to plot. ``illuminants`` elements can be of any type or form supported by the :func:`colour.plotting.common.filter_passthrough` definition. chromaticity_diagram_callable Callable responsible for drawing the *Chromaticity Diagram*. method *Chromaticity Diagram* method. annotate_kwargs Keyword arguments for the :func:`matplotlib.pyplot.annotate` definition, used to annotate the resulting chromaticity coordinates with their respective spectral distribution names. ``annotate_kwargs`` can be either a single dictionary applied to all the arrows with same settings or a sequence of dictionaries with different settings for each spectral distribution. The following special keyword arguments can also be used: - ``annotate`` : Whether to annotate the spectral distributions. plot_kwargs Keyword arguments for the :func:`matplotlib.pyplot.plot` definition, used to control the style of the plotted illuminants. ``plot_kwargs`` can be either a single dictionary applied to all the plotted illuminants with the same settings or a sequence of dictionaries with different settings for eachplotted illuminant. Other Parameters ---------------- kwargs {:func:`colour.plotting.artist`, :func:`colour.plotting.diagrams.plot_chromaticity_diagram`, :func:`colour.plotting.temperature.plot_planckian_locus`, :func:`colour.plotting.render`}, See the documentation of the previously listed definitions. Returns ------- :class:`tuple` Current figure and axes. Examples -------- >>> annotate_kwargs = [ ... {"xytext": (-25, 15), "arrowprops": {"arrowstyle": "-"}}, ... {"arrowprops": {"arrowstyle": "-["}}, ... {}, ... ] >>> plot_kwargs = [ ... { ... "markersize": 15, ... }, ... {"color": "r"}, ... {}, ... ] >>> plot_planckian_locus_in_chromaticity_diagram( ... ["A", "B", "C"], ... annotate_kwargs=annotate_kwargs, ... plot_kwargs=plot_kwargs, ... ) # doctest: +ELLIPSIS (<Figure size ... with 1 Axes>, <...Axes...>) .. image:: ../_static/Plotting_\ Plot_Planckian_Locus_In_Chromaticity_Diagram.png :align: center :alt: plot_planckian_locus_in_chromaticity_diagram """ illuminants = optional(illuminants, []) method = validate_method(method, ("CIE 1931", "CIE 1960 UCS", "CIE 1976 UCS")) cmfs = MSDS_CMFS["CIE 1931 2 Degree Standard Observer"] illuminants_filtered = filter_passthrough(CCS_ILLUMINANTS[cmfs.name], illuminants) settings: Dict[str, Any] = {"uniform": True} settings.update(kwargs) _figure, axes = artist(**settings) method = method.upper() settings = {"axes": axes, "method": method} settings.update(kwargs) settings["show"] = False chromaticity_diagram_callable(**settings) plot_planckian_locus(**settings) xy_to_ij = METHODS_CHROMATICITY_DIAGRAM[method]["xy_to_ij"] if method == "CIE 1931": bounding_box = (-0.1, 0.9, -0.1, 0.9) elif method == "CIE 1960 UCS": bounding_box = (-0.1, 0.7, -0.2, 0.6) elif method == "CIE 1976 UCS": bounding_box = (-0.1, 0.7, -0.1, 0.7) annotate_settings_collection = [ { "annotate": True, "xytext": (-50, 30), "textcoords": "offset points", "arrowprops": CONSTANTS_ARROW_STYLE, "zorder": CONSTANTS_COLOUR_STYLE.zorder.foreground_annotation, } for _ in range(len(illuminants_filtered)) ] if annotate_kwargs is not None: update_settings_collection( annotate_settings_collection, annotate_kwargs, len(illuminants_filtered), ) plot_settings_collection = [ { "color": CONSTANTS_COLOUR_STYLE.colour.brightest, "label": f"{illuminant}", "marker": "o", "markeredgecolor": CONSTANTS_COLOUR_STYLE.colour.dark, "markeredgewidth": CONSTANTS_COLOUR_STYLE.geometry.short * 0.75, "markersize": ( CONSTANTS_COLOUR_STYLE.geometry.short * 6 + CONSTANTS_COLOUR_STYLE.geometry.short * 0.75 ), "zorder": CONSTANTS_COLOUR_STYLE.zorder.foreground_line, } for illuminant in illuminants_filtered ] if plot_kwargs is not None: update_settings_collection( plot_settings_collection, plot_kwargs, len(illuminants_filtered) ) for i, (illuminant, xy) in enumerate(illuminants_filtered.items()): plot_settings = plot_settings_collection[i] ij = cast(tuple[float, float], xy_to_ij(xy)) axes.plot(ij[0], ij[1], **plot_settings) if annotate_settings_collection[i]["annotate"]: annotate_settings = annotate_settings_collection[i] annotate_settings.pop("annotate") axes.annotate(illuminant, xy=ij, **annotate_settings) title = ( ( f"{', '.join(illuminants_filtered)} Illuminants - Planckian Locus\n" f"{method.upper()} Chromaticity Diagram - " "CIE 1931 2 Degree Standard Observer" ) if illuminants_filtered else ( f"Planckian Locus\n{method.upper()} Chromaticity Diagram - " f"CIE 1931 2 Degree Standard Observer" ) ) settings.update( { "axes": axes, "show": True, "bounding_box": bounding_box, "title": title, } ) settings.update(kwargs) return render(**settings)
[docs] @override_style() def plot_planckian_locus_in_chromaticity_diagram_CIE1931( illuminants: str | Sequence[str] | None = None, chromaticity_diagram_callable_CIE1931: Callable = ( plot_chromaticity_diagram_CIE1931 ), annotate_kwargs: dict | List[dict] | None = None, plot_kwargs: dict | List[dict] | None = None, **kwargs: Any, ) -> Tuple[Figure, Axes]: """ Plot the *Planckian Locus* and given illuminants in *CIE 1931 Chromaticity Diagram*. Parameters ---------- illuminants Illuminants to plot. ``illuminants`` elements can be of any type or form supported by the :func:`colour.plotting.common.filter_passthrough` definition. chromaticity_diagram_callable_CIE1931 Callable responsible for drawing the *CIE 1931 Chromaticity Diagram*. annotate_kwargs Keyword arguments for the :func:`matplotlib.pyplot.annotate` definition, used to annotate the resulting chromaticity coordinates with their respective spectral distribution names. ``annotate_kwargs`` can be either a single dictionary applied to all the arrows with same settings or a sequence of dictionaries with different settings for each spectral distribution. The following special keyword arguments can also be used: - ``annotate`` : Whether to annotate the spectral distributions. plot_kwargs Keyword arguments for the :func:`matplotlib.pyplot.plot` definition, used to control the style of the plotted illuminants. ``plot_kwargs`` can be either a single dictionary applied to all the plotted illuminants with the same settings or a sequence of dictionaries with different settings for eachplotted illuminant. Other Parameters ---------------- kwargs {:func:`colour.plotting.artist`, :func:`colour.plotting.diagrams.plot_chromaticity_diagram`, :func:`colour.plotting.temperature.plot_planckian_locus`, :func:`colour.plotting.temperature.\ plot_planckian_locus_in_chromaticity_diagram`, :func:`colour.plotting.render`}, See the documentation of the previously listed definitions. Returns ------- :class:`tuple` Current figure and axes. Examples -------- >>> plot_planckian_locus_in_chromaticity_diagram_CIE1931(["A", "B", "C"]) ... # doctest: +ELLIPSIS (<Figure size ... with 1 Axes>, <...Axes...>) .. image:: ../_static/Plotting_\ Plot_Planckian_Locus_In_Chromaticity_Diagram_CIE1931.png :align: center :alt: plot_planckian_locus_in_chromaticity_diagram_CIE1931 """ settings = dict(kwargs) settings.update({"method": "CIE 1931"}) return plot_planckian_locus_in_chromaticity_diagram( illuminants, chromaticity_diagram_callable_CIE1931, annotate_kwargs=annotate_kwargs, plot_kwargs=plot_kwargs, **settings, )
[docs] @override_style() def plot_planckian_locus_in_chromaticity_diagram_CIE1960UCS( illuminants: str | Sequence[str] | None = None, chromaticity_diagram_callable_CIE1960UCS: Callable = ( plot_chromaticity_diagram_CIE1960UCS ), annotate_kwargs: dict | List[dict] | None = None, plot_kwargs: dict | List[dict] | None = None, **kwargs: Any, ) -> Tuple[Figure, Axes]: """ Plot the *Planckian Locus* and given illuminants in *CIE 1960 UCS Chromaticity Diagram*. Parameters ---------- illuminants Illuminants to plot. ``illuminants`` elements can be of any type or form supported by the :func:`colour.plotting.common.filter_passthrough` definition. chromaticity_diagram_callable_CIE1960UCS Callable responsible for drawing the *CIE 1960 UCS Chromaticity Diagram*. annotate_kwargs Keyword arguments for the :func:`matplotlib.pyplot.annotate` definition, used to annotate the resulting chromaticity coordinates with their respective spectral distribution names. ``annotate_kwargs`` can be either a single dictionary applied to all the arrows with same settings or a sequence of dictionaries with different settings for each spectral distribution. The following special keyword arguments can also be used: - ``annotate`` : Whether to annotate the spectral distributions. plot_kwargs Keyword arguments for the :func:`matplotlib.pyplot.plot` definition, used to control the style of the plotted illuminants. ``plot_kwargs`` can be either a single dictionary applied to all the plotted illuminants with the same settings or a sequence of dictionaries with different settings for eachplotted illuminant. Other Parameters ---------------- kwargs {:func:`colour.plotting.artist`, :func:`colour.plotting.diagrams.plot_chromaticity_diagram`, :func:`colour.plotting.temperature.plot_planckian_locus`, :func:`colour.plotting.temperature.\ plot_planckian_locus_in_chromaticity_diagram`, :func:`colour.plotting.render`}, See the documentation of the previously listed definitions. Returns ------- :class:`tuple` Current figure and axes. Examples -------- >>> plot_planckian_locus_in_chromaticity_diagram_CIE1960UCS( ... ["A", "C", "E"] ... ) # doctest: +ELLIPSIS (<Figure size ... with 1 Axes>, <...Axes...>) .. image:: ../_static/Plotting_\ Plot_Planckian_Locus_In_Chromaticity_Diagram_CIE1960UCS.png :align: center :alt: plot_planckian_locus_in_chromaticity_diagram_CIE1960UCS """ settings = dict(kwargs) settings.update({"method": "CIE 1960 UCS"}) return plot_planckian_locus_in_chromaticity_diagram( illuminants, chromaticity_diagram_callable_CIE1960UCS, annotate_kwargs=annotate_kwargs, plot_kwargs=plot_kwargs, **settings, )
[docs] @override_style() def plot_planckian_locus_in_chromaticity_diagram_CIE1976UCS( illuminants: str | Sequence[str] | None = None, chromaticity_diagram_callable_CIE1976UCS: Callable = ( plot_chromaticity_diagram_CIE1976UCS ), annotate_kwargs: dict | List[dict] | None = None, plot_kwargs: dict | List[dict] | None = None, **kwargs: Any, ) -> Tuple[Figure, Axes]: """ Plot the *Planckian Locus* and given illuminants in *CIE 1976 UCS Chromaticity Diagram*. Parameters ---------- illuminants Illuminants to plot. ``illuminants`` elements can be of any type or form supported by the :func:`colour.plotting.common.filter_passthrough` definition. chromaticity_diagram_callable_CIE1976UCS Callable responsible for drawing the *CIE 1976 UCS Chromaticity Diagram*. annotate_kwargs Keyword arguments for the :func:`matplotlib.pyplot.annotate` definition, used to annotate the resulting chromaticity coordinates with their respective spectral distribution names. ``annotate_kwargs`` can be either a single dictionary applied to all the arrows with same settings or a sequence of dictionaries with different settings for each spectral distribution. The following special keyword arguments can also be used: - ``annotate`` : Whether to annotate the spectral distributions. plot_kwargs Keyword arguments for the :func:`matplotlib.pyplot.plot` definition, used to control the style of the plotted illuminants. ``plot_kwargs`` can be either a single dictionary applied to all the plotted illuminants with the same settings or a sequence of dictionaries with different settings for eachplotted illuminant. Other Parameters ---------------- kwargs {:func:`colour.plotting.artist`, :func:`colour.plotting.diagrams.plot_chromaticity_diagram`, :func:`colour.plotting.temperature.plot_planckian_locus`, :func:`colour.plotting.temperature.\ plot_planckian_locus_in_chromaticity_diagram`, :func:`colour.plotting.render`}, See the documentation of the previously listed definitions. Returns ------- :class:`tuple` Current figure and axes. Examples -------- >>> plot_planckian_locus_in_chromaticity_diagram_CIE1976UCS( ... ["A", "C", "E"] ... ) # doctest: +ELLIPSIS (<Figure size ... with 1 Axes>, <...Axes...>) .. image:: ../_static/Plotting_\ Plot_Planckian_Locus_In_Chromaticity_Diagram_CIE1976UCS.png :align: center :alt: plot_planckian_locus_in_chromaticity_diagram_CIE1976UCS """ settings = dict(kwargs) settings.update({"method": "CIE 1976 UCS"}) return plot_planckian_locus_in_chromaticity_diagram( illuminants, chromaticity_diagram_callable_CIE1976UCS, annotate_kwargs=annotate_kwargs, plot_kwargs=plot_kwargs, **settings, )