1use elicitation::emit_code::{CrateDep, EmitCode, ToCodeLiteral};
13use elicitation::{
14 BevyAtmosphere, BevyColor, BevyFalloff, BevyPhaseFunction, BevyScatteringTerm, ElicitPlugin,
15 elicit_tool,
16};
17use proc_macro2::TokenStream;
18use quote::quote;
19use rmcp::ErrorData;
20use rmcp::model::{CallToolResult, Content};
21use schemars::JsonSchema;
22use serde::{Deserialize, Deserializer, Serialize};
23use tracing::instrument;
24
25#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
27#[serde(rename_all = "snake_case")]
28pub enum BevyRenderTargetKind {
29 PrimaryWindow,
31 WindowEntity,
33 Image,
35 TextureView,
37}
38
39#[derive(
41 Debug,
42 Clone,
43 Copy,
44 Serialize,
45 Deserialize,
46 JsonSchema,
47 PartialEq,
48 Eq,
49 elicitation::ToCodeLiteral,
50)]
51#[serde(rename_all = "snake_case")]
52#[to_code_literal(path = "::bevy::core_pipeline::tonemapping::Tonemapping")]
53pub enum BevyTonemappingVariant {
54 None,
56 Reinhard,
58 ReinhardLuminance,
60 AcesFitted,
62 AgX,
64 SomewhatBoringDisplayTransform,
66 TonyMcMapface,
68 BlenderFilmic,
70}
71
72#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
74#[serde(rename_all = "snake_case")]
75pub enum BevyRenderAlphaModeVariant {
76 Opaque,
78 Mask,
80 Blend,
82 Premultiplied,
84 AlphaToCoverage,
86 Add,
88 Multiply,
90}
91
92#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema)]
94struct BevyRenderTargetFields {
95 pub kind: BevyRenderTargetKind,
97 #[serde(default)]
99 pub target_expr: Option<String>,
100}
101
102#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
104#[to_code_literal(transparent, path = "::bevy::camera::RenderTarget")]
105pub struct BevyRenderTargetParams {
106 #[serde(flatten)]
108 #[to_code_literal(to_tokens = "render_target_tokens")]
109 fields: BevyRenderTargetFields,
110}
111
112#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
114#[to_code_literal(transparent)]
115pub struct BevyTonemappingParams {
116 pub variant: BevyTonemappingVariant,
118}
119
120#[derive(
122 Debug,
123 Clone,
124 Copy,
125 Serialize,
126 Deserialize,
127 JsonSchema,
128 PartialEq,
129 Eq,
130 elicitation::ToCodeLiteral,
131)]
132#[serde(rename_all = "snake_case")]
133#[to_code_literal(path = "::bevy::core_pipeline::tonemapping::DebandDither")]
134pub enum BevyDebandDitherVariant {
135 Disabled,
137 Enabled,
139}
140
141#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
143#[to_code_literal(transparent)]
144pub struct BevyDebandDitherParams {
145 pub variant: BevyDebandDitherVariant,
147}
148
149#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
151#[to_code_literal(
152 path = "::bevy::core_pipeline::oit::OrderIndependentTransparencySettings",
153 update = "::std::default::Default::default()",
154 default_expr = "::bevy::core_pipeline::oit::OrderIndependentTransparencySettings::default()"
155)]
156pub struct BevyOrderIndependentTransparencySettingsParams {
157 #[serde(default)]
159 #[to_code_literal(optional)]
160 pub layer_count: Option<i32>,
161 #[serde(default)]
163 #[to_code_literal(optional)]
164 pub alpha_threshold: Option<f32>,
165}
166
167#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
169#[serde(rename_all = "snake_case")]
170pub enum BevyScalingModeVariant {
171 WindowSize,
173 Fixed,
175 AutoMin,
177 AutoMax,
179 FixedVertical,
181 FixedHorizontal,
183}
184
185#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
187#[serde(tag = "variant", rename_all = "snake_case")]
188#[to_code_literal(path = "::bevy::camera::ScalingMode")]
189pub enum BevyScalingModeParams {
190 WindowSize,
192 Fixed {
194 width: f32,
196 height: f32,
198 },
199 AutoMin {
201 min_width: f32,
203 min_height: f32,
205 },
206 AutoMax {
208 max_width: f32,
210 max_height: f32,
212 },
213 FixedVertical {
215 viewport_height: f32,
217 },
218 FixedHorizontal {
220 viewport_width: f32,
222 },
223}
224
225#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
227#[to_code_literal(
228 path = "::bevy::camera::PerspectiveProjection",
229 update = "::bevy::camera::PerspectiveProjection::default()",
230 default_expr = "::bevy::camera::PerspectiveProjection::default()"
231)]
232pub struct BevyPerspectiveProjectionParams {
233 #[serde(default)]
235 #[to_code_literal(optional)]
236 pub fov: Option<f32>,
237 #[serde(default)]
239 #[to_code_literal(optional)]
240 pub aspect_ratio: Option<f32>,
241 #[serde(default)]
243 #[to_code_literal(optional)]
244 pub near: Option<f32>,
245 #[serde(default)]
247 #[to_code_literal(optional)]
248 pub far: Option<f32>,
249 #[serde(default)]
251 #[to_code_literal(rename = "near_clip_plane", expr, optional)]
252 pub near_clip_plane_expr: Option<String>,
253}
254
255#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default)]
257pub(crate) struct BevyOrthographicProjectionFields {
258 #[serde(default)]
260 pub use_2d_defaults: Option<bool>,
261 #[serde(default)]
263 pub near: Option<f32>,
264 #[serde(default)]
266 pub far: Option<f32>,
267 #[serde(default)]
269 pub viewport_origin_expr: Option<String>,
270 #[serde(default)]
272 pub scaling_mode_expr: Option<String>,
273 #[serde(default)]
275 pub scale: Option<f32>,
276 #[serde(default)]
278 pub area_expr: Option<String>,
279}
280
281#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
283#[to_code_literal(transparent, path = "::bevy::camera::OrthographicProjection")]
284pub struct BevyOrthographicProjectionParams {
285 #[serde(flatten)]
287 #[to_code_literal(to_tokens = "orthographic_projection_tokens")]
288 pub(crate) fields: BevyOrthographicProjectionFields,
289}
290
291#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
293#[serde(rename_all = "snake_case")]
294pub enum BevyClearColorConfigVariant {
295 Default,
297 Custom,
299 None,
301}
302
303#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
305#[serde(tag = "variant", content = "color_expr", rename_all = "snake_case")]
306#[to_code_literal(path = "::bevy::camera::ClearColorConfig")]
307pub enum BevyClearColorConfigParams {
308 Default,
310 Custom(#[to_code_literal(expr)] String),
312 None,
314}
315
316#[derive(
318 Debug,
319 Clone,
320 Copy,
321 Serialize,
322 Deserialize,
323 JsonSchema,
324 PartialEq,
325 Eq,
326 elicitation::ToCodeLiteral,
327)]
328#[serde(rename_all = "snake_case")]
329#[to_code_literal(path = "::bevy::camera::MsaaWriteback")]
330pub enum BevyMsaaWritebackVariant {
331 Off,
333 Auto,
335 Always,
337}
338
339#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
341#[to_code_literal(transparent)]
342pub struct BevyMsaaWritebackParams {
343 pub variant: BevyMsaaWritebackVariant,
345}
346
347#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
349#[serde(rename_all = "snake_case")]
350pub enum BevyExposurePreset {
351 Sunlight,
353 Overcast,
355 Indoor,
357 Blender,
359}
360
361#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default)]
362struct BevyExposureFields {
363 #[serde(default)]
365 preset: Option<BevyExposurePreset>,
366 #[serde(default)]
368 ev100: Option<f32>,
369}
370
371#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
373#[to_code_literal(path = "::bevy::camera::Exposure", transparent)]
374pub struct BevyExposureParams {
375 #[serde(flatten)]
376 #[to_code_literal(to_tokens = "exposure_tokens")]
377 fields: BevyExposureFields,
378}
379
380#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
382#[to_code_literal(path = "::bevy::camera::ClearColor", transparent)]
383pub struct BevyClearColorParams {
384 #[serde(default)]
386 #[to_code_literal(to_tokens = "clear_color_tokens")]
387 pub color_expr: Option<String>,
388}
389
390#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq, Default)]
392#[serde(rename_all = "snake_case")]
393pub enum BevyCamera3dDepthLoadOpVariant {
394 #[default]
396 Clear,
397 Load,
399}
400
401#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
403#[serde(tag = "variant", rename_all = "snake_case")]
404#[to_code_literal(path = "::bevy::camera::Camera3dDepthLoadOp")]
405pub enum BevyCamera3dDepthLoadOpParams {
406 #[to_code_literal(tuple)]
408 Clear {
409 #[serde(default = "default_camera_3d_depth_clear")]
411 depth: f32,
412 },
413 Load,
415}
416
417impl Default for BevyCamera3dDepthLoadOpParams {
418 fn default() -> Self {
419 Self::Clear {
420 depth: default_camera_3d_depth_clear(),
421 }
422 }
423}
424
425#[derive(
427 Debug,
428 Clone,
429 Copy,
430 Serialize,
431 Deserialize,
432 JsonSchema,
433 PartialEq,
434 Eq,
435 Default,
436 elicitation::ToCodeLiteral,
437)]
438#[serde(rename_all = "snake_case")]
439#[to_code_literal(path = "::bevy::camera::ScreenSpaceTransmissionQuality")]
440pub enum BevyScreenSpaceTransmissionQualityVariant {
441 Low,
443 #[default]
445 Medium,
446 High,
448 Ultra,
450}
451
452#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
454#[to_code_literal(transparent)]
455pub struct BevyScreenSpaceTransmissionQualityParams {
456 pub variant: BevyScreenSpaceTransmissionQualityVariant,
458}
459
460#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema)]
461struct BevyMainPassResolutionOverrideFields {
462 width: u32,
464 height: u32,
466}
467
468#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
470#[to_code_literal(path = "::bevy::camera::MainPassResolutionOverride", transparent)]
471pub struct BevyMainPassResolutionOverrideParams {
472 #[serde(flatten)]
473 #[to_code_literal(to_tokens = "main_pass_resolution_override_tokens")]
474 fields: BevyMainPassResolutionOverrideFields,
475}
476
477#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema)]
478struct BevySubCameraViewFields {
479 full_width: u32,
481 full_height: u32,
483 offset_x: f32,
485 offset_y: f32,
487 width: u32,
489 height: u32,
491}
492
493#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
495#[to_code_literal(path = "::bevy::camera::SubCameraView", transparent)]
496pub struct BevySubCameraViewParams {
497 #[serde(flatten)]
498 #[to_code_literal(to_tokens = "sub_camera_view_tokens")]
499 fields: BevySubCameraViewFields,
500}
501
502#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
504#[to_code_literal(path = "::bevy::camera::visibility::NoCpuCulling")]
505pub struct BevyNoCpuCullingParams;
506
507#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
509#[to_code_literal(path = "::bevy::camera::visibility::NoFrustumCulling")]
510pub struct BevyNoFrustumCullingParams;
511
512#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema)]
513struct BevyVisibilityRangeFields {
514 start_margin_start: f32,
516 start_margin_end: f32,
518 end_margin_start: f32,
520 end_margin_end: f32,
522 #[serde(default)]
524 use_aabb: Option<bool>,
525}
526
527#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
529#[to_code_literal(path = "::bevy::camera::visibility::VisibilityRange", transparent)]
530pub struct BevyVisibilityRangeParams {
531 #[serde(flatten)]
532 #[to_code_literal(to_tokens = "visibility_range_tokens")]
533 fields: BevyVisibilityRangeFields,
534}
535
536#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
538#[to_code_literal(transparent)]
539pub struct BevyColorParams {
540 pub color: BevyColor,
542}
543
544#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
546#[serde(tag = "variant", rename_all = "snake_case")]
547#[to_code_literal(path = "::bevy::render::alpha::AlphaMode")]
548pub enum BevyRenderAlphaModeParams {
549 Opaque,
551 #[to_code_literal(tuple)]
553 Mask {
554 #[serde(default = "default_render_alpha_mode_threshold")]
556 threshold: f32,
557 },
558 Blend,
560 Premultiplied,
562 AlphaToCoverage,
564 Add,
566 Multiply,
568}
569
570#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
572#[serde(rename_all = "snake_case")]
573#[to_code_literal(path = "::bevy::pbr::UvChannel")]
574pub enum BevyUvChannelVariant {
575 Uv0,
577 Uv1,
579}
580
581#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
583#[to_code_literal(transparent)]
584pub struct BevyUvChannelParams {
585 pub variant: BevyUvChannelVariant,
587}
588
589#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema)]
591#[serde(rename_all = "snake_case")]
592pub enum BevyParallaxMappingMethodVariant {
593 Occlusion,
595 Relief,
597}
598
599#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
601#[serde(tag = "variant", rename_all = "snake_case")]
602#[to_code_literal(path = "::bevy::pbr::ParallaxMappingMethod")]
603pub enum BevyParallaxMappingMethodParams {
604 Occlusion,
606 Relief {
608 #[serde(default = "default_parallax_relief_max_steps")]
610 max_steps: u32,
611 },
612}
613
614#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
616#[serde(rename_all = "snake_case")]
617#[to_code_literal(path = "::bevy::pbr::OpaqueRendererMethod")]
618pub enum BevyOpaqueRendererMethodVariant {
619 Auto,
621 Forward,
623 Deferred,
625}
626
627#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
629#[to_code_literal(transparent)]
630pub struct BevyOpaqueRendererMethodParams {
631 pub variant: BevyOpaqueRendererMethodVariant,
633}
634
635#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema)]
637#[serde(rename_all = "snake_case")]
638pub enum BevyDefaultOpaqueRendererMethodVariant {
639 Default,
641 Forward,
643 Deferred,
645}
646
647#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
649#[to_code_literal(path = "::bevy::pbr::DefaultOpaqueRendererMethod", transparent)]
650pub struct BevyDefaultOpaqueRendererMethodParams {
651 #[to_code_literal(to_tokens = "default_opaque_renderer_method_tokens")]
653 pub variant: BevyDefaultOpaqueRendererMethodVariant,
654}
655
656#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema)]
658#[serde(rename_all = "snake_case")]
659pub enum BevyAlphaMode2dVariant {
660 Opaque,
662 Mask,
664 Blend,
666}
667
668#[derive(
670 Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq, elicitation::ToCodeLiteral,
671)]
672#[serde(tag = "variant", content = "threshold", rename_all = "snake_case")]
673#[to_code_literal(path = "::bevy::sprite_render::AlphaMode2d")]
674pub enum BevyAlphaMode2dParams {
675 Opaque,
677 Mask(f32),
679 Blend,
681}
682
683#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
685#[to_code_literal(path = "::bevy::pbr::StandardMaterial", default_update)]
686pub struct BevyStandardMaterialParams {
687 #[serde(default)]
689 #[to_code_literal(optional, rename = "base_color", expr)]
690 pub base_color_expr: Option<String>,
691 #[serde(default)]
693 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
694 pub base_color_channel: Option<BevyUvChannelVariant>,
695 #[serde(default)]
697 #[to_code_literal(
698 optional,
699 rename = "base_color_texture",
700 to_tokens = "some_expr_tokens"
701 )]
702 pub base_color_texture_expr: Option<String>,
703 #[serde(default)]
705 #[to_code_literal(optional, rename = "emissive", expr)]
706 pub emissive_expr: Option<String>,
707 #[serde(default)]
709 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
710 pub emissive_channel: Option<BevyUvChannelVariant>,
711 #[serde(default)]
713 #[to_code_literal(optional, rename = "emissive_texture", to_tokens = "some_expr_tokens")]
714 pub emissive_texture_expr: Option<String>,
715 #[serde(default)]
717 #[to_code_literal(optional)]
718 pub emissive_exposure_weight: Option<f32>,
719 #[serde(default)]
721 #[to_code_literal(optional)]
722 pub metallic: Option<f32>,
723 #[serde(default)]
725 #[to_code_literal(optional)]
726 pub perceptual_roughness: Option<f32>,
727 #[serde(default)]
729 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
730 pub metallic_roughness_channel: Option<BevyUvChannelVariant>,
731 #[serde(default)]
733 #[to_code_literal(
734 optional,
735 rename = "metallic_roughness_texture",
736 to_tokens = "some_expr_tokens"
737 )]
738 pub metallic_roughness_texture_expr: Option<String>,
739 #[serde(default)]
741 #[to_code_literal(optional)]
742 pub reflectance: Option<f32>,
743 #[serde(default)]
745 #[to_code_literal(optional, rename = "specular_tint", expr)]
746 pub specular_tint_expr: Option<String>,
747 #[serde(default)]
749 #[to_code_literal(optional)]
750 pub diffuse_transmission: Option<f32>,
751 #[serde(default)]
753 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
754 pub diffuse_transmission_channel: Option<BevyUvChannelVariant>,
755 #[serde(default)]
757 #[to_code_literal(
758 optional,
759 rename = "diffuse_transmission_texture",
760 to_tokens = "some_expr_tokens"
761 )]
762 pub diffuse_transmission_texture_expr: Option<String>,
763 #[serde(default)]
765 #[to_code_literal(optional)]
766 pub specular_transmission: Option<f32>,
767 #[serde(default)]
769 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
770 pub specular_transmission_channel: Option<BevyUvChannelVariant>,
771 #[serde(default)]
773 #[to_code_literal(
774 optional,
775 rename = "specular_transmission_texture",
776 to_tokens = "some_expr_tokens"
777 )]
778 pub specular_transmission_texture_expr: Option<String>,
779 #[serde(default)]
781 #[to_code_literal(optional)]
782 pub thickness: Option<f32>,
783 #[serde(default)]
785 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
786 pub thickness_channel: Option<BevyUvChannelVariant>,
787 #[serde(default)]
789 #[to_code_literal(optional, rename = "thickness_texture", to_tokens = "some_expr_tokens")]
790 pub thickness_texture_expr: Option<String>,
791 #[serde(default)]
793 #[to_code_literal(optional)]
794 pub ior: Option<f32>,
795 #[serde(default)]
797 #[to_code_literal(optional)]
798 pub attenuation_distance: Option<f32>,
799 #[serde(default)]
801 #[to_code_literal(optional, rename = "attenuation_color", expr)]
802 pub attenuation_color_expr: Option<String>,
803 #[serde(default)]
805 #[to_code_literal(optional)]
806 pub clearcoat: Option<f32>,
807 #[serde(default)]
809 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
810 pub clearcoat_channel: Option<BevyUvChannelVariant>,
811 #[serde(default)]
813 #[to_code_literal(optional, rename = "clearcoat_texture", to_tokens = "some_expr_tokens")]
814 pub clearcoat_texture_expr: Option<String>,
815 #[serde(default)]
817 #[to_code_literal(optional)]
818 pub clearcoat_perceptual_roughness: Option<f32>,
819 #[serde(default)]
821 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
822 pub clearcoat_roughness_channel: Option<BevyUvChannelVariant>,
823 #[serde(default)]
825 #[to_code_literal(
826 optional,
827 rename = "clearcoat_roughness_texture",
828 to_tokens = "some_expr_tokens"
829 )]
830 pub clearcoat_roughness_texture_expr: Option<String>,
831 #[serde(default)]
833 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
834 pub clearcoat_normal_channel: Option<BevyUvChannelVariant>,
835 #[serde(default)]
837 #[to_code_literal(
838 optional,
839 rename = "clearcoat_normal_texture",
840 to_tokens = "some_expr_tokens"
841 )]
842 pub clearcoat_normal_texture_expr: Option<String>,
843 #[serde(default)]
845 #[to_code_literal(optional)]
846 pub anisotropy_strength: Option<f32>,
847 #[serde(default)]
849 #[to_code_literal(optional)]
850 pub anisotropy_rotation: Option<f32>,
851 #[serde(default)]
853 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
854 pub anisotropy_channel: Option<BevyUvChannelVariant>,
855 #[serde(default)]
857 #[to_code_literal(
858 optional,
859 rename = "anisotropy_texture",
860 to_tokens = "some_expr_tokens"
861 )]
862 pub anisotropy_texture_expr: Option<String>,
863 #[serde(default)]
865 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
866 pub normal_map_channel: Option<BevyUvChannelVariant>,
867 #[serde(default)]
869 #[to_code_literal(
870 optional,
871 rename = "normal_map_texture",
872 to_tokens = "some_expr_tokens"
873 )]
874 pub normal_map_texture_expr: Option<String>,
875 #[serde(default)]
877 #[to_code_literal(optional)]
878 pub flip_normal_map_y: Option<bool>,
879 #[serde(default)]
881 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
882 pub occlusion_channel: Option<BevyUvChannelVariant>,
883 #[serde(default)]
885 #[to_code_literal(optional, rename = "occlusion_texture", to_tokens = "some_expr_tokens")]
886 pub occlusion_texture_expr: Option<String>,
887 #[serde(default)]
889 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
890 pub specular_channel: Option<BevyUvChannelVariant>,
891 #[serde(default)]
893 #[to_code_literal(optional, rename = "specular_texture", to_tokens = "some_expr_tokens")]
894 pub specular_texture_expr: Option<String>,
895 #[serde(default)]
897 #[to_code_literal(optional, to_tokens = "emit_uv_channel_variant_tokens")]
898 pub specular_tint_channel: Option<BevyUvChannelVariant>,
899 #[serde(default)]
901 #[to_code_literal(
902 optional,
903 rename = "specular_tint_texture",
904 to_tokens = "some_expr_tokens"
905 )]
906 pub specular_tint_texture_expr: Option<String>,
907 #[serde(default)]
909 #[to_code_literal(optional, rename = "alpha_mode", expr)]
910 pub alpha_mode_expr: Option<String>,
911 #[serde(default)]
913 #[to_code_literal(optional)]
914 pub double_sided: Option<bool>,
915 #[serde(default)]
917 #[to_code_literal(optional)]
918 pub unlit: Option<bool>,
919 #[serde(default)]
921 #[to_code_literal(optional)]
922 pub fog_enabled: Option<bool>,
923 #[serde(default)]
925 #[to_code_literal(optional, rename = "cull_mode", to_tokens = "some_expr_tokens")]
926 pub cull_mode_expr: Option<String>,
927 #[serde(default)]
929 #[to_code_literal(optional)]
930 pub depth_bias: Option<f32>,
931 #[serde(default)]
933 #[to_code_literal(optional, rename = "depth_map", to_tokens = "some_expr_tokens")]
934 pub depth_map_expr: Option<String>,
935 #[serde(default)]
937 #[to_code_literal(optional)]
938 pub parallax_depth_scale: Option<f32>,
939 #[serde(default)]
941 #[to_code_literal(optional, rename = "parallax_mapping_method", expr)]
942 pub parallax_mapping_method_expr: Option<String>,
943 #[serde(default)]
945 #[to_code_literal(optional)]
946 pub max_parallax_layer_count: Option<f32>,
947 #[serde(default)]
949 #[to_code_literal(optional)]
950 pub lightmap_exposure: Option<f32>,
951 #[serde(default)]
953 #[to_code_literal(optional, rename = "opaque_render_method", expr)]
954 pub opaque_render_method_expr: Option<String>,
955 #[serde(default)]
957 #[to_code_literal(optional)]
958 pub deferred_lighting_pass_id: Option<u8>,
959 #[serde(default)]
961 #[to_code_literal(optional, rename = "uv_transform", expr)]
962 pub uv_transform_expr: Option<String>,
963}
964
965#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
967#[to_code_literal(path = "::bevy::pbr::Lightmap", default_update)]
968pub struct BevyLightmapParams {
969 #[to_code_literal(rename = "image", expr)]
971 pub image_expr: String,
972 #[serde(default)]
974 #[to_code_literal(rename = "uv_rect", expr, optional)]
975 pub uv_rect_expr: Option<String>,
976 #[serde(default)]
978 #[to_code_literal(optional)]
979 pub bicubic_sampling: Option<bool>,
980}
981
982#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
984#[to_code_literal(path = "::bevy::sprite_render::ColorMaterial", default_update)]
985pub struct BevyColorMaterialParams {
986 #[serde(default)]
988 #[to_code_literal(rename = "color", expr, optional)]
989 pub color_expr: Option<String>,
990 #[serde(default)]
992 #[to_code_literal(rename = "alpha_mode", expr, optional)]
993 pub alpha_mode_expr: Option<String>,
994 #[serde(default)]
996 #[to_code_literal(rename = "uv_transform", expr, optional)]
997 pub uv_transform_expr: Option<String>,
998 #[serde(default)]
1000 #[to_code_literal(rename = "texture", optional, to_tokens = "some_expr_tokens")]
1001 pub texture_expr: Option<String>,
1002}
1003
1004#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1006#[to_code_literal(path = "::bevy::core_pipeline::Skybox", default_update)]
1007pub struct BevySkyboxParams {
1008 #[to_code_literal(rename = "image", expr)]
1010 pub image_expr: String,
1011 #[serde(default)]
1013 #[to_code_literal(optional)]
1014 pub brightness: Option<f32>,
1015 #[serde(default)]
1017 #[to_code_literal(rename = "rotation", expr, optional)]
1018 pub rotation_expr: Option<String>,
1019}
1020
1021#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1023#[to_code_literal(path = "::bevy::core_pipeline::prepass::DepthPrepass")]
1024pub struct BevyDepthPrepassParams;
1025
1026#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1028#[to_code_literal(path = "::bevy::core_pipeline::prepass::NormalPrepass")]
1029pub struct BevyNormalPrepassParams;
1030
1031#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1033#[to_code_literal(path = "::bevy::core_pipeline::prepass::MotionVectorPrepass")]
1034pub struct BevyMotionVectorPrepassParams;
1035
1036#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1038#[to_code_literal(path = "::bevy::core_pipeline::prepass::DeferredPrepass")]
1039pub struct BevyDeferredPrepassParams;
1040
1041#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1043#[to_code_literal(path = "::bevy::core_pipeline::prepass::DepthPrepassDoubleBuffer")]
1044pub struct BevyDepthPrepassDoubleBufferParams;
1045
1046#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1048#[to_code_literal(path = "::bevy::core_pipeline::prepass::DeferredPrepassDoubleBuffer")]
1049pub struct BevyDeferredPrepassDoubleBufferParams;
1050
1051#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1053#[to_code_literal(path = "::bevy::light::AmbientLight", default_update)]
1054pub struct BevyAmbientLightParams {
1055 #[serde(default)]
1057 #[to_code_literal(rename = "color", expr, optional)]
1058 pub color_expr: Option<String>,
1059 #[serde(default)]
1061 #[to_code_literal(optional)]
1062 pub brightness: Option<f32>,
1063 #[serde(default)]
1065 #[to_code_literal(optional)]
1066 pub affects_lightmapped_meshes: Option<bool>,
1067}
1068
1069#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1071#[to_code_literal(path = "::bevy::light::DirectionalLight", default_update)]
1072pub struct BevyDirectionalLightParams {
1073 #[serde(default)]
1075 #[to_code_literal(rename = "color", expr, optional)]
1076 pub color_expr: Option<String>,
1077 #[serde(default)]
1079 #[to_code_literal(optional)]
1080 pub illuminance: Option<f32>,
1081 #[serde(default)]
1083 #[to_code_literal(optional)]
1084 pub shadows_enabled: Option<bool>,
1085}
1086
1087#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1089#[to_code_literal(path = "::bevy::light::GlobalAmbientLight", default_update)]
1090pub struct BevyGlobalAmbientLightParams {
1091 #[serde(default)]
1093 #[to_code_literal(rename = "color", expr, optional)]
1094 pub color_expr: Option<String>,
1095 #[serde(default)]
1097 #[to_code_literal(optional)]
1098 pub brightness: Option<f32>,
1099 #[serde(default)]
1101 #[to_code_literal(optional)]
1102 pub affects_lightmapped_meshes: Option<bool>,
1103}
1104
1105#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1107#[to_code_literal(path = "::bevy::light::PointLight", default_update)]
1108pub struct BevyPointLightParams {
1109 #[serde(default)]
1111 #[to_code_literal(rename = "color", expr, optional)]
1112 pub color_expr: Option<String>,
1113 #[serde(default)]
1115 #[to_code_literal(optional)]
1116 pub intensity: Option<f32>,
1117 #[serde(default)]
1119 #[to_code_literal(optional)]
1120 pub range: Option<f32>,
1121 #[serde(default)]
1123 #[to_code_literal(optional)]
1124 pub radius: Option<f32>,
1125 #[serde(default)]
1127 #[to_code_literal(optional)]
1128 pub shadows_enabled: Option<bool>,
1129}
1130
1131#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1133#[to_code_literal(path = "::bevy::light::SpotLight", default_update)]
1134pub struct BevySpotLightParams {
1135 #[serde(default)]
1137 #[to_code_literal(rename = "color", expr, optional)]
1138 pub color_expr: Option<String>,
1139 #[serde(default)]
1141 #[to_code_literal(optional)]
1142 pub intensity: Option<f32>,
1143 #[serde(default)]
1145 #[to_code_literal(optional)]
1146 pub range: Option<f32>,
1147 #[serde(default)]
1149 #[to_code_literal(optional)]
1150 pub radius: Option<f32>,
1151 #[serde(default)]
1153 #[to_code_literal(optional)]
1154 pub inner_angle: Option<f32>,
1155 #[serde(default)]
1157 #[to_code_literal(optional)]
1158 pub outer_angle: Option<f32>,
1159 #[serde(default)]
1161 #[to_code_literal(optional)]
1162 pub shadows_enabled: Option<bool>,
1163}
1164
1165#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1167#[to_code_literal(
1168 path = "::bevy::light::DirectionalLightShadowMap",
1169 default_expr = "::bevy::light::DirectionalLightShadowMap::default()"
1170)]
1171pub struct BevyDirectionalLightShadowMapParams {
1172 #[serde(default)]
1174 #[to_code_literal(optional)]
1175 pub size: Option<usize>,
1176}
1177
1178#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1180#[to_code_literal(
1181 path = "::bevy::light::PointLightShadowMap",
1182 default_expr = "::bevy::light::PointLightShadowMap::default()"
1183)]
1184pub struct BevyPointLightShadowMapParams {
1185 #[serde(default)]
1187 #[to_code_literal(optional)]
1188 pub size: Option<usize>,
1189}
1190
1191#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1193#[to_code_literal(path = "::bevy::light::EnvironmentMapLight", default_update)]
1194pub struct BevyEnvironmentMapLightParams {
1195 #[to_code_literal(rename = "diffuse_map", expr)]
1197 pub diffuse_map_expr: String,
1198 #[to_code_literal(rename = "specular_map", expr)]
1200 pub specular_map_expr: String,
1201 #[serde(default)]
1203 #[to_code_literal(optional)]
1204 pub intensity: Option<f32>,
1205 #[serde(default)]
1207 #[to_code_literal(rename = "rotation", expr, optional)]
1208 pub rotation_expr: Option<String>,
1209 #[serde(default)]
1211 #[to_code_literal(optional)]
1212 pub affects_lightmapped_mesh_diffuse: Option<bool>,
1213}
1214
1215#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1217#[to_code_literal(path = "::bevy::light::GeneratedEnvironmentMapLight", default_update)]
1218pub struct BevyGeneratedEnvironmentMapLightParams {
1219 #[to_code_literal(rename = "environment_map", expr)]
1221 pub environment_map_expr: String,
1222 #[serde(default)]
1224 #[to_code_literal(optional)]
1225 pub intensity: Option<f32>,
1226 #[serde(default)]
1228 #[to_code_literal(rename = "rotation", expr, optional)]
1229 pub rotation_expr: Option<String>,
1230 #[serde(default)]
1232 #[to_code_literal(optional)]
1233 pub affects_lightmapped_mesh_diffuse: Option<bool>,
1234}
1235
1236#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1238#[to_code_literal(
1239 path = "::bevy::light::AtmosphereEnvironmentMapLight",
1240 default_update,
1241 default_expr = "::bevy::light::AtmosphereEnvironmentMapLight::default()"
1242)]
1243pub struct BevyAtmosphereEnvironmentMapLightParams {
1244 #[serde(default)]
1246 #[to_code_literal(optional)]
1247 pub intensity: Option<f32>,
1248 #[serde(default)]
1250 #[to_code_literal(optional)]
1251 pub affects_lightmapped_mesh_diffuse: Option<bool>,
1252 #[serde(default)]
1254 #[to_code_literal(optional, to_tokens = "uvec2_array_tokens")]
1255 pub size: Option<[u32; 2]>,
1256}
1257
1258#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1260#[to_code_literal(path = "::bevy::light::VolumetricLight")]
1261pub struct BevyVolumetricLightParams;
1262
1263#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1265#[to_code_literal(path = "::bevy::light::VolumetricFog", default_update)]
1266pub struct BevyVolumetricFogParams {
1267 #[serde(default)]
1269 #[to_code_literal(rename = "ambient_color", expr, optional)]
1270 pub ambient_color_expr: Option<String>,
1271 #[serde(default)]
1273 #[to_code_literal(optional)]
1274 pub ambient_intensity: Option<f32>,
1275 #[serde(default)]
1277 #[to_code_literal(optional)]
1278 pub jitter: Option<f32>,
1279 #[serde(default)]
1281 #[to_code_literal(optional)]
1282 pub step_count: Option<u32>,
1283}
1284
1285#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1287#[to_code_literal(path = "::bevy::light::FogVolume", default_update)]
1288pub struct BevyFogVolumeParams {
1289 #[serde(default)]
1291 #[to_code_literal(rename = "fog_color", expr, optional)]
1292 pub fog_color_expr: Option<String>,
1293 #[serde(default)]
1295 #[to_code_literal(optional)]
1296 pub density_factor: Option<f32>,
1297 #[serde(default)]
1299 #[to_code_literal(rename = "density_texture", optional, to_tokens = "some_expr_tokens")]
1300 pub density_texture_expr: Option<String>,
1301 #[serde(default)]
1303 #[to_code_literal(rename = "density_texture_offset", expr, optional)]
1304 pub density_texture_offset_expr: Option<String>,
1305 #[serde(default)]
1307 #[to_code_literal(optional)]
1308 pub absorption: Option<f32>,
1309 #[serde(default)]
1311 #[to_code_literal(optional)]
1312 pub scattering: Option<f32>,
1313 #[serde(default)]
1315 #[to_code_literal(optional)]
1316 pub scattering_asymmetry: Option<f32>,
1317 #[serde(default)]
1319 #[to_code_literal(rename = "light_tint", expr, optional)]
1320 pub light_tint_expr: Option<String>,
1321 #[serde(default)]
1323 #[to_code_literal(optional)]
1324 pub light_intensity: Option<f32>,
1325}
1326
1327#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1329#[to_code_literal(path = "::bevy::light::LightProbe")]
1330pub struct BevyLightProbeParams;
1331
1332#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1334#[to_code_literal(path = "::bevy::light::IrradianceVolume", default_update)]
1335pub struct BevyIrradianceVolumeParams {
1336 #[to_code_literal(rename = "voxels", expr)]
1338 pub voxels_expr: String,
1339 #[serde(default)]
1341 #[to_code_literal(optional)]
1342 pub intensity: Option<f32>,
1343 #[serde(default)]
1345 #[to_code_literal(optional)]
1346 pub affects_lightmapped_meshes: Option<bool>,
1347}
1348
1349#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1351#[to_code_literal(path = "::bevy::light::SunDisk", default_update)]
1352pub struct BevySunDiskParams {
1353 #[serde(default)]
1355 #[to_code_literal(optional)]
1356 pub angular_size: Option<f32>,
1357 #[serde(default)]
1359 #[to_code_literal(optional)]
1360 pub intensity: Option<f32>,
1361}
1362
1363#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1365#[to_code_literal(path = "::bevy::light::NotShadowCaster")]
1366pub struct BevyNotShadowCasterParams;
1367
1368#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1370#[to_code_literal(path = "::bevy::light::NotShadowReceiver")]
1371pub struct BevyNotShadowReceiverParams;
1372
1373#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1375#[to_code_literal(path = "::bevy::light::TransmittedShadowReceiver")]
1376pub struct BevyTransmittedShadowReceiverParams;
1377
1378#[derive(
1380 Debug,
1381 Clone,
1382 Copy,
1383 Serialize,
1384 Deserialize,
1385 JsonSchema,
1386 PartialEq,
1387 Eq,
1388 elicitation::ToCodeLiteral,
1389)]
1390#[serde(rename_all = "snake_case")]
1391#[to_code_literal(path = "::bevy::light::ShadowFilteringMethod")]
1392pub enum BevyShadowFilteringMethodVariant {
1393 Hardware2x2,
1395 Gaussian,
1397 Temporal,
1399}
1400
1401#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1403#[to_code_literal(transparent)]
1404pub struct BevyShadowFilteringMethodParams {
1405 pub variant: BevyShadowFilteringMethodVariant,
1407}
1408
1409#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1411#[serde(rename_all = "snake_case")]
1412pub enum BevyClusterFarZModeKind {
1413 MaxClusterableObjectRange,
1415 Constant,
1417}
1418
1419#[derive(
1421 Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq, elicitation::ToCodeLiteral,
1422)]
1423#[serde(tag = "kind", content = "constant", rename_all = "snake_case")]
1424#[to_code_literal(path = "::bevy::light::ClusterFarZMode")]
1425pub enum BevyClusterFarZModeParams {
1426 MaxClusterableObjectRange,
1428 Constant(f32),
1430}
1431
1432#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1434#[to_code_literal(
1435 path = "::bevy::light::ClusterZConfig",
1436 default_update,
1437 default_expr = "::std::default::Default::default()"
1438)]
1439pub struct BevyClusterZConfigParams {
1440 #[serde(default)]
1442 #[to_code_literal(optional)]
1443 pub first_slice_depth: Option<f32>,
1444 #[serde(default)]
1446 #[to_code_literal(rename = "far_z_mode", optional, to_tokens = "emit_code_tokens")]
1447 pub far_z_mode: Option<BevyClusterFarZModeParams>,
1448}
1449
1450#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1452#[serde(tag = "kind", rename_all = "snake_case")]
1453#[to_code_literal(path = "::bevy::light::ClusterConfig")]
1454pub enum BevyClusterConfigParams {
1455 None,
1457 Single,
1459 #[serde(rename = "xyz")]
1461 XYZ {
1462 #[to_code_literal(to_tokens = "uvec3_array_tokens")]
1464 dimensions: [u32; 3],
1465 #[serde(default)]
1467 z_config: BevyClusterZConfigParams,
1468 #[serde(default = "default_true")]
1470 dynamic_resizing: bool,
1471 },
1472 FixedZ {
1474 total: u32,
1476 z_slices: u32,
1478 #[serde(default)]
1480 z_config: BevyClusterZConfigParams,
1481 #[serde(default = "default_true")]
1483 dynamic_resizing: bool,
1484 },
1485}
1486
1487#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1489#[to_code_literal(path = "::bevy::pbr::ScreenSpaceReflections", default_update)]
1490pub struct BevyScreenSpaceReflectionsParams {
1491 #[serde(default)]
1493 #[to_code_literal(optional)]
1494 pub perceptual_roughness_threshold: Option<f32>,
1495 #[serde(default)]
1497 #[to_code_literal(optional)]
1498 pub thickness: Option<f32>,
1499 #[serde(default)]
1501 #[to_code_literal(optional)]
1502 pub linear_steps: Option<u32>,
1503 #[serde(default)]
1505 #[to_code_literal(optional)]
1506 pub linear_march_exponent: Option<f32>,
1507 #[serde(default)]
1509 #[to_code_literal(optional)]
1510 pub bisection_steps: Option<u32>,
1511 #[serde(default)]
1513 #[to_code_literal(optional)]
1514 pub use_secant: Option<bool>,
1515}
1516
1517#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1519#[to_code_literal(path = "::bevy::light::ClusteredDecal", default_update)]
1520pub struct BevyClusteredDecalParams {
1521 #[serde(default)]
1523 #[to_code_literal(
1524 rename = "base_color_texture",
1525 optional,
1526 to_tokens = "some_expr_tokens"
1527 )]
1528 pub base_color_texture_expr: Option<String>,
1529 #[serde(default)]
1531 #[to_code_literal(
1532 rename = "normal_map_texture",
1533 optional,
1534 to_tokens = "some_expr_tokens"
1535 )]
1536 pub normal_map_texture_expr: Option<String>,
1537 #[serde(default)]
1539 #[to_code_literal(
1540 rename = "metallic_roughness_texture",
1541 optional,
1542 to_tokens = "some_expr_tokens"
1543 )]
1544 pub metallic_roughness_texture_expr: Option<String>,
1545 #[serde(default)]
1547 #[to_code_literal(rename = "emissive_texture", optional, to_tokens = "some_expr_tokens")]
1548 pub emissive_texture_expr: Option<String>,
1549 #[serde(default)]
1551 #[to_code_literal(optional)]
1552 pub tag: Option<u32>,
1553}
1554
1555#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1557#[to_code_literal(path = "::bevy::mesh::Mesh3d", tuple)]
1558pub struct BevyMesh3dParams {
1559 #[to_code_literal(expr)]
1561 pub mesh_expr: String,
1562}
1563
1564#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1566#[to_code_literal(path = "::bevy::mesh::Mesh2d", tuple)]
1567pub struct BevyMesh2dParams {
1568 #[to_code_literal(expr)]
1570 pub mesh_expr: String,
1571}
1572
1573#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1575#[to_code_literal(path = "::bevy::pbr::MeshMaterial3d", tuple)]
1576pub struct BevyMeshMaterial3dParams {
1577 #[to_code_literal(expr)]
1579 pub material_expr: String,
1580}
1581
1582#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1584#[to_code_literal(path = "::bevy::sprite_render::MeshMaterial2d", tuple)]
1585pub struct BevyMeshMaterial2dParams {
1586 #[to_code_literal(expr)]
1588 pub material_expr: String,
1589}
1590
1591#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1593#[to_code_literal(path = "::bevy::pbr::Wireframe")]
1594pub struct BevyWireframeParams;
1595
1596#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1598#[to_code_literal(path = "::bevy::pbr::WireframeColor")]
1599pub struct BevyWireframeColorParams {
1600 #[to_code_literal(rename = "color", expr)]
1602 pub color_expr: String,
1603}
1604
1605#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1607#[to_code_literal(path = "::bevy::pbr::NoWireframe")]
1608pub struct BevyNoWireframeParams;
1609
1610#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1612#[to_code_literal(
1613 path = "::bevy::pbr::WireframeConfig",
1614 default_update,
1615 default_expr = "::bevy::pbr::WireframeConfig::default()"
1616)]
1617pub struct BevyWireframeConfigParams {
1618 #[serde(default)]
1620 #[to_code_literal(optional)]
1621 pub global: Option<bool>,
1622 #[serde(default)]
1624 #[to_code_literal(rename = "default_color", expr, optional)]
1625 pub default_color_expr: Option<String>,
1626}
1627
1628#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1630#[to_code_literal(path = "::bevy::pbr::Mesh3dWireframe", tuple)]
1631pub struct BevyMesh3dWireframeParams {
1632 #[to_code_literal(expr)]
1634 pub material_expr: String,
1635}
1636
1637#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1639#[to_code_literal(path = "::bevy::sprite_render::Wireframe2d")]
1640pub struct BevyWireframe2dParams;
1641
1642#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1644#[to_code_literal(path = "::bevy::sprite_render::Wireframe2dColor")]
1645pub struct BevyWireframe2dColorParams {
1646 #[to_code_literal(rename = "color", expr)]
1648 pub color_expr: String,
1649}
1650
1651#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1653#[to_code_literal(path = "::bevy::sprite_render::NoWireframe2d")]
1654pub struct BevyNoWireframe2dParams;
1655
1656#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1658#[to_code_literal(
1659 path = "::bevy::sprite_render::Wireframe2dConfig",
1660 default_update,
1661 default_expr = "::bevy::sprite_render::Wireframe2dConfig::default()"
1662)]
1663pub struct BevyWireframe2dConfigParams {
1664 #[serde(default)]
1666 #[to_code_literal(optional)]
1667 pub global: Option<bool>,
1668 #[serde(default)]
1670 #[to_code_literal(rename = "default_color", expr, optional)]
1671 pub default_color_expr: Option<String>,
1672}
1673
1674#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1676#[to_code_literal(path = "::bevy::sprite_render::Mesh2dWireframe", tuple)]
1677pub struct BevyMesh2dWireframeParams {
1678 #[to_code_literal(expr)]
1680 pub material_expr: String,
1681}
1682
1683#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema)]
1685pub struct BevyCamera3dParams {
1686 #[serde(default = "default_commands_var")]
1688 pub commands_var: String,
1689 #[serde(default)]
1691 pub transform_expr: Option<String>,
1692 #[serde(default)]
1694 pub fov: Option<f32>,
1695 #[serde(default)]
1697 pub near: Option<f32>,
1698 #[serde(default)]
1700 pub far: Option<f32>,
1701 #[serde(default)]
1703 pub hdr: Option<bool>,
1704 #[serde(default)]
1706 pub render_target: Option<BevyRenderTargetParams>,
1707 #[serde(default)]
1709 pub tonemapping_expr: Option<String>,
1710}
1711
1712#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema)]
1714pub struct BevyCamera2dParams {
1715 #[serde(default = "default_commands_var")]
1717 pub commands_var: String,
1718 #[serde(default)]
1720 pub transform_expr: Option<String>,
1721 #[serde(default)]
1723 pub near: Option<f32>,
1724 #[serde(default)]
1726 pub far: Option<f32>,
1727 #[serde(default)]
1729 pub scale: Option<f32>,
1730 #[serde(default)]
1732 pub hdr: Option<bool>,
1733 #[serde(default)]
1735 pub render_target: Option<BevyRenderTargetParams>,
1736 #[serde(default)]
1738 pub tonemapping_expr: Option<String>,
1739}
1740
1741#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1743#[to_code_literal(path = "::bevy::camera::Viewport")]
1744pub struct BevyViewportParams {
1745 #[to_code_literal(to_tokens = "uvec2_array_tokens")]
1747 pub physical_position: [u32; 2],
1748 #[to_code_literal(to_tokens = "uvec2_array_tokens")]
1750 pub physical_size: [u32; 2],
1751 #[serde(default)]
1753 #[to_code_literal(to_tokens = "viewport_depth_tokens")]
1754 pub depth: Option<[f32; 2]>,
1755}
1756
1757#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1759#[to_code_literal(path = "::bevy::pbr::DistanceFog", default_update)]
1760pub struct BevyFogSettingsParams {
1761 #[serde(default)]
1763 #[to_code_literal(rename = "color", optional, to_tokens = "into_expr_tokens")]
1764 pub color_expr: Option<String>,
1765 #[serde(default)]
1767 #[to_code_literal(
1768 rename = "directional_light_color",
1769 optional,
1770 to_tokens = "into_expr_tokens"
1771 )]
1772 pub directional_light_color_expr: Option<String>,
1773 #[serde(default)]
1775 #[to_code_literal(optional)]
1776 pub directional_light_exponent: Option<f32>,
1777 #[serde(default)]
1779 #[to_code_literal(rename = "falloff", expr, optional)]
1780 pub falloff_expr: Option<String>,
1781}
1782
1783#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1785#[serde(rename_all = "snake_case")]
1786pub enum BevyBloomPreset {
1787 Natural,
1789 Anamorphic,
1791 OldSchool,
1793 ScreenBlur,
1795}
1796
1797#[derive(
1799 Debug,
1800 Clone,
1801 Copy,
1802 Serialize,
1803 Deserialize,
1804 JsonSchema,
1805 PartialEq,
1806 Eq,
1807 elicitation::ToCodeLiteral,
1808)]
1809#[serde(rename_all = "snake_case")]
1810#[to_code_literal(path = "::bevy::post_process::bloom::BloomCompositeMode")]
1811pub enum BevyBloomCompositeModeVariant {
1812 EnergyConserving,
1814 Additive,
1816}
1817
1818#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1820#[to_code_literal(transparent)]
1821pub struct BevyBloomCompositeModeParams {
1822 pub variant: BevyBloomCompositeModeVariant,
1824}
1825
1826#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema)]
1828pub struct BevyBloomSettingsParams {
1829 #[serde(default)]
1831 pub preset: Option<BevyBloomPreset>,
1832 #[serde(default)]
1834 pub intensity: Option<f32>,
1835 #[serde(default)]
1837 pub low_frequency_boost: Option<f32>,
1838 #[serde(default)]
1840 pub low_frequency_boost_curvature: Option<f32>,
1841 #[serde(default)]
1843 pub high_pass_frequency: Option<f32>,
1844 #[serde(default)]
1846 pub prefilter_threshold: Option<f32>,
1847 #[serde(default)]
1849 pub prefilter_threshold_softness: Option<f32>,
1850 #[serde(default)]
1852 pub composite_mode: Option<BevyBloomCompositeModeVariant>,
1853 #[serde(default)]
1855 pub max_mip_dimension: Option<u32>,
1856 #[serde(default)]
1858 pub scale_expr: Option<String>,
1859}
1860
1861#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1863#[to_code_literal(
1864 path = "::bevy::sprite::Sprite",
1865 default_update,
1866 default_expr = "::bevy::sprite::Sprite { ..::std::default::Default::default() }"
1867)]
1868pub struct BevySpriteParams {
1869 #[serde(default)]
1871 #[to_code_literal(rename = "image", expr, optional)]
1872 pub image_expr: Option<String>,
1873 #[serde(default)]
1875 #[to_code_literal(rename = "color", optional, to_tokens = "into_expr_tokens")]
1876 pub color_expr: Option<String>,
1877 #[serde(default)]
1879 #[to_code_literal(optional)]
1880 pub flip_x: Option<bool>,
1881 #[serde(default)]
1883 #[to_code_literal(optional)]
1884 pub flip_y: Option<bool>,
1885 #[serde(default)]
1887 #[to_code_literal(rename = "custom_size", optional, to_tokens = "some_expr_tokens")]
1888 pub custom_size_expr: Option<String>,
1889}
1890
1891#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1892#[to_code_literal(
1893 path = "::bevy::text::TextFont",
1894 default_update,
1895 default_expr = "::bevy::text::TextFont::default()"
1896)]
1897struct BevyTextFontParams {
1898 #[serde(default)]
1900 #[to_code_literal(rename = "font", expr, optional)]
1901 font_handle_expr: Option<String>,
1902 #[serde(default)]
1904 #[to_code_literal(optional)]
1905 font_size: Option<f32>,
1906}
1907
1908#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1909#[to_code_literal(transparent)]
1910struct BevyTextColorParams {
1911 #[serde(default)]
1913 #[to_code_literal(to_tokens = "text_color_tokens")]
1914 color_expr: Option<String>,
1915}
1916
1917#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, Default, elicitation::ToCodeLiteral)]
1918#[to_code_literal(
1919 path = "::bevy::text::TextLayout",
1920 default_update,
1921 default_expr = "::bevy::text::TextLayout::default()"
1922)]
1923struct BevyTextLayoutParams {
1924 #[serde(default)]
1926 #[to_code_literal(rename = "justify", expr, optional)]
1927 justify_expr: Option<String>,
1928 #[serde(default)]
1930 #[to_code_literal(rename = "linebreak", expr, optional)]
1931 linebreak_expr: Option<String>,
1932}
1933
1934#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1936#[to_code_literal(raw_tuple)]
1937pub struct BevyTextStyleParams {
1938 #[serde(flatten)]
1940 font: BevyTextFontParams,
1941 #[serde(flatten)]
1943 color: BevyTextColorParams,
1944 #[serde(flatten)]
1946 layout: BevyTextLayoutParams,
1947}
1948
1949#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1951#[serde(rename_all = "snake_case")]
1952pub enum BevySsaoQualityVariant {
1953 Low,
1955 Medium,
1957 High,
1959 Ultra,
1961 Custom,
1963}
1964
1965#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1967#[serde(tag = "variant", rename_all = "snake_case")]
1968#[to_code_literal(path = "::bevy::pbr::ScreenSpaceAmbientOcclusionQualityLevel")]
1969pub enum BevySsaoQualityParams {
1970 Low,
1972 Medium,
1974 High,
1976 Ultra,
1978 Custom {
1980 slice_count: u32,
1982 samples_per_slice_side: u32,
1984 },
1985}
1986
1987#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
1989#[to_code_literal(path = "::bevy::pbr::ScreenSpaceAmbientOcclusion", default_update)]
1990pub struct BevySsaoParams {
1991 #[serde(default)]
1993 #[to_code_literal(optional, to_tokens = "emit_code_tokens")]
1994 pub quality_level: Option<BevySsaoQualityParams>,
1995 #[serde(default)]
1997 #[to_code_literal(optional)]
1998 pub constant_object_thickness: Option<f32>,
1999}
2000
2001#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
2003#[to_code_literal(path = "::bevy::anti_alias::taa::TemporalAntiAliasing", default_update)]
2004pub struct BevyTemporalAntiAliasingParams {
2005 #[serde(default)]
2007 #[to_code_literal(optional)]
2008 pub reset: Option<bool>,
2009}
2010
2011#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
2012#[to_code_literal(transparent)]
2013struct BevyCascadeShadowBoundsParams(
2014 #[to_code_literal(to_tokens = "cascade_bounds_tokens")] Vec<f32>,
2015);
2016
2017#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
2019#[to_code_literal(
2020 path = "::bevy::light::CascadeShadowConfig",
2021 default_update,
2022 default_expr = "::bevy::light::CascadeShadowConfig::default()"
2023)]
2024pub struct BevyCascadeShadowConfigParams {
2025 #[serde(
2027 default,
2028 deserialize_with = "deserialize_optional_cascade_bounds",
2029 skip_serializing_if = "Option::is_none"
2030 )]
2031 #[to_code_literal(optional)]
2032 bounds: Option<BevyCascadeShadowBoundsParams>,
2033 #[serde(default)]
2035 #[to_code_literal(optional)]
2036 pub overlap_proportion: Option<f32>,
2037 #[serde(default)]
2039 #[to_code_literal(optional)]
2040 pub minimum_distance: Option<f32>,
2041}
2042
2043#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, elicitation::ToCodeLiteral)]
2045#[to_code_literal(path = "::bevy::light::CascadeShadowConfigBuilder", default_update)]
2046pub struct BevyCascadeShadowConfigBuilderParams {
2047 #[serde(default)]
2049 #[to_code_literal(optional)]
2050 pub num_cascades: Option<usize>,
2051 #[serde(default)]
2053 #[to_code_literal(optional)]
2054 pub minimum_distance: Option<f32>,
2055 #[serde(default)]
2057 #[to_code_literal(optional)]
2058 pub maximum_distance: Option<f32>,
2059 #[serde(default)]
2061 #[to_code_literal(optional)]
2062 pub first_cascade_far_bound: Option<f32>,
2063 #[serde(default)]
2065 #[to_code_literal(optional)]
2066 pub overlap_proportion: Option<f32>,
2067}
2068
2069#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2071#[serde(rename_all = "snake_case")]
2072#[derive(Default)]
2073pub enum BevyFullscreenGraphKind {
2074 Core2d,
2076 #[default]
2078 Core3d,
2079}
2080
2081fn default_parallax_relief_max_steps() -> u32 {
2082 32
2083}
2084
2085fn default_render_alpha_mode_threshold() -> f32 {
2086 0.5
2087}
2088
2089fn default_camera_3d_depth_clear() -> f32 {
2090 0.0
2091}
2092
2093#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema)]
2095pub struct BevyAtmosphereParams {
2096 #[serde(default = "default_scattering_media_var")]
2098 pub scattering_media_var: String,
2099 #[serde(default)]
2101 pub atmosphere: Option<BevyAtmosphere>,
2102 #[serde(default)]
2104 pub medium_label: Option<String>,
2105 #[serde(default = "default_scattering_resolution")]
2107 pub falloff_resolution: u32,
2108 #[serde(default = "default_scattering_resolution")]
2110 pub phase_resolution: u32,
2111 #[serde(default)]
2113 pub terms: Vec<BevyScatteringTerm>,
2114 #[serde(default)]
2116 pub density_multiplier: Option<f32>,
2117}
2118
2119#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema)]
2121pub struct BevyFullscreenMaterialParams {
2122 pub material_type: String,
2124 pub shader_path: String,
2126 #[serde(default)]
2128 pub graph: BevyFullscreenGraphKind,
2129 #[serde(default)]
2131 pub start_node_expr: Option<String>,
2132 #[serde(default)]
2134 pub end_node_expr: Option<String>,
2135}
2136
2137fn default_commands_var() -> String {
2138 "commands".to_string()
2139}
2140
2141fn default_true() -> bool {
2142 true
2143}
2144
2145fn default_scattering_media_var() -> String {
2146 "scattering_media".to_string()
2147}
2148
2149fn default_scattering_resolution() -> u32 {
2150 256
2151}
2152
2153fn tool_err(msg: impl std::fmt::Display) -> ErrorData {
2154 ErrorData::invalid_params(msg.to_string(), None)
2155}
2156
2157fn ok_source(source: String) -> Result<CallToolResult, ErrorData> {
2158 Ok(CallToolResult::success(vec![Content::text(source)]))
2159}
2160
2161fn parse_expr(src: &str, context: &str) -> Result<syn::Expr, ErrorData> {
2162 syn::parse_str::<syn::Expr>(src)
2163 .map_err(|error| tool_err(format!("invalid {context} expression `{src}`: {error}")))
2164}
2165
2166fn parse_type(src: &str, context: &str) -> Result<syn::Type, ErrorData> {
2167 syn::parse_str::<syn::Type>(src)
2168 .map_err(|error| tool_err(format!("invalid {context} type `{src}`: {error}")))
2169}
2170
2171fn expr_tokens(src: &str, context: &str) -> syn::Expr {
2172 parse_expr(src, context).expect("validated expressions must parse")
2173}
2174
2175fn type_tokens(src: &str, context: &str) -> syn::Type {
2176 parse_type(src, context).expect("validated types must parse")
2177}
2178
2179fn uvec2_array_tokens(value: &[u32; 2]) -> TokenStream {
2180 let [x, y] = *value;
2181 quote! { ::bevy::math::UVec2::new(#x, #y) }
2182}
2183
2184fn viewport_depth_tokens(depth: &Option<[f32; 2]>) -> TokenStream {
2185 let [min, max] = depth.unwrap_or([0.0, 1.0]);
2186 quote! { #min..#max }
2187}
2188
2189fn uvec3_array_tokens(value: &[u32; 3]) -> TokenStream {
2190 let [x, y, z] = *value;
2191 quote! { ::bevy::math::UVec3::new(#x, #y, #z) }
2192}
2193
2194fn some_expr_tokens(value: &str) -> TokenStream {
2195 let expr = expr_tokens(value, "optional expression field");
2196 quote! { Some(#expr) }
2197}
2198
2199fn into_expr_tokens(value: &str) -> TokenStream {
2200 let expr = expr_tokens(value, "into expression field");
2201 quote! { (#expr).into() }
2202}
2203
2204fn text_color_tokens(value: &Option<String>) -> TokenStream {
2205 match value.as_deref() {
2206 Some(expr) => {
2207 let expr = expr_tokens(expr, "text color");
2208 quote! { ::bevy::text::TextColor((#expr).into()) }
2209 }
2210 None => quote! { ::bevy::text::TextColor::default() },
2211 }
2212}
2213
2214fn cascade_bounds_tokens(value: &[f32]) -> TokenStream {
2215 let bounds = value.iter().map(|bound| quote! { #bound });
2216 quote! { vec![#(#bounds),*] }
2217}
2218
2219fn deserialize_optional_cascade_bounds<'de, D>(
2220 deserializer: D,
2221) -> Result<Option<BevyCascadeShadowBoundsParams>, D::Error>
2222where
2223 D: Deserializer<'de>,
2224{
2225 let bounds = Option::<Vec<f32>>::deserialize(deserializer)?;
2226 Ok(bounds
2227 .filter(|values| !values.is_empty())
2228 .map(BevyCascadeShadowBoundsParams))
2229}
2230
2231fn emit_code_tokens<T: EmitCode>(value: &T) -> TokenStream {
2232 value.emit_code()
2233}
2234
2235fn bevy_dep() -> Vec<CrateDep> {
2236 vec![CrateDep::new("bevy", "0.18")]
2237}
2238
2239macro_rules! impl_bevy_literal_emit {
2240 ($($ty:ty),+ $(,)?) => {
2241 $(
2242 impl EmitCode for $ty {
2243 fn emit_code(&self) -> TokenStream {
2244 self.to_code_literal()
2245 }
2246
2247 fn crate_deps(&self) -> Vec<CrateDep> {
2248 bevy_dep()
2249 }
2250 }
2251 )+
2252 };
2253}
2254
2255fn validate_optional_expr(src: &Option<String>, context: &str) -> Result<(), ErrorData> {
2256 if let Some(src) = src {
2257 let _ = parse_expr(src, context)?;
2258 }
2259 Ok(())
2260}
2261
2262pub(crate) fn validate_render_target(params: &BevyRenderTargetParams) -> Result<(), ErrorData> {
2263 match params.fields.kind {
2264 BevyRenderTargetKind::PrimaryWindow => {
2265 if params.fields.target_expr.is_some() {
2266 return Err(tool_err(
2267 "primary_window render target does not accept target_expr",
2268 ));
2269 }
2270 }
2271 BevyRenderTargetKind::WindowEntity
2272 | BevyRenderTargetKind::Image
2273 | BevyRenderTargetKind::TextureView => {
2274 let target = params
2275 .fields
2276 .target_expr
2277 .as_deref()
2278 .ok_or_else(|| tool_err("render target kind requires target_expr"))?;
2279 let _ = parse_expr(target, "render target")?;
2280 }
2281 }
2282 Ok(())
2283}
2284
2285fn validate_order_independent_transparency_settings(
2286 params: &BevyOrderIndependentTransparencySettingsParams,
2287) -> Result<(), ErrorData> {
2288 if let Some(layer_count) = params.layer_count
2289 && layer_count <= 0
2290 {
2291 return Err(tool_err(
2292 "order independent transparency layer_count must be positive",
2293 ));
2294 }
2295 if let Some(alpha_threshold) = params.alpha_threshold {
2296 if !alpha_threshold.is_finite() {
2297 return Err(tool_err(
2298 "order independent transparency alpha_threshold must be finite",
2299 ));
2300 }
2301 if alpha_threshold < 0.0 {
2302 return Err(tool_err(
2303 "order independent transparency alpha_threshold must be non-negative",
2304 ));
2305 }
2306 }
2307 Ok(())
2308}
2309
2310fn validate_scaling_mode(params: &BevyScalingModeParams) -> Result<(), ErrorData> {
2311 match params {
2312 BevyScalingModeParams::WindowSize => {}
2313 BevyScalingModeParams::Fixed { width, height } => {
2314 validate_optional_non_negative_f32(Some(*width), "scaling mode width")?;
2315 validate_optional_non_negative_f32(Some(*height), "scaling mode height")?;
2316 }
2317 BevyScalingModeParams::AutoMin {
2318 min_width,
2319 min_height,
2320 } => {
2321 validate_optional_non_negative_f32(Some(*min_width), "scaling mode min_width")?;
2322 validate_optional_non_negative_f32(Some(*min_height), "scaling mode min_height")?;
2323 }
2324 BevyScalingModeParams::AutoMax {
2325 max_width,
2326 max_height,
2327 } => {
2328 validate_optional_non_negative_f32(Some(*max_width), "scaling mode max_width")?;
2329 validate_optional_non_negative_f32(Some(*max_height), "scaling mode max_height")?;
2330 }
2331 BevyScalingModeParams::FixedVertical { viewport_height } => {
2332 validate_optional_non_negative_f32(
2333 Some(*viewport_height),
2334 "scaling mode viewport_height",
2335 )?;
2336 }
2337 BevyScalingModeParams::FixedHorizontal { viewport_width } => {
2338 validate_optional_non_negative_f32(
2339 Some(*viewport_width),
2340 "scaling mode viewport_width",
2341 )?;
2342 }
2343 }
2344 Ok(())
2345}
2346
2347pub(crate) fn validate_perspective_projection(
2348 params: &BevyPerspectiveProjectionParams,
2349) -> Result<(), ErrorData> {
2350 validate_optional_expr(¶ms.near_clip_plane_expr, "near clip plane")?;
2351 validate_optional_non_negative_f32(params.fov, "perspective fov")?;
2352 validate_optional_non_negative_f32(params.aspect_ratio, "perspective aspect_ratio")?;
2353 validate_optional_non_negative_f32(params.near, "perspective near")?;
2354 validate_optional_non_negative_f32(params.far, "perspective far")?;
2355 Ok(())
2356}
2357
2358pub(crate) fn validate_orthographic_projection(
2359 params: &BevyOrthographicProjectionParams,
2360) -> Result<(), ErrorData> {
2361 validate_optional_expr(¶ms.fields.viewport_origin_expr, "viewport origin")?;
2362 validate_optional_expr(¶ms.fields.scaling_mode_expr, "scaling mode")?;
2363 validate_optional_expr(¶ms.fields.area_expr, "orthographic area")?;
2364 validate_optional_finite_f32(params.fields.near, "orthographic near")?;
2365 validate_optional_finite_f32(params.fields.far, "orthographic far")?;
2366 validate_optional_non_negative_f32(params.fields.scale, "orthographic scale")?;
2367 Ok(())
2368}
2369
2370fn validate_clear_color_config(params: &BevyClearColorConfigParams) -> Result<(), ErrorData> {
2371 match params {
2372 BevyClearColorConfigParams::Default | BevyClearColorConfigParams::None => {}
2373 BevyClearColorConfigParams::Custom(color_expr) => {
2374 let _ = parse_expr(color_expr, "clear color")?;
2375 }
2376 }
2377 Ok(())
2378}
2379
2380fn validate_exposure(params: &BevyExposureParams) -> Result<(), ErrorData> {
2381 if params.fields.preset.is_some() && params.fields.ev100.is_some() {
2382 return Err(tool_err(
2383 "exposure accepts either preset or ev100, but not both",
2384 ));
2385 }
2386 validate_optional_finite_f32(params.fields.ev100, "exposure ev100")
2387}
2388
2389fn validate_clear_color(params: &BevyClearColorParams) -> Result<(), ErrorData> {
2390 validate_optional_expr(¶ms.color_expr, "clear color")
2391}
2392
2393fn validate_camera_3d_depth_load_op(
2394 params: &BevyCamera3dDepthLoadOpParams,
2395) -> Result<(), ErrorData> {
2396 match params {
2397 BevyCamera3dDepthLoadOpParams::Clear { depth } => {
2398 validate_optional_finite_f32(Some(*depth), "camera 3d depth clear value")
2399 }
2400 BevyCamera3dDepthLoadOpParams::Load => Ok(()),
2401 }
2402}
2403
2404fn validate_screen_space_transmission_quality(
2405 _params: &BevyScreenSpaceTransmissionQualityParams,
2406) -> Result<(), ErrorData> {
2407 Ok(())
2408}
2409
2410fn validate_main_pass_resolution_override(
2411 params: &BevyMainPassResolutionOverrideParams,
2412) -> Result<(), ErrorData> {
2413 if params.fields.width == 0 || params.fields.height == 0 {
2414 return Err(tool_err(
2415 "main_pass_resolution_override width and height must be positive",
2416 ));
2417 }
2418 Ok(())
2419}
2420
2421fn validate_sub_camera_view(params: &BevySubCameraViewParams) -> Result<(), ErrorData> {
2422 if params.fields.full_width == 0 || params.fields.full_height == 0 {
2423 return Err(tool_err("sub_camera_view full size must be positive"));
2424 }
2425 if params.fields.width == 0 || params.fields.height == 0 {
2426 return Err(tool_err("sub_camera_view size must be positive"));
2427 }
2428 if !params.fields.offset_x.is_finite() || !params.fields.offset_y.is_finite() {
2429 return Err(tool_err("sub_camera_view offsets must be finite"));
2430 }
2431 Ok(())
2432}
2433
2434fn validate_visibility_range(params: &BevyVisibilityRangeParams) -> Result<(), ErrorData> {
2435 for (value, context) in [
2436 (
2437 params.fields.start_margin_start,
2438 "visibility_range start_margin_start",
2439 ),
2440 (
2441 params.fields.start_margin_end,
2442 "visibility_range start_margin_end",
2443 ),
2444 (
2445 params.fields.end_margin_start,
2446 "visibility_range end_margin_start",
2447 ),
2448 (
2449 params.fields.end_margin_end,
2450 "visibility_range end_margin_end",
2451 ),
2452 ] {
2453 if !value.is_finite() {
2454 return Err(tool_err(format!("{context} must be finite")));
2455 }
2456 if value < 0.0 {
2457 return Err(tool_err(format!("{context} must be non-negative")));
2458 }
2459 }
2460 if params.fields.start_margin_start > params.fields.start_margin_end {
2461 return Err(tool_err(
2462 "visibility_range start_margin_start must be <= start_margin_end",
2463 ));
2464 }
2465 if params.fields.end_margin_start > params.fields.end_margin_end {
2466 return Err(tool_err(
2467 "visibility_range end_margin_start must be <= end_margin_end",
2468 ));
2469 }
2470 if params.fields.start_margin_end > params.fields.end_margin_start {
2471 return Err(tool_err(
2472 "visibility_range start_margin_end must be <= end_margin_start",
2473 ));
2474 }
2475 Ok(())
2476}
2477
2478fn render_target_tokens(params: &BevyRenderTargetFields) -> TokenStream {
2479 match params.kind {
2480 BevyRenderTargetKind::PrimaryWindow => {
2481 quote! {
2482 ::bevy::camera::RenderTarget::Window(::bevy::window::WindowRef::Primary)
2483 }
2484 }
2485 BevyRenderTargetKind::WindowEntity => {
2486 let target = expr_tokens(
2487 params
2488 .target_expr
2489 .as_deref()
2490 .expect("validated render target must have target expr"),
2491 "window entity",
2492 );
2493 quote! {
2494 ::bevy::camera::RenderTarget::Window(::bevy::window::WindowRef::Entity(#target))
2495 }
2496 }
2497 BevyRenderTargetKind::Image => {
2498 let target = expr_tokens(
2499 params
2500 .target_expr
2501 .as_deref()
2502 .expect("validated render target must have target expr"),
2503 "image target",
2504 );
2505 quote! { ::bevy::camera::RenderTarget::Image((#target).into()) }
2506 }
2507 BevyRenderTargetKind::TextureView => {
2508 let target = expr_tokens(
2509 params
2510 .target_expr
2511 .as_deref()
2512 .expect("validated render target must have target expr"),
2513 "texture-view target",
2514 );
2515 quote! { ::bevy::camera::RenderTarget::TextureView(#target) }
2516 }
2517 }
2518}
2519
2520fn orthographic_projection_tokens(params: &BevyOrthographicProjectionFields) -> TokenStream {
2521 let constructor = if params.use_2d_defaults.unwrap_or(false) {
2522 quote! { ::bevy::camera::OrthographicProjection::default_2d() }
2523 } else {
2524 quote! { ::bevy::camera::OrthographicProjection::default_3d() }
2525 };
2526 if params.near.is_none()
2527 && params.far.is_none()
2528 && params.viewport_origin_expr.is_none()
2529 && params.scaling_mode_expr.is_none()
2530 && params.scale.is_none()
2531 && params.area_expr.is_none()
2532 {
2533 constructor
2534 } else {
2535 let near = params
2536 .near
2537 .map(|value| quote! { near: #value, })
2538 .unwrap_or_default();
2539 let far = params
2540 .far
2541 .map(|value| quote! { far: #value, })
2542 .unwrap_or_default();
2543 let viewport_origin = params
2544 .viewport_origin_expr
2545 .as_deref()
2546 .map(|expr| {
2547 let expr = expr_tokens(expr, "viewport origin");
2548 quote! { viewport_origin: #expr, }
2549 })
2550 .unwrap_or_default();
2551 let scaling_mode = params
2552 .scaling_mode_expr
2553 .as_deref()
2554 .map(|expr| {
2555 let expr = expr_tokens(expr, "scaling mode");
2556 quote! { scaling_mode: #expr, }
2557 })
2558 .unwrap_or_default();
2559 let scale = params
2560 .scale
2561 .map(|value| quote! { scale: #value, })
2562 .unwrap_or_default();
2563 let area = params
2564 .area_expr
2565 .as_deref()
2566 .map(|expr| {
2567 let expr = expr_tokens(expr, "orthographic area");
2568 quote! { area: #expr, }
2569 })
2570 .unwrap_or_default();
2571 quote! {
2572 ::bevy::camera::OrthographicProjection {
2573 #near
2574 #far
2575 #viewport_origin
2576 #scaling_mode
2577 #scale
2578 #area
2579 ..#constructor
2580 }
2581 }
2582 }
2583}
2584
2585impl_bevy_literal_emit!(
2586 BevyRenderTargetParams,
2587 BevyTonemappingParams,
2588 BevyDebandDitherParams,
2589 BevyOrderIndependentTransparencySettingsParams,
2590 BevyScalingModeParams,
2591 BevyPerspectiveProjectionParams,
2592 BevyClearColorConfigParams,
2593 BevyExposureParams,
2594 BevyClearColorParams,
2595 BevyMsaaWritebackParams,
2596 BevyCamera3dDepthLoadOpParams,
2597 BevyScreenSpaceTransmissionQualityParams,
2598 BevyMainPassResolutionOverrideParams,
2599 BevySubCameraViewParams,
2600 BevyNoCpuCullingParams,
2601 BevyNoFrustumCullingParams,
2602 BevyVisibilityRangeParams,
2603 BevyColorParams,
2604 BevyRenderAlphaModeParams,
2605 BevyUvChannelParams,
2606 BevyOpaqueRendererMethodParams,
2607 BevyDefaultOpaqueRendererMethodParams,
2608 BevyDepthPrepassParams,
2609 BevyNormalPrepassParams,
2610 BevyMotionVectorPrepassParams,
2611 BevyDeferredPrepassParams,
2612 BevyDepthPrepassDoubleBufferParams,
2613 BevyDeferredPrepassDoubleBufferParams,
2614 BevyAmbientLightParams,
2615 BevyDirectionalLightParams,
2616 BevyGlobalAmbientLightParams,
2617 BevyPointLightParams,
2618 BevySpotLightParams,
2619 BevyDirectionalLightShadowMapParams,
2620 BevyPointLightShadowMapParams,
2621 BevyEnvironmentMapLightParams,
2622 BevyGeneratedEnvironmentMapLightParams,
2623 BevyAtmosphereEnvironmentMapLightParams,
2624 BevyVolumetricLightParams,
2625 BevyVolumetricFogParams,
2626 BevyLightProbeParams,
2627 BevyIrradianceVolumeParams,
2628 BevySunDiskParams,
2629 BevyWireframeColorParams,
2630 BevyWireframeConfigParams,
2631 BevyWireframe2dColorParams,
2632 BevyWireframe2dConfigParams,
2633 BevyNotShadowCasterParams,
2634 BevyNotShadowReceiverParams,
2635 BevyTransmittedShadowReceiverParams,
2636 BevyShadowFilteringMethodParams,
2637 BevyClusterFarZModeParams,
2638 BevyScreenSpaceReflectionsParams,
2639 BevyViewportParams,
2640 BevyBloomCompositeModeParams,
2641 BevyTemporalAntiAliasingParams,
2642 BevyCascadeShadowConfigBuilderParams,
2643 BevyParallaxMappingMethodParams,
2644 BevyLightmapParams,
2645 BevyColorMaterialParams,
2646 BevySkyboxParams,
2647 BevyFogVolumeParams,
2648 BevyFogSettingsParams,
2649 BevySsaoQualityParams,
2650 BevySsaoParams,
2651 BevyClusterZConfigParams,
2652 BevyClusterConfigParams,
2653 BevyAlphaMode2dParams,
2654 BevyMesh3dParams,
2655 BevyMesh2dParams,
2656 BevyMeshMaterial3dParams,
2657 BevyMeshMaterial2dParams,
2658 BevyClusteredDecalParams,
2659 BevyMesh3dWireframeParams,
2660 BevyMesh2dWireframeParams,
2661 BevyWireframeParams,
2662 BevyNoWireframeParams,
2663 BevyWireframe2dParams,
2664 BevyNoWireframe2dParams,
2665 BevySpriteParams,
2666 BevyTextStyleParams,
2667 BevyCascadeShadowConfigParams,
2668 BevyOrthographicProjectionParams,
2669 BevyStandardMaterialParams,
2670);
2671
2672fn emit_uv_channel_variant_tokens(variant: &BevyUvChannelVariant) -> TokenStream {
2673 let variant = match variant {
2674 BevyUvChannelVariant::Uv0 => quote! { Uv0 },
2675 BevyUvChannelVariant::Uv1 => quote! { Uv1 },
2676 };
2677 quote! { ::bevy::pbr::UvChannel::#variant }
2678}
2679
2680fn default_opaque_renderer_method_tokens(
2681 variant: &BevyDefaultOpaqueRendererMethodVariant,
2682) -> TokenStream {
2683 match variant {
2684 BevyDefaultOpaqueRendererMethodVariant::Default => {
2685 quote! { ::bevy::pbr::DefaultOpaqueRendererMethod::default() }
2686 }
2687 BevyDefaultOpaqueRendererMethodVariant::Forward => {
2688 quote! { ::bevy::pbr::DefaultOpaqueRendererMethod::forward() }
2689 }
2690 BevyDefaultOpaqueRendererMethodVariant::Deferred => {
2691 quote! { ::bevy::pbr::DefaultOpaqueRendererMethod::deferred() }
2692 }
2693 }
2694}
2695
2696fn exposure_tokens(fields: &BevyExposureFields) -> TokenStream {
2697 match (fields.preset, fields.ev100) {
2698 (Some(BevyExposurePreset::Sunlight), None) => {
2699 quote! { ::bevy::camera::Exposure::SUNLIGHT }
2700 }
2701 (Some(BevyExposurePreset::Overcast), None) => {
2702 quote! { ::bevy::camera::Exposure::OVERCAST }
2703 }
2704 (Some(BevyExposurePreset::Indoor), None) => {
2705 quote! { ::bevy::camera::Exposure::INDOOR }
2706 }
2707 (Some(BevyExposurePreset::Blender), None) => {
2708 quote! { ::bevy::camera::Exposure::BLENDER }
2709 }
2710 (None, Some(ev100)) => quote! { ::bevy::camera::Exposure { ev100: #ev100 } },
2711 (None, None) => quote! { ::bevy::camera::Exposure::default() },
2712 (Some(_), Some(_)) => unreachable!("validated exposure params"),
2713 }
2714}
2715
2716fn clear_color_tokens(color_expr: &Option<String>) -> TokenStream {
2717 match color_expr.as_deref() {
2718 Some(expr) => {
2719 let expr = expr_tokens(expr, "clear color");
2720 quote! { ::bevy::camera::ClearColor(#expr) }
2721 }
2722 None => quote! { ::bevy::camera::ClearColor::default() },
2723 }
2724}
2725
2726fn main_pass_resolution_override_tokens(
2727 fields: &BevyMainPassResolutionOverrideFields,
2728) -> TokenStream {
2729 let width = fields.width;
2730 let height = fields.height;
2731 quote! {
2732 ::bevy::camera::MainPassResolutionOverride(::bevy::math::UVec2::new(#width, #height))
2733 }
2734}
2735
2736fn sub_camera_view_tokens(fields: &BevySubCameraViewFields) -> TokenStream {
2737 let full_width = fields.full_width;
2738 let full_height = fields.full_height;
2739 let offset_x = fields.offset_x;
2740 let offset_y = fields.offset_y;
2741 let width = fields.width;
2742 let height = fields.height;
2743 quote! {
2744 ::bevy::camera::SubCameraView {
2745 full_size: ::bevy::math::UVec2::new(#full_width, #full_height),
2746 offset: ::bevy::math::Vec2::new(#offset_x, #offset_y),
2747 size: ::bevy::math::UVec2::new(#width, #height),
2748 }
2749 }
2750}
2751
2752fn visibility_range_tokens(fields: &BevyVisibilityRangeFields) -> TokenStream {
2753 let start_margin_start = fields.start_margin_start;
2754 let start_margin_end = fields.start_margin_end;
2755 let end_margin_start = fields.end_margin_start;
2756 let end_margin_end = fields.end_margin_end;
2757 let use_aabb = fields.use_aabb.unwrap_or(false);
2758 quote! {
2759 ::bevy::camera::visibility::VisibilityRange {
2760 start_margin: #start_margin_start..#start_margin_end,
2761 end_margin: #end_margin_start..#end_margin_end,
2762 use_aabb: #use_aabb,
2763 }
2764 }
2765}
2766
2767impl EmitCode for BevyCamera3dParams {
2768 fn emit_code(&self) -> TokenStream {
2769 let commands = expr_tokens(&self.commands_var, "commands receiver");
2770 let transform = self
2771 .transform_expr
2772 .as_deref()
2773 .map(|expr| {
2774 let expr = expr_tokens(expr, "transform");
2775 quote! { #expr, }
2776 })
2777 .unwrap_or_default();
2778 let hdr = self
2779 .hdr
2780 .map(|value| quote! { ::bevy::camera::Camera { hdr: #value, ..::std::default::Default::default() }, })
2781 .unwrap_or_default();
2782 let render_target = self
2783 .render_target
2784 .as_ref()
2785 .map(|target| {
2786 let target = target.emit_code();
2787 quote! { #target, }
2788 })
2789 .unwrap_or_else(|| {
2790 quote! {
2791 ::bevy::camera::RenderTarget::Window(::bevy::window::WindowRef::Primary),
2792 }
2793 });
2794 let tonemapping = self
2795 .tonemapping_expr
2796 .as_deref()
2797 .map(|expr| {
2798 let expr = expr_tokens(expr, "tonemapping");
2799 quote! { #expr, }
2800 })
2801 .unwrap_or_default();
2802 let projection = if self.fov.is_none() && self.near.is_none() && self.far.is_none() {
2803 quote! { ::bevy::camera::PerspectiveProjection::default() }
2804 } else {
2805 let fov = self
2806 .fov
2807 .map(|value| quote! { fov: #value, })
2808 .unwrap_or_default();
2809 let near = self
2810 .near
2811 .map(|value| quote! { near: #value, })
2812 .unwrap_or_default();
2813 let far = self
2814 .far
2815 .map(|value| quote! { far: #value, })
2816 .unwrap_or_default();
2817 quote! {
2818 ::bevy::camera::PerspectiveProjection {
2819 #fov
2820 #near
2821 #far
2822 ..::bevy::camera::PerspectiveProjection::default()
2823 }
2824 }
2825 };
2826 quote! {
2827 #commands.spawn((
2828 ::bevy::camera::Camera3d::default(),
2829 ::bevy::camera::Projection::Perspective(#projection),
2830 #render_target
2831 #tonemapping
2832 #hdr
2833 #transform
2834 ))
2835 }
2836 }
2837
2838 fn crate_deps(&self) -> Vec<CrateDep> {
2839 bevy_dep()
2840 }
2841}
2842
2843impl EmitCode for BevyCamera2dParams {
2844 fn emit_code(&self) -> TokenStream {
2845 let commands = expr_tokens(&self.commands_var, "commands receiver");
2846 let transform = self
2847 .transform_expr
2848 .as_deref()
2849 .map(|expr| {
2850 let expr = expr_tokens(expr, "transform");
2851 quote! { #expr, }
2852 })
2853 .unwrap_or_default();
2854 let hdr = self
2855 .hdr
2856 .map(|value| quote! { ::bevy::camera::Camera { hdr: #value, ..::std::default::Default::default() }, })
2857 .unwrap_or_default();
2858 let render_target = self
2859 .render_target
2860 .as_ref()
2861 .map(|target| {
2862 let target = target.emit_code();
2863 quote! { #target, }
2864 })
2865 .unwrap_or_else(|| {
2866 quote! {
2867 ::bevy::camera::RenderTarget::Window(::bevy::window::WindowRef::Primary),
2868 }
2869 });
2870 let tonemapping = self
2871 .tonemapping_expr
2872 .as_deref()
2873 .map(|expr| {
2874 let expr = expr_tokens(expr, "tonemapping");
2875 quote! { #expr, }
2876 })
2877 .unwrap_or_default();
2878 let projection = if self.near.is_none() && self.far.is_none() && self.scale.is_none() {
2879 quote! { ::bevy::camera::OrthographicProjection::default_2d() }
2880 } else {
2881 let near = self
2882 .near
2883 .map(|value| quote! { near: #value, })
2884 .unwrap_or_default();
2885 let far = self
2886 .far
2887 .map(|value| quote! { far: #value, })
2888 .unwrap_or_default();
2889 let scale = self
2890 .scale
2891 .map(|value| quote! { scale: #value, })
2892 .unwrap_or_default();
2893 quote! {
2894 ::bevy::camera::OrthographicProjection {
2895 #near
2896 #far
2897 #scale
2898 ..::bevy::camera::OrthographicProjection::default_2d()
2899 }
2900 }
2901 };
2902 quote! {
2903 #commands.spawn((
2904 ::bevy::camera::Camera2d::default(),
2905 ::bevy::camera::Projection::Orthographic(#projection),
2906 #render_target
2907 #tonemapping
2908 #hdr
2909 #transform
2910 ))
2911 }
2912 }
2913
2914 fn crate_deps(&self) -> Vec<CrateDep> {
2915 bevy_dep()
2916 }
2917}
2918
2919impl EmitCode for BevyBloomSettingsParams {
2920 fn emit_code(&self) -> TokenStream {
2921 let preset = match self.preset {
2922 Some(BevyBloomPreset::Natural) => {
2923 quote! { ::bevy::post_process::bloom::Bloom::NATURAL }
2924 }
2925 Some(BevyBloomPreset::Anamorphic) => {
2926 quote! { ::bevy::post_process::bloom::Bloom::ANAMORPHIC }
2927 }
2928 Some(BevyBloomPreset::OldSchool) => {
2929 quote! { ::bevy::post_process::bloom::Bloom::OLD_SCHOOL }
2930 }
2931 Some(BevyBloomPreset::ScreenBlur) => {
2932 quote! { ::bevy::post_process::bloom::Bloom::SCREEN_BLUR }
2933 }
2934 None => quote! { ::bevy::post_process::bloom::Bloom::default() },
2935 };
2936 if self.intensity.is_none()
2937 && self.low_frequency_boost.is_none()
2938 && self.low_frequency_boost_curvature.is_none()
2939 && self.high_pass_frequency.is_none()
2940 && self.prefilter_threshold.is_none()
2941 && self.prefilter_threshold_softness.is_none()
2942 && self.composite_mode.is_none()
2943 && self.max_mip_dimension.is_none()
2944 && self.scale_expr.is_none()
2945 {
2946 preset
2947 } else {
2948 let intensity = self
2949 .intensity
2950 .map(|value| quote! { intensity: #value, })
2951 .unwrap_or_default();
2952 let low_frequency_boost = self
2953 .low_frequency_boost
2954 .map(|value| quote! { low_frequency_boost: #value, })
2955 .unwrap_or_default();
2956 let low_frequency_boost_curvature = self
2957 .low_frequency_boost_curvature
2958 .map(|value| quote! { low_frequency_boost_curvature: #value, })
2959 .unwrap_or_default();
2960 let high_pass_frequency = self
2961 .high_pass_frequency
2962 .map(|value| quote! { high_pass_frequency: #value, })
2963 .unwrap_or_default();
2964 let prefilter = if self.prefilter_threshold.is_none()
2965 && self.prefilter_threshold_softness.is_none()
2966 {
2967 TokenStream::new()
2968 } else {
2969 let threshold = self
2970 .prefilter_threshold
2971 .map(|value| quote! { threshold: #value, })
2972 .unwrap_or_default();
2973 let threshold_softness = self
2974 .prefilter_threshold_softness
2975 .map(|value| quote! { threshold_softness: #value, })
2976 .unwrap_or_default();
2977 quote! {
2978 prefilter: ::bevy::post_process::bloom::BloomPrefilter {
2979 #threshold
2980 #threshold_softness
2981 ..(#preset).prefilter
2982 },
2983 }
2984 };
2985 let composite_mode = self
2986 .composite_mode
2987 .map(|variant| {
2988 let variant = emit_bloom_composite_mode_tokens(variant);
2989 quote! { composite_mode: #variant, }
2990 })
2991 .unwrap_or_default();
2992 let max_mip_dimension = self
2993 .max_mip_dimension
2994 .map(|value| quote! { max_mip_dimension: #value, })
2995 .unwrap_or_default();
2996 let scale = self
2997 .scale_expr
2998 .as_deref()
2999 .map(|expr| {
3000 let expr = expr_tokens(expr, "bloom scale");
3001 quote! { scale: #expr, }
3002 })
3003 .unwrap_or_default();
3004 quote! {
3005 ::bevy::post_process::bloom::Bloom {
3006 #intensity
3007 #low_frequency_boost
3008 #low_frequency_boost_curvature
3009 #high_pass_frequency
3010 #prefilter
3011 #composite_mode
3012 #max_mip_dimension
3013 #scale
3014 ..#preset
3015 }
3016 }
3017 }
3018 }
3019
3020 fn crate_deps(&self) -> Vec<CrateDep> {
3021 bevy_dep()
3022 }
3023}
3024
3025fn emit_bloom_composite_mode_tokens(variant: BevyBloomCompositeModeVariant) -> TokenStream {
3026 match variant {
3027 BevyBloomCompositeModeVariant::EnergyConserving => {
3028 quote! { ::bevy::post_process::bloom::BloomCompositeMode::EnergyConserving }
3029 }
3030 BevyBloomCompositeModeVariant::Additive => {
3031 quote! { ::bevy::post_process::bloom::BloomCompositeMode::Additive }
3032 }
3033 }
3034}
3035
3036fn emit_falloff_tokens(falloff: &BevyFalloff) -> TokenStream {
3037 match falloff {
3038 BevyFalloff::Linear => quote! { ::bevy::pbr::Falloff::Linear },
3039 BevyFalloff::Exponential { scale } => {
3040 quote! { ::bevy::pbr::Falloff::Exponential { scale: #scale } }
3041 }
3042 BevyFalloff::Tent { center, width } => {
3043 quote! { ::bevy::pbr::Falloff::Tent { center: #center, width: #width } }
3044 }
3045 }
3046}
3047
3048fn emit_phase_tokens(phase: &BevyPhaseFunction) -> TokenStream {
3049 match phase {
3050 BevyPhaseFunction::Isotropic => quote! { ::bevy::pbr::PhaseFunction::Isotropic },
3051 BevyPhaseFunction::Rayleigh => quote! { ::bevy::pbr::PhaseFunction::Rayleigh },
3052 BevyPhaseFunction::Mie { asymmetry } => {
3053 quote! { ::bevy::pbr::PhaseFunction::Mie { asymmetry: #asymmetry } }
3054 }
3055 }
3056}
3057
3058fn emit_scattering_term_tokens(term: &BevyScatteringTerm) -> TokenStream {
3059 let absorption = term.absorption.to_code_literal();
3060 let scattering = term.scattering.to_code_literal();
3061 let falloff = emit_falloff_tokens(&term.falloff);
3062 let phase = emit_phase_tokens(&term.phase);
3063 quote! {
3064 ::bevy::pbr::ScatteringTerm {
3065 absorption: #absorption,
3066 scattering: #scattering,
3067 falloff: #falloff,
3068 phase: #phase,
3069 }
3070 }
3071}
3072
3073fn emit_atmosphere_component_tokens(atmosphere: &BevyAtmosphere) -> TokenStream {
3074 let bottom_radius = atmosphere.bottom_radius;
3075 let top_radius = atmosphere.top_radius;
3076 let ground_albedo = atmosphere.ground_albedo.to_code_literal();
3077 quote! {
3078 ::bevy::pbr::Atmosphere {
3079 bottom_radius: #bottom_radius,
3080 top_radius: #top_radius,
3081 ground_albedo: #ground_albedo,
3082 medium,
3083 }
3084 }
3085}
3086
3087fn default_fullscreen_edge_tokens(graph: BevyFullscreenGraphKind) -> (TokenStream, TokenStream) {
3088 match graph {
3089 BevyFullscreenGraphKind::Core2d => (
3090 quote! { ::bevy::core_pipeline::core_2d::graph::Node2d::Tonemapping },
3091 quote! { ::bevy::core_pipeline::core_2d::graph::Node2d::EndMainPassPostProcessing },
3092 ),
3093 BevyFullscreenGraphKind::Core3d => (
3094 quote! { ::bevy::core_pipeline::core_3d::graph::Node3d::Tonemapping },
3095 quote! { ::bevy::core_pipeline::core_3d::graph::Node3d::EndMainPassPostProcessing },
3096 ),
3097 }
3098}
3099
3100impl EmitCode for BevyAtmosphereParams {
3101 fn emit_code(&self) -> TokenStream {
3102 let scattering_media = expr_tokens(&self.scattering_media_var, "scattering media");
3103 let falloff_resolution = self.falloff_resolution;
3104 let phase_resolution = self.phase_resolution;
3105 let terms = self
3106 .terms
3107 .iter()
3108 .map(emit_scattering_term_tokens)
3109 .collect::<Vec<_>>();
3110 let medium_base = if terms.is_empty() {
3111 quote! {
3112 ::bevy::pbr::ScatteringMedium::earthlike(#falloff_resolution, #phase_resolution)
3113 }
3114 } else {
3115 quote! {
3116 ::bevy::pbr::ScatteringMedium::new(
3117 #falloff_resolution,
3118 #phase_resolution,
3119 [#(#terms),*],
3120 )
3121 }
3122 };
3123 let medium_base = if let Some(label) = &self.medium_label {
3124 let label = syn::LitStr::new(label, proc_macro2::Span::call_site());
3125 quote! { (#medium_base).with_label(#label) }
3126 } else {
3127 medium_base
3128 };
3129 let medium_base = if let Some(multiplier) = self.density_multiplier {
3130 quote! { (#medium_base).with_density_multiplier(#multiplier) }
3131 } else {
3132 medium_base
3133 };
3134 let atmosphere = self
3135 .atmosphere
3136 .as_ref()
3137 .map(emit_atmosphere_component_tokens)
3138 .unwrap_or_else(|| quote! { ::bevy::pbr::Atmosphere::earthlike(medium) });
3139 quote! {{
3140 let medium = (#scattering_media).add(#medium_base);
3141 #atmosphere
3142 }}
3143 }
3144
3145 fn crate_deps(&self) -> Vec<CrateDep> {
3146 bevy_dep()
3147 }
3148}
3149
3150impl EmitCode for BevyFullscreenMaterialParams {
3151 fn emit_code(&self) -> TokenStream {
3152 let material_type = type_tokens(&self.material_type, "fullscreen material");
3153 let shader_path = syn::LitStr::new(&self.shader_path, proc_macro2::Span::call_site());
3154 let (default_start, default_end) = default_fullscreen_edge_tokens(self.graph);
3155 let start = self
3156 .start_node_expr
3157 .as_deref()
3158 .map(|expr| {
3159 let expr = expr_tokens(expr, "fullscreen start node");
3160 quote! { #expr }
3161 })
3162 .unwrap_or(default_start);
3163 let end = self
3164 .end_node_expr
3165 .as_deref()
3166 .map(|expr| {
3167 let expr = expr_tokens(expr, "fullscreen end node");
3168 quote! { #expr }
3169 })
3170 .unwrap_or(default_end);
3171 quote! {
3172 impl ::bevy::core_pipeline::fullscreen_material::FullscreenMaterial for #material_type {
3173 fn fragment_shader() -> ::bevy::shader::ShaderRef {
3174 #shader_path.into()
3175 }
3176
3177 fn node_edges() -> ::std::vec::Vec<::bevy::render::render_graph::InternedRenderLabel> {
3178 use ::bevy::render::render_graph::RenderLabel as _;
3179
3180 vec![
3181 (#start).intern(),
3182 Self::node_label().intern(),
3183 (#end).intern(),
3184 ]
3185 }
3186 }
3187 }
3188 }
3189
3190 fn crate_deps(&self) -> Vec<CrateDep> {
3191 bevy_dep()
3192 }
3193}
3194
3195elicitation::register_emit!("render_target", BevyRenderTargetParams);
3196elicitation::register_emit!("tonemapping", BevyTonemappingParams);
3197elicitation::register_emit!("deband_dither", BevyDebandDitherParams);
3198elicitation::register_emit!(
3199 "order_independent_transparency_settings",
3200 BevyOrderIndependentTransparencySettingsParams
3201);
3202elicitation::register_emit!("scaling_mode", BevyScalingModeParams);
3203elicitation::register_emit!("perspective_projection", BevyPerspectiveProjectionParams);
3204elicitation::register_emit!("orthographic_projection", BevyOrthographicProjectionParams);
3205elicitation::register_emit!("clear_color_config", BevyClearColorConfigParams);
3206elicitation::register_emit!("msaa_writeback", BevyMsaaWritebackParams);
3207elicitation::register_emit!("exposure", BevyExposureParams);
3208elicitation::register_emit!("clear_color", BevyClearColorParams);
3209elicitation::register_emit!("camera_3d_depth_load_op", BevyCamera3dDepthLoadOpParams);
3210elicitation::register_emit!(
3211 "screen_space_transmission_quality",
3212 BevyScreenSpaceTransmissionQualityParams
3213);
3214elicitation::register_emit!(
3215 "main_pass_resolution_override",
3216 BevyMainPassResolutionOverrideParams
3217);
3218elicitation::register_emit!("sub_camera_view", BevySubCameraViewParams);
3219elicitation::register_emit!("no_cpu_culling", BevyNoCpuCullingParams);
3220elicitation::register_emit!("no_frustum_culling", BevyNoFrustumCullingParams);
3221elicitation::register_emit!("visibility_range", BevyVisibilityRangeParams);
3222elicitation::register_emit!("color", BevyColorParams);
3223elicitation::register_emit!("alpha_mode", BevyRenderAlphaModeParams);
3224elicitation::register_emit!("uv_channel", BevyUvChannelParams);
3225elicitation::register_emit!("parallax_mapping_method", BevyParallaxMappingMethodParams);
3226elicitation::register_emit!("opaque_renderer_method", BevyOpaqueRendererMethodParams);
3227elicitation::register_emit!(
3228 "default_opaque_renderer_method",
3229 BevyDefaultOpaqueRendererMethodParams
3230);
3231elicitation::register_emit!("alpha_mode_2d", BevyAlphaMode2dParams);
3232elicitation::register_emit!("standard_material", BevyStandardMaterialParams);
3233elicitation::register_emit!("lightmap", BevyLightmapParams);
3234elicitation::register_emit!("color_material", BevyColorMaterialParams);
3235elicitation::register_emit!("skybox", BevySkyboxParams);
3236elicitation::register_emit!("depth_prepass", BevyDepthPrepassParams);
3237elicitation::register_emit!("normal_prepass", BevyNormalPrepassParams);
3238elicitation::register_emit!("motion_vector_prepass", BevyMotionVectorPrepassParams);
3239elicitation::register_emit!("deferred_prepass", BevyDeferredPrepassParams);
3240elicitation::register_emit!(
3241 "depth_prepass_double_buffer",
3242 BevyDepthPrepassDoubleBufferParams
3243);
3244elicitation::register_emit!(
3245 "deferred_prepass_double_buffer",
3246 BevyDeferredPrepassDoubleBufferParams
3247);
3248elicitation::register_emit!("ambient_light", BevyAmbientLightParams);
3249elicitation::register_emit!("global_ambient_light", BevyGlobalAmbientLightParams);
3250elicitation::register_emit!("directional_light", BevyDirectionalLightParams);
3251elicitation::register_emit!("point_light", BevyPointLightParams);
3252elicitation::register_emit!("spot_light", BevySpotLightParams);
3253elicitation::register_emit!(
3254 "directional_light_shadow_map",
3255 BevyDirectionalLightShadowMapParams
3256);
3257elicitation::register_emit!("point_light_shadow_map", BevyPointLightShadowMapParams);
3258elicitation::register_emit!("environment_map_light", BevyEnvironmentMapLightParams);
3259elicitation::register_emit!(
3260 "generated_environment_map_light",
3261 BevyGeneratedEnvironmentMapLightParams
3262);
3263elicitation::register_emit!(
3264 "atmosphere_environment_map_light",
3265 BevyAtmosphereEnvironmentMapLightParams
3266);
3267elicitation::register_emit!("volumetric_light", BevyVolumetricLightParams);
3268elicitation::register_emit!("volumetric_fog", BevyVolumetricFogParams);
3269elicitation::register_emit!("fog_volume", BevyFogVolumeParams);
3270elicitation::register_emit!("light_probe", BevyLightProbeParams);
3271elicitation::register_emit!("irradiance_volume", BevyIrradianceVolumeParams);
3272elicitation::register_emit!("sun_disk", BevySunDiskParams);
3273elicitation::register_emit!("not_shadow_caster", BevyNotShadowCasterParams);
3274elicitation::register_emit!("not_shadow_receiver", BevyNotShadowReceiverParams);
3275elicitation::register_emit!(
3276 "transmitted_shadow_receiver",
3277 BevyTransmittedShadowReceiverParams
3278);
3279elicitation::register_emit!("shadow_filtering_method", BevyShadowFilteringMethodParams);
3280elicitation::register_emit!("cluster_far_z_mode", BevyClusterFarZModeParams);
3281elicitation::register_emit!("cluster_z_config", BevyClusterZConfigParams);
3282elicitation::register_emit!("cluster_config", BevyClusterConfigParams);
3283elicitation::register_emit!("screen_space_reflections", BevyScreenSpaceReflectionsParams);
3284elicitation::register_emit!("clustered_decal", BevyClusteredDecalParams);
3285elicitation::register_emit!("mesh_3d", BevyMesh3dParams);
3286elicitation::register_emit!("mesh_2d", BevyMesh2dParams);
3287elicitation::register_emit!("mesh_material_3d", BevyMeshMaterial3dParams);
3288elicitation::register_emit!("mesh_material_2d", BevyMeshMaterial2dParams);
3289elicitation::register_emit!("wireframe", BevyWireframeParams);
3290elicitation::register_emit!("wireframe_color", BevyWireframeColorParams);
3291elicitation::register_emit!("no_wireframe", BevyNoWireframeParams);
3292elicitation::register_emit!("wireframe_config", BevyWireframeConfigParams);
3293elicitation::register_emit!("mesh_3d_wireframe", BevyMesh3dWireframeParams);
3294elicitation::register_emit!("wireframe_2d", BevyWireframe2dParams);
3295elicitation::register_emit!("wireframe_2d_color", BevyWireframe2dColorParams);
3296elicitation::register_emit!("no_wireframe_2d", BevyNoWireframe2dParams);
3297elicitation::register_emit!("wireframe_2d_config", BevyWireframe2dConfigParams);
3298elicitation::register_emit!("mesh_2d_wireframe", BevyMesh2dWireframeParams);
3299elicitation::register_emit!("camera_3d", BevyCamera3dParams);
3300elicitation::register_emit!("camera_2d", BevyCamera2dParams);
3301elicitation::register_emit!("viewport", BevyViewportParams);
3302elicitation::register_emit!("fog_settings", BevyFogSettingsParams);
3303elicitation::register_emit!("bloom_composite_mode", BevyBloomCompositeModeParams);
3304elicitation::register_emit!("bloom_settings", BevyBloomSettingsParams);
3305elicitation::register_emit!("sprite", BevySpriteParams);
3306elicitation::register_emit!("text_style", BevyTextStyleParams);
3307elicitation::register_emit!("ssao_quality", BevySsaoQualityParams);
3308elicitation::register_emit!("ssao", BevySsaoParams);
3309elicitation::register_emit!("temporal_anti_aliasing", BevyTemporalAntiAliasingParams);
3310elicitation::register_emit!("cascade_shadow_config", BevyCascadeShadowConfigParams);
3311elicitation::register_emit!(
3312 "cascade_shadow_config_builder",
3313 BevyCascadeShadowConfigBuilderParams
3314);
3315elicitation::register_emit!("atmosphere", BevyAtmosphereParams);
3316elicitation::register_emit!("fullscreen_material", BevyFullscreenMaterialParams);
3317
3318#[derive(Debug, ElicitPlugin)]
3320#[plugin(name = "bevy_render")]
3321pub struct BevyRenderPlugin;
3322
3323impl BevyRenderPlugin {
3324 #[instrument]
3326 pub fn new() -> Self {
3327 Self
3328 }
3329}
3330
3331impl Default for BevyRenderPlugin {
3332 fn default() -> Self {
3333 Self::new()
3334 }
3335}
3336
3337fn validate_standard_material(params: &BevyStandardMaterialParams) -> Result<(), ErrorData> {
3338 validate_optional_expr(¶ms.base_color_expr, "base color")?;
3339 validate_optional_expr(¶ms.base_color_texture_expr, "base color texture")?;
3340 validate_optional_expr(¶ms.emissive_expr, "emissive")?;
3341 validate_optional_expr(¶ms.emissive_texture_expr, "emissive texture")?;
3342 validate_optional_expr(
3343 ¶ms.metallic_roughness_texture_expr,
3344 "metallic roughness texture",
3345 )?;
3346 validate_optional_expr(¶ms.specular_tint_expr, "specular tint")?;
3347 validate_optional_expr(
3348 ¶ms.diffuse_transmission_texture_expr,
3349 "diffuse transmission texture",
3350 )?;
3351 validate_optional_expr(
3352 ¶ms.specular_transmission_texture_expr,
3353 "specular transmission texture",
3354 )?;
3355 validate_optional_expr(¶ms.thickness_texture_expr, "thickness texture")?;
3356 validate_optional_expr(¶ms.attenuation_color_expr, "attenuation color")?;
3357 validate_optional_expr(¶ms.clearcoat_texture_expr, "clearcoat texture")?;
3358 validate_optional_expr(
3359 ¶ms.clearcoat_roughness_texture_expr,
3360 "clearcoat roughness texture",
3361 )?;
3362 validate_optional_expr(
3363 ¶ms.clearcoat_normal_texture_expr,
3364 "clearcoat normal texture",
3365 )?;
3366 validate_optional_expr(¶ms.anisotropy_texture_expr, "anisotropy texture")?;
3367 validate_optional_expr(¶ms.normal_map_texture_expr, "normal map texture")?;
3368 validate_optional_expr(¶ms.occlusion_texture_expr, "occlusion texture")?;
3369 validate_optional_expr(¶ms.specular_texture_expr, "specular texture")?;
3370 validate_optional_expr(¶ms.specular_tint_texture_expr, "specular tint texture")?;
3371 validate_optional_expr(¶ms.alpha_mode_expr, "alpha mode")?;
3372 validate_optional_expr(¶ms.cull_mode_expr, "cull mode")?;
3373 validate_optional_expr(¶ms.depth_map_expr, "depth map")?;
3374 validate_optional_expr(
3375 ¶ms.parallax_mapping_method_expr,
3376 "parallax mapping method",
3377 )?;
3378 validate_optional_expr(¶ms.opaque_render_method_expr, "opaque render method")?;
3379 validate_optional_expr(¶ms.uv_transform_expr, "uv transform")?;
3380 validate_optional_finite_f32(params.emissive_exposure_weight, "emissive exposure weight")?;
3381 validate_optional_finite_f32(params.depth_bias, "depth bias")?;
3382 validate_optional_finite_f32(params.parallax_depth_scale, "parallax depth scale")?;
3383 validate_optional_non_negative_f32(
3384 params.max_parallax_layer_count,
3385 "max parallax layer count",
3386 )?;
3387 validate_optional_non_negative_f32(params.lightmap_exposure, "lightmap exposure")?;
3388 validate_optional_non_negative_f32(params.diffuse_transmission, "diffuse transmission")?;
3389 validate_optional_non_negative_f32(params.specular_transmission, "specular transmission")?;
3390 validate_optional_non_negative_f32(params.thickness, "thickness")?;
3391 validate_optional_non_negative_f32(params.ior, "index of refraction")?;
3392 validate_optional_non_negative_f32(params.attenuation_distance, "attenuation distance")?;
3393 validate_optional_non_negative_f32(params.clearcoat, "clearcoat")?;
3394 validate_optional_non_negative_f32(
3395 params.clearcoat_perceptual_roughness,
3396 "clearcoat perceptual roughness",
3397 )?;
3398 validate_optional_non_negative_f32(params.anisotropy_strength, "anisotropy strength")?;
3399 validate_optional_finite_f32(params.anisotropy_rotation, "anisotropy rotation")?;
3400 Ok(())
3401}
3402
3403fn validate_uv_channel(_params: &BevyUvChannelParams) -> Result<(), ErrorData> {
3404 Ok(())
3405}
3406
3407fn validate_parallax_mapping_method(
3408 params: &BevyParallaxMappingMethodParams,
3409) -> Result<(), ErrorData> {
3410 match params {
3411 BevyParallaxMappingMethodParams::Occlusion => {}
3412 BevyParallaxMappingMethodParams::Relief { max_steps } => {
3413 if *max_steps == 0 {
3414 return Err(tool_err(
3415 "relief parallax mapping max_steps must be greater than zero",
3416 ));
3417 }
3418 }
3419 }
3420 Ok(())
3421}
3422
3423fn validate_opaque_renderer_method(
3424 _params: &BevyOpaqueRendererMethodParams,
3425) -> Result<(), ErrorData> {
3426 Ok(())
3427}
3428
3429fn validate_default_opaque_renderer_method(
3430 _params: &BevyDefaultOpaqueRendererMethodParams,
3431) -> Result<(), ErrorData> {
3432 Ok(())
3433}
3434
3435fn validate_alpha_mode_2d(params: &BevyAlphaMode2dParams) -> Result<(), ErrorData> {
3436 if let BevyAlphaMode2dParams::Mask(threshold) = params
3437 && !threshold.is_finite()
3438 {
3439 return Err(tool_err("alpha_mode_2d threshold must be finite"));
3440 }
3441 Ok(())
3442}
3443
3444fn validate_lightmap(params: &BevyLightmapParams) -> Result<(), ErrorData> {
3445 let _ = parse_expr(¶ms.image_expr, "lightmap image")?;
3446 validate_optional_expr(¶ms.uv_rect_expr, "lightmap uv_rect")
3447}
3448
3449fn validate_color_material(params: &BevyColorMaterialParams) -> Result<(), ErrorData> {
3450 validate_optional_expr(¶ms.color_expr, "color material color")?;
3451 validate_optional_expr(¶ms.alpha_mode_expr, "color material alpha mode")?;
3452 validate_optional_expr(¶ms.uv_transform_expr, "color material uv transform")?;
3453 validate_optional_expr(¶ms.texture_expr, "color material texture")
3454}
3455
3456fn validate_skybox(params: &BevySkyboxParams) -> Result<(), ErrorData> {
3457 let _ = parse_expr(¶ms.image_expr, "skybox image")?;
3458 validate_optional_expr(¶ms.rotation_expr, "skybox rotation")?;
3459 validate_optional_non_negative_f32(params.brightness, "skybox brightness")
3460}
3461
3462fn validate_depth_prepass(_params: &BevyDepthPrepassParams) -> Result<(), ErrorData> {
3463 Ok(())
3464}
3465
3466fn validate_normal_prepass(_params: &BevyNormalPrepassParams) -> Result<(), ErrorData> {
3467 Ok(())
3468}
3469
3470fn validate_motion_vector_prepass(
3471 _params: &BevyMotionVectorPrepassParams,
3472) -> Result<(), ErrorData> {
3473 Ok(())
3474}
3475
3476fn validate_deferred_prepass(_params: &BevyDeferredPrepassParams) -> Result<(), ErrorData> {
3477 Ok(())
3478}
3479
3480fn validate_depth_prepass_double_buffer(
3481 _params: &BevyDepthPrepassDoubleBufferParams,
3482) -> Result<(), ErrorData> {
3483 Ok(())
3484}
3485
3486fn validate_deferred_prepass_double_buffer(
3487 _params: &BevyDeferredPrepassDoubleBufferParams,
3488) -> Result<(), ErrorData> {
3489 Ok(())
3490}
3491
3492fn validate_ambient_light(params: &BevyAmbientLightParams) -> Result<(), ErrorData> {
3493 validate_optional_expr(¶ms.color_expr, "ambient light color")?;
3494 validate_optional_non_negative_f32(params.brightness, "ambient light brightness")
3495}
3496
3497fn validate_global_ambient_light(params: &BevyGlobalAmbientLightParams) -> Result<(), ErrorData> {
3498 validate_optional_expr(¶ms.color_expr, "global ambient light color")?;
3499 validate_optional_non_negative_f32(params.brightness, "global ambient light brightness")
3500}
3501
3502fn validate_directional_light(params: &BevyDirectionalLightParams) -> Result<(), ErrorData> {
3503 validate_optional_expr(¶ms.color_expr, "directional light color")
3504}
3505
3506fn validate_point_light(params: &BevyPointLightParams) -> Result<(), ErrorData> {
3507 validate_optional_expr(¶ms.color_expr, "point light color")
3508}
3509
3510fn validate_spot_light(params: &BevySpotLightParams) -> Result<(), ErrorData> {
3511 validate_optional_expr(¶ms.color_expr, "spot light color")
3512}
3513
3514fn validate_directional_light_shadow_map(
3515 params: &BevyDirectionalLightShadowMapParams,
3516) -> Result<(), ErrorData> {
3517 validate_shadow_map_size(params.size, "directional light shadow map")
3518}
3519
3520fn validate_point_light_shadow_map(
3521 params: &BevyPointLightShadowMapParams,
3522) -> Result<(), ErrorData> {
3523 validate_shadow_map_size(params.size, "point light shadow map")
3524}
3525
3526fn validate_environment_map_light(params: &BevyEnvironmentMapLightParams) -> Result<(), ErrorData> {
3527 let _ = parse_expr(¶ms.diffuse_map_expr, "environment diffuse map")?;
3528 let _ = parse_expr(¶ms.specular_map_expr, "environment specular map")?;
3529 validate_optional_expr(¶ms.rotation_expr, "environment rotation")?;
3530 validate_optional_non_negative_f32(params.intensity, "environment map light intensity")?;
3531 Ok(())
3532}
3533
3534fn validate_generated_environment_map_light(
3535 params: &BevyGeneratedEnvironmentMapLightParams,
3536) -> Result<(), ErrorData> {
3537 let _ = parse_expr(¶ms.environment_map_expr, "generated environment map")?;
3538 validate_optional_expr(¶ms.rotation_expr, "generated environment rotation")?;
3539 validate_optional_non_negative_f32(
3540 params.intensity,
3541 "generated environment map light intensity",
3542 )?;
3543 Ok(())
3544}
3545
3546fn validate_atmosphere_environment_map_light(
3547 params: &BevyAtmosphereEnvironmentMapLightParams,
3548) -> Result<(), ErrorData> {
3549 validate_optional_non_negative_f32(
3550 params.intensity,
3551 "atmosphere environment map light intensity",
3552 )?;
3553 if let Some([width, height]) = params.size {
3554 validate_shadow_map_u32_size(width, "atmosphere environment map width")?;
3555 validate_shadow_map_u32_size(height, "atmosphere environment map height")?;
3556 }
3557 Ok(())
3558}
3559
3560fn validate_volumetric_light(_params: &BevyVolumetricLightParams) -> Result<(), ErrorData> {
3561 Ok(())
3562}
3563
3564fn validate_volumetric_fog(params: &BevyVolumetricFogParams) -> Result<(), ErrorData> {
3565 validate_optional_expr(¶ms.ambient_color_expr, "volumetric fog ambient color")?;
3566 validate_optional_non_negative_f32(
3567 params.ambient_intensity,
3568 "volumetric fog ambient_intensity",
3569 )?;
3570 validate_optional_non_negative_f32(params.jitter, "volumetric fog jitter")?;
3571 if let Some(step_count) = params.step_count
3572 && step_count == 0
3573 {
3574 return Err(tool_err(
3575 "volumetric fog step_count must be greater than zero",
3576 ));
3577 }
3578 Ok(())
3579}
3580
3581fn validate_fog_volume(params: &BevyFogVolumeParams) -> Result<(), ErrorData> {
3582 validate_optional_expr(¶ms.fog_color_expr, "fog volume color")?;
3583 validate_optional_expr(¶ms.density_texture_expr, "fog volume density texture")?;
3584 validate_optional_expr(
3585 ¶ms.density_texture_offset_expr,
3586 "fog volume density texture offset",
3587 )?;
3588 validate_optional_expr(¶ms.light_tint_expr, "fog volume light tint")?;
3589 validate_optional_non_negative_f32(params.density_factor, "fog volume density_factor")?;
3590 validate_optional_non_negative_f32(params.absorption, "fog volume absorption")?;
3591 validate_optional_non_negative_f32(params.scattering, "fog volume scattering")?;
3592 validate_optional_finite_f32(
3593 params.scattering_asymmetry,
3594 "fog volume scattering_asymmetry",
3595 )?;
3596 validate_optional_non_negative_f32(params.light_intensity, "fog volume light_intensity")?;
3597 Ok(())
3598}
3599
3600fn validate_light_probe(_params: &BevyLightProbeParams) -> Result<(), ErrorData> {
3601 Ok(())
3602}
3603
3604fn validate_irradiance_volume(params: &BevyIrradianceVolumeParams) -> Result<(), ErrorData> {
3605 let _ = parse_expr(¶ms.voxels_expr, "irradiance volume voxels")?;
3606 validate_optional_non_negative_f32(params.intensity, "irradiance volume intensity")?;
3607 Ok(())
3608}
3609
3610fn validate_sun_disk(params: &BevySunDiskParams) -> Result<(), ErrorData> {
3611 validate_optional_non_negative_f32(params.angular_size, "sun disk angular_size")?;
3612 validate_optional_non_negative_f32(params.intensity, "sun disk intensity")
3613}
3614
3615fn validate_not_shadow_caster(_params: &BevyNotShadowCasterParams) -> Result<(), ErrorData> {
3616 Ok(())
3617}
3618
3619fn validate_not_shadow_receiver(_params: &BevyNotShadowReceiverParams) -> Result<(), ErrorData> {
3620 Ok(())
3621}
3622
3623fn validate_transmitted_shadow_receiver(
3624 _params: &BevyTransmittedShadowReceiverParams,
3625) -> Result<(), ErrorData> {
3626 Ok(())
3627}
3628
3629fn validate_shadow_filtering_method(
3630 _params: &BevyShadowFilteringMethodParams,
3631) -> Result<(), ErrorData> {
3632 Ok(())
3633}
3634
3635fn validate_cluster_far_z_mode(params: &BevyClusterFarZModeParams) -> Result<(), ErrorData> {
3636 match params {
3637 BevyClusterFarZModeParams::MaxClusterableObjectRange => {}
3638 BevyClusterFarZModeParams::Constant(constant) => {
3639 validate_optional_non_negative_f32(Some(*constant), "cluster far-z constant")?;
3640 }
3641 }
3642 Ok(())
3643}
3644
3645fn validate_cluster_z_config(params: &BevyClusterZConfigParams) -> Result<(), ErrorData> {
3646 validate_optional_non_negative_f32(
3647 params.first_slice_depth,
3648 "cluster z config first_slice_depth",
3649 )?;
3650 if let Some(mode) = ¶ms.far_z_mode {
3651 validate_cluster_far_z_mode(mode)?;
3652 }
3653 Ok(())
3654}
3655
3656fn validate_cluster_config(params: &BevyClusterConfigParams) -> Result<(), ErrorData> {
3657 match params {
3658 BevyClusterConfigParams::None | BevyClusterConfigParams::Single => {}
3659 BevyClusterConfigParams::XYZ {
3660 dimensions,
3661 z_config,
3662 ..
3663 } => {
3664 let [x, y, z] = *dimensions;
3665 if x == 0 || y == 0 || z == 0 {
3666 return Err(tool_err(
3667 "cluster config xyz dimensions must all be greater than zero",
3668 ));
3669 }
3670 validate_cluster_z_config(z_config)?;
3671 }
3672 BevyClusterConfigParams::FixedZ {
3673 total,
3674 z_slices,
3675 z_config,
3676 ..
3677 } => {
3678 if *total == 0 || *z_slices == 0 {
3679 return Err(tool_err(
3680 "cluster config fixed_z total and z_slices must be greater than zero",
3681 ));
3682 }
3683 validate_cluster_z_config(z_config)?;
3684 }
3685 }
3686 Ok(())
3687}
3688
3689fn validate_screen_space_reflections(
3690 params: &BevyScreenSpaceReflectionsParams,
3691) -> Result<(), ErrorData> {
3692 if let Some(value) = params.perceptual_roughness_threshold
3693 && (!value.is_finite() || !(0.0..=1.0).contains(&value))
3694 {
3695 return Err(tool_err(
3696 "screen-space reflections perceptual_roughness_threshold must be in [0.0, 1.0]",
3697 ));
3698 }
3699 validate_optional_non_negative_f32(params.thickness, "screen-space reflections thickness")?;
3700 if let Some(linear_steps) = params.linear_steps
3701 && linear_steps == 0
3702 {
3703 return Err(tool_err(
3704 "screen-space reflections linear_steps must be greater than zero",
3705 ));
3706 }
3707 validate_optional_non_negative_f32(
3708 params.linear_march_exponent,
3709 "screen-space reflections linear_march_exponent",
3710 )?;
3711 Ok(())
3712}
3713
3714fn validate_clustered_decal(params: &BevyClusteredDecalParams) -> Result<(), ErrorData> {
3715 validate_optional_expr(
3716 ¶ms.base_color_texture_expr,
3717 "clustered decal base_color_texture",
3718 )?;
3719 validate_optional_expr(
3720 ¶ms.normal_map_texture_expr,
3721 "clustered decal normal_map_texture",
3722 )?;
3723 validate_optional_expr(
3724 ¶ms.metallic_roughness_texture_expr,
3725 "clustered decal metallic_roughness_texture",
3726 )?;
3727 validate_optional_expr(
3728 ¶ms.emissive_texture_expr,
3729 "clustered decal emissive_texture",
3730 )?;
3731 Ok(())
3732}
3733
3734fn validate_shadow_map_size(size: Option<usize>, context: &str) -> Result<(), ErrorData> {
3735 if let Some(size) = size {
3736 validate_shadow_map_usize_size(size, context)?;
3737 }
3738 Ok(())
3739}
3740
3741fn validate_mesh_3d(params: &BevyMesh3dParams) -> Result<(), ErrorData> {
3742 let _ = parse_expr(¶ms.mesh_expr, "mesh_3d mesh")?;
3743 Ok(())
3744}
3745
3746fn validate_mesh_2d(params: &BevyMesh2dParams) -> Result<(), ErrorData> {
3747 let _ = parse_expr(¶ms.mesh_expr, "mesh_2d mesh")?;
3748 Ok(())
3749}
3750
3751fn validate_mesh_material_3d(params: &BevyMeshMaterial3dParams) -> Result<(), ErrorData> {
3752 let _ = parse_expr(¶ms.material_expr, "mesh_material_3d material")?;
3753 Ok(())
3754}
3755
3756fn validate_mesh_material_2d(params: &BevyMeshMaterial2dParams) -> Result<(), ErrorData> {
3757 let _ = parse_expr(¶ms.material_expr, "mesh_material_2d material")?;
3758 Ok(())
3759}
3760
3761fn validate_wireframe(_params: &BevyWireframeParams) -> Result<(), ErrorData> {
3762 Ok(())
3763}
3764
3765fn validate_wireframe_color(params: &BevyWireframeColorParams) -> Result<(), ErrorData> {
3766 let _ = parse_expr(¶ms.color_expr, "wireframe_color color")?;
3767 Ok(())
3768}
3769
3770fn validate_no_wireframe(_params: &BevyNoWireframeParams) -> Result<(), ErrorData> {
3771 Ok(())
3772}
3773
3774fn validate_wireframe_config(params: &BevyWireframeConfigParams) -> Result<(), ErrorData> {
3775 validate_optional_expr(¶ms.default_color_expr, "wireframe_config default color")
3776}
3777
3778fn validate_mesh_3d_wireframe(params: &BevyMesh3dWireframeParams) -> Result<(), ErrorData> {
3779 let _ = parse_expr(¶ms.material_expr, "mesh_3d_wireframe material")?;
3780 Ok(())
3781}
3782
3783fn validate_wireframe_2d(_params: &BevyWireframe2dParams) -> Result<(), ErrorData> {
3784 Ok(())
3785}
3786
3787fn validate_wireframe_2d_color(params: &BevyWireframe2dColorParams) -> Result<(), ErrorData> {
3788 let _ = parse_expr(¶ms.color_expr, "wireframe_2d_color color")?;
3789 Ok(())
3790}
3791
3792fn validate_no_wireframe_2d(_params: &BevyNoWireframe2dParams) -> Result<(), ErrorData> {
3793 Ok(())
3794}
3795
3796fn validate_wireframe_2d_config(params: &BevyWireframe2dConfigParams) -> Result<(), ErrorData> {
3797 validate_optional_expr(
3798 ¶ms.default_color_expr,
3799 "wireframe_2d_config default color",
3800 )
3801}
3802
3803fn validate_mesh_2d_wireframe(params: &BevyMesh2dWireframeParams) -> Result<(), ErrorData> {
3804 let _ = parse_expr(¶ms.material_expr, "mesh_2d_wireframe material")?;
3805 Ok(())
3806}
3807
3808fn validate_shadow_map_usize_size(size: usize, context: &str) -> Result<(), ErrorData> {
3809 if size == 0 {
3810 return Err(tool_err(format!(
3811 "{context} size must be greater than zero"
3812 )));
3813 }
3814 if !size.is_power_of_two() {
3815 return Err(tool_err(format!("{context} size must be a power of two")));
3816 }
3817 Ok(())
3818}
3819
3820fn validate_shadow_map_u32_size(size: u32, context: &str) -> Result<(), ErrorData> {
3821 if size == 0 {
3822 return Err(tool_err(format!("{context} must be greater than zero")));
3823 }
3824 if !size.is_power_of_two() {
3825 return Err(tool_err(format!("{context} must be a power of two")));
3826 }
3827 Ok(())
3828}
3829
3830fn validate_optional_non_negative_f32(value: Option<f32>, context: &str) -> Result<(), ErrorData> {
3831 if let Some(value) = value
3832 && (!value.is_finite() || value < 0.0)
3833 {
3834 return Err(tool_err(format!(
3835 "{context} must be a finite non-negative number"
3836 )));
3837 }
3838 Ok(())
3839}
3840
3841fn validate_optional_finite_f32(value: Option<f32>, context: &str) -> Result<(), ErrorData> {
3842 if let Some(value) = value
3843 && !value.is_finite()
3844 {
3845 return Err(tool_err(format!("{context} must be finite")));
3846 }
3847 Ok(())
3848}
3849
3850fn validate_camera_3d(params: &BevyCamera3dParams) -> Result<(), ErrorData> {
3851 let _ = parse_expr(¶ms.commands_var, "commands receiver")?;
3852 validate_optional_expr(¶ms.transform_expr, "transform")?;
3853 validate_optional_expr(¶ms.tonemapping_expr, "tonemapping")?;
3854 if let Some(target) = ¶ms.render_target {
3855 validate_render_target(target)?;
3856 }
3857 Ok(())
3858}
3859
3860fn validate_camera_2d(params: &BevyCamera2dParams) -> Result<(), ErrorData> {
3861 let _ = parse_expr(¶ms.commands_var, "commands receiver")?;
3862 validate_optional_expr(¶ms.transform_expr, "transform")?;
3863 validate_optional_expr(¶ms.tonemapping_expr, "tonemapping")?;
3864 if let Some(target) = ¶ms.render_target {
3865 validate_render_target(target)?;
3866 }
3867 Ok(())
3868}
3869
3870fn validate_viewport(params: &BevyViewportParams) -> Result<(), ErrorData> {
3871 if let Some([min, max]) = params.depth
3872 && min > max
3873 {
3874 return Err(tool_err(
3875 "viewport depth min must be less than or equal to max",
3876 ));
3877 }
3878 Ok(())
3879}
3880
3881fn validate_fog_settings(params: &BevyFogSettingsParams) -> Result<(), ErrorData> {
3882 validate_optional_expr(¶ms.color_expr, "fog color")?;
3883 validate_optional_expr(
3884 ¶ms.directional_light_color_expr,
3885 "fog directional light color",
3886 )?;
3887 validate_optional_expr(¶ms.falloff_expr, "fog falloff")?;
3888 Ok(())
3889}
3890
3891fn validate_bloom_settings(params: &BevyBloomSettingsParams) -> Result<(), ErrorData> {
3892 if let Some(softness) = params.prefilter_threshold_softness
3893 && !softness.is_finite()
3894 {
3895 return Err(tool_err(
3896 "bloom prefilter threshold softness must be finite",
3897 ));
3898 }
3899 validate_optional_expr(¶ms.scale_expr, "bloom scale")
3900}
3901
3902fn validate_sprite(params: &BevySpriteParams) -> Result<(), ErrorData> {
3903 validate_optional_expr(¶ms.image_expr, "sprite image")?;
3904 validate_optional_expr(¶ms.color_expr, "sprite color")?;
3905 validate_optional_expr(¶ms.custom_size_expr, "sprite custom size")?;
3906 Ok(())
3907}
3908
3909fn validate_text_style(params: &BevyTextStyleParams) -> Result<(), ErrorData> {
3910 validate_optional_expr(¶ms.font.font_handle_expr, "font handle")?;
3911 validate_optional_expr(¶ms.color.color_expr, "text color")?;
3912 validate_optional_expr(¶ms.layout.justify_expr, "text justify")?;
3913 validate_optional_expr(¶ms.layout.linebreak_expr, "text linebreak")?;
3914 Ok(())
3915}
3916
3917fn validate_ssao_quality(params: &BevySsaoQualityParams) -> Result<(), ErrorData> {
3918 if let BevySsaoQualityParams::Custom {
3919 slice_count,
3920 samples_per_slice_side,
3921 } = params
3922 {
3923 if *slice_count == 0 {
3924 return Err(tool_err(
3925 "custom ssao slice_count must be greater than zero",
3926 ));
3927 }
3928 if *samples_per_slice_side == 0 {
3929 return Err(tool_err(
3930 "custom ssao samples_per_slice_side must be greater than zero",
3931 ));
3932 }
3933 }
3934 Ok(())
3935}
3936
3937fn validate_ssao(params: &BevySsaoParams) -> Result<(), ErrorData> {
3938 if let Some(quality) = ¶ms.quality_level {
3939 validate_ssao_quality(quality)?;
3940 }
3941 if let Some(value) = params.constant_object_thickness
3942 && (!value.is_finite() || value < 0.0)
3943 {
3944 return Err(tool_err(
3945 "ssao constant_object_thickness must be a finite non-negative number",
3946 ));
3947 }
3948 Ok(())
3949}
3950
3951fn validate_temporal_anti_aliasing(
3952 _params: &BevyTemporalAntiAliasingParams,
3953) -> Result<(), ErrorData> {
3954 Ok(())
3955}
3956
3957fn validate_cascade_shadow_config(params: &BevyCascadeShadowConfigParams) -> Result<(), ErrorData> {
3958 if let Some(value) = params.minimum_distance
3959 && (!value.is_finite() || value < 0.0)
3960 {
3961 return Err(tool_err(
3962 "cascade minimum_distance must be a finite non-negative number",
3963 ));
3964 }
3965 if let Some(value) = params.overlap_proportion
3966 && (!value.is_finite() || !(0.0..1.0).contains(&value))
3967 {
3968 return Err(tool_err(
3969 "cascade overlap_proportion must be in the range [0.0, 1.0)",
3970 ));
3971 }
3972 if let Some(bounds) = ¶ms.bounds {
3973 let mut previous = None;
3974 for bound in &bounds.0 {
3975 if !bound.is_finite() || *bound <= 0.0 {
3976 return Err(tool_err(
3977 "cascade bounds must be finite positive far-bound distances",
3978 ));
3979 }
3980 if let Some(prev) = previous
3981 && *bound <= prev
3982 {
3983 return Err(tool_err(
3984 "cascade bounds must be strictly increasing far-bound distances",
3985 ));
3986 }
3987 previous = Some(*bound);
3988 }
3989 }
3990 Ok(())
3991}
3992
3993fn validate_cascade_shadow_config_builder(
3994 params: &BevyCascadeShadowConfigBuilderParams,
3995) -> Result<(), ErrorData> {
3996 const DEFAULT_MINIMUM_DISTANCE: f32 = 0.1;
3997 const DEFAULT_FIRST_CASCADE_FAR_BOUND: f32 = 10.0;
3998
3999 if let Some(num_cascades) = params.num_cascades
4000 && num_cascades == 0
4001 {
4002 return Err(tool_err(
4003 "cascade builder num_cascades must be greater than zero",
4004 ));
4005 }
4006
4007 let minimum_distance = params.minimum_distance.unwrap_or(DEFAULT_MINIMUM_DISTANCE);
4008 if !minimum_distance.is_finite() || minimum_distance < 0.0 {
4009 return Err(tool_err(
4010 "cascade builder minimum_distance must be a finite non-negative number",
4011 ));
4012 }
4013
4014 if let Some(maximum_distance) = params.maximum_distance
4015 && (!maximum_distance.is_finite() || maximum_distance <= minimum_distance)
4016 {
4017 return Err(tool_err(
4018 "cascade builder maximum_distance must be finite and greater than minimum_distance",
4019 ));
4020 }
4021
4022 if let Some(first_cascade_far_bound) = params.first_cascade_far_bound
4023 && (!first_cascade_far_bound.is_finite()
4024 || first_cascade_far_bound <= 0.0
4025 || (params.num_cascades.unwrap_or(4) != 1
4026 && minimum_distance >= first_cascade_far_bound))
4027 {
4028 return Err(tool_err(
4029 "cascade builder first_cascade_far_bound must be finite, positive, and greater than minimum_distance when using multiple cascades",
4030 ));
4031 }
4032
4033 if params.num_cascades.unwrap_or(4) != 1
4034 && params.first_cascade_far_bound.is_none()
4035 && minimum_distance >= DEFAULT_FIRST_CASCADE_FAR_BOUND
4036 {
4037 return Err(tool_err(
4038 "cascade builder minimum_distance must be less than the default first_cascade_far_bound for multi-cascade builds",
4039 ));
4040 }
4041
4042 if let Some(overlap_proportion) = params.overlap_proportion
4043 && (!overlap_proportion.is_finite() || !(0.0..1.0).contains(&overlap_proportion))
4044 {
4045 return Err(tool_err(
4046 "cascade builder overlap_proportion must be in the range [0.0, 1.0)",
4047 ));
4048 }
4049
4050 Ok(())
4051}
4052
4053pub(crate) fn validate_atmosphere(params: &BevyAtmosphereParams) -> Result<(), ErrorData> {
4054 let _ = parse_expr(¶ms.scattering_media_var, "scattering media")?;
4055 if params.falloff_resolution == 0 {
4056 return Err(tool_err("falloff_resolution must be greater than zero"));
4057 }
4058 if params.phase_resolution == 0 {
4059 return Err(tool_err("phase_resolution must be greater than zero"));
4060 }
4061 if let Some(multiplier) = params.density_multiplier
4062 && !multiplier.is_finite()
4063 {
4064 return Err(tool_err("density_multiplier must be finite"));
4065 }
4066 Ok(())
4067}
4068
4069fn validate_fullscreen_material(params: &BevyFullscreenMaterialParams) -> Result<(), ErrorData> {
4070 let _ = parse_type(¶ms.material_type, "fullscreen material")?;
4071 if params.shader_path.trim().is_empty() {
4072 return Err(tool_err("shader_path must not be empty"));
4073 }
4074 validate_optional_expr(¶ms.start_node_expr, "fullscreen start node")?;
4075 validate_optional_expr(¶ms.end_node_expr, "fullscreen end node")?;
4076 Ok(())
4077}
4078
4079#[elicit_tool(
4080 plugin = "bevy_render",
4081 name = "render_target",
4082 description = "Emit a `RenderTarget` component for primary-window, entity-window, image, or texture-view outputs.",
4083 emit = None
4084)]
4085#[instrument(skip_all)]
4086async fn render_target(p: BevyRenderTargetParams) -> Result<CallToolResult, ErrorData> {
4087 validate_render_target(&p)?;
4088 ok_source(p.emit_code().to_string())
4089}
4090
4091#[elicit_tool(
4092 plugin = "bevy_render",
4093 name = "tonemapping",
4094 description = "Emit a `Tonemapping` enum expression.",
4095 emit = None
4096)]
4097#[instrument(skip_all)]
4098async fn tonemapping(p: BevyTonemappingParams) -> Result<CallToolResult, ErrorData> {
4099 ok_source(p.emit_code().to_string())
4100}
4101
4102#[elicit_tool(
4103 plugin = "bevy_render",
4104 name = "deband_dither",
4105 description = "Emit a `DebandDither` camera component for final-image debanding control.",
4106 emit = None
4107)]
4108#[instrument(skip_all)]
4109async fn deband_dither(p: BevyDebandDitherParams) -> Result<CallToolResult, ErrorData> {
4110 ok_source(p.emit_code().to_string())
4111}
4112
4113#[elicit_tool(
4114 plugin = "bevy_render",
4115 name = "order_independent_transparency_settings",
4116 description = "Emit an `OrderIndependentTransparencySettings` camera component with optional layer-count and alpha-threshold overrides.",
4117 emit = None
4118)]
4119#[instrument(skip_all)]
4120async fn order_independent_transparency_settings(
4121 p: BevyOrderIndependentTransparencySettingsParams,
4122) -> Result<CallToolResult, ErrorData> {
4123 validate_order_independent_transparency_settings(&p)?;
4124 ok_source(p.emit_code().to_string())
4125}
4126
4127#[elicit_tool(
4128 plugin = "bevy_render",
4129 name = "scaling_mode",
4130 description = "Emit a `ScalingMode` expression for orthographic camera projections.",
4131 emit = None
4132)]
4133#[instrument(skip_all)]
4134async fn scaling_mode(p: BevyScalingModeParams) -> Result<CallToolResult, ErrorData> {
4135 validate_scaling_mode(&p)?;
4136 ok_source(p.emit_code().to_string())
4137}
4138
4139#[elicit_tool(
4140 plugin = "bevy_render",
4141 name = "perspective_projection",
4142 description = "Emit a `PerspectiveProjection` literal using Bevy defaults plus optional overrides.",
4143 emit = None
4144)]
4145#[instrument(skip_all)]
4146async fn perspective_projection(
4147 p: BevyPerspectiveProjectionParams,
4148) -> Result<CallToolResult, ErrorData> {
4149 validate_perspective_projection(&p)?;
4150 ok_source(p.emit_code().to_string())
4151}
4152
4153#[elicit_tool(
4154 plugin = "bevy_render",
4155 name = "orthographic_projection",
4156 description = "Emit an `OrthographicProjection` literal using Bevy 2D or 3D defaults plus optional overrides.",
4157 emit = None
4158)]
4159#[instrument(skip_all)]
4160async fn orthographic_projection(
4161 p: BevyOrthographicProjectionParams,
4162) -> Result<CallToolResult, ErrorData> {
4163 validate_orthographic_projection(&p)?;
4164 ok_source(p.emit_code().to_string())
4165}
4166
4167#[elicit_tool(
4168 plugin = "bevy_render",
4169 name = "clear_color_config",
4170 description = "Emit a `ClearColorConfig` expression for camera clear behavior.",
4171 emit = None
4172)]
4173#[instrument(skip_all)]
4174async fn clear_color_config(p: BevyClearColorConfigParams) -> Result<CallToolResult, ErrorData> {
4175 validate_clear_color_config(&p)?;
4176 ok_source(p.emit_code().to_string())
4177}
4178
4179#[elicit_tool(
4180 plugin = "bevy_render",
4181 name = "msaa_writeback",
4182 description = "Emit an `MsaaWriteback` expression for camera layering behavior.",
4183 emit = None
4184)]
4185#[instrument(skip_all)]
4186async fn msaa_writeback(p: BevyMsaaWritebackParams) -> Result<CallToolResult, ErrorData> {
4187 ok_source(p.emit_code().to_string())
4188}
4189
4190#[elicit_tool(
4191 plugin = "bevy_render",
4192 name = "exposure",
4193 description = "Emit an `Exposure` component using a preset or explicit EV100 value.",
4194 emit = None
4195)]
4196#[instrument(skip_all)]
4197async fn exposure(p: BevyExposureParams) -> Result<CallToolResult, ErrorData> {
4198 validate_exposure(&p)?;
4199 ok_source(p.emit_code().to_string())
4200}
4201
4202#[elicit_tool(
4203 plugin = "bevy_render",
4204 name = "clear_color",
4205 description = "Emit a `ClearColor` resource literal using Bevy's default or an explicit color.",
4206 emit = None
4207)]
4208#[instrument(skip_all)]
4209async fn clear_color(p: BevyClearColorParams) -> Result<CallToolResult, ErrorData> {
4210 validate_clear_color(&p)?;
4211 ok_source(p.emit_code().to_string())
4212}
4213
4214#[elicit_tool(
4215 plugin = "bevy_render",
4216 name = "camera_3d_depth_load_op",
4217 description = "Emit a `Camera3dDepthLoadOp` expression for main-pass depth behavior.",
4218 emit = None
4219)]
4220#[instrument(skip_all)]
4221async fn camera_3d_depth_load_op(
4222 p: BevyCamera3dDepthLoadOpParams,
4223) -> Result<CallToolResult, ErrorData> {
4224 validate_camera_3d_depth_load_op(&p)?;
4225 ok_source(p.emit_code().to_string())
4226}
4227
4228#[elicit_tool(
4229 plugin = "bevy_render",
4230 name = "screen_space_transmission_quality",
4231 description = "Emit a `ScreenSpaceTransmissionQuality` resource value.",
4232 emit = None
4233)]
4234#[instrument(skip_all)]
4235async fn screen_space_transmission_quality(
4236 p: BevyScreenSpaceTransmissionQualityParams,
4237) -> Result<CallToolResult, ErrorData> {
4238 validate_screen_space_transmission_quality(&p)?;
4239 ok_source(p.emit_code().to_string())
4240}
4241
4242#[elicit_tool(
4243 plugin = "bevy_render",
4244 name = "main_pass_resolution_override",
4245 description = "Emit a `MainPassResolutionOverride` component for camera render scaling.",
4246 emit = None
4247)]
4248#[instrument(skip_all)]
4249async fn main_pass_resolution_override(
4250 p: BevyMainPassResolutionOverrideParams,
4251) -> Result<CallToolResult, ErrorData> {
4252 validate_main_pass_resolution_override(&p)?;
4253 ok_source(p.emit_code().to_string())
4254}
4255
4256#[elicit_tool(
4257 plugin = "bevy_render",
4258 name = "sub_camera_view",
4259 description = "Emit a `SubCameraView` value for tiled or multi-monitor camera layouts.",
4260 emit = None
4261)]
4262#[instrument(skip_all)]
4263async fn sub_camera_view(p: BevySubCameraViewParams) -> Result<CallToolResult, ErrorData> {
4264 validate_sub_camera_view(&p)?;
4265 ok_source(p.emit_code().to_string())
4266}
4267
4268#[elicit_tool(
4269 plugin = "bevy_render",
4270 name = "no_cpu_culling",
4271 description = "Emit a `NoCpuCulling` marker component.",
4272 emit = None
4273)]
4274#[instrument(skip_all)]
4275async fn no_cpu_culling(p: BevyNoCpuCullingParams) -> Result<CallToolResult, ErrorData> {
4276 ok_source(p.emit_code().to_string())
4277}
4278
4279#[elicit_tool(
4280 plugin = "bevy_render",
4281 name = "no_frustum_culling",
4282 description = "Emit a `NoFrustumCulling` marker component.",
4283 emit = None
4284)]
4285#[instrument(skip_all)]
4286async fn no_frustum_culling(p: BevyNoFrustumCullingParams) -> Result<CallToolResult, ErrorData> {
4287 ok_source(p.emit_code().to_string())
4288}
4289
4290#[elicit_tool(
4291 plugin = "bevy_render",
4292 name = "visibility_range",
4293 description = "Emit a `VisibilityRange` component with explicit near and far fade bands.",
4294 emit = None
4295)]
4296#[instrument(skip_all)]
4297async fn visibility_range(p: BevyVisibilityRangeParams) -> Result<CallToolResult, ErrorData> {
4298 validate_visibility_range(&p)?;
4299 ok_source(p.emit_code().to_string())
4300}
4301
4302#[elicit_tool(
4303 plugin = "bevy_render",
4304 name = "color",
4305 description = "Emit a structured `bevy::color::Color` expression using the selected Bevy color space.",
4306 emit = None
4307)]
4308#[instrument(skip_all)]
4309async fn color(p: BevyColorParams) -> Result<CallToolResult, ErrorData> {
4310 ok_source(p.emit_code().to_string())
4311}
4312
4313#[elicit_tool(
4314 plugin = "bevy_render",
4315 name = "alpha_mode",
4316 description = "Emit an `AlphaMode` enum expression.",
4317 emit = None
4318)]
4319#[instrument(skip_all)]
4320async fn alpha_mode(p: BevyRenderAlphaModeParams) -> Result<CallToolResult, ErrorData> {
4321 ok_source(p.emit_code().to_string())
4322}
4323
4324#[elicit_tool(
4325 plugin = "bevy_render",
4326 name = "uv_channel",
4327 description = "Emit a `UvChannel` enum expression.",
4328 emit = None
4329)]
4330#[instrument(skip_all)]
4331async fn uv_channel(p: BevyUvChannelParams) -> Result<CallToolResult, ErrorData> {
4332 validate_uv_channel(&p)?;
4333 ok_source(p.emit_code().to_string())
4334}
4335
4336#[elicit_tool(
4337 plugin = "bevy_render",
4338 name = "parallax_mapping_method",
4339 description = "Emit a `ParallaxMappingMethod` enum expression.",
4340 emit = None
4341)]
4342#[instrument(skip_all)]
4343async fn parallax_mapping_method(
4344 p: BevyParallaxMappingMethodParams,
4345) -> Result<CallToolResult, ErrorData> {
4346 validate_parallax_mapping_method(&p)?;
4347 ok_source(p.emit_code().to_string())
4348}
4349
4350#[elicit_tool(
4351 plugin = "bevy_render",
4352 name = "opaque_renderer_method",
4353 description = "Emit an `OpaqueRendererMethod` enum expression.",
4354 emit = None
4355)]
4356#[instrument(skip_all)]
4357async fn opaque_renderer_method(
4358 p: BevyOpaqueRendererMethodParams,
4359) -> Result<CallToolResult, ErrorData> {
4360 validate_opaque_renderer_method(&p)?;
4361 ok_source(p.emit_code().to_string())
4362}
4363
4364#[elicit_tool(
4365 plugin = "bevy_render",
4366 name = "default_opaque_renderer_method",
4367 description = "Emit a `DefaultOpaqueRendererMethod` resource constructor expression.",
4368 emit = None
4369)]
4370#[instrument(skip_all)]
4371async fn default_opaque_renderer_method(
4372 p: BevyDefaultOpaqueRendererMethodParams,
4373) -> Result<CallToolResult, ErrorData> {
4374 validate_default_opaque_renderer_method(&p)?;
4375 ok_source(p.emit_code().to_string())
4376}
4377
4378#[elicit_tool(
4379 plugin = "bevy_render",
4380 name = "alpha_mode_2d",
4381 description = "Emit an `AlphaMode2d` enum expression for 2D mesh materials.",
4382 emit = None
4383)]
4384#[instrument(skip_all)]
4385async fn alpha_mode_2d(p: BevyAlphaMode2dParams) -> Result<CallToolResult, ErrorData> {
4386 validate_alpha_mode_2d(&p)?;
4387 ok_source(p.emit_code().to_string())
4388}
4389
4390#[elicit_tool(
4391 plugin = "bevy_render",
4392 name = "standard_material",
4393 description = "Emit a `StandardMaterial` struct literal with common surface fields.",
4394 emit = None
4395)]
4396#[instrument(skip_all)]
4397async fn standard_material(p: BevyStandardMaterialParams) -> Result<CallToolResult, ErrorData> {
4398 validate_standard_material(&p)?;
4399 ok_source(p.emit_code().to_string())
4400}
4401
4402#[elicit_tool(
4403 plugin = "bevy_render",
4404 name = "lightmap",
4405 description = "Emit a `Lightmap` component for baked 3D lighting with optional atlas rect and bicubic sampling.",
4406 emit = None
4407)]
4408#[instrument(skip_all)]
4409async fn lightmap(p: BevyLightmapParams) -> Result<CallToolResult, ErrorData> {
4410 validate_lightmap(&p)?;
4411 ok_source(p.emit_code().to_string())
4412}
4413
4414#[elicit_tool(
4415 plugin = "bevy_render",
4416 name = "color_material",
4417 description = "Emit a `ColorMaterial` asset literal with optional tint, alpha mode, UV transform, and texture handle.",
4418 emit = None
4419)]
4420#[instrument(skip_all)]
4421async fn color_material(p: BevyColorMaterialParams) -> Result<CallToolResult, ErrorData> {
4422 validate_color_material(&p)?;
4423 ok_source(p.emit_code().to_string())
4424}
4425
4426#[elicit_tool(
4427 plugin = "bevy_render",
4428 name = "skybox",
4429 description = "Emit a `Skybox` component with cubemap handle, optional brightness, and optional rotation.",
4430 emit = None
4431)]
4432#[instrument(skip_all)]
4433async fn skybox(p: BevySkyboxParams) -> Result<CallToolResult, ErrorData> {
4434 validate_skybox(&p)?;
4435 ok_source(p.emit_code().to_string())
4436}
4437
4438#[elicit_tool(
4439 plugin = "bevy_render",
4440 name = "depth_prepass",
4441 description = "Emit the `DepthPrepass` camera marker component.",
4442 emit = None
4443)]
4444#[instrument(skip_all)]
4445async fn depth_prepass(p: BevyDepthPrepassParams) -> Result<CallToolResult, ErrorData> {
4446 validate_depth_prepass(&p)?;
4447 ok_source(p.emit_code().to_string())
4448}
4449
4450#[elicit_tool(
4451 plugin = "bevy_render",
4452 name = "normal_prepass",
4453 description = "Emit the `NormalPrepass` camera marker component.",
4454 emit = None
4455)]
4456#[instrument(skip_all)]
4457async fn normal_prepass(p: BevyNormalPrepassParams) -> Result<CallToolResult, ErrorData> {
4458 validate_normal_prepass(&p)?;
4459 ok_source(p.emit_code().to_string())
4460}
4461
4462#[elicit_tool(
4463 plugin = "bevy_render",
4464 name = "motion_vector_prepass",
4465 description = "Emit the `MotionVectorPrepass` camera marker component.",
4466 emit = None
4467)]
4468#[instrument(skip_all)]
4469async fn motion_vector_prepass(
4470 p: BevyMotionVectorPrepassParams,
4471) -> Result<CallToolResult, ErrorData> {
4472 validate_motion_vector_prepass(&p)?;
4473 ok_source(p.emit_code().to_string())
4474}
4475
4476#[elicit_tool(
4477 plugin = "bevy_render",
4478 name = "deferred_prepass",
4479 description = "Emit the `DeferredPrepass` camera marker component.",
4480 emit = None
4481)]
4482#[instrument(skip_all)]
4483async fn deferred_prepass(p: BevyDeferredPrepassParams) -> Result<CallToolResult, ErrorData> {
4484 validate_deferred_prepass(&p)?;
4485 ok_source(p.emit_code().to_string())
4486}
4487
4488#[elicit_tool(
4489 plugin = "bevy_render",
4490 name = "depth_prepass_double_buffer",
4491 description = "Emit the `DepthPrepassDoubleBuffer` marker component for previous-frame depth queries.",
4492 emit = None
4493)]
4494#[instrument(skip_all)]
4495async fn depth_prepass_double_buffer(
4496 p: BevyDepthPrepassDoubleBufferParams,
4497) -> Result<CallToolResult, ErrorData> {
4498 validate_depth_prepass_double_buffer(&p)?;
4499 ok_source(p.emit_code().to_string())
4500}
4501
4502#[elicit_tool(
4503 plugin = "bevy_render",
4504 name = "deferred_prepass_double_buffer",
4505 description = "Emit the `DeferredPrepassDoubleBuffer` marker component for previous-frame deferred g-buffer queries.",
4506 emit = None
4507)]
4508#[instrument(skip_all)]
4509async fn deferred_prepass_double_buffer(
4510 p: BevyDeferredPrepassDoubleBufferParams,
4511) -> Result<CallToolResult, ErrorData> {
4512 validate_deferred_prepass_double_buffer(&p)?;
4513 ok_source(p.emit_code().to_string())
4514}
4515
4516#[elicit_tool(
4517 plugin = "bevy_render",
4518 name = "ambient_light",
4519 description = "Emit an `AmbientLight` struct literal.",
4520 emit = None
4521)]
4522#[instrument(skip_all)]
4523async fn ambient_light(p: BevyAmbientLightParams) -> Result<CallToolResult, ErrorData> {
4524 validate_ambient_light(&p)?;
4525 ok_source(p.emit_code().to_string())
4526}
4527
4528#[elicit_tool(
4529 plugin = "bevy_render",
4530 name = "global_ambient_light",
4531 description = "Emit a `GlobalAmbientLight` resource literal for scene-wide ambient lighting defaults.",
4532 emit = None
4533)]
4534#[instrument(skip_all)]
4535async fn global_ambient_light(
4536 p: BevyGlobalAmbientLightParams,
4537) -> Result<CallToolResult, ErrorData> {
4538 validate_global_ambient_light(&p)?;
4539 ok_source(p.emit_code().to_string())
4540}
4541
4542#[elicit_tool(
4543 plugin = "bevy_render",
4544 name = "directional_light",
4545 description = "Emit a `DirectionalLight` struct literal.",
4546 emit = None
4547)]
4548#[instrument(skip_all)]
4549async fn directional_light(p: BevyDirectionalLightParams) -> Result<CallToolResult, ErrorData> {
4550 validate_directional_light(&p)?;
4551 ok_source(p.emit_code().to_string())
4552}
4553
4554#[elicit_tool(
4555 plugin = "bevy_render",
4556 name = "point_light",
4557 description = "Emit a `PointLight` struct literal.",
4558 emit = None
4559)]
4560#[instrument(skip_all)]
4561async fn point_light(p: BevyPointLightParams) -> Result<CallToolResult, ErrorData> {
4562 validate_point_light(&p)?;
4563 ok_source(p.emit_code().to_string())
4564}
4565
4566#[elicit_tool(
4567 plugin = "bevy_render",
4568 name = "spot_light",
4569 description = "Emit a `SpotLight` struct literal.",
4570 emit = None
4571)]
4572#[instrument(skip_all)]
4573async fn spot_light(p: BevySpotLightParams) -> Result<CallToolResult, ErrorData> {
4574 validate_spot_light(&p)?;
4575 ok_source(p.emit_code().to_string())
4576}
4577
4578#[elicit_tool(
4579 plugin = "bevy_render",
4580 name = "directional_light_shadow_map",
4581 description = "Emit a `DirectionalLightShadowMap` resource expression with an optional power-of-two cascade size.",
4582 emit = None
4583)]
4584#[instrument(skip_all)]
4585async fn directional_light_shadow_map(
4586 p: BevyDirectionalLightShadowMapParams,
4587) -> Result<CallToolResult, ErrorData> {
4588 validate_directional_light_shadow_map(&p)?;
4589 ok_source(p.emit_code().to_string())
4590}
4591
4592#[elicit_tool(
4593 plugin = "bevy_render",
4594 name = "point_light_shadow_map",
4595 description = "Emit a `PointLightShadowMap` resource expression with an optional power-of-two cubemap-face size.",
4596 emit = None
4597)]
4598#[instrument(skip_all)]
4599async fn point_light_shadow_map(
4600 p: BevyPointLightShadowMapParams,
4601) -> Result<CallToolResult, ErrorData> {
4602 validate_point_light_shadow_map(&p)?;
4603 ok_source(p.emit_code().to_string())
4604}
4605
4606#[elicit_tool(
4607 plugin = "bevy_render",
4608 name = "environment_map_light",
4609 description = "Emit an `EnvironmentMapLight` component with diffuse/specular cubemap handles and optional tuning fields.",
4610 emit = None
4611)]
4612#[instrument(skip_all)]
4613async fn environment_map_light(
4614 p: BevyEnvironmentMapLightParams,
4615) -> Result<CallToolResult, ErrorData> {
4616 validate_environment_map_light(&p)?;
4617 ok_source(p.emit_code().to_string())
4618}
4619
4620#[elicit_tool(
4621 plugin = "bevy_render",
4622 name = "generated_environment_map_light",
4623 description = "Emit a `GeneratedEnvironmentMapLight` component for runtime-filtered cubemap lighting.",
4624 emit = None
4625)]
4626#[instrument(skip_all)]
4627async fn generated_environment_map_light(
4628 p: BevyGeneratedEnvironmentMapLightParams,
4629) -> Result<CallToolResult, ErrorData> {
4630 validate_generated_environment_map_light(&p)?;
4631 ok_source(p.emit_code().to_string())
4632}
4633
4634#[elicit_tool(
4635 plugin = "bevy_render",
4636 name = "atmosphere_environment_map_light",
4637 description = "Emit an `AtmosphereEnvironmentMapLight` component for atmosphere-driven image-based lighting.",
4638 emit = None
4639)]
4640#[instrument(skip_all)]
4641async fn atmosphere_environment_map_light(
4642 p: BevyAtmosphereEnvironmentMapLightParams,
4643) -> Result<CallToolResult, ErrorData> {
4644 validate_atmosphere_environment_map_light(&p)?;
4645 ok_source(p.emit_code().to_string())
4646}
4647
4648#[elicit_tool(
4649 plugin = "bevy_render",
4650 name = "volumetric_light",
4651 description = "Emit the `VolumetricLight` marker component used for light shafts and god rays.",
4652 emit = None
4653)]
4654#[instrument(skip_all)]
4655async fn volumetric_light(p: BevyVolumetricLightParams) -> Result<CallToolResult, ErrorData> {
4656 validate_volumetric_light(&p)?;
4657 ok_source(p.emit_code().to_string())
4658}
4659
4660#[elicit_tool(
4661 plugin = "bevy_render",
4662 name = "volumetric_fog",
4663 description = "Emit a `VolumetricFog` component for Bevy 0.18 camera-based volumetric fog.",
4664 emit = None
4665)]
4666#[instrument(skip_all)]
4667async fn volumetric_fog(p: BevyVolumetricFogParams) -> Result<CallToolResult, ErrorData> {
4668 validate_volumetric_fog(&p)?;
4669 ok_source(p.emit_code().to_string())
4670}
4671
4672#[elicit_tool(
4673 plugin = "bevy_render",
4674 name = "fog_volume",
4675 description = "Emit a `FogVolume` component with optional density texture, optical coefficients, and artistic tint controls.",
4676 emit = None
4677)]
4678#[instrument(skip_all)]
4679async fn fog_volume(p: BevyFogVolumeParams) -> Result<CallToolResult, ErrorData> {
4680 validate_fog_volume(&p)?;
4681 ok_source(p.emit_code().to_string())
4682}
4683
4684#[elicit_tool(
4685 plugin = "bevy_render",
4686 name = "light_probe",
4687 description = "Emit the `LightProbe` marker component for probe-bounded indirect lighting regions.",
4688 emit = None
4689)]
4690#[instrument(skip_all)]
4691async fn light_probe(p: BevyLightProbeParams) -> Result<CallToolResult, ErrorData> {
4692 validate_light_probe(&p)?;
4693 ok_source(p.emit_code().to_string())
4694}
4695
4696#[elicit_tool(
4697 plugin = "bevy_render",
4698 name = "irradiance_volume",
4699 description = "Emit an `IrradianceVolume` component with voxel texture, intensity, and lightmap interaction controls.",
4700 emit = None
4701)]
4702#[instrument(skip_all)]
4703async fn irradiance_volume(p: BevyIrradianceVolumeParams) -> Result<CallToolResult, ErrorData> {
4704 validate_irradiance_volume(&p)?;
4705 ok_source(p.emit_code().to_string())
4706}
4707
4708#[elicit_tool(
4709 plugin = "bevy_render",
4710 name = "sun_disk",
4711 description = "Emit a `SunDisk` component for atmosphere-visible directional-light disks.",
4712 emit = None
4713)]
4714#[instrument(skip_all)]
4715async fn sun_disk(p: BevySunDiskParams) -> Result<CallToolResult, ErrorData> {
4716 validate_sun_disk(&p)?;
4717 ok_source(p.emit_code().to_string())
4718}
4719
4720#[elicit_tool(
4721 plugin = "bevy_render",
4722 name = "not_shadow_caster",
4723 description = "Emit the `NotShadowCaster` marker component to disable mesh shadow casting.",
4724 emit = None
4725)]
4726#[instrument(skip_all)]
4727async fn not_shadow_caster(p: BevyNotShadowCasterParams) -> Result<CallToolResult, ErrorData> {
4728 validate_not_shadow_caster(&p)?;
4729 ok_source(p.emit_code().to_string())
4730}
4731
4732#[elicit_tool(
4733 plugin = "bevy_render",
4734 name = "not_shadow_receiver",
4735 description = "Emit the `NotShadowReceiver` marker component to disable mesh shadow reception.",
4736 emit = None
4737)]
4738#[instrument(skip_all)]
4739async fn not_shadow_receiver(p: BevyNotShadowReceiverParams) -> Result<CallToolResult, ErrorData> {
4740 validate_not_shadow_receiver(&p)?;
4741 ok_source(p.emit_code().to_string())
4742}
4743
4744#[elicit_tool(
4745 plugin = "bevy_render",
4746 name = "transmitted_shadow_receiver",
4747 description = "Emit the `TransmittedShadowReceiver` marker component for diffuse transmission shadows.",
4748 emit = None
4749)]
4750#[instrument(skip_all)]
4751async fn transmitted_shadow_receiver(
4752 p: BevyTransmittedShadowReceiverParams,
4753) -> Result<CallToolResult, ErrorData> {
4754 validate_transmitted_shadow_receiver(&p)?;
4755 ok_source(p.emit_code().to_string())
4756}
4757
4758#[elicit_tool(
4759 plugin = "bevy_render",
4760 name = "shadow_filtering_method",
4761 description = "Emit a `ShadowFilteringMethod` camera component for shadow edge filtering mode.",
4762 emit = None
4763)]
4764#[instrument(skip_all)]
4765async fn shadow_filtering_method(
4766 p: BevyShadowFilteringMethodParams,
4767) -> Result<CallToolResult, ErrorData> {
4768 validate_shadow_filtering_method(&p)?;
4769 ok_source(p.emit_code().to_string())
4770}
4771
4772#[elicit_tool(
4773 plugin = "bevy_render",
4774 name = "cluster_far_z_mode",
4775 description = "Emit a `ClusterFarZMode` expression for clustered-lighting depth strategy.",
4776 emit = None
4777)]
4778#[instrument(skip_all)]
4779async fn cluster_far_z_mode(p: BevyClusterFarZModeParams) -> Result<CallToolResult, ErrorData> {
4780 validate_cluster_far_z_mode(&p)?;
4781 ok_source(p.emit_code().to_string())
4782}
4783
4784#[elicit_tool(
4785 plugin = "bevy_render",
4786 name = "cluster_z_config",
4787 description = "Emit a `ClusterZConfig` literal for clustered-lighting depth slicing.",
4788 emit = None
4789)]
4790#[instrument(skip_all)]
4791async fn cluster_z_config(p: BevyClusterZConfigParams) -> Result<CallToolResult, ErrorData> {
4792 validate_cluster_z_config(&p)?;
4793 ok_source(p.emit_code().to_string())
4794}
4795
4796#[elicit_tool(
4797 plugin = "bevy_render",
4798 name = "cluster_config",
4799 description = "Emit a `ClusterConfig` camera component for Bevy clustered-lighting strategy.",
4800 emit = None
4801)]
4802#[instrument(skip_all)]
4803async fn cluster_config(p: BevyClusterConfigParams) -> Result<CallToolResult, ErrorData> {
4804 validate_cluster_config(&p)?;
4805 ok_source(p.emit_code().to_string())
4806}
4807
4808#[elicit_tool(
4809 plugin = "bevy_render",
4810 name = "screen_space_reflections",
4811 description = "Emit a `ScreenSpaceReflections` camera component for deferred screen-space reflections.",
4812 emit = None
4813)]
4814#[instrument(skip_all)]
4815async fn screen_space_reflections(
4816 p: BevyScreenSpaceReflectionsParams,
4817) -> Result<CallToolResult, ErrorData> {
4818 validate_screen_space_reflections(&p)?;
4819 ok_source(p.emit_code().to_string())
4820}
4821
4822#[elicit_tool(
4823 plugin = "bevy_render",
4824 name = "clustered_decal",
4825 description = "Emit a `ClusteredDecal` component with optional texture handles and application tag.",
4826 emit = None
4827)]
4828#[instrument(skip_all)]
4829async fn clustered_decal(p: BevyClusteredDecalParams) -> Result<CallToolResult, ErrorData> {
4830 validate_clustered_decal(&p)?;
4831 ok_source(p.emit_code().to_string())
4832}
4833
4834#[elicit_tool(
4835 plugin = "bevy_render",
4836 name = "mesh_3d",
4837 description = "Emit a `Mesh3d` component from a mesh handle expression.",
4838 emit = None
4839)]
4840#[instrument(skip_all)]
4841async fn mesh_3d(p: BevyMesh3dParams) -> Result<CallToolResult, ErrorData> {
4842 validate_mesh_3d(&p)?;
4843 ok_source(p.emit_code().to_string())
4844}
4845
4846#[elicit_tool(
4847 plugin = "bevy_render",
4848 name = "mesh_2d",
4849 description = "Emit a `Mesh2d` component from a mesh handle expression.",
4850 emit = None
4851)]
4852#[instrument(skip_all)]
4853async fn mesh_2d(p: BevyMesh2dParams) -> Result<CallToolResult, ErrorData> {
4854 validate_mesh_2d(&p)?;
4855 ok_source(p.emit_code().to_string())
4856}
4857
4858#[elicit_tool(
4859 plugin = "bevy_render",
4860 name = "mesh_material_3d",
4861 description = "Emit a generic `MeshMaterial3d<M>` component from a typed material handle expression.",
4862 emit = None
4863)]
4864#[instrument(skip_all)]
4865async fn mesh_material_3d(p: BevyMeshMaterial3dParams) -> Result<CallToolResult, ErrorData> {
4866 validate_mesh_material_3d(&p)?;
4867 ok_source(p.emit_code().to_string())
4868}
4869
4870#[elicit_tool(
4871 plugin = "bevy_render",
4872 name = "mesh_material_2d",
4873 description = "Emit a generic `MeshMaterial2d<M>` component from a typed material handle expression.",
4874 emit = None
4875)]
4876#[instrument(skip_all)]
4877async fn mesh_material_2d(p: BevyMeshMaterial2dParams) -> Result<CallToolResult, ErrorData> {
4878 validate_mesh_material_2d(&p)?;
4879 ok_source(p.emit_code().to_string())
4880}
4881
4882#[elicit_tool(
4883 plugin = "bevy_render",
4884 name = "wireframe",
4885 description = "Emit the `Wireframe` marker component for 3D meshes.",
4886 emit = None
4887)]
4888#[instrument(skip_all)]
4889async fn wireframe(p: BevyWireframeParams) -> Result<CallToolResult, ErrorData> {
4890 validate_wireframe(&p)?;
4891 ok_source(p.emit_code().to_string())
4892}
4893
4894#[elicit_tool(
4895 plugin = "bevy_render",
4896 name = "wireframe_color",
4897 description = "Emit a `WireframeColor` component for overriding 3D wireframe tint.",
4898 emit = None
4899)]
4900#[instrument(skip_all)]
4901async fn wireframe_color(p: BevyWireframeColorParams) -> Result<CallToolResult, ErrorData> {
4902 validate_wireframe_color(&p)?;
4903 ok_source(p.emit_code().to_string())
4904}
4905
4906#[elicit_tool(
4907 plugin = "bevy_render",
4908 name = "no_wireframe",
4909 description = "Emit the `NoWireframe` marker component to opt out of global 3D wireframes.",
4910 emit = None
4911)]
4912#[instrument(skip_all)]
4913async fn no_wireframe(p: BevyNoWireframeParams) -> Result<CallToolResult, ErrorData> {
4914 validate_no_wireframe(&p)?;
4915 ok_source(p.emit_code().to_string())
4916}
4917
4918#[elicit_tool(
4919 plugin = "bevy_render",
4920 name = "wireframe_config",
4921 description = "Emit a `WireframeConfig` resource with optional global flag and fallback color.",
4922 emit = None
4923)]
4924#[instrument(skip_all)]
4925async fn wireframe_config(p: BevyWireframeConfigParams) -> Result<CallToolResult, ErrorData> {
4926 validate_wireframe_config(&p)?;
4927 ok_source(p.emit_code().to_string())
4928}
4929
4930#[elicit_tool(
4931 plugin = "bevy_render",
4932 name = "mesh_3d_wireframe",
4933 description = "Emit a `Mesh3dWireframe` component from a wireframe material handle expression.",
4934 emit = None
4935)]
4936#[instrument(skip_all)]
4937async fn mesh_3d_wireframe(p: BevyMesh3dWireframeParams) -> Result<CallToolResult, ErrorData> {
4938 validate_mesh_3d_wireframe(&p)?;
4939 ok_source(p.emit_code().to_string())
4940}
4941
4942#[elicit_tool(
4943 plugin = "bevy_render",
4944 name = "wireframe_2d",
4945 description = "Emit the `Wireframe2d` marker component for 2D meshes.",
4946 emit = None
4947)]
4948#[instrument(skip_all)]
4949async fn wireframe_2d(p: BevyWireframe2dParams) -> Result<CallToolResult, ErrorData> {
4950 validate_wireframe_2d(&p)?;
4951 ok_source(p.emit_code().to_string())
4952}
4953
4954#[elicit_tool(
4955 plugin = "bevy_render",
4956 name = "wireframe_2d_color",
4957 description = "Emit a `Wireframe2dColor` component for overriding 2D wireframe tint.",
4958 emit = None
4959)]
4960#[instrument(skip_all)]
4961async fn wireframe_2d_color(p: BevyWireframe2dColorParams) -> Result<CallToolResult, ErrorData> {
4962 validate_wireframe_2d_color(&p)?;
4963 ok_source(p.emit_code().to_string())
4964}
4965
4966#[elicit_tool(
4967 plugin = "bevy_render",
4968 name = "no_wireframe_2d",
4969 description = "Emit the `NoWireframe2d` marker component to opt out of global 2D wireframes.",
4970 emit = None
4971)]
4972#[instrument(skip_all)]
4973async fn no_wireframe_2d(p: BevyNoWireframe2dParams) -> Result<CallToolResult, ErrorData> {
4974 validate_no_wireframe_2d(&p)?;
4975 ok_source(p.emit_code().to_string())
4976}
4977
4978#[elicit_tool(
4979 plugin = "bevy_render",
4980 name = "wireframe_2d_config",
4981 description = "Emit a `Wireframe2dConfig` resource with optional global flag and fallback color.",
4982 emit = None
4983)]
4984#[instrument(skip_all)]
4985async fn wireframe_2d_config(p: BevyWireframe2dConfigParams) -> Result<CallToolResult, ErrorData> {
4986 validate_wireframe_2d_config(&p)?;
4987 ok_source(p.emit_code().to_string())
4988}
4989
4990#[elicit_tool(
4991 plugin = "bevy_render",
4992 name = "mesh_2d_wireframe",
4993 description = "Emit a `Mesh2dWireframe` component from a 2D wireframe material handle expression.",
4994 emit = None
4995)]
4996#[instrument(skip_all)]
4997async fn mesh_2d_wireframe(p: BevyMesh2dWireframeParams) -> Result<CallToolResult, ErrorData> {
4998 validate_mesh_2d_wireframe(&p)?;
4999 ok_source(p.emit_code().to_string())
5000}
5001
5002#[elicit_tool(
5003 plugin = "bevy_render",
5004 name = "camera_3d",
5005 description = "Emit a Bevy 0.18 camera spawn tuple with `Camera3d`, `Projection`, and `RenderTarget`.",
5006 emit = None
5007)]
5008#[instrument(skip_all)]
5009async fn camera_3d(p: BevyCamera3dParams) -> Result<CallToolResult, ErrorData> {
5010 validate_camera_3d(&p)?;
5011 ok_source(p.emit_code().to_string())
5012}
5013
5014#[elicit_tool(
5015 plugin = "bevy_render",
5016 name = "camera_2d",
5017 description = "Emit a Bevy 0.18 camera spawn tuple with `Camera2d`, `Projection`, and `RenderTarget`.",
5018 emit = None
5019)]
5020#[instrument(skip_all)]
5021async fn camera_2d(p: BevyCamera2dParams) -> Result<CallToolResult, ErrorData> {
5022 validate_camera_2d(&p)?;
5023 ok_source(p.emit_code().to_string())
5024}
5025
5026#[elicit_tool(
5027 plugin = "bevy_render",
5028 name = "viewport",
5029 description = "Emit a `Viewport` literal with physical position, size, and depth range.",
5030 emit = None
5031)]
5032#[instrument(skip_all)]
5033async fn viewport(p: BevyViewportParams) -> Result<CallToolResult, ErrorData> {
5034 validate_viewport(&p)?;
5035 ok_source(p.emit_code().to_string())
5036}
5037
5038#[elicit_tool(
5039 plugin = "bevy_render",
5040 name = "fog_settings",
5041 description = "Emit a Bevy 0.18 `DistanceFog` literal; this replaces the older `FogSettings` surface.",
5042 emit = None
5043)]
5044#[instrument(skip_all)]
5045async fn fog_settings(p: BevyFogSettingsParams) -> Result<CallToolResult, ErrorData> {
5046 validate_fog_settings(&p)?;
5047 ok_source(p.emit_code().to_string())
5048}
5049
5050#[elicit_tool(
5051 plugin = "bevy_render",
5052 name = "bloom_composite_mode",
5053 description = "Emit a `BloomCompositeMode` enum expression.",
5054 emit = None
5055)]
5056#[instrument(skip_all)]
5057async fn bloom_composite_mode(
5058 p: BevyBloomCompositeModeParams,
5059) -> Result<CallToolResult, ErrorData> {
5060 ok_source(p.emit_code().to_string())
5061}
5062
5063#[elicit_tool(
5064 plugin = "bevy_render",
5065 name = "bloom_settings",
5066 description = "Emit a Bevy 0.18 `Bloom` value, starting from an optional preset and overriding common fields.",
5067 emit = None
5068)]
5069#[instrument(skip_all)]
5070async fn bloom_settings(p: BevyBloomSettingsParams) -> Result<CallToolResult, ErrorData> {
5071 validate_bloom_settings(&p)?;
5072 ok_source(p.emit_code().to_string())
5073}
5074
5075#[elicit_tool(
5076 plugin = "bevy_render",
5077 name = "sprite",
5078 description = "Emit a current Bevy `Sprite` literal with image, tint, flips, and optional custom size.",
5079 emit = None
5080)]
5081#[instrument(skip_all)]
5082async fn sprite(p: BevySpriteParams) -> Result<CallToolResult, ErrorData> {
5083 validate_sprite(&p)?;
5084 ok_source(p.emit_code().to_string())
5085}
5086
5087#[elicit_tool(
5088 plugin = "bevy_render",
5089 name = "text_style",
5090 description = "Emit the current Bevy text-style component tuple: `TextFont`, `TextColor`, and `TextLayout`.",
5091 emit = None
5092)]
5093#[instrument(skip_all)]
5094async fn text_style(p: BevyTextStyleParams) -> Result<CallToolResult, ErrorData> {
5095 validate_text_style(&p)?;
5096 ok_source(p.emit_code().to_string())
5097}
5098
5099#[elicit_tool(
5100 plugin = "bevy_render",
5101 name = "ssao_quality",
5102 description = "Emit a `ScreenSpaceAmbientOcclusionQualityLevel` enum expression, including custom slice/sample counts.",
5103 emit = None
5104)]
5105#[instrument(skip_all)]
5106async fn ssao_quality(p: BevySsaoQualityParams) -> Result<CallToolResult, ErrorData> {
5107 validate_ssao_quality(&p)?;
5108 ok_source(p.emit_code().to_string())
5109}
5110
5111#[elicit_tool(
5112 plugin = "bevy_render",
5113 name = "ssao",
5114 description = "Emit a `ScreenSpaceAmbientOcclusion` component literal for Bevy 0.18.",
5115 emit = None
5116)]
5117#[instrument(skip_all)]
5118async fn ssao(p: BevySsaoParams) -> Result<CallToolResult, ErrorData> {
5119 validate_ssao(&p)?;
5120 ok_source(p.emit_code().to_string())
5121}
5122
5123#[elicit_tool(
5124 plugin = "bevy_render",
5125 name = "temporal_anti_aliasing",
5126 description = "Emit the current Bevy 0.18 `TemporalAntiAliasing` component literal.",
5127 emit = None
5128)]
5129#[instrument(skip_all)]
5130async fn temporal_anti_aliasing(
5131 p: BevyTemporalAntiAliasingParams,
5132) -> Result<CallToolResult, ErrorData> {
5133 validate_temporal_anti_aliasing(&p)?;
5134 ok_source(p.emit_code().to_string())
5135}
5136
5137#[elicit_tool(
5138 plugin = "bevy_render",
5139 name = "cascade_shadow_config",
5140 description = "Emit a `CascadeShadowConfig` expression for Bevy 0.18 directional-light shadows.",
5141 emit = None
5142)]
5143#[instrument(skip_all)]
5144async fn cascade_shadow_config(
5145 p: BevyCascadeShadowConfigParams,
5146) -> Result<CallToolResult, ErrorData> {
5147 validate_cascade_shadow_config(&p)?;
5148 ok_source(p.emit_code().to_string())
5149}
5150
5151#[elicit_tool(
5152 plugin = "bevy_render",
5153 name = "cascade_shadow_config_builder",
5154 description = "Emit a `CascadeShadowConfigBuilder` literal with optional overrides over Bevy's defaults.",
5155 emit = None
5156)]
5157#[instrument(skip_all)]
5158async fn cascade_shadow_config_builder(
5159 p: BevyCascadeShadowConfigBuilderParams,
5160) -> Result<CallToolResult, ErrorData> {
5161 validate_cascade_shadow_config_builder(&p)?;
5162 ok_source(p.emit_code().to_string())
5163}
5164
5165#[elicit_tool(
5166 plugin = "bevy_render",
5167 name = "atmosphere",
5168 description = "Emit a block expression that adds a `ScatteringMedium` asset and returns a Bevy 0.18 `Atmosphere` component.",
5169 emit = None
5170)]
5171#[instrument(skip_all)]
5172async fn atmosphere(p: BevyAtmosphereParams) -> Result<CallToolResult, ErrorData> {
5173 validate_atmosphere(&p)?;
5174 ok_source(p.emit_code().to_string())
5175}
5176
5177#[elicit_tool(
5178 plugin = "bevy_render",
5179 name = "fullscreen_material",
5180 description = "Emit `impl FullscreenMaterial` boilerplate for an existing fullscreen effect component.",
5181 emit = None
5182)]
5183#[instrument(skip_all)]
5184async fn fullscreen_material(p: BevyFullscreenMaterialParams) -> Result<CallToolResult, ErrorData> {
5185 validate_fullscreen_material(&p)?;
5186 ok_source(p.emit_code().to_string())
5187}