from __future__ import annotations
import matplotlib as mpl
import matplotlib.pyplot as plt
try:
import cmcrameri.cm except ImportError:
pass
_FONT_STACK = [
"Inter",
"Helvetica Neue",
"Helvetica",
"Arial",
"DejaVu Sans",
"sans-serif",
]
DSFB_PRIMARY = "#0F4C5C"
DSFB_REFERENCE = "#4F6173"
DSFB_ACCENT = "#E36414"
DSFB_HIGHLIGHT = "#2A9D8F"
DSFB_GRAY = "#7C7E80"
DSFB_BG = "#F2EFE8"
DSFB_LADDER = ["#9CCC65", "#FFB300", "#F4511E", "#C62828"]
GRAMMAR_PALETTE = {
"Admissible": "#F2EFE8",
"Boundary": "#E36414",
"Violation": "#9A031E",
}
POLICY_PALETTE = {
"Silent": "#FFFFFF",
"Watch": "#A8DADC",
"Review": "#E36414",
"Escalate": "#9A031E",
}
def install():
rcparams = {
"font.family": "sans-serif",
"font.sans-serif": _FONT_STACK,
"font.size": 9,
"axes.labelsize": 9,
"axes.titlesize": 11,
"axes.titleweight": "bold",
"axes.labelweight": "regular",
"axes.spines.top": False,
"axes.spines.right": False,
"axes.linewidth": 0.8,
"axes.edgecolor": "#444",
"axes.titlepad": 8,
"axes.labelpad": 6,
"xtick.labelsize": 8,
"ytick.labelsize": 8,
"xtick.major.width": 0.6,
"ytick.major.width": 0.6,
"xtick.color": "#222",
"ytick.color": "#222",
"xtick.direction": "out",
"ytick.direction": "out",
"axes.grid": True,
"grid.color": "#E5E5E5",
"grid.linewidth": 0.5,
"grid.linestyle": "-",
"axes.axisbelow": True,
"legend.frameon": False,
"legend.fontsize": 8,
"legend.labelspacing": 0.4,
"legend.handlelength": 1.4,
"legend.handletextpad": 0.6,
"savefig.dpi": 300,
"savefig.bbox": "tight",
"savefig.pad_inches": 0.08,
"figure.dpi": 100,
"figure.facecolor": "white",
"axes.facecolor": "white",
"lines.linewidth": 1.6,
"lines.markersize": 4.0,
"lines.markeredgewidth": 0.8,
"patch.linewidth": 0.6,
"patch.edgecolor": "#444",
}
mpl.rcParams.update(rcparams)
def figsize(kind: str = "single") -> tuple[float, float]:
mm_per_in = 25.4
table = {
"single": (88, 65),
"double": (180, 110),
"wide": (180, 90),
"square": (110, 110),
"tall": (88, 130),
"twocol": (180, 100),
}
w, h = table.get(kind, (180, 110))
return (w / mm_per_in, h / mm_per_in)
def add_caption(fig, text: str, y: float = -0.04, fontsize: int = 8):
fig.text(
0.0, y, text,
ha="left", va="top",
fontsize=fontsize, color="#333",
wrap=True,
transform=fig.transFigure,
)
def annotate_value(ax, x, y, label, dx=0, dy=0, **kwargs):
ax.annotate(
label, xy=(x, y), xytext=(x + dx, y + dy),
fontsize=8, color="#222", ha="left", va="center",
**kwargs,
)