{"spec_id":"climograph-walter-lieth","library":"pygal","language":"python","code":"\"\"\" anyplot.ai\nclimograph-walter-lieth: Walter-Lieth Climate Diagram\nLibrary: pygal 3.1.0 | Python 3.13.13\nQuality: 85/100 | Created: 2026-06-15\n\"\"\"\n\nimport os\nimport sys\n\n\n# Prevent the local pygal.py from shadowing the installed pygal package\n_script_dir = os.path.dirname(os.path.abspath(__file__))\nif _script_dir in sys.path:\n    sys.path.remove(_script_dir)\n\nimport pygal\nfrom pygal.style import Style\n\n\n# Theme tokens\nTHEME = os.getenv(\"ANYPLOT_THEME\", \"light\")\nPAGE_BG = \"#FAF8F1\" if THEME == \"light\" else \"#1A1A17\"\nINK = \"#1A1A17\" if THEME == \"light\" else \"#F0EFE8\"\nINK_MUTED = \"#6B6A63\" if THEME == \"light\" else \"#A8A79F\"\n\n# Semantic color exception: precipitation = blue (water), temperature = red (heat)\nPRECIP_COLOR = \"#4467A3\"\nTEMP_COLOR = \"#AE3030\"\n\n# Station: Athens, Greece — Mediterranean Csa (1991-2020 normals)\nstation = \"Athens, Greece\"\nelevation = 107\nmonths = [\"Jan\", \"Feb\", \"Mar\", \"Apr\", \"May\", \"Jun\", \"Jul\", \"Aug\", \"Sep\", \"Oct\", \"Nov\", \"Dec\"]\ntemp_c = [9.3, 10.3, 12.4, 16.3, 21.0, 26.1, 28.7, 28.5, 24.1, 19.2, 14.3, 10.7]\nprecip_mm = [48, 36, 33, 23, 17, 7, 6, 5, 11, 46, 54, 57]\n\ntemp_annual = round(sum(temp_c) / 12, 1)\nprecip_annual = sum(precip_mm)\n\n# Walter-Lieth: 10 °C = 20 mm → scale precipitation onto the temperature axis\nprecip_scaled = [p / 2 for p in precip_mm]\n\n# Overlap base: the region below BOTH curves gets no fill (masked with background)\nbase = [min(p, t) for p, t in zip(precip_scaled, temp_c, strict=True)]\n\ntitle_str = \"climograph-walter-lieth · python · pygal · anyplot.ai\"\nstation_meta = f\"{station} ({elevation} m a.s.l.)   T = {temp_annual} °C   P = {precip_annual} mm\"\n\ntitle_fs = max(44, round(66 * 67 / len(title_str)))\n\n# Colors tuple ordered by series add() sequence:\n# 1. PRECIP_COLOR — humid fill (blue, bottom layer)\n# 2. TEMP_COLOR   — arid fill  (red, covers blue where temp > precip)\n# 3. PAGE_BG      — background mask (hides fill in overlap region 0→min)\n# 4. PRECIP_COLOR — precipitation outline line\n# 5. TEMP_COLOR   — temperature outline line\ncolors_tuple = (PRECIP_COLOR, TEMP_COLOR, PAGE_BG, PRECIP_COLOR, TEMP_COLOR)\n\ncustom_style = Style(\n    background=PAGE_BG,\n    plot_background=PAGE_BG,\n    foreground=INK,\n    foreground_strong=INK,\n    foreground_subtle=INK_MUTED,\n    colors=colors_tuple,\n    title_font_size=title_fs,\n    label_font_size=40,\n    major_label_font_size=44,\n    legend_font_size=44,\n    value_font_size=0,\n    stroke_width=4.0,\n)\n\nchart = pygal.Line(\n    width=3200,\n    height=1800,\n    style=custom_style,\n    title=title_str,\n    x_title=station_meta,\n    y_title=\"Temperature (°C)  /  Precipitation ÷ 2 (mm)\",\n    show_legend=True,\n    legend_at_bottom=True,\n    fill=False,\n    show_x_guides=False,\n    show_y_guides=True,\n    interpolate=\"cubic\",\n    dots_size=0,\n    range=(0, 35),\n)\n\nchart.x_labels = months\nchart.y_labels = [0, 10, 20, 30]\n\n# Differential fill — 3-layer stacking trick:\n#   Layer 1 (blue, bottom): 0 → precip_scaled everywhere\n#   Layer 2 (red, on top):  0 → temp_c everywhere (covers blue where temp > precip)\n#   Layer 3 (bg mask, top): 0 → min(precip, temp) — erases fill in the shared base region\n# Net result: blue between temp and precip/2 (humid), red between precip/2 and temp (arid)\nchart.add(\"Humid period\", precip_scaled, fill=True, stroke_style={\"width\": 0})\nchart.add(\"Arid period\", temp_c, fill=True, stroke_style={\"width\": 0})\nchart.add(\" \", base, fill=True, stroke_style={\"width\": 0})\n\n# Outline lines rendered on top of fills\nchart.add(\"Precipitation (mm ÷ 2)\", precip_scaled, fill=False, stroke_style={\"width\": 4})\nchart.add(\"Temperature (°C)\", temp_c, fill=False, stroke_style={\"width\": 6})\n\nchart.render_to_png(f\"plot-{THEME}.png\")\nwith open(f\"plot-{THEME}.html\", \"wb\") as f:\n    f.write(chart.render())\n"}