use strafesnet_graphics::setup;

const LIMITS:wgpu::Limits=wgpu::Limits::defaults();

fn create_window(title:&str,event_loop:&winit::event_loop::EventLoop<()>)->Result<winit::window::Window,winit::error::OsError>{
	let mut attr=winit::window::WindowAttributes::default();
	attr=attr.with_title(title);
	event_loop.create_window(attr)
}

pub async fn setup_and_start(title:&str){
	let event_loop=winit::event_loop::EventLoop::new().unwrap();

	let window=create_window(title,&event_loop).unwrap();

	println!("Initializing the surface...");

	let desc=wgpu::InstanceDescriptor::new_with_display_handle_from_env(Box::new(event_loop.owned_display_handle()));
	let instance=wgpu::Instance::new(desc);

	let surface=setup::step2::create_surface(&instance,&window).unwrap();

	let adapter=setup::step3::pick_adapter(&instance,&surface).await.expect("No suitable GPU adapters found on the system!");

	let adapter_info=adapter.get_info();
	println!("Using {} ({:?})",adapter_info.name,adapter_info.backend);

	let (device,queue)=setup::step4::request_device(&adapter,LIMITS).await.unwrap();

	let size=window.inner_size();
	let surface=setup::step5::configure_surface(&adapter,&device,surface,(size.width,size.height)).unwrap();

	//dedicated thread to ping request redraw back and resize the window doesn't seem logical

	//the thread that spawns the physics thread
	let mut window_thread=crate::window::worker(
		&window,
		device,
		queue,
		surface,
		LIMITS,
	);

	for arg in std::env::args().skip(1){
		window_thread.send(strafesnet_common::instruction::TimedInstruction{
			time:strafesnet_common::integer::Time::ZERO,
			instruction:crate::window::Instruction::WindowEvent(winit::event::WindowEvent::DroppedFile(arg.into())),
		}).unwrap();
	};

	println!("Entering event loop...");
	let mut app=crate::app::App::new(
		std::time::Instant::now(),
		window_thread
	);
	event_loop.run_app(&mut app).unwrap();
}
