%% dvd-thing — ports and adapters.
%% Every dependency arrow points inward. domain knows nothing; application knows
%% only domain; adapters know both but are known by neither.
flowchart TB
subgraph root["bin — composition root"]
main["main.rs
the only place that names Wayland"]
end
subgraph adapters["adapters — std"]
direction LR
subgraph wayland["wayland"]
display["WaylandDisplay
layer-shell surface, frame pacing, signals"]
renderer["SoftwareRenderer
double-buffered shm, damage tracking"]
logoimage["LogoImage
decode, scale, tint cache"]
state["WaylandState
protocol dispatch"]
end
subgraph assets["assets"]
filesource["FileLogoSource
$DVD_LOGO, XDG / macOS / Windows"]
end
end
subgraph app["application — no_std, no alloc"]
direction LR
subgraph portsgroup["ports"]
displayport["DisplayOverlayPort
screen_dimensions, wait_for_frame"]
rendererport["RendererPort
render_frame"]
logoport["LogoSourcePort
load"]
end
usecases["use_cases
run · blocking loop
step · one frame, for callback platforms"]
apperror["ApplicationError
heapless Message, 108 bytes"]
end
subgraph dom["domain — no_std, no alloc"]
direction LR
scene["ScreensaverScene
aggregate root
sole entry point: tick, sprites"]
logo["BouncingLogo
pub(crate)"]
sparkle["Sparkle
pub(crate)"]
sprite["Sprite + SpriteKind
what to draw, not how"]
vo["Value objects
Point2D · Vector2D
Dimensions · Color
self-validating, const fn"]
domerror["DomainError
InvalidDimensions"]
end
main --> usecases
main --> scene
main -.->|constructs| display
main -.->|constructs| renderer
main -.->|constructs| filesource
usecases --> displayport
usecases --> rendererport
usecases --> scene
display -.->|implements| displayport
renderer -.->|implements| rendererport
filesource -.->|implements| logoport
renderer -->|"sprites()"| scene
renderer --> logoimage
logoimage -->|"load()"| logoport
renderer --> display
display --> state
scene -->|owns| logo
scene -->|"owns [Option Sparkle; 108]"| sparkle
logo --> sprite
sparkle --> sprite
sprite --> vo
scene --> vo
scene -.->|"new() rejects"| domerror
apperror -.->|wraps| domerror
classDef domainStyle fill:#1f4e3d,stroke:#41b883,color:#e8f5ee
classDef appStyle fill:#1e3a5f,stroke:#4a9eff,color:#e6f0ff
classDef adapterStyle fill:#4a3410,stroke:#d99a2b,color:#fdf3e0
classDef rootStyle fill:#3d2645,stroke:#b06fc9,color:#f6ecfa
style root fill:#88888810,stroke:#9a9a9a
style adapters fill:#88888810,stroke:#9a9a9a
style wayland fill:#88888810,stroke:#9a9a9a
style assets fill:#88888810,stroke:#9a9a9a
style app fill:#88888810,stroke:#9a9a9a
style portsgroup fill:#88888810,stroke:#9a9a9a
style dom fill:#88888810,stroke:#9a9a9a
class scene,logo,sparkle,sprite,vo,domerror domainStyle
class displayport,rendererport,logoport,usecases,apperror appStyle
class display,renderer,logoimage,state,filesource adapterStyle
class main rootStyle