viewport_lib_wind/lib.rs
1//! Wind field for `viewport-lib`.
2//!
3//! A single global wind vector with gust modulation, driven once per frame on
4//! the CPU and pushed into a deformer slot's `slot_params` on the GPU.
5//! Consumers read the field from two places:
6//!
7//! - The standard mesh shaders apply per-vertex wind through the deformer
8//! registry. [`WindPlugin::install`] registers the deformer; the GPU half
9//! keeps its slot params in sync with the CPU clock.
10//! - Rust code calls [`WindField::sample`] for spring bones, particles, or
11//! any other CPU consumer that needs the same vector the renderer sees.
12//!
13//! Typical setup:
14//!
15//! ```ignore
16//! use viewport_lib::runtime::ViewportRuntime;
17//! use viewport_lib_wind::{WindAuthoring, WindPlugin, WindSwayWeights};
18//!
19//! let wind = WindPlugin::new(WindAuthoring::default());
20//! wind.install(&mut resources, &device).expect("register wind deformer");
21//!
22//! let runtime = ViewportRuntime::new()
23//! .with_plugin(wind.cpu_plugin())
24//! .with_gpu_plugin(wind.gpu_plugin());
25//!
26//! // Per wind-affected mesh:
27//! let mask = WindSwayWeights::height_falloff(&positions, 0.0, top_y);
28//! wind.attach_sway_mask(&mut resources, &device, mesh_id, &mask);
29//! ```
30//!
31//! The CPU sampler and the WGSL deformer body use the same formula, so a
32//! vertex drawn through the deformer and a spring bone tracking the same
33//! world position see the same wind to within float precision.
34
35mod field;
36mod globals;
37mod plugin;
38mod shader;
39
40pub use field::{WindAuthoring, WindField};
41pub use globals::WindGlobals;
42pub use plugin::{WindMaterialParams, WindPlugin, WindSwayWeights};
43#[allow(deprecated)]
44pub use shader::SHARED_WIND_WGSL;
45pub use shader::{
46 WGSL_VERSION, WIND_DEFORMER_BODY, WIND_DEFORMER_NAME, WIND_MATERIAL_PARAMS_STRIDE_BYTES,
47 WIND_SWAY_STRIDE_BYTES,
48};
49
50/// Catalogue version of `viewport-lib` this crate was built against.
51///
52/// Bump in lockstep with `viewport_lib::plugin_api::shared_wgsl::WGSL_VERSION`
53/// whenever the shared-WGSL contract changes. The compile-time assertion
54/// below catches accidental drift.
55pub const VIEWPORT_LIB_WGSL_VERSION: u32 = 6;
56
57const _: () = assert!(
58 viewport_lib::plugin_api::shared_wgsl::WGSL_VERSION == VIEWPORT_LIB_WGSL_VERSION,
59 "viewport-lib catalogue version drifted; update VIEWPORT_LIB_WGSL_VERSION and review WIND_DEFORMER_BODY",
60);