OS Windowing APIs
The library deep-dives document how fifteen toolkits talk to the platform window system. This sub-tree documents the layer beneath them: the raw OS windowing API each platform exposes — the exact functions and objects that winit, SDL, GTK, Qt, and the rest ultimately call, and the irreducible code to open a window yourself. Every platform here carries a minimal, dependency-light D program that opens (or bootstraps) a window by calling the OS API directly, with no windowing-abstraction library.
Last reviewed: June 9, 2026
Catalog
| Platform | Native API | Window handle | Event-loop primitive | Coordinate unit | Decoration owner | Survey · Example |
|---|---|---|---|---|---|---|
| Wayland | Wayland protocol (libwayland-client) | wl_surface + xdg_toplevel role | wl_display fd, wl_display_dispatch (readiness) | Logical (1/120ths fractional) | Client-side (CSD); SSD optional | survey · app.d |
| X11 | Xlib (X11 protocol) | Window (an XID) | X connection fd, XNextEvent (readiness) | Physical pixels | Server-side (window manager) | survey · app.d |
| Windows (Win32) | Win32 / User32 | HWND | thread message queue, GetMessage (readiness) | Physical px (per-monitor DPI) | Server-side (DWM) | survey · app.d |
| macOS (AppKit) | Cocoa / AppKit | NSWindow | [NSApp run] → NSRunLoop/CFRunLoop | Points (logical) | Server-side (NSWindowStyleMask) | survey · app.d |
| iOS / iPadOS (UIKit) | UIKit | UIWindow | UIApplicationMain → CFRunLoop | Points (logical) | System (full-screen; N/A) | survey · app.d |
| Android (NDK) | NDK native-activity | ANativeWindow | ALooper (ALooper_pollOnce, epoll) | Physical px | System (WindowManager) | survey · app.d |
How to read these
Each survey follows the same shape (metadata table → "What it is" → a walk of the minimal program → the windowing spine: lifecycle, event loop & frame pacing, input/IME, coordinates & scaling, decorations & popups, clipboard/DnD → what toolkits build on it). The shared vocabulary they link to lives in concepts; the cross-platform contrasts are drawn together in the summary.
The minimal programs bind the OS directly, choosing the most honest mechanism per platform:
- X11, Wayland, Android use ImportC — a tiny
c.cshim that#includes the real system header, so the D compiler parses the actual types/signatures (no hand-written bindings to drift). See the ImportC guide for the pkg-config wiring. - macOS / iOS use D's built-in
extern(Objective-C)+@selector(the same mechanism theobjective-dpackage wraps), since ImportC does not parse Objective-C. - Win32 uses druntime's built-in
core.sys.windows(zero third-party); theRolandTaverner/windows-dfork is the full-SDK option for when that is insufficient.
NOTE
What is verified, and how. X11 and Wayland build and run on Linux (X11 opens a real window; Wayland completes the wl_registry bootstrap), and print SKIP + exit 0 when headless. AppKit builds and shows a real NSWindow on macOS. iOS and Win32 are compile-for-target verified (an iOS-Simulator arm64 object; a Windows amd64 object), with a real Win32 run on the windows-latest CI runner and the iOS Simulator run documented as manual. Android cross-compiles via the opt-in nix develop .#android shell (note the glue-header ImportC limitation); its emulator run is a documented manual step. Mobile (iOS/Android) is out of CI scope.
Sources
- The per-platform surveys below, each grounded in primary sources (protocol XML, the Xlib manual, Microsoft Learn, Apple developer docs, the Android NDK reference, and the OS headers themselves).
- Concepts — the shared windowing vocabulary these surveys reference.
- Comparison & recommendations — the framework-level synthesis this layer underpins.