{"spec_id":"pictogram-basic","library":"matplotlib","language":"python","code":"\"\"\" anyplot.ai\npictogram-basic: Pictogram Chart (Isotype Visualization)\nLibrary: matplotlib 3.10.9 | Python 3.13.13\nQuality: 88/100 | Created: 2026-06-03\n\"\"\"\n\nimport os\n\nimport matplotlib.patches as mpatches\nimport matplotlib.pyplot as plt\nimport numpy as np\nfrom matplotlib.patches import Polygon\n\n\n# Theme tokens — Imprint palette chrome\nTHEME = os.getenv(\"ANYPLOT_THEME\", \"light\")\nPAGE_BG = \"#FAF8F1\" if THEME == \"light\" else \"#1A1A17\"\nELEVATED_BG = \"#FFFDF6\" if THEME == \"light\" else \"#242420\"\nINK = \"#1A1A17\" if THEME == \"light\" else \"#F0EFE8\"\nINK_SOFT = \"#4A4A44\" if THEME == \"light\" else \"#B8B7B0\"\nINK_MUTED = \"#6B6A63\" if THEME == \"light\" else \"#A8A79F\"\n\nBRAND = \"#009E73\"  # Imprint palette position 1 — always first series\n\n# Data — estimated global fruit production (million tonnes), 1 icon = 5 Mt\ncategories = [\"Apples\", \"Oranges\", \"Bananas\", \"Grapes\", \"Mangoes\"]\nvalues = [43, 32, 27, 18, 23]\nicon_unit = 5\n\nn_cats = len(categories)\nfull_icons = [v // icon_unit for v in values]\npartials = [(v % icon_unit) / icon_unit for v in values]\nmax_icons = max(full_icons) + 1  # 9 (8 full + 1 partial for Apples)\n\n# Layout parameters\nicon_r = 0.33  # icon radius in data units\nx_step = 0.88  # center-to-center horizontal spacing\ny_rows = list(range(n_cats - 1, -1, -1))  # [4, 3, 2, 1, 0] top → bottom\n\n# Figure\nfig, ax = plt.subplots(figsize=(8, 4.5), dpi=400, facecolor=PAGE_BG)\nax.set_facecolor(PAGE_BG)\n\n# Draw icons row by row\nfor row_idx, (n_full, frac) in enumerate(zip(full_icons, partials, strict=True)):\n    y = y_rows[row_idx]\n\n    # Full filled icons\n    for i in range(n_full):\n        ax.add_patch(\n            mpatches.Circle(\n                (i * x_step, y), icon_r, facecolor=BRAND, edgecolor=\"none\", transform=ax.transData, zorder=3\n            )\n        )\n\n    # Partial icon: muted background + left-filled arc polygon\n    if frac > 0:\n        x_p = n_full * x_step\n        ax.add_patch(\n            mpatches.Circle(\n                (x_p, y), icon_r, facecolor=INK_MUTED, alpha=0.25, edgecolor=\"none\", transform=ax.transData, zorder=2\n            )\n        )\n        # Build a filled polygon for the left `frac` of the circle\n        # The vertical chord is at x = x_p + icon_r*(2*frac - 1)\n        theta_chord = np.arccos(np.clip(2 * frac - 1, -1.0, 1.0))\n        n_arc = 64\n        theta_arc = np.linspace(theta_chord, 2 * np.pi - theta_chord, n_arc)\n        arc_verts = np.column_stack([x_p + icon_r * np.cos(theta_arc), y + icon_r * np.sin(theta_arc)])\n        # Close with the vertical chord (last arc point back to first)\n        poly_verts = np.vstack([arc_verts, arc_verts[[0]]])\n        ax.add_patch(\n            Polygon(poly_verts, closed=True, facecolor=BRAND, edgecolor=\"none\", transform=ax.transData, zorder=3)\n        )\n\n    # Value annotation at row end\n    x_end = (n_full + (1 if frac > 0 else 0)) * x_step + icon_r + 0.20\n    ax.text(x_end, y, f\"{values[row_idx]} Mt\", fontsize=9, color=INK_SOFT, va=\"center\", ha=\"left\")\n\n# Axes bounds\nax.set_xlim(-icon_r * 2.2, (max_icons - 1) * x_step + icon_r + 1.9)\nax.set_ylim(-0.72, n_cats - 0.28)\n\n# Category labels on left axis\nax.set_yticks(y_rows)\nax.set_yticklabels(categories, fontsize=10, color=INK_SOFT)\nax.tick_params(axis=\"y\", length=0, labelcolor=INK_SOFT)\nax.set_xticks([])\n\n# Spine styling — L-frame (left + bottom) for row anchoring\nax.spines[\"top\"].set_visible(False)\nax.spines[\"right\"].set_visible(False)\nax.spines[\"bottom\"].set_color(INK_SOFT)\nax.spines[\"bottom\"].set_linewidth(0.5)\nax.spines[\"left\"].set_color(INK_SOFT)\nax.spines[\"left\"].set_linewidth(0.5)\n\n# Title\ntitle = \"Estimated Global Fruit Production · pictogram-basic · python · matplotlib · anyplot.ai\"\nn_t = len(title)\ntitle_fs = max(8, round(12 * 67 / n_t)) if n_t > 67 else 12\nax.set_title(title, fontsize=title_fs, fontweight=\"medium\", color=INK, pad=12)\n\n# Legend: unit key\nleg = ax.legend(\n    handles=[mpatches.Patch(facecolor=BRAND, label=\"= 5 million tonnes\")],\n    fontsize=8,\n    loc=\"lower right\",\n    facecolor=ELEVATED_BG,\n    edgecolor=INK_SOFT,\n    framealpha=0.9,\n)\nleg.get_frame().set_linewidth(0.5)\nplt.setp(leg.get_texts(), color=INK_SOFT)\n\nfig.subplots_adjust(left=0.13, right=0.97, top=0.91, bottom=0.06)\n\nplt.savefig(f\"plot-{THEME}.png\", dpi=400, facecolor=PAGE_BG)\nplt.close()\n"}