digraph dataflow { rankdir=TB; pad="0.3"; fontname="Helvetica"; node [fontname="Helvetica", fontsize=12, margin="0.15,0.1"]; edge [fontname="Helvetica", fontsize=10]; labelloc="t"; label="Deck in a Dash — dataflow for one reading"; fontsize=16; node [shape=box, style="rounded,filled"]; subgraph cluster_inputs { label="Inputs (two equivalent entry points)"; style=dashed; color=gray40; fontsize=11; cli [label="Direct CLI flags\n--seed --birth-* --date --format", fillcolor="#e3e3e3"]; runsh [label="run.sh:\nOS clock -> seed + --date\nuser.properties -> birth-*", fillcolor="#e3e3e3"]; } main [label="main.c\nparses args into:\nseed (string), BirthData, utc_moment", fillcolor="#cfe8fb"]; reading_generate [label="reading_generate()\nreading.c", shape=box, style="rounded,filled", fillcolor="#9fd3f5", peripheries=2]; natal_fn [label="astro_compute_natal_chart()\nastro.c", fillcolor="#cfe8fb"]; transit_fn [label="astro_compute_daily_transits()\nastro.c", fillcolor="#cfe8fb"]; tarot_fn [label="tarot_draw_celtic_cross()\ntarot.c", fillcolor="#cfe8fb"]; natal_data [label="NatalChart\nbodies[10]: sign + degree\nascendant_longitude\nhouses[12] (whole-sign)", shape=note, fillcolor="#fdf3d0"]; transit_data [label="DailyTransits\nbodies[10]\nmoon_phase\naspects[]: transiting/natal\nplanet, type, orb", shape=note, fillcolor="#fdf3d0"]; spread_data [label="CelticCrossSpread\npositions[10]: card, reversed", shape=note, fillcolor="#fdf3d0"]; daily_reading [label="DailyReading\n{ natal, transits, spread }", shape=note, fillcolor="#fbe3c8", peripheries=2]; print_text [label="reading_print_text()", fillcolor="#cfe8fb"]; print_html [label="reading_print_html()", fillcolor="#cfe8fb"]; watch_fn [label="watchapp UI code\n(future — walks the struct\ndirectly, no print_* call)", fillcolor=white, color=firebrick, fontcolor=firebrick, style="rounded,dashed"]; out_text [label="stdout: plain-text report", shape=parallelogram, fillcolor="#c8f0c8"]; out_html [label="stdout: reading.html\n( per card)", shape=parallelogram, fillcolor="#c8f0c8"]; out_watch [label="watch screens\n(future)", shape=parallelogram, fillcolor=white, color=firebrick, fontcolor=firebrick, style="dashed"]; cli -> main; runsh -> main; main -> reading_generate [label="seed, birth,\nutc_moment"]; reading_generate -> natal_fn [label="birth"]; natal_fn -> natal_data; reading_generate -> transit_fn [label="utc_moment,\nNatalChart"]; natal_data -> transit_fn [style=dotted, color=gray40, label="natal chart\nread-only"]; transit_fn -> transit_data; reading_generate -> tarot_fn [label="seed"]; tarot_fn -> spread_data; natal_data -> daily_reading; transit_data -> daily_reading; spread_data -> daily_reading; daily_reading -> print_text; daily_reading -> print_html; daily_reading -> watch_fn [style=dashed, color=firebrick]; print_text -> out_text; print_html -> out_html; watch_fn -> out_watch [style=dashed, color=firebrick]; }