Skip to main content

Module perf

Module perf 

Source
Expand description

A live frame-time/FPS overlay: PerfOverlayApp wraps any App with one, on any Backend. PerfOverlayApp: a live frame-time/FPS overlay for any App, on any Backend.

Wrap an existing App once and it gains a toggleable perf readout on every backend, with no backend-specific code in the wrapped app itself:

use retroglyph_core::app::run_blocking;
use retroglyph_core::backend::{Backend, Headless};
use retroglyph_core::terminal::Terminal;
use retroglyph_ui::PerfOverlayApp;

let term = Terminal::new(Headless::new(40, 10));
let app = PerfOverlayApp::new(MyGame, "headless");
run_blocking(term, app).expect("run_blocking");

§What’s generic and what’s backend-specific

The frame-time bookkeeping (FrameStats), the toggle-key check, and the decision of when to draw are all backend-agnostic: PerfOverlayApp::update only ever talks to Terminal/Surface, which every Backend implements identically. The one thing every caller still supplies by hand is the backend label string (there is no portable way to ask a Backend what to call itself); everything else, including toggling the overlay on and off, works unmodified on crossterm, a native window, or a browser tab.

§Rendering

DefaultPerfRenderer (used by PerfOverlayApp::new) draws a single-row NNNfps MM.Mms minMM.M maxMM.M <backend> readout, compact enough to fit an 80-column terminal alongside a long backend label. For a richer overlay (a bordered panel, a frame-time sparkline, extra app-supplied metrics like resolution or vsync state), pass a closure to PerfOverlayApp::with_closure: composing this crate’s Panel/ Sparkline widgets, or PerfOverlay directly, requires no glue code beyond the closure itself. Implement PerfRenderer directly, and construct with PerfOverlayApp::with_renderer, only for a named, reusable renderer type instead of a closure.

This whole wrapper exists in large part because FrameStats::record needs a Frame, which a plain widget draw call had no way to reach: PerfOverlayApp::update is what intercepts Frame on the way through and calls FrameStats::record for the widget that otherwise couldn’t. An app that doesn’t need this wrapper’s other job (generic toggle-key handling across any wrapped App, on every backend) no longer needs it just for that: AnimatedPerfOverlay reaches Frame directly, so an app that already owns a FrameStats field can record and draw it in a single call, with no decorator at all.

§Toggling

PerfOverlayApp::update drains every event out of the wrapped Terminal before handing control to the inner App, keeps any that match the toggle key (backtick, or F1 as an alias, by default; see default_is_toggle_key), and re-queues the rest via Terminal::requeue_events so the inner app sees exactly the input it would have without the overlay, minus the toggle presses. This works identically on every backend because it only goes through Terminal’s own event queue, never a backend-specific input path (in particular, never Input::push_event, whose documented default is a no-op for backends that never receive events from outside their own poll_event).

The toggle key doesn’t just flip visibility: it cycles through PerfOverlayMode: Off -> Compact -> Full -> back to Off. Full only exists once PerfOverlayApp::cycle_with registers a second, richer PerfRenderer (typically PerfOverlay, a bordered panel with a frame-time Sparkline); without it, the cycle degrades to the plain two-state Off/Compact toggle.

Structs§

DefaultPerfRenderer
The built-in PerfRenderer, used by PerfOverlayApp::new.
PerfOverlayApp
Wraps an App with a toggleable perf overlay. See the module docs.

Enums§

PerfOverlayMode
How much detail super::PerfOverlayApp currently shows, advanced by the toggle key.

Constants§

DEFAULT_LAYER
PerfOverlayApp’s default overlay layer: Layer::Debug.
FRAME_HISTORY
How many frames PerfOverlayApp’s internal FrameStats remembers.

Traits§

PerfRenderer
Draws a super::PerfOverlayApp’s stats into a rectangular area of a Surface.

Functions§

default_is_toggle_key
Whether event is the overlay’s default toggle key.