Implemented simulation and update function

This commit is contained in:
Verox001 2025-05-04 12:12:09 +02:00
parent 60bd8c67d6
commit 10fea1d695

View File

@ -1,5 +1,7 @@
use std::cmp::max; use std::cmp::max;
use std::sync::Arc; use std::sync::{Arc, RwLock};
use std::thread;
use std::time::Duration;
use cgmath::num_traits::ToPrimitive; use cgmath::num_traits::ToPrimitive;
use cgmath::Rotation3; use cgmath::Rotation3;
use pollster::FutureExt; use pollster::FutureExt;
@ -10,6 +12,7 @@ use winit::dpi::PhysicalSize;
use winit::event::WindowEvent; use winit::event::WindowEvent;
use winit::event_loop::{ActiveEventLoop, EventLoop}; use winit::event_loop::{ActiveEventLoop, EventLoop};
use winit::window::{Window, WindowId}; use winit::window::{Window, WindowId};
use solar_engine::{Body, Simulator};
pub async fn run() { pub async fn run() {
let event_loop = EventLoop::new().unwrap(); let event_loop = EventLoop::new().unwrap();
@ -154,6 +157,8 @@ struct State<'a> {
num_vertices: u32, num_vertices: u32,
num_indices: u32, num_indices: u32,
simulator: Arc<RwLock<Simulator>>,
} }
impl<'a> State<'a> { impl<'a> State<'a> {
@ -175,21 +180,50 @@ impl<'a> State<'a> {
let num_vertices = VERTICES.len() as u32; let num_vertices = VERTICES.len() as u32;
let num_indices = INDICES.len() as u32; let num_indices = INDICES.len() as u32;
let instances = vec![ let mut sim = Simulator::new(60.0 * 60.0 * 24.0);
RenderInstance { sim.add_body(Body {
position: cgmath::Vector3::new(0.0, 0.0, 0.0), name: "Sun".to_string(),
position: [0.0, 0.0],
velocity: [0.0, 0.0],
mass: 1.989e30,
});
sim.add_body(Body {
name: "Earth".to_string(),
position: [1.496e11, 0.0],
velocity: [0.0, 29780.0],
mass: 5.972e24,
});
let simulator = Arc::new(RwLock::new(sim));
let sim_clone = simulator.clone();
thread::spawn(move || {
loop {
{
let mut sim = sim_clone.write().unwrap();
sim.step();
}
thread::sleep(Duration::from_millis(16));
}
});
let instances = {
let sim = simulator.read().unwrap();
sim.bodies.iter().map(|b| RenderInstance {
position: cgmath::Vector3::new(
(b.position[0] / 1.496e11) as f32,
(b.position[1] / 1.496e11) as f32,
0.0,
),
rotation: cgmath::Quaternion::from_angle_z(cgmath::Deg(0.0)), rotation: cgmath::Quaternion::from_angle_z(cgmath::Deg(0.0)),
}, }).collect::<Vec<_>>()
RenderInstance { };
position: cgmath::Vector3::new(1.0, 1.0, 0.0),
rotation: cgmath::Quaternion::from_angle_z(cgmath::Deg(45.0)),
},
];
let instance_data: Vec<InstanceRaw> = instances.iter().map(RenderInstance::to_raw).collect(); let instance_data: Vec<InstanceRaw> = instances.iter().map(RenderInstance::to_raw).collect();
let instance_buffer = device.create_buffer_init(&wgpu::util::BufferInitDescriptor { let instance_buffer = device.create_buffer_init(&wgpu::util::BufferInitDescriptor {
label: Some("Instance Buffer"), label: Some("Instance Buffer"),
contents: bytemuck::cast_slice(&instance_data), contents: bytemuck::cast_slice(&instance_data),
usage: wgpu::BufferUsages::VERTEX, usage: wgpu::BufferUsages::VERTEX | wgpu::BufferUsages::COPY_DST,
}); });
Self { Self {
@ -209,6 +243,8 @@ impl<'a> State<'a> {
num_vertices, num_vertices,
num_indices, num_indices,
simulator,
} }
} }
@ -217,7 +253,17 @@ impl<'a> State<'a> {
} }
fn update(&mut self) { fn update(&mut self) {
// TODO: Update logic here let updated_instances: Vec<RenderInstance> = {
let sim = self.simulator.read().unwrap();
sim.bodies.iter().map(|b| RenderInstance {
position: cgmath::Vector3::new((b.position[0] / 1.496e11) as f32, (b.position[1] / 1.496e11) as f32, 0.0),
rotation: cgmath::Quaternion::from_angle_z(cgmath::Deg(0.0)),
}).collect()
};
let instance_data: Vec<InstanceRaw> = updated_instances.iter().map(RenderInstance::to_raw).collect();
self.queue.write_buffer(&self.instance_buffer, 0, bytemuck::cast_slice(&instance_data));
self.instances = updated_instances;
} }
fn create_index_buffer(device: &Device) -> wgpu::Buffer { fn create_index_buffer(device: &Device) -> wgpu::Buffer {
@ -380,12 +426,14 @@ impl<'a> State<'a> {
occlusion_query_set: None, occlusion_query_set: None,
timestamp_writes: None, timestamp_writes: None,
}); });
render_pass.set_pipeline(&self.render_pipeline); render_pass.set_pipeline(&self.render_pipeline);
render_pass.set_vertex_buffer(0, self.vertex_buffer.slice(..)); render_pass.set_vertex_buffer(0, self.vertex_buffer.slice(..));
render_pass.set_vertex_buffer(1, self.instance_buffer.slice(..));
render_pass.set_index_buffer(self.index_buffer.slice(..), wgpu::IndexFormat::Uint16); render_pass.set_index_buffer(self.index_buffer.slice(..), wgpu::IndexFormat::Uint16);
render_pass.draw_indexed(0..self.num_indices, 0, 0..self.instances.len() as u32); if !self.instances.is_empty() {
render_pass.set_vertex_buffer(1, self.instance_buffer.slice(..));
render_pass.draw_indexed(0..self.num_indices, 0, 0..self.instances.len() as u32);
}
} }
self.queue.submit(std::iter::once(encoder.finish())); self.queue.submit(std::iter::once(encoder.finish()));