use bevy::{pbr::{ExtendedMaterial, MaterialExtension}, prelude::*, render::render_resource::{AsBindGroup, ShaderRef}}; fn main() { App::new() .add_plugins(DefaultPlugins) .add_plugins(MaterialPlugin::::default()) .insert_resource(Speed(0.3)) .add_systems(Startup, init) .add_systems(Update, add_shadows) .add_systems(Update, process_material) .add_systems(Update, rotate_monkey) .run(); } fn init( server: Res, mut meshes: ResMut>, mut monkey_materials: ResMut>, mut commands: Commands ) { commands.spawn(SceneBundle { scene: server.load("models/shadow-example.gltf#Scene0"), ..default() }); commands.spawn(MaterialMeshBundle { mesh: meshes.add(Sphere::new(1.0)), transform: Transform::from_xyz(0.0, 0.5, 0.0), material: monkey_materials.add(ExtendedMaterial { base: StandardMaterial { base_color: Color::RED.into(), alpha_mode: AlphaMode::Mask(1.0), ..Default::default() }, extension: MonkeyMaterialExtension { percentage: 0.5 }, }), ..default() }); } fn add_shadows( mut lights: Query<(Entity, &mut PointLight), Added>, mut commands: Commands, ) { lights.iter_mut().for_each(|(e, mut l)| { info!("Fixing up shadows"); l.shadows_enabled = true; let config: bevy::pbr::CascadeShadowConfig = bevy::pbr::CascadeShadowConfigBuilder { ..default() }.into(); commands.entity(e).insert(config); }); } type MonkeyMaterial = ExtendedMaterial; #[derive(Asset, AsBindGroup, Reflect, Debug, Clone)] struct MonkeyMaterialExtension { #[uniform(100)] percentage: f32, } impl MaterialExtension for MonkeyMaterialExtension { fn fragment_shader() -> ShaderRef { "shaders/dissolve.wgsl".into() } fn deferred_fragment_shader() -> ShaderRef { "shaders/dissolve.wgsl".into() } } fn process_material( query: Query<(Entity, &Handle, &Name), Added>>, base_materials: Res>, mut monkey_materials: ResMut>, mut commands: Commands, ) { query.iter().for_each(|(e, h, n)| { info!("Extended Materials"); let mut base = base_materials.get(h).unwrap().clone(); base.alpha_mode = AlphaMode::Mask(1.0); // base.base_color = base.base_color.clone().with_a(0.0); let extension = MonkeyMaterialExtension { percentage: 0.5 }; let monkey_material = monkey_materials.add( ExtendedMaterial { base, extension } ); commands .entity(e) .remove::>() .insert(monkey_material); }) } #[derive(Resource)] struct Speed(f32); fn rotate_monkey( mut query: Query<(&mut Transform, &Name)>, time: Res