1use log::error;
2use pixels::{Error, Pixels, SurfaceTexture};
3use winit::dpi::LogicalSize;
4use winit::event::{Event, VirtualKeyCode};
5use winit::event_loop::{ControlFlow, EventLoop};
6use winit::window::WindowBuilder;
7use winit_input_helper::WinitInputHelper;
8pub struct StateBW {
12 pub active: Vec<bool>,width: u32,
14 height: u32,
15}
16impl StateBW {
17 fn new(width: u32, height: u32) -> StateBW {
18 StateBW{ active: vec![true; width as usize*height as usize], width: width, height: height}
19 }
20 fn draw(&self, frame: &mut [u8]) {
22 for (i, pixel) in frame.chunks_exact_mut(4).enumerate() {
23 let rgba = if self.active[i] {
24 [0xFF, 0xFF, 0xFF, 0xFF]
25 } else {
26 [0x00, 0x00, 0x00, 0x00]
27 };
28 pixel.copy_from_slice(&rgba);
29 }
30 }
31 pub fn get(&self, x: u32, y: u32) -> bool {
33 self.active[ (y*self.width + x) as usize ]
34 }
35 pub fn set(&mut self, x: u32, y: u32, new: bool) {
37 self.active[ (y*self.width + x) as usize ] = new;
38 }
39 pub fn switch(&mut self, x: u32, y: u32) {
41 self.active[ (y*self.width + x) as usize ] = !self.get(x, y);
42 }
43}
44
45pub struct WinBW {
46 width: u32,
47 height: u32,
48}
49
50impl WinBW {
51 pub fn new(width: u32, height: u32) -> WinBW {
52 WinBW{width: width, height: height}
53 }
54 pub fn run<T>(&mut self, looper: &'static (dyn for<'r, 's> Fn(&'r mut StateBW, &'s mut T) + 'static), mut state_manager: T , fps: u64) -> Result<(), Error> {
60 env_logger::init();
61 let event_loop = EventLoop::new();
62 let mut input = WinitInputHelper::new();
63 let window = {
64 let size = LogicalSize::new(self.width as f64, self.height as f64);
65 WindowBuilder::new()
66 .with_title("Emulator")
67 .with_inner_size(size)
68 .with_min_inner_size(size)
69 .build(&event_loop)
70 .unwrap()
71 };
72
73 let mut pixels = {
74 let window_size = window.inner_size();
75 let surface_texture = SurfaceTexture::new(window_size.width, window_size.height, &window);
76 Pixels::new(self.width, self.height, surface_texture)?
77 };
78
79 let mut world = StateBW::new(self.width, self.height);
80
81 event_loop.run(move |event, _, control_flow| {
84
85 if let Event::RedrawRequested(_) = event {
89 world.draw(pixels.get_frame());
90 if pixels
91 .render()
92 .map_err(|e| error!("pixels.render() failed: {}", e))
93 .is_err()
94 {
95 *control_flow = ControlFlow::Exit;
96 return;
97 }
98 }
99
100 if input.update(&event) {
102
103 if input.key_pressed(VirtualKeyCode::Escape) || input.quit() {
104 *control_flow = ControlFlow::Exit;
105 return;
106 }
107
108 if let Some(size) = input.window_resized() {
109 pixels.resize_surface(size.width, size.height);
110 }
111
112 looper(&mut world, &mut state_manager);
113 window.request_redraw();
114
115 }
116
117 });
118 }
119}