Skip to main content

Module render

Module render 

Source
Expand description

Render-world half of layer compositing — a custom pass over stock bevy_ui_render, public API only (no fork). Mechanism per frame:

  1. extract_ui_layers (ExtractSchedule, after extract_ui_camera_view): per promoted layer, spawn a synthetic view whose clip_from_view is an orthographic projection over the layer’s capture rect — the same physical screen space stock UI vertices live in — and register an empty TransparentUi phase for it. Stock extraction / queue never know it exists.
  2. redistribute_ui_layers (PhaseSort, before the stock sort): move the already-queued phase items whose main_entity lies in a promoted subtree, verbatim, from the camera’s UI phase into their layer’s synthetic phase — stock prepare_uinodes (and sibling prepares) iterate all phases, so the moved items are batched by stock code against the synthetic view’s ViewUniformOffset. Then inject one composite-quad item per layer at the position of its first stolen item.
  3. ui_layer_capture_pass (Core2d/Core3d, before ui_pass): render each synthetic phase into the layer’s offscreen texture (cleared transparent). Straight-alpha blending onto transparent black accumulates premultiplied color, so…
  4. …a layer with a filter chain then replays its staged filter run (same graph node, right after that layer’s capture): fullscreen passes capture → ping-pong textures (LayerFilterMeta::runs, staged by prepare_layer_filters), all of them or none — an uncompiled pass pipeline aborts the whole run and FilterSlot::output_valid stays false, so the layer restages and retries next frame. And…
  5. …a layer with the TRANSFORM3D promotion reason replays its staged mip-downsample chain last in the iteration (mips) — its sampled texture (capture, or filter output) carries a full mip chain, rebuilt only when level 0 was rewritten. Finally…
  6. …the composite quad (DrawLayerComposite, drawn inside the stock ui_pass at the subtree’s stacking position) samples the capture — or, for a filtered layer, the final filter pass’s output — with premultiplied blending (One/OneMinusSrcAlpha) and multiplies rgb and alpha by the group alpha. 3D-transformed quads sample trilinear + anisotropic over the mip chain (minification shimmer) and feather ~1px of coverage at their silhouette (composite.wgsl’s edge AA — diagonal edges rasterize without MSAA).

Re-verify on Bevy upgrades (spike checklist): TransparentUi field set, SortedRenderPhase::{items, transient_items} visibility, prepare_uinodes iterating all phases, ViewSortedRenderPhases::prepare_for_new_frame draining transients, straight ALPHA_BLENDING in UiPipeline, the Queue → PhaseSort → PrepareBindGroups schedule shape, naga_oil NOT re-exporting an import’s entry points (the split-stage filter pipelines rely on pass shaders having no vertex entry of their own), naga’s namer renaming digit-suffixed identifiers (the pad_a/pad_b constraint in composable WGSL modules), and wgpu accepting per-stage shader modules in RenderPipelineDescriptor (filter vertex stage = prelude module, fragment stage = pass module).

Re-exports§

pub use store::*;

Modules§

backdrop
Render-world half of backdropFilter: the snapshot blit, the backdrop filter run, and the backdrop composite quad.
clip
Render-world half of clip-independent layer capture: the extract-window clip swap, and the composite quad’s rect clamp.
mips
Mip-chain generation for 3D-transformed layers’ capture textures.
store
The persistent capture-texture store — the resource that makes layer capture caching possible. Split from render.rs (which stays the pass / composite half): slot structs, allocation, and the per-frame prepare_layer_textures maintenance. Everything is re-exported through super so consumers keep their render::… paths.
transform3d
Render-world plumbing for the composite quad’s per-layer uniforms: the 3D model matrix and the screen-space clip rect (transform3d support).

Structs§

DrawLayerQuad
ExtractedChain
A layer’s filter chain, extracted from ResolvedFilterChain. Only the render-side fields cross: wire_index/layout/outset_px/scale are main-world concerns (animation metadata, capture sizing) and stay there.
ExtractedFilterPass
One filter pass of an extracted chain: the pass shader plus its packed uniform params.
ExtractedLayer
One promoted layer, as seen by the render world this frame.
ExtractedUiLayers
Per-frame extraction output. layers is index-aligned with LayerAtlases::textures and LayerCompositeMeta::atlas_bind_groups.
FilterUniforms
The Rust mirror of the prelude’s FilterUniforms (layer/filter_prelude.wgsl) — one entry per staged filter pass in LayerFilterMeta::uniforms. The explicit pad fields reproduce the WGSL uniform-address-space layout byte for byte (160 bytes total; asserted by filter_uniforms_match_the_documented_wgsl_layout). The digit-free pad_a/pad_b names are load-bearing on the WGSL side: naga’s namer appends _ to identifiers ending in a digit, which naga_oil rejects in composable modules — and the mirror matches field for field.
LayerCompositeBatch
The composite quad’s draw data on its render entity (mirrors UiBatch).
LayerCompositeMeta
Vertex buffer + per-layer capture bind groups for the composite draws.
LayerCompositePipeline
The composite pipeline: group 0 is the stock UI view uniform (so SetUiViewBindGroup is reused verbatim), group 1 the capture texture. Blending is premultiplied (One/OneMinusSrcAlpha): capture content is premultiplied by construction (straight-alpha blending onto transparent black), and the shader multiplies rgb and alpha by the group alpha.
LayerCompositePipelineKey
LayerCompositeVertex
One composite-quad vertex: physical screen position (the stock UI view projects it), capture UV, and the group alpha. Future composite params (per-rule) extend this struct — the pass stays rule-agnostic.
LayerFilterMeta
Per-frame filter staging: the uniform buffer (one entry per staged pass) and the replay list, index-aligned with ExtractedUiLayers::layers. runs[idx] = None means “no filter work this frame” — either the layer has no chain, or its cached output is still valid (the composite samples FilterSlot.textures[output_index] either way).
LayerFilterPass
One staged filter pass, replayed by ui_layer_capture_pass: set the pipeline, bind group 0 at the dynamic offset, render 3 vertices into target.
LayerFilterPipeline
The filter-pass pipeline: ONE bind group layout for every filter — group 0 is the source texture (the capture, or the previous pass’s ping-pong output), a linear clamp-to-edge sampler, one dynamically-offset FilterUniforms, and the layer’s original capture (always bound, so any pass can sample the unfiltered input) — plus the prelude shader, which is the vertex stage of every filter pipeline.
LayerFilterPipelineKey
Specialization key: the pass’s fragment shader plus the target format (filter targets ride the capture’s format). Handle<Shader> hashes by asset id, so it works as a key directly.
LayerFilterRun
A layer’s staged filter run this frame.
SetLayerAtlasBindGroup

Functions§

extract_ui_layers
Extracts promoted layers into the render world and spawns their synthetic capture views. Must run after extract_ui_camera_view: that system ends with a retain that would drop any phase it didn’t create.
filter_output_index
Which ping-pong texture holds the final output of a len-pass chain (the last pass’s target; len is at least 1 for any staged run).
filter_source_index
Ping-pong source for pass i: None = the layer’s capture texture (pass 0), otherwise the index of the previous pass’s target.
filter_target_index
Ping-pong target for pass i.
init_layer_composite_pipeline
init_layer_filter_pipeline
needs_filter_run
Whether a layer’s filter passes must (re-)run this frame: fresh capture content, changed params, a time-driven chain, or an output that was never completed (startup, realloc, or a run whose execution was skipped).
prepare_layer_composites
Builds composite-quad vertices + bind groups and stamps LayerCompositeBatch onto the quad entities, writing each quad’s vertex range back into its phase item.
prepare_layer_filters
Stages every resource a layer’s filter passes need this frame: pipeline specialization, one uniform entry per pass, and per-pass bind groups over the capture/ping-pong textures. Execution happens in ui_layer_capture_pass, which replays LayerFilterMeta::runs right after each layer’s capture; this system also predicts that execution (phase 3) and writes FilterSlot::output_valid accordingly, so the downstream prepare_layer_composites gate is same-frame accurate.
redistribute_ui_layers
Moves promoted subtrees’ phase items from the camera’s UI phase into their layer’s synthetic phase, then injects one composite quad per layer. Runs after queueing, before the stock sort (which then sorts every phase, stolen items keeping their global stack-index sort keys).
ui_layer_capture_pass
Renders each layer’s synthetic phase into its capture texture, then replays the layer’s staged filter run (if any) capture → ping-pong textures. Runs in the camera’s schedule right before the stock ui_pass consumes the composite quads.

Type Aliases§

DrawLayerComposite
The composite quad’s draw stack — view uniform reuse means the quad rides whatever view its phase belongs to (screen, or an outer layer’s capture).