Skip to content

Gallery

HTML gallery generation from pipeline results, plus the one-line plot_result entry point for rendering a single concept straight from a PipelineResult.

The gallery is assembled from a GalleryModel of PlotConcept entries built by build_gallery_model; generate_gallery renders it to a self-contained HTML page.

One-line plotting

plot_result

plot_result(
    result: PipelineResult,
    concept: str,
    level: Level | str | None = None,
    *,
    backend: str = "matplotlib",
    volume_scale: float | None = None,
    **overrides: Any,
) -> Any

Render one plot concept straight from a :class:PipelineResult.

The one-liner the gallery is built on, without the gallery: it derives the same per-face context (spread, focus window, snapshot, volume scale) via :func:build_gallery_model -- the single source of truth for how each concept binds to its prepare function -- then prepares and renders the face. So plot_result(result, "depth_heatmap") replaces having to know the private prepare_price_levels_data name and its argument shape.

Parameters:

Name Type Description Default
result PipelineResult

Pipeline output (events / trades / depth / depth_summary).

required
concept str

Concept key, e.g. "trade_tape" (see :data:available_concepts).

required
level Level or str or None

"L2" / "L3" (or a :class:Level). None picks the concept's only level, preferring L2 when both exist.

None
backend str

"matplotlib" (default) or "plotly".

'matplotlib'
volume_scale float or None

Display volume scale; None auto-infers (as the gallery does).

None
**overrides Any

Extra keyword arguments merged over the prepare call (e.g. col_bias=0.1 for the depth heatmap).

{}

Returns:

Type Description
A Matplotlib ``Figure`` or a Plotly ``Figure``, per *backend*.

Raises:

Type Description
KeyError

If concept is not built for this result, or has no variant at level. The message lists what is available.

available_concepts

available_concepts(
    result: PipelineResult,
) -> dict[str, list[str]]

Concept keys built for result, mapped to their available level names.

A discoverability companion to :func:plot_result: shows what plot_result(result, concept, level=...) can render for this dataset (which varies by format -- e.g. hidden_executions is LOBSTER-only).

build_gallery_model(
    result: PipelineResult,
    *,
    volume_scale: float | None = None,
) -> GalleryModel

Build the default gallery model from pipeline results.

Every order-book concept is registered with its Level.L2 variant (the L3 faces are added by later renderers; a concept becomes :attr:~PlotConcept.comparable automatically once both exist). Analytics are not derived here -- callers append computed analytic panels (built with the *_panel helpers) to :attr:GalleryModel.analytics.

Parameters:

Name Type Description Default
result PipelineResult

Pipeline output.

required
volume_scale float or None

Volume display scale. None (default) auto-infers a power-of-10 scale from result.events['volume'] via :func:infer_volume_scale.

None

Returns:

Type Description
GalleryModel

GalleryModel dataclass

GalleryModel(
    concepts: list[PlotConcept],
    analytics: list[PlotSpec] = list(),
)

The gallery's inventory: leveled concepts + level-less analytics.

PlotConcept dataclass

PlotConcept(
    key: str,
    title: str,
    variants: dict[Level, PlotSpec],
    note: str = "",
)

A level-neutral plot identity with up to one variant per :class:Level.

The key never carries a level; the level lives in the registry coordinate (concept, level, backend) and in the keys of variants.

comparable property

comparable: bool

True when both an L2 and an L3 face are registered.

Derived, never curated: the existence of both variants is the L2<->L3 pairing, so it can never drift out of sync with what is built.

at

at(level: Level) -> PlotSpec | None

Return the variant registered at level, or None.

PlotSpec dataclass

PlotSpec(
    name: str,
    title: str,
    plot_name: str,
    prepare: Callable[..., dict],
    prep_kwargs: dict[str, Any] = dict(),
)

How to prepare and label a single plot face.

A spec carries no level of its own -- the level is a coordinate on the owning :class:PlotConcept (for leveled concepts) or None (for the level-less analytics in :attr:GalleryModel.analytics).

Parameters:

Name Type Description Default
name str

Identifier / file stem for analytic panels (e.g. "vpin"). For a concept variant the file stem is derived from the concept + level, so name is only metadata there.

required
title str

Human-readable title (used directly for analytic cards; concept cards take their title from the concept).

required
plot_name str

Dispatcher concept key for :func:ob_analytics.visualization.plot.

required
prepare Callable

prepare_<name>_data helper returning the renderer payload.

required
prep_kwargs dict

Keyword arguments passed to prepare.

dict()
generate_gallery(
    result: PipelineResult | None,
    output_dir: str | Path,
    *,
    model: GalleryModel | None = None,
    view: str = "both",
    volume_scale: float | None = None,
    backends: list[str] | None = None,
    title: str = "ob-analytics Plot Gallery",
) -> Path

Render a gallery view and write a standalone HTML page.

Parameters:

Name Type Description Default
result PipelineResult or None

Pipeline output. May be None when model is supplied (the result is only consulted by :func:build_gallery_model).

required
output_dir str or Path

Root directory for gallery output.

required
model GalleryModel

Inventory to render. Defaults to :func:build_gallery_model.

None
view str

One of "l2", "l3", "both" (default), "comparison".

'both'
volume_scale float or None

Volume display scale, forwarded to :func:build_gallery_model when model is built here. Ignored when model is supplied.

None
backends list of str

Backends to render. Defaults to ["plotly", "matplotlib"] when plotly is installed (plotly is the primary column), else ["matplotlib"]. In comparison view the backend axis collapses to a single backend (plotly if available) so the two columns carry L2 vs L3.

None
title str

Gallery page title.

'ob-analytics Plot Gallery'

Returns:

Type Description
Path

Path to the generated HTML gallery file.

Extra panels

Build optional flow-toxicity and LOBSTER panels and append them via generate_gallery(..., extra_panels=[...]).

vpin_panel

vpin_panel(
    vpin_df: DataFrame, *, threshold: float = 0.7
) -> PlotSpec

Build a VPIN analytic panel for :attr:GalleryModel.analytics.

ofi_panel

ofi_panel(
    ofi_df: DataFrame, trades: DataFrame | None = None
) -> PlotSpec

Build an order-flow-imbalance analytic panel.

ofi_horizon_panel

ofi_horizon_panel(
    trades: DataFrame,
    *,
    horizons: tuple[str, ...] = (
        "5s",
        "15s",
        "60s",
        "300s",
    ),
    grid: str = "5s",
    start_time: Timestamp | None = None,
    end_time: Timestamp | None = None,
) -> PlotSpec

Build an OFI-vs-horizon analytic panel (diverging band per horizon).

kyle_panel

kyle_panel(kyle_result: Any) -> PlotSpec

Build a Kyle's-Lambda analytic panel.

trading_halts_panel

trading_halts_panel(
    trades: DataFrame, halts: DataFrame
) -> PlotSpec

Build a trading-halts analytic panel.

LOBSTER halts are not part of the slim :class:PipelineResult; read them from :attr:~ob_analytics.lobster.LobsterLoader.trading_halts and pass them here.