Skip to content

Add subplot / multi-panel layout (Figure::subplot()) #7

Description

@MoonFlowww

Summary

Add support for arranging multiple plots in a grid layout within a single Figure, matching matplotlib's plt.subplot() / fig.add_subplot() workflow.

Motivation

Performance comparisons routinely need side-by-side panels: throughput vs. latency, before vs. after, different input sizes. Without subplots, users must create separate PPM files and stitch them manually. This is a significant quality-of-life gap vs. matplotlib.

Proposed API

sepia::plot2d::Figure fig(1200, 800);

auto ax1 = fig.subplot(2, 2, 0);   // 2 rows, 2 cols, panel index 0 (top-left)
auto ax2 = fig.subplot(2, 2, 1);   // top-right
auto ax3 = fig.subplot(2, 2, 2);   // bottom-left
auto ax4 = fig.subplot(2, 2, 3);   // bottom-right

ax1.plot(x1, y1, n).label("throughput");
ax2.plot(x2, y2, n).label("latency");
// ...

fig.render();
fig.save_ppm("comparison.ppm");

Each Axes object returned by subplot() has the same API as Figure today (plot, scatter, bar, set_xlabel, etc.) but renders into a sub-region of the parent canvas.

Implementation Notes

  • subplot(rows, cols, idx) computes a BBox (pixel rect) for that cell and stores it
  • Returns an Axes handle that holds a reference to the parent Canvas and a CoordTransform scoped to that cell's pixel rect
  • Each Axes renders its own grid, axis, and legend within its BBox
  • Layout: divide Figure pixel area into a uniform grid, apply shared margins + inter-panel spacing parameter
  • Figure::render() iterates all Axes and calls axes.render_into(canvas)
  • Shared X/Y axis labels: subplot(2,1,0, share_x=true) suppresses X tick labels on the top panel

Acceptance Criteria

  • subplot(rows, cols, idx) allocates correct pixel regions
  • Each panel has independent data, axis, and legend
  • Panels do not overdraw each other
  • share_x / share_y suppresses redundant axis labels
  • Example: examples/subplots.cpp with a 2×2 performance comparison grid

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions