From 00bdd27cd070c34b0789825330f6851c4eee890c Mon Sep 17 00:00:00 2001 From: Tom Barrett Date: Sun, 31 Jan 2021 16:32:14 +0100 Subject: can now move tiles --- src/main.rs | 200 ++++++++++++++++++++++++++++++++++++++++++++++++++++++------ 1 file changed, 183 insertions(+), 17 deletions(-) diff --git a/src/main.rs b/src/main.rs index 1caa62a..888c494 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,18 +1,22 @@ use ggez; use ggez::event; use ggez::graphics::{ - self, spritebatch::SpriteBatch, DrawParam, FilterMode, Image, Rect, WrapMode, + self, spritebatch::SpriteBatch, Color, DrawMode, DrawParam, FilterMode, Image, Mesh, Rect, + StrokeOptions, WrapMode, }; -use ggez::nalgebra::{Point2, Vector2}; +use ggez::input::mouse; +use ggez::mint::{Point2, Vector2}; use rand::{ distributions::{Distribution, Standard}, Rng, }; -pub const TILE_SCALE: f32 = 3.0; +pub const TILE_SCALE: f32 = 2.0; pub const TILE_HEIGHT: f32 = 16.0; pub const TILE_WIDTH: f32 = 16.0; +pub const BORDER_SIZE: f32 = 3.0; +#[derive(Clone, Copy)] enum Occupant { None, Green, @@ -33,9 +37,12 @@ impl Distribution for Standard { } } +#[derive(Clone, Copy)] struct Cell { occupant: Occupant, position: Point2, + hover: bool, + clicked: bool, } impl Cell { @@ -43,10 +50,42 @@ impl Cell { Cell { occupant: rand::random(), position: position, + hover: false, + clicked: false, } } - pub fn draw(&self, spritebatch: &mut SpriteBatch) { + pub fn contains(&self, position: Point2) -> bool { + if position.x > self.position.x { + if position.y > self.position.y { + if position.x < self.position.x + TILE_WIDTH * TILE_SCALE { + if position.y < self.position.y + TILE_WIDTH * TILE_SCALE { + return true; + } + } + } + } + + false + } + + pub fn clicked_on(&mut self) { + self.clicked = true; + } + + pub fn clicked_off(&mut self) { + self.clicked = false; + } + + pub fn hover_on(&mut self) { + self.hover = true; + } + + pub fn hover_off(&mut self) { + self.hover = false; + } + + pub fn draw(&self, context: &mut ggez::Context, spritebatch: &mut SpriteBatch) { let source = match self.occupant { Occupant::None => None, Occupant::Green => Some(Rect::new(0.0, 0.0, 0.25, 1.0)), @@ -60,13 +99,46 @@ impl Cell { DrawParam::default() .src(source) .dest(self.position) - .scale(Vector2::new(TILE_SCALE, TILE_SCALE)), + .scale(Vector2 { + x: TILE_SCALE, + y: TILE_SCALE, + }), + ); + } + + if self.hover { + let mesh = Mesh::new_rectangle( + context, + DrawMode::Stroke(StrokeOptions::default()), + Rect::new( + self.position.x, + self.position.y, + TILE_WIDTH * TILE_SCALE, + TILE_HEIGHT * TILE_SCALE, + ), + Color::from_rgb(255, 100, 100), + ); + graphics::draw(context, &mesh.unwrap(), DrawParam::default()).unwrap(); + } + if self.clicked { + let mesh = Mesh::new_rectangle( + context, + DrawMode::Stroke(StrokeOptions::default()), + Rect::new( + self.position.x, + self.position.y, + TILE_WIDTH * TILE_SCALE, + TILE_HEIGHT * TILE_SCALE, + ), + Color::from_rgb(100, 255, 100), ); + graphics::draw(context, &mesh.unwrap(), DrawParam::default()).unwrap(); } } } struct Game { + selected: Option<(usize, usize)>, spritebatch: SpriteBatch, grid: Vec>, } @@ -81,37 +153,131 @@ impl Game { let mut y = 0.0; for _ in 0..8 { let mut column = Vec::new(); - column.push(Cell::new(Point2::new(0.0, y))); - column.push(Cell::new(Point2::new(TILE_WIDTH * TILE_SCALE, y))); - column.push(Cell::new(Point2::new(2.0 * TILE_WIDTH * TILE_SCALE, y))); - column.push(Cell::new(Point2::new(3.0 * TILE_WIDTH * TILE_SCALE, y))); - column.push(Cell::new(Point2::new(4.0 * TILE_WIDTH * TILE_SCALE, y))); - column.push(Cell::new(Point2::new(5.0 * TILE_WIDTH * TILE_SCALE, y))); - column.push(Cell::new(Point2::new(6.0 * TILE_WIDTH * TILE_SCALE, y))); - column.push(Cell::new(Point2::new(7.0 * TILE_WIDTH * TILE_SCALE, y))); - - y += TILE_HEIGHT * TILE_SCALE; + column.push(Cell::new(Point2 { x: 0.0, y: y })); + column.push(Cell::new(Point2 { + x: 1.0 * (TILE_WIDTH * TILE_SCALE + BORDER_SIZE), + y: y, + })); + column.push(Cell::new(Point2 { + x: 2.0 * (TILE_WIDTH * TILE_SCALE + BORDER_SIZE), + y: y, + })); + column.push(Cell::new(Point2 { + x: 3.0 * (TILE_WIDTH * TILE_SCALE + BORDER_SIZE), + y: y, + })); + column.push(Cell::new(Point2 { + x: 4.0 * (TILE_WIDTH * TILE_SCALE + BORDER_SIZE), + y: y, + })); + column.push(Cell::new(Point2 { + x: 5.0 * (TILE_WIDTH * TILE_SCALE + BORDER_SIZE), + y: y, + })); + column.push(Cell::new(Point2 { + x: 6.0 * (TILE_WIDTH * TILE_SCALE + BORDER_SIZE), + y: y, + })); + column.push(Cell::new(Point2 { + x: 7.0 * (TILE_WIDTH * TILE_SCALE + BORDER_SIZE), + y: y, + })); + + y += TILE_HEIGHT * TILE_SCALE + BORDER_SIZE; grid.push(column); } Ok(Game { grid: grid, + selected: None, spritebatch: SpriteBatch::new(image), }) } } impl event::EventHandler for Game { - fn update(&mut self, _context: &mut ggez::Context) -> ggez::GameResult { + fn update(&mut self, context: &mut ggez::Context) -> ggez::GameResult { + for row in self.grid.iter_mut() { + for cell in row.iter_mut() { + cell.hover_off(); + } + } + + let position = mouse::position(context); + + for row in self.grid.iter_mut() { + for cell in row.iter_mut() { + if cell.contains(position) { + cell.hover_on(); + } + } + } + Ok(()) } + fn mouse_button_down_event( + &mut self, + _context: &mut ggez::Context, + button: mouse::MouseButton, + x: f32, + y: f32, + ) { + if button == mouse::MouseButton::Left { + let position = Point2 { x: x, y: y }; + for (i, row) in self.grid.iter_mut().enumerate() { + for (j, cell) in row.iter_mut().enumerate() { + if cell.contains(position) { + self.selected = Some((i, j)); + cell.clicked_on(); + } + } + } + } + } + + fn mouse_button_up_event( + &mut self, + _context: &mut ggez::Context, + button: mouse::MouseButton, + x: f32, + y: f32, + ) { + if button == mouse::MouseButton::Left { + for row in self.grid.iter_mut() { + for cell in row.iter_mut() { + cell.clicked_off(); + } + } + + if let Some(selected) = self.selected { + let position = Point2 { x: x, y: y }; + let mut swap = None; + for (i, row) in self.grid.iter_mut().enumerate() { + for (j, cell) in row.iter_mut().enumerate() { + if cell.contains(position) { + if (i + 1 == selected.0) && (j == selected.1) { + swap = Some((i, j)); + } + } + } + } + if let Some((i, j)) = swap { + let clone = self.grid[i][j].occupant.clone(); + self.grid[i][j].occupant = self.grid[selected.0][selected.1].occupant; + self.grid[selected.0][selected.1].occupant = clone; + self.selected = None; + } + } + } + } + fn draw(&mut self, context: &mut ggez::Context) -> ggez::GameResult { graphics::clear(context, [0.1, 0.2, 0.3, 1.0].into()); for row in self.grid.iter() { for cell in row.iter() { - cell.draw(&mut self.spritebatch) + cell.draw(context, &mut self.spritebatch) } } -- cgit v1.2.3