pub struct WgpuRenderer { /* private fields */ }Expand description
WGPU-based renderer for GPU-accelerated 2D rendering.
This renderer supports:
- GPU-accelerated shape rendering (rectangles, rounded rectangles)
- Gradients (solid, linear, radial)
- GPU text rendering via retained raster image batches
- Cross-platform support (Desktop, Web, Android)
Implementations§
Source§impl WgpuRenderer
impl WgpuRenderer
Sourcepub fn new(fonts: &[&[u8]]) -> Self
pub fn new(fonts: &[&[u8]]) -> Self
Create a new WGPU renderer.
fonts– font bytes to load, ordered by priority (first = highest priority). Pass&[]to load no fonts; text will not render until fonts are provided.
Call init_gpu before rendering.
Sourcepub fn with_font_set(fonts: SoftwareTextFontSet) -> Self
pub fn with_font_set(fonts: SoftwareTextFontSet) -> Self
Create a renderer over an already-parsed font set.
Measurement and rasterization both take clones of this one set, so an app-supplied family resolves identically on both sides.
pub fn with_text_system(text_system: WgpuTextSystem) -> Self
Sourcepub fn init_gpu(
&mut self,
device: Arc<Device>,
queue: Arc<Queue>,
surface_format: TextureFormat,
adapter_backend: Backend,
adapter_downlevel: DownlevelFlags,
)
pub fn init_gpu( &mut self, device: Arc<Device>, queue: Arc<Queue>, surface_format: TextureFormat, adapter_backend: Backend, adapter_downlevel: DownlevelFlags, )
Initialize GPU resources with a WGPU device and queue.
Replacing a live renderer (Android surface recreation, device loss)
drops every retained replay slot with the old GpuRenderer, so the
bypass contract fails closed BEFORE the new renderer exists: every
slot confirmation is revoked and the feed generation bumped — no
scene build may omit primitives against buffers that died, and
already-built frames rematerialize their bypassed spans instead of
referencing the dead renderer’s slot ids.
Sourcepub fn set_display_visible_region(&mut self, region: DisplayVisibleRegion)
pub fn set_display_visible_region(&mut self, region: DisplayVisibleRegion)
The display’s visible region — the part of this renderer’s
full-screen surface the panel physically shows. Set by the
platform layer (never by app content); the renderer then culls
everything outside the region on the full-frame pass, for any app
and any layout. The round display is the first provider: Android’s
AConfiguration screenRound maps to
DisplayVisibleRegion::InscribedCircle for a non-multi-window
activity. Future providers (display cutouts/insets, host-declared
clips) plug in as new region variants without touching the cull
machinery. Default DisplayVisibleRegion::Full: rendering is
bitwise identical to a renderer without this capability.
Threaded mode routes the region to the present thread as a control message; the message queue is FIFO, so it lands before any packet published after this call — the same ordering the sync path’s direct call has.
Sourcepub fn init_gpu_threaded(
&mut self,
device: Arc<Device>,
queue: Arc<Queue>,
surface_format: TextureFormat,
adapter_backend: Backend,
adapter_downlevel: DownlevelFlags,
waker: Arc<dyn Fn() + Send + Sync>,
clock: Option<Arc<dyn Fn() -> i64 + Send + Sync>>,
) -> Result<(), WgpuRendererError>
pub fn init_gpu_threaded( &mut self, device: Arc<Device>, queue: Arc<Queue>, surface_format: TextureFormat, adapter_backend: Backend, adapter_downlevel: DownlevelFlags, waker: Arc<dyn Fn() + Send + Sync>, clock: Option<Arc<dyn Fn() -> i64 + Send + Sync>>, ) -> Result<(), WgpuRendererError>
init_gpu for the threaded present runtime
(Android): the same epoch bump and planner replacement hygiene, but
instead of constructing a GpuRenderer here, everything it needs —
all owned, all Send — crosses to a spawned present thread that
constructs its own (its Rc caches are thread-confined). Frames
then flow through publish_frame /
drain_present_returns under the
depth-one credit protocol instead of render.
waker— wakes the producer’s event loop after every returns send (the Android frame waker).clock— producer’s monotonic nanosecond clock, so present-sidePresentTimingsshare the producer telemetry’s clock domain;Noneleaves timings at zero.
Sourcepub fn note_surface_reconfigured(&mut self)
pub fn note_surface_reconfigured(&mut self)
Record that the surface was reconfigured (resize, format change, swapchain recreation): bumps the surface epoch stamped into every subsequent packet, so a packet built against the previous configuration is cancelled by the present stage instead of drawn.
Sourcepub fn set_root_scale(&mut self, scale: f32)
pub fn set_root_scale(&mut self, scale: f32)
Set root scale factor for text rendering (e.g., density scaling on Android)
pub fn root_scale(&self) -> f32
Sourcepub fn render(
&mut self,
view: &TextureView,
width: u32,
height: u32,
) -> Result<(), WgpuRendererError>
pub fn render( &mut self, view: &TextureView, width: u32, height: u32, ) -> Result<(), WgpuRendererError>
Render the scene to a texture view.
Producer first, present second: the frontend lowers the frame into a
[frame_packet::FramePacket] (direct root, root surface, and dev
overlay alike), the GPU renderer consumes it, and the present
stage’s returns — the recycled scene and the replay ack — fold back
into the frontend afterwards.
pub fn render_surface_texture( &mut self, texture: &Texture, view: &TextureView, width: u32, height: u32, ) -> Result<(), WgpuRendererError>
Sourcepub fn capture_frame(
&mut self,
width: u32,
height: u32,
) -> Result<CapturedFrame, WgpuRendererError>
pub fn capture_frame( &mut self, width: u32, height: u32, ) -> Result<CapturedFrame, WgpuRendererError>
Render the current scene into an RGBA pixel buffer for robot tests.
Uses the renderer’s configured root scale.
Sourcepub fn capture_frame_with_scale(
&mut self,
width: u32,
height: u32,
root_scale: f32,
) -> Result<CapturedFrame, WgpuRendererError>
pub fn capture_frame_with_scale( &mut self, width: u32, height: u32, root_scale: f32, ) -> Result<CapturedFrame, WgpuRendererError>
Render the current scene into an RGBA pixel buffer with an explicit scale.
Sourcepub fn has_frame_credit(&self) -> bool
pub fn has_frame_credit(&self) -> bool
Threaded mode: whether the depth-one slot has room for a packet.
The Android loop checks this BEFORE shell.update() so
backpressure lands before the expensive update/lowering work.
Always true on the sync path, which has no slot to fill.
Sourcepub fn publish_frame(&mut self, width: u32, height: u32) -> PublishOutcome
pub fn publish_frame(&mut self, width: u32, height: u32) -> PublishOutcome
Threaded mode: lower the current scene into a packet and hand it to
the present runtime. Credit is checked FIRST — a NoCredit return
means no packet was built at all (frame_sequence does not
advance). Returns NoCredit (with an error log) when the renderer
is not in threaded mode.
Sourcepub fn drain_present_returns(&mut self) -> usize
pub fn drain_present_returns(&mut self) -> usize
Threaded mode: fold every pending [RenderReturns] back into
producer state (scene recycling, replay ack, planner re-queue of
cancelled plans) and free the publish credit. Returns how many were
drained. No-op outside threaded mode.
Sourcepub fn drain_present_returns_with(
&mut self,
on_return: &mut dyn FnMut(u64, PresentOutcome, PresentTimings),
) -> usize
pub fn drain_present_returns_with( &mut self, on_return: &mut dyn FnMut(u64, PresentOutcome, PresentTimings), ) -> usize
drain_present_returns, reporting
each drained frame’s id, outcome and present-thread timings — the
Android loop feeds its frame telemetry from this.
Sourcepub fn present_replace_surface(
&mut self,
surface: Surface<'static>,
config: SurfaceConfiguration,
) -> bool
pub fn present_replace_surface( &mut self, surface: Surface<'static>, config: SurfaceConfiguration, ) -> bool
Threaded mode: install a (re)created surface on the present thread
and wait for the acknowledgement. The caller must have bumped the
surface epoch first ([note_surface_reconfigured]
Self::note_surface_reconfigured) when the message invalidates
in-flight packets; the message carries the current epoch.
Sourcepub fn present_reconfigure(&mut self, config: SurfaceConfiguration) -> bool
pub fn present_reconfigure(&mut self, config: SurfaceConfiguration) -> bool
Threaded mode: reconfigure the present thread’s surface (resize)
and wait for the acknowledgement. Same epoch contract as
present_replace_surface.
Sourcepub fn present_drop_surface(&mut self) -> bool
pub fn present_drop_surface(&mut self) -> bool
Threaded mode: drop the present thread’s surface (the window died; the renderer survives for the next one) and wait for the acknowledgement. Bump the epoch first so in-flight packets cancel.
Sourcepub fn shutdown_present_runtime(&mut self)
pub fn shutdown_present_runtime(&mut self)
Threaded mode: drain outstanding returns, stop the present thread and join it. The renderer returns to the uninitialized state.
Sourcepub fn last_published_frame_id(&self) -> u64
pub fn last_published_frame_id(&self) -> u64
The producer’s monotone packet sequence: the frame_id stamped on
the most recently lowered packet. After a Published outcome this
is the published frame’s id (the Android loop keys its telemetry on
it); it also proves a NoCredit publish never lowered a frame.
pub fn last_frame_stats(&self) -> Option<RenderStatsSnapshot>
pub fn debug_cpu_allocation_stats(&self) -> DebugCpuAllocationStats
Sourcepub fn try_device(&self) -> Option<&Device>
pub fn try_device(&self) -> Option<&Device>
Return the WGPU device when GPU resources are initialized. Sync backend only (desktop/web reconfigure paths); the threaded runtime owns its device on the present thread.
Trait Implementations§
Source§impl Default for WgpuRenderer
impl Default for WgpuRenderer
Source§impl Renderer for WgpuRenderer
impl Renderer for WgpuRenderer
type Scene = Scene
type Error = WgpuRendererError
Source§fn attach_app_context_services(&mut self, app_context: &AppContext)
fn attach_app_context_services(&mut self, app_context: &AppContext)
fn scene(&self) -> &Self::Scene
fn scene_mut(&mut self) -> &mut Self::Scene
fn rebuild_scene( &mut self, layout_tree: &LayoutTree, _viewport: Size, ) -> Result<(), Self::Error>
Source§fn rebuild_scene_from_applier(
&mut self,
applier: &mut MemoryApplier,
root: NodeId,
_viewport: Size,
) -> Result<(), Self::Error>
fn rebuild_scene_from_applier( &mut self, applier: &mut MemoryApplier, root: NodeId, _viewport: Size, ) -> Result<(), Self::Error>
fn update_scene_from_applier( &mut self, applier: &mut MemoryApplier, root: NodeId, viewport: Size, dirty_nodes: &[NodeId], ) -> Result<(), Self::Error>
fn update_visual_scene_from_applier( &mut self, applier: &mut MemoryApplier, root: NodeId, viewport: Size, dirty_nodes: &[NodeId], ) -> Result<(), Self::Error>
Source§fn draw_dev_overlay(&mut self, text: &str, viewport: Size)
fn draw_dev_overlay(&mut self, text: &str, viewport: Size)
Source§fn needs_frame_warmup(&self) -> bool
fn needs_frame_warmup(&self) -> bool
Auto Trait Implementations§
impl !Freeze for WgpuRenderer
impl !RefUnwindSafe for WgpuRenderer
impl !Send for WgpuRenderer
impl !Sync for WgpuRenderer
impl !UnwindSafe for WgpuRenderer
impl Unpin for WgpuRenderer
impl UnsafeUnpin for WgpuRenderer
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read more