fix zoom, rework chunkmap events
This commit is contained in:
+7
-8
@@ -3,7 +3,6 @@ use bevy::input::mouse::{MouseScrollUnit, MouseWheel};
|
||||
use bevy::prelude::*;
|
||||
use bevy::render::camera::{OrthographicProjection, Projection};
|
||||
|
||||
use crate::constants::TILE_SIZE;
|
||||
use crate::{game, tilemap};
|
||||
|
||||
#[derive(Component)]
|
||||
@@ -81,10 +80,10 @@ pub fn spawn_panning_camera(mut commands: Commands) {
|
||||
}
|
||||
|
||||
pub fn scroll_events(mut evr_scroll: EventReader<MouseWheel>, mut query: Query<&mut Projection>) {
|
||||
const ZOOM_SENSITIVITY: f32 = 0.035;
|
||||
const LINE_SENSITIVITY: f32 = 0.035;
|
||||
const PIXEL_SENSITIVITY: f32 = 0.001;
|
||||
const MIN_SCALE: f32 = 0.2;
|
||||
const MAX_SCALE: f32 = 2.0;
|
||||
const MIN_SCALE: f32 = 0.3;
|
||||
const MAX_SCALE: f32 = 1.75;
|
||||
|
||||
for ev in evr_scroll.read() {
|
||||
for mut projection_component in query.iter_mut() {
|
||||
@@ -97,14 +96,14 @@ pub fn scroll_events(mut evr_scroll: EventReader<MouseWheel>, mut query: Query<&
|
||||
};
|
||||
|
||||
let new_scale = match ev.unit {
|
||||
MouseScrollUnit::Line => current_scale + ev.y * ZOOM_SENSITIVITY,
|
||||
MouseScrollUnit::Pixel => current_scale + ev.y * PIXEL_SENSITIVITY,
|
||||
MouseScrollUnit::Line => current_scale + ev.y * LINE_SENSITIVITY, // win, x11
|
||||
MouseScrollUnit::Pixel => current_scale + ev.y * PIXEL_SENSITIVITY, // macos, wayland
|
||||
};
|
||||
|
||||
|
||||
*projection_component = Projection::Orthographic(OrthographicProjection {
|
||||
scale: new_scale.max(MIN_SCALE).min(MAX_SCALE),
|
||||
..OrthographicProjection::default_2d()
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+3
-3
@@ -435,13 +435,13 @@ pub fn spawn_citizens(mut commands: Commands, asset_server: Res<AssetServer>) {
|
||||
let mut rng = rand::rng();
|
||||
|
||||
// Spawn a handful of citizens
|
||||
for _ in 0..100 {
|
||||
for _ in 0..10 {
|
||||
let cit = commands
|
||||
.spawn(Citizen::new(
|
||||
&asset_server,
|
||||
Vec3::new(
|
||||
rng.random_range(-25.0f32..25.0f32).round(),
|
||||
rng.random_range(-25.0f32..25.0f32).round(),
|
||||
rng.random_range(-8.0f32..8.0f32).round(),
|
||||
rng.random_range(-8.0f32..8.0f32).round(),
|
||||
35.0,
|
||||
) * TILE_SIZE,
|
||||
))
|
||||
|
||||
+48
-33
@@ -25,7 +25,7 @@ pub const SEED: u32 = 420;
|
||||
|
||||
#[derive(Resource)]
|
||||
pub struct ChunkMap {
|
||||
pub loaded_chunks: HashMap<IVec2, bool>,
|
||||
pub loaded_chunks: HashMap<IVec2, (bool, i32)>,
|
||||
}
|
||||
|
||||
impl Default for ChunkMap {
|
||||
@@ -193,18 +193,44 @@ pub fn generate_surface_terrain(x: i32, y: i32) -> f32 {
|
||||
(noise_value * 2.5) as f32
|
||||
}
|
||||
|
||||
fn chunkmap_despawn_timer_system(
|
||||
mut chunk_map: ResMut<ChunkMap>,
|
||||
mut cwss: ResMut<CurrentWorldSpriteState>,
|
||||
) {
|
||||
for (_, (is_loaded, timer)) in chunk_map.loaded_chunks.iter_mut() {
|
||||
if !*is_loaded {
|
||||
continue;
|
||||
}
|
||||
if *timer > 0 {
|
||||
*timer -= 1;
|
||||
} else {
|
||||
//TODO - remove chunk from chunkmap
|
||||
|
||||
*is_loaded = false;
|
||||
cwss.state = TerrainSpriteState::WaitingForRender;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn handle_chunk_events(
|
||||
mut chunk_events: EventReader<GenerateChunkEvent>,
|
||||
mut chunk_map: ResMut<ChunkMap>,
|
||||
mut terrain_event_writer: EventWriter<ChunkTerrainEvent>,
|
||||
mut weathering_event_writer: EventWriter<ChunkWeatheringAndPrecipitationEvent>,
|
||||
mut foliage_event_writer: EventWriter<ChunkFoliageEvent>,
|
||||
mut fauna_event_writer: EventWriter<ChunkFaunaEvent>,
|
||||
mut cwss: ResMut<CurrentWorldSpriteState>,
|
||||
) {
|
||||
let count = chunk_events.len();
|
||||
// Fire each terrain pass. They will all fire sequentially.
|
||||
for event in chunk_events.read() {
|
||||
let chunk_pos = event.chunk_position;
|
||||
let mut any = false;
|
||||
for event in chunk_events.par_read() {
|
||||
let chunk_pos = event.0.chunk_position;
|
||||
if let Some((true, _)) = chunk_map.loaded_chunks.get(&chunk_pos) {
|
||||
continue;
|
||||
}
|
||||
any = true;
|
||||
let chunk_map_updates: Mutex<HashMap<IVec2, bool>> = Mutex::new(HashMap::new());
|
||||
// Mark chunk as loaded in our thread-safe collection
|
||||
chunk_map_updates.lock().unwrap().insert(chunk_pos, true);
|
||||
terrain_event_writer.write(ChunkTerrainEvent {
|
||||
chunk_position: chunk_pos,
|
||||
});
|
||||
@@ -217,8 +243,12 @@ fn handle_chunk_events(
|
||||
fauna_event_writer.write(ChunkFaunaEvent {
|
||||
chunk_position: chunk_pos,
|
||||
});
|
||||
// Apply all collected updates to the actual resources
|
||||
for (chunk_pos, value) in chunk_map_updates.into_inner().unwrap() {
|
||||
chunk_map.loaded_chunks.insert(chunk_pos, (value, 1800));
|
||||
}
|
||||
}
|
||||
if count > 0 {
|
||||
if any {
|
||||
cwss.state = TerrainSpriteState::WaitingForRender;
|
||||
}
|
||||
}
|
||||
@@ -226,36 +256,23 @@ fn handle_chunk_events(
|
||||
fn generate_chunk_terrain(
|
||||
commands: ParallelCommands<'_, '_>, // Use ParallelCommands for parallel spawning
|
||||
mut events: EventReader<ChunkTerrainEvent>,
|
||||
mut chunk_map: ResMut<ChunkMap>,
|
||||
mut tilemap: ResMut<TileMap>,
|
||||
mut forrestry_event_writer: EventWriter<ChunkForrestryEvent>,
|
||||
mut occlusion_event_writer: EventWriter<TileOcclusionEvent>,
|
||||
) {
|
||||
let is_empty = events.is_empty();
|
||||
let start = Instant::now();
|
||||
let count = events.len();
|
||||
let count: usize = events.len();
|
||||
|
||||
let cave_noise = Perlin::new(SEED);
|
||||
|
||||
// Create mutexes for our shared resources
|
||||
let chunk_map_updates = Mutex::new(HashMap::new());
|
||||
let tilemap_updates = Mutex::new(HashMap::new());
|
||||
let forrestry_events = Mutex::new(Vec::new());
|
||||
|
||||
events.par_read().for_each(|event| {
|
||||
let chunk_pos = event.chunk_position;
|
||||
|
||||
// Check if chunk is already loaded - using a local check first to avoid locking
|
||||
{
|
||||
let chunk_map_guard = chunk_map.loaded_chunks.get(&chunk_pos);
|
||||
if let Some(true) = chunk_map_guard {
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// Mark chunk as loaded in our thread-safe collection
|
||||
chunk_map_updates.lock().unwrap().insert(chunk_pos, true);
|
||||
|
||||
let start_x = chunk_pos.x * CHUNK_SIZE;
|
||||
let start_y = chunk_pos.y * CHUNK_SIZE;
|
||||
|
||||
@@ -356,11 +373,6 @@ fn generate_chunk_terrain(
|
||||
});
|
||||
});
|
||||
|
||||
// Apply all collected updates to the actual resources
|
||||
for (chunk_pos, value) in chunk_map_updates.into_inner().unwrap() {
|
||||
chunk_map.loaded_chunks.insert(chunk_pos, value);
|
||||
}
|
||||
|
||||
for (pos, data) in tilemap_updates.into_inner().unwrap() {
|
||||
tilemap.floor_tiles.insert(pos, data);
|
||||
occlusion_event_writer.write(TileOcclusionEvent { tile_position: pos });
|
||||
@@ -623,14 +635,17 @@ impl Plugin for TilemapPlugin {
|
||||
.add_systems(
|
||||
FixedUpdate,
|
||||
(
|
||||
handle_chunk_events,
|
||||
generate_chunk_terrain,
|
||||
generate_chunk_weathering_and_precipitation,
|
||||
generate_chunk_forrestry,
|
||||
generate_chunk_foliage,
|
||||
generate_chunk_fauna,
|
||||
)
|
||||
.chain(),
|
||||
(
|
||||
handle_chunk_events,
|
||||
generate_chunk_terrain,
|
||||
generate_chunk_weathering_and_precipitation,
|
||||
generate_chunk_forrestry,
|
||||
generate_chunk_foliage,
|
||||
generate_chunk_fauna,
|
||||
)
|
||||
.chain(),
|
||||
chunkmap_despawn_timer_system,
|
||||
),
|
||||
)
|
||||
.add_systems(
|
||||
Update,
|
||||
|
||||
Reference in New Issue
Block a user