Example #1
0
    def test_is_integer(self):
        """
        Tests :func:`colour.utilities.common.is_integer` definition.
        """

        self.assertTrue(is_integer(1))

        self.assertTrue(is_integer(1.001))

        self.assertFalse(is_integer(1.01))
Example #2
0
    def test_is_integer(self):
        """
        Tests :func:`colour.utilities.common.is_integer` definition.
        """

        self.assertTrue(is_integer(1))

        self.assertTrue(is_integer(1.001))

        self.assertFalse(is_integer(1.01))
Example #3
0
    def window(self, value):
        """
        Setter for the **self.window** property.
        """

        if value is not None:
            assert is_integer(value), '"window" must be an integer!'

            assert value >= 1, '"window" must be equal or superior to 1!'

            self._window = value

            # Triggering "self._x_p" update.
            if self._x is not None:
                self.x = self._x

            # Triggering "self._y_p" update.
            if self._y is not None:
                self.y = self._y
Example #4
0
def nadir_grid(
    limits: Optional[ArrayLike] = None,
    segments: Integer = 10,
    labels: Optional[Sequence[str]] = None,
    axes: Optional[plt.Axes] = None,
    **kwargs: Any,
) -> Tuple[NDArray, NDArray, NDArray]:
    """
    Return a grid on *CIE xy* plane made of quad geometric elements and its
    associated faces and edges colours. Ticks and labels are added to the
    given axes according to the extended grid settings.

    Parameters
    ----------
    limits
        Extended grid limits.
    segments
        Edge segments count for the extended grid.
    labels
        Axis labels.
    axes
        Axes to add the grid.

    Other Parameters
    ----------------
    grid_edge_alpha
        Grid edge opacity value such as `grid_edge_alpha = 0.5`.
    grid_edge_colours
        Grid edge colours array such as
        `grid_edge_colours = (0.25, 0.25, 0.25)`.
    grid_face_alpha
        Grid face opacity value such as `grid_face_alpha = 0.1`.
    grid_face_colours
        Grid face colours array such as
        `grid_face_colours = (0.25, 0.25, 0.25)`.
    ticks_and_label_location
        Location of the *X* and *Y* axis ticks and labels such as
        `ticks_and_label_location = ('-x', '-y')`.
    x_axis_colour
        *X* axis colour array such as `x_axis_colour = (0.0, 0.0, 0.0, 1.0)`.
    x_label_colour
        *X* axis label colour array such as
        `x_label_colour = (0.0, 0.0, 0.0, 0.85)`.
    x_ticks_colour
        *X* axis ticks colour array such as
        `x_ticks_colour = (0.0, 0.0, 0.0, 0.85)`.
    y_axis_colour
        *Y* axis colour array such as `y_axis_colour = (0.0, 0.0, 0.0, 1.0)`.
    y_label_colour
        *Y* axis label colour array such as
        `y_label_colour = (0.0, 0.0, 0.0, 0.85)`.
    y_ticks_colour
        *Y* axis ticks colour array such as
        `y_ticks_colour = (0.0, 0.0, 0.0, 0.85)`.

    Returns
    -------
    :class:`tuple`
        Grid quads, faces colours, edges colours.

    Examples
    --------
    >>> nadir_grid(segments=1)
    (array([[[-1.   , -1.   ,  0.   ],
            [ 1.   , -1.   ,  0.   ],
            [ 1.   ,  1.   ,  0.   ],
            [-1.   ,  1.   ,  0.   ]],
    <BLANKLINE>
           [[-1.   , -1.   ,  0.   ],
            [ 0.   , -1.   ,  0.   ],
            [ 0.   ,  0.   ,  0.   ],
            [-1.   ,  0.   ,  0.   ]],
    <BLANKLINE>
           [[-1.   ,  0.   ,  0.   ],
            [ 0.   ,  0.   ,  0.   ],
            [ 0.   ,  1.   ,  0.   ],
            [-1.   ,  1.   ,  0.   ]],
    <BLANKLINE>
           [[ 0.   , -1.   ,  0.   ],
            [ 1.   , -1.   ,  0.   ],
            [ 1.   ,  0.   ,  0.   ],
            [ 0.   ,  0.   ,  0.   ]],
    <BLANKLINE>
           [[ 0.   ,  0.   ,  0.   ],
            [ 1.   ,  0.   ,  0.   ],
            [ 1.   ,  1.   ,  0.   ],
            [ 0.   ,  1.   ,  0.   ]],
    <BLANKLINE>
           [[-1.   , -0.001,  0.   ],
            [ 1.   , -0.001,  0.   ],
            [ 1.   ,  0.001,  0.   ],
            [-1.   ,  0.001,  0.   ]],
    <BLANKLINE>
           [[-0.001, -1.   ,  0.   ],
            [ 0.001, -1.   ,  0.   ],
            [ 0.001,  1.   ,  0.   ],
            [-0.001,  1.   ,  0.   ]]]), array([[ 0.25,  0.25,  0.25,  0.1 ],
           [ 0.  ,  0.  ,  0.  ,  0.  ],
           [ 0.  ,  0.  ,  0.  ,  0.  ],
           [ 0.  ,  0.  ,  0.  ,  0.  ],
           [ 0.  ,  0.  ,  0.  ,  0.  ],
           [ 0.  ,  0.  ,  0.  ,  1.  ],
           [ 0.  ,  0.  ,  0.  ,  1.  ]]), array([[ 0.5 ,  0.5 ,  0.5 ,  0.5 ],
           [ 0.75,  0.75,  0.75,  0.25],
           [ 0.75,  0.75,  0.75,  0.25],
           [ 0.75,  0.75,  0.75,  0.25],
           [ 0.75,  0.75,  0.75,  0.25],
           [ 0.  ,  0.  ,  0.  ,  1.  ],
           [ 0.  ,  0.  ,  0.  ,  1.  ]]))
    """

    limits = as_float_array(
        cast(ArrayLike, optional(limits, np.array([[-1, 1], [-1, 1]]))))
    labels = cast(Sequence, optional(labels, ("x", "y")))

    extent = np.max(np.abs(limits[..., 1] - limits[..., 0]))

    settings = Structure(
        **{
            "grid_face_colours": (0.25, 0.25, 0.25),
            "grid_edge_colours": (0.50, 0.50, 0.50),
            "grid_face_alpha": 0.1,
            "grid_edge_alpha": 0.5,
            "x_axis_colour": (0.0, 0.0, 0.0, 1.0),
            "y_axis_colour": (0.0, 0.0, 0.0, 1.0),
            "x_ticks_colour": (0.0, 0.0, 0.0, 0.85),
            "y_ticks_colour": (0.0, 0.0, 0.0, 0.85),
            "x_label_colour": (0.0, 0.0, 0.0, 0.85),
            "y_label_colour": (0.0, 0.0, 0.0, 0.85),
            "ticks_and_label_location": ("-x", "-y"),
        })
    settings.update(**kwargs)

    # Outer grid.
    quads_g = primitive_vertices_grid_mpl(
        origin=(-extent / 2, -extent / 2),
        width=extent,
        height=extent,
        height_segments=segments,
        width_segments=segments,
    )

    RGB_g = ones((quads_g.shape[0], quads_g.shape[-1]))
    RGB_gf = RGB_g * settings.grid_face_colours
    RGB_gf = np.hstack(
        [RGB_gf, full((RGB_gf.shape[0], 1), settings.grid_face_alpha)])
    RGB_ge = RGB_g * settings.grid_edge_colours
    RGB_ge = np.hstack(
        [RGB_ge, full((RGB_ge.shape[0], 1), settings.grid_edge_alpha)])

    # Inner grid.
    quads_gs = primitive_vertices_grid_mpl(
        origin=(-extent / 2, -extent / 2),
        width=extent,
        height=extent,
        height_segments=segments * 2,
        width_segments=segments * 2,
    )

    RGB_gs = ones((quads_gs.shape[0], quads_gs.shape[-1]))
    RGB_gsf = RGB_gs * 0
    RGB_gsf = np.hstack([RGB_gsf, full((RGB_gsf.shape[0], 1), 0)])
    RGB_gse = np.clip(RGB_gs * settings.grid_edge_colours * 1.5, 0, 1)
    RGB_gse = np.hstack(
        (RGB_gse, full((RGB_gse.shape[0], 1), settings.grid_edge_alpha / 2)))

    # Axis.
    thickness = extent / 1000
    quad_x = primitive_vertices_grid_mpl(origin=(limits[0, 0], -thickness / 2),
                                         width=extent,
                                         height=thickness)
    RGB_x = ones((quad_x.shape[0], quad_x.shape[-1] + 1))
    RGB_x = RGB_x * settings.x_axis_colour

    quad_y = primitive_vertices_grid_mpl(origin=(-thickness / 2, limits[1, 0]),
                                         width=thickness,
                                         height=extent)
    RGB_y = ones((quad_y.shape[0], quad_y.shape[-1] + 1))
    RGB_y = RGB_y * settings.y_axis_colour

    if axes is not None:
        # Ticks.
        x_s = 1 if "+x" in settings.ticks_and_label_location else -1
        y_s = 1 if "+y" in settings.ticks_and_label_location else -1
        for i, axis in enumerate("xy"):
            h_a = "center" if axis == "x" else "left" if x_s == 1 else "right"
            v_a = "center"

            ticks = list(sorted(set(quads_g[..., 0, i])))
            ticks += [ticks[-1] + ticks[-1] - ticks[-2]]
            for tick in ticks:
                x = (limits[1, 1 if x_s == 1 else 0] +
                     (x_s * extent / 25) if i else tick)
                y = (tick if i else limits[0, 1 if y_s == 1 else 0] +
                     (y_s * extent / 25))

                tick = as_int_scalar(tick) if is_integer(tick) else tick
                c = settings[f"{axis}_ticks_colour"]

                axes.text(
                    x,
                    y,
                    0,
                    tick,
                    "x",
                    horizontalalignment=h_a,
                    verticalalignment=v_a,
                    color=c,
                    clip_on=True,
                )

        # Labels.
        for i, axis in enumerate("xy"):
            h_a = "center" if axis == "x" else "left" if x_s == 1 else "right"
            v_a = "center"

            x = (limits[1, 1 if x_s == 1 else 0] +
                 (x_s * extent / 10) if i else 0)
            y = (0 if i else limits[0, 1 if y_s == 1 else 0] +
                 (y_s * extent / 10))

            c = settings[f"{axis}_label_colour"]

            axes.text(
                x,
                y,
                0,
                labels[i],
                "x",
                horizontalalignment=h_a,
                verticalalignment=v_a,
                color=c,
                size=20,
                clip_on=True,
            )

    quads = np.vstack([quads_g, quads_gs, quad_x, quad_y])
    RGB_f = np.vstack([RGB_gf, RGB_gsf, RGB_x, RGB_y])
    RGB_e = np.vstack([RGB_ge, RGB_gse, RGB_x, RGB_y])

    return quads, RGB_f, RGB_e