Skip to main content

RendererStatsComponent

Struct RendererStatsComponent 

Source
pub struct RendererStatsComponent {
    pub enabled: bool,
    pub target: CameraTarget,
    pub update_interval_sec: f32,
    pub smoothing: f32,
    pub color: [f32; 4],
    pub emissive: bool,
    /* private fields */
}

Fields§

§enabled: bool§target: CameraTarget

Which renderer timing source this stats widget displays.

This is explicit (no scene traversal): set it to CameraTarget::Window or CameraTarget::Xr.

§update_interval_sec: f32

Minimum time between text updates.

Updating text is relatively expensive because it rebuilds glyph subtrees.

§smoothing: f32

Exponential moving-average smoothing factor in $[0, 1]$.

  • 0.0: no smoothing
  • 0.9: heavy smoothing (default)
§color: [f32; 4]

Text color (RGBA).

§emissive: bool

Whether spawned glyphs should be emissive (unlit).

Implementations§

Source§

impl RendererStatsComponent

Source

pub fn new() -> Self

Examples found in repository?
examples/vr-input.rs (line 296)
186fn main() {
187    mittens_engine::example_support::ensure_model_assets();
188    utils::logger::init();
189
190    let options = match parse_options() {
191        Ok(options) => options,
192        Err(message) => {
193            eprintln!("{message}");
194            std::process::exit(2);
195        }
196    };
197
198    println!(
199        "[vr-input] xr controller rotation filter pipeline: {}",
200        if options.xr_controller_rotation_filter {
201            "enabled"
202        } else {
203            "disabled"
204        }
205    );
206
207    let world = engine::ecs::World::default();
208    let mut universe = engine::Universe::new(world);
209
210    let renderer_settings = universe
211        .world
212        .add_component(RendererSettingsComponent::msaa_off().with_window_size(320, 240));
213    universe.add(renderer_settings);
214
215    let render_graph = universe.world.add_component(RenderGraphComponent::new());
216    let emissive_pass = universe.world.add_component(EmissivePassComponent::new());
217    let blur_pass = universe.world.add_component(
218        BlurPassComponent::new()
219            .with_radius_ndc(0.06)
220            .with_half_res(true),
221    );
222    let bloom = universe.world.add_component(
223        BloomComponent::new()
224            .with_intensity(0.95)
225            .with_emissive_scale(1.2),
226    );
227    let _ = universe.attach(emissive_pass, blur_pass);
228    let _ = universe.attach(render_graph, emissive_pass);
229    let _ = universe.attach(render_graph, bloom);
230    universe.add(render_graph);
231
232    // Sky base.
233    let background = universe
234        .world
235        .add_component(BackgroundColorComponent::new());
236    let background_c = universe
237        .world
238        .add_component(ColorComponent::rgba(0.62, 0.80, 1.00, 1.0));
239    let _ = universe.world.add_child(background, background_c);
240    universe.add(background);
241
242    // Lighting for the model.
243    let ambient = universe
244        .world
245        .add_component(AmbientLightComponent::rgb(0.18, 0.18, 0.22));
246    universe.add(ambient);
247
248    let sun = universe.world.add_component(
249        DirectionalLightComponent::new()
250            .with_intensity(1.1)
251            .with_color(1.0, 0.98, 0.95),
252    );
253    let sun_dir = universe
254        .world
255        .add_component(TransformComponent::new().with_position(0.15, -0.45, 1.0));
256    let _ = universe.attach(sun_dir, sun);
257    universe.add(sun_dir);
258
259    // --- Desktop camera rig (for debugging while in VR) ---
260    let input = universe
261        .world
262        .add_component(InputComponent::new().with_speed(1.5));
263    let input_mode = universe.world.add_component(
264        InputTransformModeComponent::forward_z()
265            .with_fps_rotation()
266            .with_roll_axis_y(),
267    );
268    let _ = universe.attach(input, input_mode);
269
270    let desktop_rig = universe
271        .world
272        .add_component(TransformComponent::new().with_position(0.0, 1.2, 3.5));
273    let _ = universe.attach(input, desktop_rig);
274
275    let camera3d = universe.world.add_component(Camera3DComponent::new());
276    let _ = universe.attach(desktop_rig, camera3d);
277
278    let pointer = universe.world.add_component(PointerComponent::new());
279    let _ = universe.attach(camera3d, pointer);
280
281    example_util::spawn_desktop_camera_controls_hint(&mut universe, desktop_rig);
282    universe.add(input);
283
284    // --- XR rig (Aim controller debug cubes only; camera has moved to AVC) ---
285    let xr_input = universe.world.add_component(InputXRComponent::on());
286    let xr_gamepad = universe.world.add_component(
287        mittens_engine::engine::ecs::component::InputXRGamepadComponent::new().speed(1.5),
288    );
289    let xr_rig = universe.world.add_component(TransformComponent::new());
290    let _ = universe.attach(xr_input, xr_rig);
291    let _ = universe.attach(xr_input, xr_gamepad);
292
293    // renderer stats
294    let renderer_stats = universe
295        .world
296        .add_component(RendererStatsComponent::new().with_camera_target(CameraTarget::Xr));
297    let render_stats_rig = universe
298        .world
299        .add_component(TransformComponent::new().with_position(0.0, 1.85, 0.6));
300    let _ = universe.attach(render_stats_rig, renderer_stats);
301    let _ = universe.attach(xr_rig, render_stats_rig);
302
303    universe.add(xr_input);
304
305    // Background "skybox" content.
306    spawn_sun_background(&mut universe);
307
308    // --- VTuber model — single-input topology ---
309    //
310    // InputXRComponent drives body translation and head rotation through AvatarControlSystem.
311    // AvatarControlSystem:
312    //   - Splices a TransformComponent under J_Bip_C_Head's parent (the neck) to drive
313    //     head rotation directly. Rotating the head — not the neck — isolates the spine
314    //     so the torso doesn't twist with HMD yaw.
315    //   - Strips rotation from model_root (body faces body_yaw, not raw HMD yaw).
316    //   - Bakes the π Y handedness correction into the head rotation math.
317    //   - Smoothly rotates body to follow head when yaw delta exceeds threshold.
318    //   - Measures J_Bip_C_Head local Y in the rest pose and sets model_root.y = -bone_local_y,
319    //     so the head bone sits at driven_t world Y (= HMD height) with no hardcoded constant.
320    //   - Re-parents CameraXRComponent under J_Bip_C_Head for first-person alignment.
321    //
322    // Topology (after AVC init):
323    //   editor_root
324    //     └── avatar_input_xr (InputXRComponent)
325    //           └── avatar_driven_t (TransformComponent)
326    //                 └── AvatarControlComponent
327    //                       ├── body_pipeline → pipeline_output
328    //                       │     └── model_root (y auto-calibrated from J_Bip_C_Head)
329    //                       │           └── GLTFComponent → ... → J_Bip_C_Head
330    //                       │                                           └── CameraXRComponent
331    //                       ├── CTLXR(Left, Grip) → re-parented to lower_arm
332    //                       └── CTLXR(Right, Grip) → re-parented to lower_arm
333
334    let editor_root = universe.world.add_component(EditorComponent::new());
335
336    let avatar_input_xr = universe.world.add_component(InputXRComponent::on());
337    let avatar_xr_gamepad = universe.world.add_component(
338        mittens_engine::engine::ecs::component::InputXRGamepadComponent::new().speed(1.5),
339    );
340    let avatar_driven_t = universe.world.add_component(TransformComponent::new());
341    let _ = universe.attach(avatar_input_xr, avatar_driven_t);
342    let _ = universe.attach(avatar_input_xr, avatar_xr_gamepad);
343
344    // AvatarControlComponent: -Z forward (OpenXR default), body starts facing -Z (π yaw).
345    // camera_bone triggers auto-calibration of model_root.y from J_Bip_C_Head rest pose height,
346    // and causes any CameraXR/Camera3D direct children of AVC to be re-parented to that bone.
347    let avatar_control = universe.world.add_component(
348        AvatarControlComponent::new()
349            .with_head_bone("J_Bip_C_Head")
350            .with_camera_bone("J_Bip_C_Head")
351            .with_left_hand_bone("J_Bip_L_Hand")
352            .with_right_hand_bone("J_Bip_R_Hand")
353            .with_initial_yaw(std::f32::consts::PI)
354            .with_hand_rotation_smoothing(220.0),
355    );
356    let _ = universe.attach(avatar_driven_t, avatar_control);
357
358    // CameraXR as a direct child of AVC — discovered and re-parented to J_Bip_C_Head at init.
359    let camera_xr = universe.world.add_component(CameraXRComponent::on());
360    let _ = universe.attach(avatar_control, camera_xr);
361    let head_pointer = universe.world.add_component(PointerComponent::new());
362    let _ = universe.attach(camera_xr, head_pointer);
363
364    // Grip controllers for hand bone splicing — children of AvatarControlComponent so
365    // AvatarControlSystem discovers them by topology. Each needs a TransformComponent
366    // child (driven_t) that OpenXRSystem writes each tick.
367    let left_grip = universe.world.add_component(ControllerXRComponent::new(
368        true,
369        ControllerHand::Left,
370        ControllerPoseKind::Grip,
371    ));
372    let left_grip_t = universe.world.add_component(TransformComponent::new());
373    let _ = universe.attach(left_grip, left_grip_t);
374    let left_pointer = universe.world.add_component(PointerComponent::new());
375    let _ = universe.attach(left_grip_t, left_pointer);
376    let _ = universe.attach(avatar_control, left_grip);
377
378    let right_grip = universe.world.add_component(ControllerXRComponent::new(
379        true,
380        ControllerHand::Right,
381        ControllerPoseKind::Grip,
382    ));
383    let right_grip_t = universe.world.add_component(TransformComponent::new());
384    let _ = universe.attach(right_grip, right_grip_t);
385    let right_pointer = universe.world.add_component(PointerComponent::new());
386    let _ = universe.attach(right_grip_t, right_pointer);
387    let _ = universe.attach(avatar_control, right_grip);
388
389    // model_root: no explicit Y offset — AvatarControlSystem calibrates it from J_Bip_C_Head.
390    let model_root = universe.world.add_component(TransformComponent::new());
391    let model = universe
392        .world
393        .add_component(GLTFComponent::new("assets/models/pc-rei.hoodie.glb"));
394    let emissive = universe.world.add_component(EmissiveComponent::on());
395    let _ = universe.attach(model, emissive);
396
397    let _ = universe.attach(editor_root, avatar_input_xr);
398    let _ = universe.attach(avatar_control, model_root);
399    let _ = universe.attach(model_root, model);
400    universe.add(editor_root);
401
402    // --- Controller debug cubes (tracked poses) ---
403    let _left = spawn_controller_cube(
404        &mut universe,
405        xr_rig,
406        ControllerHand::Left,
407        (0.10, 0.90, 1.00, 1.0),
408        220.0,
409        options.xr_controller_rotation_filter,
410    );
411    let _right = spawn_controller_cube(
412        &mut universe,
413        xr_rig,
414        ControllerHand::Right,
415        (1.00, 0.35, 0.35, 1.0),
416        220.0,
417        options.xr_controller_rotation_filter,
418    );
419
420    // Enable OpenXR runtime.
421    let xr_root = universe.world.add_component(XrComponent::on());
422    universe.add(xr_root);
423
424    universe.systems.process_commands(
425        &mut universe.world,
426        &mut universe.visuals,
427        &mut universe.render_assets,
428        &mut universe.command_queue,
429    );
430
431    // Force the glTF subtree to spawn so we can query the armature for bone markers.
432    {
433        let systems = &mut universe.systems;
434        systems.gltf.tick_with_queue(
435            &mut universe.world,
436            &mut universe.visuals,
437            &mut systems.skinned_mesh,
438            &mut universe.command_queue,
439            0.0,
440        );
441    }
442    universe.systems.process_commands(
443        &mut universe.world,
444        &mut universe.visuals,
445        &mut universe.render_assets,
446        &mut universe.command_queue,
447    );
448
449    // Bone markers for editor inspection.
450    let marker_joints: &[(&str, (f32, f32, f32, f32))] = &[
451        ("[name='J_Bip_C_Head']", (0.85, 0.20, 0.85, 0.9)),
452        ("[name='J_Bip_C_Neck']", (0.20, 0.85, 0.85, 0.9)),
453        ("[name='J_Bip_C_UpperChest']", (0.20, 0.20, 0.85, 0.9)),
454        ("[name='J_Bip_L_UpperArm']", (0.85, 0.85, 0.20, 0.9)),
455        ("[name='J_Bip_R_UpperArm']", (0.85, 0.60, 0.20, 0.9)),
456    ];
457
458    for &(selector, color) in marker_joints {
459        let Some(bone) = universe.find_component(model_root, selector) else {
460            continue;
461        };
462        let marker_t = universe
463            .world
464            .add_component(TransformComponent::new().with_scale(0.025, 0.025, 0.025));
465        let marker_r = universe.world.add_component(RenderableComponent::cube());
466        let marker_c = universe
467            .world
468            .add_component(ColorComponent::rgba(color.0, color.1, color.2, color.3));
469        let marker_rcast = universe
470            .world
471            .add_component(RaycastableComponent::enabled());
472        let _ = universe.world.add_child(marker_r, marker_c);
473        let _ = universe.world.add_child(marker_r, marker_rcast);
474        let _ = universe.world.add_child(marker_t, marker_r);
475        let _ = universe.attach(bone, marker_t);
476    }
477
478    universe.enable_repl();
479    engine::Windowing::run_app(universe).expect("Windowing failed");
480}
Source

pub fn with_camera_target(self, target: CameraTarget) -> Self

Examples found in repository?
examples/vr-input.rs (line 296)
186fn main() {
187    mittens_engine::example_support::ensure_model_assets();
188    utils::logger::init();
189
190    let options = match parse_options() {
191        Ok(options) => options,
192        Err(message) => {
193            eprintln!("{message}");
194            std::process::exit(2);
195        }
196    };
197
198    println!(
199        "[vr-input] xr controller rotation filter pipeline: {}",
200        if options.xr_controller_rotation_filter {
201            "enabled"
202        } else {
203            "disabled"
204        }
205    );
206
207    let world = engine::ecs::World::default();
208    let mut universe = engine::Universe::new(world);
209
210    let renderer_settings = universe
211        .world
212        .add_component(RendererSettingsComponent::msaa_off().with_window_size(320, 240));
213    universe.add(renderer_settings);
214
215    let render_graph = universe.world.add_component(RenderGraphComponent::new());
216    let emissive_pass = universe.world.add_component(EmissivePassComponent::new());
217    let blur_pass = universe.world.add_component(
218        BlurPassComponent::new()
219            .with_radius_ndc(0.06)
220            .with_half_res(true),
221    );
222    let bloom = universe.world.add_component(
223        BloomComponent::new()
224            .with_intensity(0.95)
225            .with_emissive_scale(1.2),
226    );
227    let _ = universe.attach(emissive_pass, blur_pass);
228    let _ = universe.attach(render_graph, emissive_pass);
229    let _ = universe.attach(render_graph, bloom);
230    universe.add(render_graph);
231
232    // Sky base.
233    let background = universe
234        .world
235        .add_component(BackgroundColorComponent::new());
236    let background_c = universe
237        .world
238        .add_component(ColorComponent::rgba(0.62, 0.80, 1.00, 1.0));
239    let _ = universe.world.add_child(background, background_c);
240    universe.add(background);
241
242    // Lighting for the model.
243    let ambient = universe
244        .world
245        .add_component(AmbientLightComponent::rgb(0.18, 0.18, 0.22));
246    universe.add(ambient);
247
248    let sun = universe.world.add_component(
249        DirectionalLightComponent::new()
250            .with_intensity(1.1)
251            .with_color(1.0, 0.98, 0.95),
252    );
253    let sun_dir = universe
254        .world
255        .add_component(TransformComponent::new().with_position(0.15, -0.45, 1.0));
256    let _ = universe.attach(sun_dir, sun);
257    universe.add(sun_dir);
258
259    // --- Desktop camera rig (for debugging while in VR) ---
260    let input = universe
261        .world
262        .add_component(InputComponent::new().with_speed(1.5));
263    let input_mode = universe.world.add_component(
264        InputTransformModeComponent::forward_z()
265            .with_fps_rotation()
266            .with_roll_axis_y(),
267    );
268    let _ = universe.attach(input, input_mode);
269
270    let desktop_rig = universe
271        .world
272        .add_component(TransformComponent::new().with_position(0.0, 1.2, 3.5));
273    let _ = universe.attach(input, desktop_rig);
274
275    let camera3d = universe.world.add_component(Camera3DComponent::new());
276    let _ = universe.attach(desktop_rig, camera3d);
277
278    let pointer = universe.world.add_component(PointerComponent::new());
279    let _ = universe.attach(camera3d, pointer);
280
281    example_util::spawn_desktop_camera_controls_hint(&mut universe, desktop_rig);
282    universe.add(input);
283
284    // --- XR rig (Aim controller debug cubes only; camera has moved to AVC) ---
285    let xr_input = universe.world.add_component(InputXRComponent::on());
286    let xr_gamepad = universe.world.add_component(
287        mittens_engine::engine::ecs::component::InputXRGamepadComponent::new().speed(1.5),
288    );
289    let xr_rig = universe.world.add_component(TransformComponent::new());
290    let _ = universe.attach(xr_input, xr_rig);
291    let _ = universe.attach(xr_input, xr_gamepad);
292
293    // renderer stats
294    let renderer_stats = universe
295        .world
296        .add_component(RendererStatsComponent::new().with_camera_target(CameraTarget::Xr));
297    let render_stats_rig = universe
298        .world
299        .add_component(TransformComponent::new().with_position(0.0, 1.85, 0.6));
300    let _ = universe.attach(render_stats_rig, renderer_stats);
301    let _ = universe.attach(xr_rig, render_stats_rig);
302
303    universe.add(xr_input);
304
305    // Background "skybox" content.
306    spawn_sun_background(&mut universe);
307
308    // --- VTuber model — single-input topology ---
309    //
310    // InputXRComponent drives body translation and head rotation through AvatarControlSystem.
311    // AvatarControlSystem:
312    //   - Splices a TransformComponent under J_Bip_C_Head's parent (the neck) to drive
313    //     head rotation directly. Rotating the head — not the neck — isolates the spine
314    //     so the torso doesn't twist with HMD yaw.
315    //   - Strips rotation from model_root (body faces body_yaw, not raw HMD yaw).
316    //   - Bakes the π Y handedness correction into the head rotation math.
317    //   - Smoothly rotates body to follow head when yaw delta exceeds threshold.
318    //   - Measures J_Bip_C_Head local Y in the rest pose and sets model_root.y = -bone_local_y,
319    //     so the head bone sits at driven_t world Y (= HMD height) with no hardcoded constant.
320    //   - Re-parents CameraXRComponent under J_Bip_C_Head for first-person alignment.
321    //
322    // Topology (after AVC init):
323    //   editor_root
324    //     └── avatar_input_xr (InputXRComponent)
325    //           └── avatar_driven_t (TransformComponent)
326    //                 └── AvatarControlComponent
327    //                       ├── body_pipeline → pipeline_output
328    //                       │     └── model_root (y auto-calibrated from J_Bip_C_Head)
329    //                       │           └── GLTFComponent → ... → J_Bip_C_Head
330    //                       │                                           └── CameraXRComponent
331    //                       ├── CTLXR(Left, Grip) → re-parented to lower_arm
332    //                       └── CTLXR(Right, Grip) → re-parented to lower_arm
333
334    let editor_root = universe.world.add_component(EditorComponent::new());
335
336    let avatar_input_xr = universe.world.add_component(InputXRComponent::on());
337    let avatar_xr_gamepad = universe.world.add_component(
338        mittens_engine::engine::ecs::component::InputXRGamepadComponent::new().speed(1.5),
339    );
340    let avatar_driven_t = universe.world.add_component(TransformComponent::new());
341    let _ = universe.attach(avatar_input_xr, avatar_driven_t);
342    let _ = universe.attach(avatar_input_xr, avatar_xr_gamepad);
343
344    // AvatarControlComponent: -Z forward (OpenXR default), body starts facing -Z (π yaw).
345    // camera_bone triggers auto-calibration of model_root.y from J_Bip_C_Head rest pose height,
346    // and causes any CameraXR/Camera3D direct children of AVC to be re-parented to that bone.
347    let avatar_control = universe.world.add_component(
348        AvatarControlComponent::new()
349            .with_head_bone("J_Bip_C_Head")
350            .with_camera_bone("J_Bip_C_Head")
351            .with_left_hand_bone("J_Bip_L_Hand")
352            .with_right_hand_bone("J_Bip_R_Hand")
353            .with_initial_yaw(std::f32::consts::PI)
354            .with_hand_rotation_smoothing(220.0),
355    );
356    let _ = universe.attach(avatar_driven_t, avatar_control);
357
358    // CameraXR as a direct child of AVC — discovered and re-parented to J_Bip_C_Head at init.
359    let camera_xr = universe.world.add_component(CameraXRComponent::on());
360    let _ = universe.attach(avatar_control, camera_xr);
361    let head_pointer = universe.world.add_component(PointerComponent::new());
362    let _ = universe.attach(camera_xr, head_pointer);
363
364    // Grip controllers for hand bone splicing — children of AvatarControlComponent so
365    // AvatarControlSystem discovers them by topology. Each needs a TransformComponent
366    // child (driven_t) that OpenXRSystem writes each tick.
367    let left_grip = universe.world.add_component(ControllerXRComponent::new(
368        true,
369        ControllerHand::Left,
370        ControllerPoseKind::Grip,
371    ));
372    let left_grip_t = universe.world.add_component(TransformComponent::new());
373    let _ = universe.attach(left_grip, left_grip_t);
374    let left_pointer = universe.world.add_component(PointerComponent::new());
375    let _ = universe.attach(left_grip_t, left_pointer);
376    let _ = universe.attach(avatar_control, left_grip);
377
378    let right_grip = universe.world.add_component(ControllerXRComponent::new(
379        true,
380        ControllerHand::Right,
381        ControllerPoseKind::Grip,
382    ));
383    let right_grip_t = universe.world.add_component(TransformComponent::new());
384    let _ = universe.attach(right_grip, right_grip_t);
385    let right_pointer = universe.world.add_component(PointerComponent::new());
386    let _ = universe.attach(right_grip_t, right_pointer);
387    let _ = universe.attach(avatar_control, right_grip);
388
389    // model_root: no explicit Y offset — AvatarControlSystem calibrates it from J_Bip_C_Head.
390    let model_root = universe.world.add_component(TransformComponent::new());
391    let model = universe
392        .world
393        .add_component(GLTFComponent::new("assets/models/pc-rei.hoodie.glb"));
394    let emissive = universe.world.add_component(EmissiveComponent::on());
395    let _ = universe.attach(model, emissive);
396
397    let _ = universe.attach(editor_root, avatar_input_xr);
398    let _ = universe.attach(avatar_control, model_root);
399    let _ = universe.attach(model_root, model);
400    universe.add(editor_root);
401
402    // --- Controller debug cubes (tracked poses) ---
403    let _left = spawn_controller_cube(
404        &mut universe,
405        xr_rig,
406        ControllerHand::Left,
407        (0.10, 0.90, 1.00, 1.0),
408        220.0,
409        options.xr_controller_rotation_filter,
410    );
411    let _right = spawn_controller_cube(
412        &mut universe,
413        xr_rig,
414        ControllerHand::Right,
415        (1.00, 0.35, 0.35, 1.0),
416        220.0,
417        options.xr_controller_rotation_filter,
418    );
419
420    // Enable OpenXR runtime.
421    let xr_root = universe.world.add_component(XrComponent::on());
422    universe.add(xr_root);
423
424    universe.systems.process_commands(
425        &mut universe.world,
426        &mut universe.visuals,
427        &mut universe.render_assets,
428        &mut universe.command_queue,
429    );
430
431    // Force the glTF subtree to spawn so we can query the armature for bone markers.
432    {
433        let systems = &mut universe.systems;
434        systems.gltf.tick_with_queue(
435            &mut universe.world,
436            &mut universe.visuals,
437            &mut systems.skinned_mesh,
438            &mut universe.command_queue,
439            0.0,
440        );
441    }
442    universe.systems.process_commands(
443        &mut universe.world,
444        &mut universe.visuals,
445        &mut universe.render_assets,
446        &mut universe.command_queue,
447    );
448
449    // Bone markers for editor inspection.
450    let marker_joints: &[(&str, (f32, f32, f32, f32))] = &[
451        ("[name='J_Bip_C_Head']", (0.85, 0.20, 0.85, 0.9)),
452        ("[name='J_Bip_C_Neck']", (0.20, 0.85, 0.85, 0.9)),
453        ("[name='J_Bip_C_UpperChest']", (0.20, 0.20, 0.85, 0.9)),
454        ("[name='J_Bip_L_UpperArm']", (0.85, 0.85, 0.20, 0.9)),
455        ("[name='J_Bip_R_UpperArm']", (0.85, 0.60, 0.20, 0.9)),
456    ];
457
458    for &(selector, color) in marker_joints {
459        let Some(bone) = universe.find_component(model_root, selector) else {
460            continue;
461        };
462        let marker_t = universe
463            .world
464            .add_component(TransformComponent::new().with_scale(0.025, 0.025, 0.025));
465        let marker_r = universe.world.add_component(RenderableComponent::cube());
466        let marker_c = universe
467            .world
468            .add_component(ColorComponent::rgba(color.0, color.1, color.2, color.3));
469        let marker_rcast = universe
470            .world
471            .add_component(RaycastableComponent::enabled());
472        let _ = universe.world.add_child(marker_r, marker_c);
473        let _ = universe.world.add_child(marker_r, marker_rcast);
474        let _ = universe.world.add_child(marker_t, marker_r);
475        let _ = universe.attach(bone, marker_t);
476    }
477
478    universe.enable_repl();
479    engine::Windowing::run_app(universe).expect("Windowing failed");
480}
Source

pub fn id(&self) -> Option<ComponentId>

Source

pub fn accumulate_time(&mut self, dt_sec: f32)

Source

pub fn should_update(&self) -> bool

Source

pub fn reset_update_timer(&mut self)

Source

pub fn smooth_fps(&mut self, fps: f32) -> f32

Trait Implementations§

Source§

impl Clone for RendererStatsComponent

Source§

fn clone(&self) -> RendererStatsComponent

Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl Component for RendererStatsComponent

Source§

fn name(&self) -> &'static str

Short debug/type name for this component kind (e.g. “transform”, “camera”).
Source§

fn set_id(&mut self, component: ComponentId)

Source§

fn as_any(&self) -> &dyn Any

Source§

fn as_any_mut(&mut self) -> &mut dyn Any

Source§

fn to_mms_ast(&self, _world: &World) -> ComponentExpression

Encode this component as an MMS Component Expression AST node. Read more
Source§

fn init(&mut self, _emit: &mut dyn SignalEmitter, _component: ComponentId)

Called when component is added to the World
Source§

fn cleanup(&mut self, _emit: &mut dyn SignalEmitter, _component: ComponentId)

Called when component is removed from the World.
Source§

fn encode(&self) -> HashMap<String, Value>

Encode component data to a HashMap for serialization. Read more
Source§

fn decode(&mut self, _data: &HashMap<String, Value>) -> Result<(), String>

Decode component data from a HashMap after deserialization. Read more
Source§

impl Debug for RendererStatsComponent

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl Default for RendererStatsComponent

Source§

fn default() -> Self

Returns the “default value” for a type. Read more

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> Downcast for T
where T: Any,

Source§

fn into_any(self: Box<T>) -> Box<dyn Any>

Convert Box<dyn Trait> (where Trait: Downcast) to Box<dyn Any>. Box<dyn Any> can then be further downcast into Box<ConcreteType> where ConcreteType implements Trait.
Source§

fn into_any_rc(self: Rc<T>) -> Rc<dyn Any>

Convert Rc<Trait> (where Trait: Downcast) to Rc<Any>. Rc<Any> can then be further downcast into Rc<ConcreteType> where ConcreteType implements Trait.
Source§

fn as_any(&self) -> &(dyn Any + 'static)

Convert &Trait (where Trait: Downcast) to &Any. This is needed since Rust cannot generate &Any’s vtable from &Trait’s.
Source§

fn as_any_mut(&mut self) -> &mut (dyn Any + 'static)

Convert &mut Trait (where Trait: Downcast) to &Any. This is needed since Rust cannot generate &mut Any’s vtable from &mut Trait’s.
Source§

impl<T> DowncastSync for T
where T: Any + Send + Sync,

Source§

fn into_any_arc(self: Arc<T>) -> Arc<dyn Any + Sync + Send>

Convert Arc<Trait> (where Trait: Downcast) to Arc<Any>. Arc<Any> can then be further downcast into Arc<ConcreteType> where ConcreteType implements Trait.
Source§

impl<S, T> Duplex<S> for T
where T: FromSample<S> + ToSample<S>,

Source§

impl<T> DynClone for T
where T: Clone,

Source§

fn __clone_box(&self, _: Private) -> *mut ()

Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<S> FromSample<S> for S

Source§

fn from_sample_(s: S) -> S

Source§

impl<T> Instrument for T

Source§

fn instrument(self, span: Span) -> Instrumented<Self>

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more
Source§

fn in_current_span(self) -> Instrumented<Self>

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<F, T> IntoSample<T> for F
where T: FromSample<F>,

Source§

fn into_sample(self) -> T

Source§

impl<T> PolicyExt for T
where T: ?Sized,

Source§

fn and<P, B, E>(self, other: P) -> And<T, P>
where T: Sized + Policy<B, E>, P: Policy<B, E>,

Create a new Policy that returns Action::Follow only if self and other return Action::Follow. Read more
Source§

fn or<P, B, E>(self, other: P) -> Or<T, P>
where T: Sized + Policy<B, E>, P: Policy<B, E>,

Create a new Policy that returns Action::Follow if either self or other returns Action::Follow. Read more
Source§

impl<T> Same for T

Source§

type Output = T

Should always be Self
Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> ToSample<U> for T
where U: FromSample<T>,

Source§

fn to_sample_(self) -> U

Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
Source§

impl<V, T> VZip<V> for T
where V: MultiLane<T>,

Source§

fn vzip(self) -> V

Source§

impl<T> WithSubscriber for T

Source§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self>
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more
Source§

fn with_current_subscriber(self) -> WithDispatch<Self>

Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more