{
 "cells": [
  {
   "cell_type": "raw",
   "id": "fb8e120d-5dcf-483b-a0d1-74857d09ce7d",
   "metadata": {},
   "source": [
    ".. currentmodule:: seaborn.objects"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "9252d5a5-8af1-4f99-b799-ee044329fb23",
   "metadata": {
    "tags": [
     "hide"
    ]
   },
   "outputs": [],
   "source": [
    "%config InlineBackend.figure_format = \"retina\"\n",
    "import seaborn as sns\n",
    "import seaborn.objects as so\n",
    "import matplotlib as mpl\n",
    "import matplotlib.pyplot as plt\n",
    "from seaborn import load_dataset\n",
    "diamonds = load_dataset(\"diamonds\")"
   ]
  },
  {
   "cell_type": "raw",
   "id": "3445ed22-7a6a-4f91-8914-49bb1af023cb",
   "metadata": {},
   "source": [
    "Passing a :class:`matplotlib.axes.Axes` object provides functionality closest to seaborn's axes-level plotting functions. Notice how the resulting image looks different from others created with :class:`Plot`. This is because the plot theme uses the global rcParams at the time the axes were created, rather than :class:`Plot` defaults:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "b816b0b1-b861-404e-bec6-9b2b0844ea5a",
   "metadata": {},
   "outputs": [],
   "source": [
    "p = so.Plot(diamonds, \"carat\", \"price\").add(so.Dots())\n",
    "f, ax = plt.subplots()\n",
    "p.on(ax).show()"
   ]
  },
  {
   "cell_type": "raw",
   "id": "ce3aa102-50fe-44ce-9e06-e25d14b410f1",
   "metadata": {},
   "source": [
    "Alternatively, calling :func:`matplotlib.pyplot.figure` will defer axes creation to :class:`Plot`, which will apply the default theme (and any customizations specified with :meth:`Plot.theme`):"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "52eefae9-d08e-48fb-a15b-27920609d53b",
   "metadata": {},
   "outputs": [],
   "source": [
    "f = plt.figure()\n",
    "p.on(f).show()"
   ]
  },
  {
   "cell_type": "raw",
   "id": "171fa466-1f7a-4c5e-8a12-61edb3f11e4a",
   "metadata": {},
   "source": [
    "Creating a :class:`matplotlib.figure.Figure` object will bypass `pyplot` altogether. This may be useful for embedding :class:`Plot` figures in a GUI application:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "bba83103-ab74-4e3c-b16e-77644f4c0431",
   "metadata": {},
   "outputs": [],
   "source": [
    "f = mpl.figure.Figure()\n",
    "p.on(f).plot()"
   ]
  },
  {
   "cell_type": "raw",
   "id": "4cce3d40-acea-4f5c-87c4-56666480d2fe",
   "metadata": {},
   "source": [
    "Using :class:`Plot.on` also provides access to the underlying matplotlib objects, which may be useful for deep customization. But it requires a careful attention to the order of operations by which the :class:`Plot` is specified, compiled, customized, and displayed:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "91823d24-8269-4b72-abeb-38201eb2db3f",
   "metadata": {},
   "outputs": [],
   "source": [
    "f = mpl.figure.Figure()\n",
    "res = p.on(f).plot()\n",
    "\n",
    "ax = f.axes[0]\n",
    "rect = mpl.patches.Rectangle(\n",
    "    xy=(0, 1), width=.4, height=.1,\n",
    "    color=\"C1\", alpha=.2,\n",
    "    transform=ax.transAxes, clip_on=False,\n",
    ")\n",
    "ax.add_artist(rect)\n",
    "ax.text(\n",
    "    x=rect.get_width() / 2, y=1 + rect.get_height() / 2,\n",
    "    s=\"Diamonds: very sparkly!\", size=12,\n",
    "    ha=\"center\", va=\"center\", transform=ax.transAxes,\n",
    ")\n",
    "\n",
    "res"
   ]
  },
  {
   "cell_type": "raw",
   "id": "61286891-25b3-4db5-8ebe-af080d5c5f31",
   "metadata": {},
   "source": [
    "Matplotlib 3.4 introduced the concept of :meth:`matplotlib.figure.Figure.subfigures`, which make it easier to composite multiple arrangements of subplots. These can also be passed to :meth:`Plot.on`, "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "ca19a28e-7a49-46b3-a727-a26f4a1099c3",
   "metadata": {},
   "outputs": [],
   "source": [
    "f = mpl.figure.Figure(figsize=(7, 4), dpi=100, layout=\"constrained\")\n",
    "sf1, sf2 = f.subfigures(1, 2)\n",
    "\n",
    "p.on(sf1).plot()\n",
    "(\n",
    "    so.Plot(diamonds, x=\"price\")\n",
    "    .add(so.Bars(), so.Hist())\n",
    "    .facet(row=\"cut\")\n",
    "    .scale(x=\"log\")\n",
    "    .share(y=False)\n",
    "    .on(sf2)\n",
    ")"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "6ecd4166-939d-4925-92be-bf886a16ae94",
   "metadata": {},
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "py310",
   "language": "python",
   "name": "py310"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.10.6"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}
