use bevy::{ input::mouse::{MouseScrollUnit, MouseWheel}, prelude::*, }; use crate::{ client::starfield::{BACK_STARFIELD_SIZE, FRONT_STARFIELD_SIZE, MID_STARFIELD_SIZE, StarfieldSize}, ecs::{MainCamera, Me, OrbitCamera, StarfieldBack, StarfieldFront, StarfieldMid, StarguideOrbit} }; use crate::ecs::{StarguideCamera, GameplayState}; pub fn zoom_plugin(app: &mut App) { app.add_systems(Update, on_scroll); } fn on_scroll( mut scroll_events: MessageReader, gameplay_state: Res>, mut gameplay_next_state: ResMut>, window: Single<&Window>, starfield_back: Single< (&mut Sprite, &mut Transform, &mut Visibility, Option<&StarfieldSize>), ( With, Without, Without, ), >, starfield_mid: Single< (&mut Sprite, &mut Transform, &mut Visibility, Option<&StarfieldSize>), ( With, Without, Without, ), >, starfield_front: Single< (&mut Sprite, &mut Transform, &mut Visibility, Option<&StarfieldSize>), ( With, Without, Without, ), >, mut starguide_camera: Single< (&mut Camera, &mut Transform), ( With, Without, Without, Without, Without, Without, ), >, mut orbit_camera: Single< &mut Camera, ( With, Without, Without, Without, Without, Without, Without, ), >, mut camera: Single< (&mut Camera, &mut Transform), ( With, Without, Without, Without, Without, Without, Without, ), >, player: Single< &Transform, ( With, Without, Without, Without, Without, ), >, ) { let (mut starfield_back, mut starfield_back_pos, mut visibility_back, size_back) = starfield_back.into_inner(); let (mut starfield_mid, mut starfield_mid_pos, mut visibility_mid, size_mid) = starfield_mid.into_inner(); let (mut starfield_front, mut starfield_front_pos, mut visibility_front, size_front) = starfield_front.into_inner(); for event in scroll_events.read() { match event.unit { MouseScrollUnit::Line | MouseScrollUnit::Pixel => { if event.y > 0.0 { camera.1.scale *= 0.97; starguide_camera.1.scale *= 0.97; } else { camera.1.scale *= 1.03; starguide_camera.1.scale *= 1.03; } if camera.1.scale.z > 20.0 && matches!(gameplay_state.get(), GameplayState::Main) { camera.0.is_active = false; starguide_camera.0.is_active = true; orbit_camera.is_active = true; starguide_camera.1.translation = player.translation; gameplay_next_state.set(GameplayState::Starguide); starfield_back.image_mode = SpriteImageMode::Auto; starfield_mid.image_mode = SpriteImageMode::Auto; starfield_front.image_mode = SpriteImageMode::Auto; *visibility_back = Visibility::Hidden; *visibility_mid = Visibility::Hidden; *visibility_front = Visibility::Hidden; } else if camera.1.scale.z <= 20.0 && matches!(gameplay_state.get(), GameplayState::Starguide) { camera.0.is_active = true; gameplay_next_state.set(GameplayState::Main); starguide_camera.0.is_active = false; orbit_camera.is_active = false; if matches!(*visibility_back, Visibility::Hidden) { if let Some(size_back) = size_back { starfield_back.image_mode = SpriteImageMode::Tiled { tile_x: true, tile_y: true, stretch_value: size_back.0, }; } if let Some(size_mid) = size_mid { starfield_mid.image_mode = SpriteImageMode::Tiled { tile_x: true, tile_y: true, stretch_value: size_mid.0, }; } if let Some(size_front) = size_front{ starfield_front.image_mode = SpriteImageMode::Tiled { tile_x: true, tile_y: true, stretch_value: size_front.0, }; } } *visibility_back = Visibility::Inherited; *visibility_mid = Visibility::Inherited; *visibility_front = Visibility::Inherited; } starfield_back.custom_size = Some(window.size() * camera.1.scale.z + Vec2::splat(BACK_STARFIELD_SIZE * 2.0)); starfield_mid.custom_size = Some(window.size() * camera.1.scale.z + Vec2::splat(MID_STARFIELD_SIZE * 2.0)); starfield_front.custom_size = Some(window.size() * camera.1.scale.z + Vec2::splat(FRONT_STARFIELD_SIZE * 2.0)); starfield_back_pos.translation = player.translation + (-player.translation / 3.0) % BACK_STARFIELD_SIZE + (Vec3::new(window.resolution.width(), -window.resolution.height(), 0.0) * camera.1.scale.z / 2.0) % BACK_STARFIELD_SIZE + Vec3::new(0.0, BACK_STARFIELD_SIZE, 0.0) - Vec3::new(0.0, 0.0, 5.0); starfield_mid_pos.translation = player.translation + (-player.translation / 2.5) % MID_STARFIELD_SIZE + (Vec3::new(window.resolution.width(), -window.resolution.height(), 0.0) * camera.1.scale.z / 2.0) % MID_STARFIELD_SIZE + Vec3::new(0.0, MID_STARFIELD_SIZE, 0.0) - Vec3::new(0.0, 0.0, 4.5); starfield_front_pos.translation = player.translation + (-player.translation / 2.0) % FRONT_STARFIELD_SIZE + (Vec3::new(window.resolution.width(), -window.resolution.height(), 0.0) * camera.1.scale.z / 2.0) % FRONT_STARFIELD_SIZE + Vec3::new(0.0, FRONT_STARFIELD_SIZE, 0.0) - Vec3::new(0.0, 0.0, 4.0); } } } }