diff options
author | curly <curlybryce@protonmail.com> | 2022-08-19 14:45:00 -0600 |
---|---|---|
committer | curly <curlybryce@protonmail.com> | 2022-08-19 14:45:00 -0600 |
commit | 5d8e223d26f272323c554b61df0f5575060a30ac (patch) | |
tree | 6991c550c1c3e931d240a54797c65178e73ec000 /src | |
parent | f0d5ddacfc97f0e88e3a7c445f890a76fabe47c7 (diff) | |
download | tetris-5d8e223d26f272323c554b61df0f5575060a30ac.tar.gz tetris-5d8e223d26f272323c554b61df0f5575060a30ac.tar.bz2 tetris-5d8e223d26f272323c554b61df0f5575060a30ac.zip |
Diffstat (limited to 'src')
-rw-r--r-- | src/input.rs | 124 | ||||
-rw-r--r-- | src/lib.rs | 98 | ||||
-rw-r--r-- | src/tetris/piece.rs | 33 |
3 files changed, 201 insertions, 54 deletions
diff --git a/src/input.rs b/src/input.rs new file mode 100644 index 0000000..874b327 --- /dev/null +++ b/src/input.rs @@ -0,0 +1,124 @@ +use sfml::window::{Event, Key}; + +#[derive(Debug)] +pub enum Action { + Left, + Right, + Down, + RotateLeft, + RotateRight, + Quit, + LostFocus, + GainedFocus, +} + +pub struct Actions { + left: bool, + right: bool, + down: bool, + rotate_left: bool, + rotate_right: bool, + quit: bool, + lost_focus: bool, + gained_focus: bool, +} +impl Actions { + pub fn new() -> Actions { + Actions{ + left: false, + right: false, + down: false, + rotate_left: false, + rotate_right: false, + quit: false, + lost_focus: false, + gained_focus: false, + } + } + + pub fn set(&mut self, a: Action, b: bool) { + match a { + Action::Left => self.left = b, + Action::Right => self.right = b, + Action::Down => self.down = b, + Action::RotateLeft => self.rotate_left = b, + Action::RotateRight => self.rotate_right = b, + Action::Quit => self.quit = b, + Action::LostFocus => self.lost_focus = b, + Action::GainedFocus => self.gained_focus = b, + } + } + pub fn get(&self, a: Action) -> &bool { + match a { + Action::Left => &self.left, + Action::Right => &self.right, + Action::Down => &self.down, + Action::RotateLeft => &self.rotate_left, + Action::RotateRight => &self.rotate_right, + Action::Quit => &self.quit, + Action::LostFocus => &self.lost_focus, + Action::GainedFocus => &self.gained_focus, + } + } +} + +pub struct Input { + window: Option<Event>, + actions: Actions, +} +impl Input { + pub fn new() -> Input { + Input { + window: None, + actions: Actions::new(), + } + } + + pub fn process(&mut self, events: Option<Event>) { + self.window = events; + self.match_actions(); + } + + + fn match_actions(&mut self) { + let x = match self.window { + Some(Event::KeyPressed {code: c, alt: _, ctrl: _, shift: _, system: _}) => Some((c, true)), + Some(Event::KeyReleased {code: c, alt: _, ctrl: _, shift: _, system: _}) => Some((c, false)), + Some(Event::Closed) => {self.set_action(Action::Quit, true); None}, + Some(Event::LostFocus) => {self.set_action(Action::LostFocus, true); self.set_action(Action::GainedFocus, false); None}, + Some(Event::GainedFocus) => {self.set_action(Action::GainedFocus, true); self.set_action(Action::LostFocus, false); None}, + _ => None + }; + match x { + Some((Key::A, n)) => self.set_action(Action::Left, n), + Some((Key::S, n)) => self.set_action(Action::Down, n), + Some((Key::D, n)) => self.set_action(Action::Right, n), + Some((Key::Q, n)) => self.set_action(Action::RotateLeft, n), + Some((Key::E, n)) => self.set_action(Action::RotateRight, n), + Some((Key::Escape, n)) => self.set_action(Action::Quit, n), + _ => (), + } + } + + pub fn set_action(&mut self, a: Action, b: bool) { + self.actions.set(a, b); + } + + pub fn get_action(&self, a: Action) -> &bool { + self.actions.get(a) + + } + + pub fn get_iter(&self) -> Vec<Action> { + let mut vec = vec![]; + if self.get_action(Action::Left) == &true {vec.push(Action::Left)} + if self.get_action(Action::Down) == &true {vec.push(Action::Down)} + if self.get_action(Action::Right) == &true {vec.push(Action::Right)} + if self.get_action(Action::RotateLeft) == &true {vec.push(Action::RotateLeft)} + if self.get_action(Action::RotateRight) == &true {vec.push(Action::RotateRight)} + if self.get_action(Action::Quit) == &true {vec.push(Action::Quit)} + if self.get_action(Action::LostFocus) == &true {vec.push(Action::LostFocus)} + if self.get_action(Action::GainedFocus) == &true {vec.push(Action::GainedFocus)} + return vec + } +}
\ No newline at end of file @@ -1,13 +1,15 @@ mod tetris; +mod input; use crate::tetris::piece; +use crate::input::Action; use std::time::{Instant, Duration}; use rand::Rng; // SFML -use sfml::window::{Style, Event, ContextSettings, Key}; -use sfml::graphics::{self, *}; +use sfml::window::{Style, ContextSettings}; +use sfml::graphics::*; use sfml::system::{Vector2f, Vector2u}; pub struct Game { @@ -16,22 +18,22 @@ pub struct Game { maxfps: u64, window_geometry: (u32, u32), window: RenderWindow, + input: input::Input, score: u64, } impl Game { pub fn new() -> Game { - let maxfps = 30; - let geometry = (480, 480); - // Window setup let mut context_settings: ContextSettings = Default::default(); context_settings.antialiasing_level = 0; + let mut window = RenderWindow::new( + (480, 480), + "Test", + Style::DEFAULT, + &context_settings); - let mut window = graphics::RenderWindow::new( - geometry, - "Test", - Style::DEFAULT, - &context_settings); + let maxfps = 30; + let geometry = (480, 480); window.set_framerate_limit(maxfps); window.set_key_repeat_enabled(false); @@ -51,6 +53,7 @@ impl Game { maxfps: 30, window_geometry: geometry, window: window, + input: input::Input::new(), score: 0, } } @@ -84,13 +87,25 @@ impl Game { fn pause(&mut self) { loop { - match self.window.wait_event() { - Some(Event::GainedFocus) => break, - _ => () - } + self.process_inputs(); + if *self.input.get_action(Action::GainedFocus) {break} } } + fn process_inputs(&mut self) { + let mut poll = self.window.poll_event(); + while poll != None { + self.input.process(poll); + poll = self.window.poll_event(); + } + } + + fn reset(&mut self) -> tetris::Tetris { + println!("{}", self.get_score()); + self.set_score(0); + tetris::Tetris::new() + } + // The actual game loop pub fn game_loop(&mut self) { // Textures @@ -130,28 +145,30 @@ impl Game { let mut tetris = tetris::Tetris::new(); let mut piece = piece::Piece::random(piece::Pos(-2,3)); let mut next_piece = piece::Piece::random(piece::Pos(3,13)); - let mut key = None; + 'main: loop { // Clear everything from display self.window.clear(Color::rgb(0,0,0)); + self.process_inputs(); + // Process events - for x in self.window.poll_event() { - match x { - Event::Closed => break 'main, - Event::Resized {width: w, height: h} => self.set_geometry((w, h)), - Event::LostFocus => self.pause(), - Event::KeyPressed {code: c, ctrl: _, alt: _, shift: _, system: _} => key = Some(c), - Event::KeyReleased {code: _, ctrl: _, alt: _, shift: _, system: _} => key = None, - _ => (), - }; - } + // for x in self.window.poll_event() { + // match x { + // Event::Closed => break 'main, + // Event::Resized {width: w, height: h} => self.set_geometry((w, h)), + // Event::LostFocus => self.pause(), + // Event::KeyPressed {code: c, ctrl: _, alt: _, shift: _, system: _} => key = Some(c), + // Event::KeyReleased {code: _, ctrl: _, alt: _, shift: _, system: _} => key = None, + // _ => (), + // }; + // } // Check if piece is dead if piece.is_alive() == false { if piece.apply_to_grid(&mut tetris) == false { // Game has been lost - break + tetris = self.reset(); } piece = next_piece; piece.set_pos(tetris::piece::Pos(-2, 3)); @@ -186,27 +203,32 @@ impl Game { // Reset the clock fpscap = Instant::now(); - // Process keys // Limited keys if key_count == 0 { - match key { - Some(Key::A) => {piece.r#move(tetris::piece::Dir::Left, &tetris)}, - Some(Key::D) => {piece.r#move(tetris::piece::Dir::Right, &tetris)}, - _ => () + for action in self.input.get_iter() { + match action { + Action::Left => piece.r#move(tetris::piece::Dir::Left, &tetris), + Action::Right => piece.r#move(tetris::piece::Dir::Right, &tetris), + _ => () + } } } //Process keys // Unlimited keys - match key { - Some(Key::S) => piece.r#move(tetris::piece::Dir::Down, &tetris), - Some(Key::Q) => {piece.rotate(tetris::piece::Rotate::Left, &tetris); key = None}, - Some(Key::E) => {piece.rotate(tetris::piece::Rotate::Right, &tetris); key = None}, - Some(Key::Escape) => break, - _ => () + for action in self.input.get_iter() { + match action { + Action::RotateLeft => {piece.rotate(tetris::piece::Rotate::Left, &tetris); self.input.set_action(Action::RotateLeft, false)}, + Action::RotateRight => {piece.rotate(tetris::piece::Rotate::Right, &tetris); self.input.set_action(Action::RotateRight, false)}, + Action::Down => piece.r#move(tetris::piece::Dir::Down, &tetris), + Action::Quit => break 'main, + Action::LostFocus => self.pause(), + _ => () + } } + // Make the limit feel good - if key != None { + if *self.input.get_action(Action::Left) != false || *self.input.get_action(Action::Right) != false { key_count += 1; } else { key_count = 0; diff --git a/src/tetris/piece.rs b/src/tetris/piece.rs index 19e8e6c..fc7d1c7 100644 --- a/src/tetris/piece.rs +++ b/src/tetris/piece.rs @@ -198,16 +198,20 @@ impl Piece { for pos in self.get_bits_pos() { let new_pos = pos + dir.get(); - // Detect blocks and kill only if Dir is down - if grid.get_grid_pos(new_pos) == 1 && *dir == Dir::Down { - self.kill(); - return Err(()) - } else if grid.get_grid_pos(new_pos) == 1 { - return Err(()) - } else if new_pos.0 > 19 { // Detect bottom and kill - self.kill(); - return Err(()) - } else if new_pos.1 > 9 || new_pos.1 < 0 { // Detect sides + if self.is_alive() { + // Detect blocks and kill only if Dir is down + if grid.get_grid_pos(new_pos) == 1 && *dir == Dir::Down { + self.kill(); + return Err(()) + } else if grid.get_grid_pos(new_pos) == 1 { + return Err(()) + } else if new_pos.0 > 19 { // Detect bottom and kill + self.kill(); + return Err(()) + } else if new_pos.1 > 9 || new_pos.1 < 0 { // Detect sides + return Err(()) + } + } else { return Err(()) } } @@ -315,15 +319,12 @@ impl Piece { self.alive = false } - // Return false if the piece cannot move pub fn r#move(&mut self, dir: Dir, grid: &Tetris) { // If a hit is detected, don't move // Otherwise move - if self.is_alive() { - match self.hit_detect(&dir, &grid) { - Ok(_) => self.apply_dir(&dir), - Err(_) => (), - } + match self.hit_detect(&dir, &grid) { + Ok(_) => self.apply_dir(&dir), + Err(_) => (), } } }
\ No newline at end of file |