Source code for plotnine.positions.position_jitter

from __future__ import annotations

import typing
from copy import deepcopy

import numpy as np

from ..utils import jitter, resolution
from .position import position

if typing.TYPE_CHECKING:
    from plotnine.typing import FloatArray, FloatArrayLike


[docs]class position_jitter(position): """ Jitter points to avoid overplotting Parameters ---------- width : float Proportion to jitter in horizontal direction. Default is ``0.4`` of the resolution of the data. height : float Proportion to jitter in vertical direction. Default is ``0.4`` of the resolution of the data. random_state : int or ~numpy.random.RandomState, optional Seed or Random number generator to use. If ``None``, then numpy global generator :class:`numpy.random` is used. """ REQUIRED_AES = {"x", "y"} def __init__(self, width=None, height=None, random_state=None): self.params = { "width": width, "height": height, "random_state": random_state, } def setup_params(self, data): params = deepcopy(self.params) if params["width"] is None: params["width"] = resolution(data["x"]) * 0.4 if params["height"] is None: params["height"] = resolution(data["y"]) * 0.4 if not params["random_state"]: params["random_state"] = np.random return params @classmethod def compute_layer(cls, data, params, layout): trans_x = None # pyright: ignore trans_y = None # pyright: ignore if params["width"]: def trans_x(x: FloatArrayLike) -> FloatArray: return jitter( x, amount=params["width"], random_state=params["random_state"], ) if params["height"]: def trans_y(y): return jitter( y, amount=params["height"], random_state=params["random_state"], ) return cls.transform_position(data, trans_x, trans_y)