From 87ee12543e5bd23a04dc63d304bac9ef5c6df417 Mon Sep 17 00:00:00 2001 From: Xevion Date: Fri, 8 Aug 2025 09:07:10 -0500 Subject: [PATCH] tests: revamp tests, remove more useless tests --- tests/animated.rs | 30 ++++---- tests/blinking.rs | 13 ++-- tests/constants.rs | 165 +++---------------------------------------- tests/direction.rs | 70 ++++++------------ tests/directional.rs | 25 ++++--- tests/game.rs | 21 ++++++ tests/graph.rs | 111 ++++++++++++++--------------- tests/helpers.rs | 44 ++++-------- tests/map_builder.rs | 46 +++--------- tests/pacman.rs | 137 ++++++++++++----------------------- tests/parser.rs | 50 ++++--------- tests/sprite.rs | 42 ++++------- 12 files changed, 233 insertions(+), 521 deletions(-) create mode 100644 tests/game.rs diff --git a/tests/animated.rs b/tests/animated.rs index 18d3189..7a21823 100644 --- a/tests/animated.rs +++ b/tests/animated.rs @@ -12,55 +12,49 @@ fn mock_atlas_tile(id: u32) -> AtlasTile { } #[test] -fn test_new_animated_texture_zero_duration() { +fn test_animated_texture_creation_errors() { let tiles = vec![mock_atlas_tile(1), mock_atlas_tile(2)]; - let result = AnimatedTexture::new(tiles, 0.0); - assert!(result.is_err()); - assert!(matches!(result.unwrap_err(), AnimatedTextureError::InvalidFrameDuration(0.0))); -} -#[test] -fn test_new_animated_texture_negative_duration() { - let tiles = vec![mock_atlas_tile(1), mock_atlas_tile(2)]; - let result = AnimatedTexture::new(tiles, -0.1); - assert!(result.is_err()); assert!(matches!( - result.unwrap_err(), + AnimatedTexture::new(tiles.clone(), 0.0).unwrap_err(), + AnimatedTextureError::InvalidFrameDuration(0.0) + )); + + assert!(matches!( + AnimatedTexture::new(tiles, -0.1).unwrap_err(), AnimatedTextureError::InvalidFrameDuration(-0.1) )); } #[test] -fn test_tick_multiple_frame_changes() { +fn test_animated_texture_advancement() { let tiles = vec![mock_atlas_tile(1), mock_atlas_tile(2), mock_atlas_tile(3)]; let mut texture = AnimatedTexture::new(tiles, 0.1).unwrap(); - // Tick with 2.5 frame durations + assert_eq!(texture.current_frame(), 0); + texture.tick(0.25); assert_eq!(texture.current_frame(), 2); assert!((texture.time_bank() - 0.05).abs() < 0.001); } #[test] -fn test_tick_wrap_around() { +fn test_animated_texture_wrap_around() { let tiles = vec![mock_atlas_tile(1), mock_atlas_tile(2)]; let mut texture = AnimatedTexture::new(tiles, 0.1).unwrap(); - // Advance to last frame texture.tick(0.1); assert_eq!(texture.current_frame(), 1); - // Advance again to wrap around texture.tick(0.1); assert_eq!(texture.current_frame(), 0); } #[test] -fn test_single_tile_animation() { +fn test_animated_texture_single_frame() { let tiles = vec![mock_atlas_tile(1)]; let mut texture = AnimatedTexture::new(tiles, 0.1).unwrap(); - // Should stay on same frame texture.tick(0.1); assert_eq!(texture.current_frame(), 0); assert_eq!(texture.current_tile().color.unwrap().r, 1); diff --git a/tests/blinking.rs b/tests/blinking.rs index 9039b08..cb9efbc 100644 --- a/tests/blinking.rs +++ b/tests/blinking.rs @@ -12,40 +12,37 @@ fn mock_atlas_tile(id: u32) -> AtlasTile { } #[test] -fn test_tick_multiple_blink_changes() { +fn test_blinking_texture() { let tile = mock_atlas_tile(1); let mut texture = BlinkingTexture::new(tile, 0.5); - // First blink + assert_eq!(texture.is_on(), true); + texture.tick(0.5); assert_eq!(texture.is_on(), false); - // Second blink (back to on) texture.tick(0.5); assert_eq!(texture.is_on(), true); - // Third blink (back to off) texture.tick(0.5); assert_eq!(texture.is_on(), false); } #[test] -fn test_tick_partial_blink_duration() { +fn test_blinking_texture_partial_duration() { let tile = mock_atlas_tile(1); let mut texture = BlinkingTexture::new(tile, 0.5); - // Tick with 1.25 blink durations texture.tick(0.625); assert_eq!(texture.is_on(), false); assert_eq!(texture.time_bank(), 0.125); } #[test] -fn test_tick_with_negative_delta_time() { +fn test_blinking_texture_negative_time() { let tile = mock_atlas_tile(1); let mut texture = BlinkingTexture::new(tile, 0.5); - // Should not cause issues texture.tick(-0.1); assert_eq!(texture.is_on(), true); assert_eq!(texture.time_bank(), -0.1); diff --git a/tests/constants.rs b/tests/constants.rs index a849191..6d60c65 100644 --- a/tests/constants.rs +++ b/tests/constants.rs @@ -1,173 +1,28 @@ -use glam::UVec2; use pacman::constants::*; #[test] -fn test_loop_time() { - // 60 FPS = 16.67ms per frame - let expected_nanos = (1_000_000_000.0 / 60.0) as u64; - assert_eq!(LOOP_TIME.as_nanos() as u64, expected_nanos); -} - -#[test] -fn test_cell_size() { - assert_eq!(CELL_SIZE, 8); -} - -#[test] -fn test_board_cell_size() { - assert_eq!(BOARD_CELL_SIZE.x, 28); - assert_eq!(BOARD_CELL_SIZE.y, 31); -} - -#[test] -fn test_scale() { - assert_eq!(SCALE, 2.6); -} - -#[test] -fn test_board_cell_offset() { - assert_eq!(BOARD_CELL_OFFSET.x, 0); - assert_eq!(BOARD_CELL_OFFSET.y, 3); -} - -#[test] -fn test_board_pixel_offset() { - let expected = UVec2::new(0 * CELL_SIZE, 3 * CELL_SIZE); - assert_eq!(BOARD_PIXEL_OFFSET, expected); - assert_eq!(BOARD_PIXEL_OFFSET.x, 0); - assert_eq!(BOARD_PIXEL_OFFSET.y, 24); // 3 * 8 -} - -#[test] -fn test_board_pixel_size() { - let expected = UVec2::new(28 * CELL_SIZE, 31 * CELL_SIZE); - assert_eq!(BOARD_PIXEL_SIZE, expected); - assert_eq!(BOARD_PIXEL_SIZE.x, 224); // 28 * 8 - assert_eq!(BOARD_PIXEL_SIZE.y, 248); // 31 * 8 -} - -#[test] -fn test_canvas_size() { - let expected = UVec2::new((28 + 0) * CELL_SIZE, (31 + 3) * CELL_SIZE); - assert_eq!(CANVAS_SIZE, expected); - assert_eq!(CANVAS_SIZE.x, 224); // (28 + 0) * 8 - assert_eq!(CANVAS_SIZE.y, 272); // (31 + 3) * 8 -} - -#[test] -fn test_map_tile_variants() { - assert_ne!(MapTile::Empty, MapTile::Wall); - assert_ne!(MapTile::Pellet, MapTile::PowerPellet); - assert_ne!(MapTile::Tunnel, MapTile::Empty); -} - -#[test] -fn test_map_tile_clone() { - let original = MapTile::Wall; - let cloned = original; - assert_eq!(original, cloned); -} - -#[test] -fn test_raw_board_dimensions() { +fn test_raw_board_structure() { assert_eq!(RAW_BOARD.len(), BOARD_CELL_SIZE.y as usize); - assert_eq!(RAW_BOARD.len(), 31); for row in RAW_BOARD.iter() { assert_eq!(row.len(), BOARD_CELL_SIZE.x as usize); - assert_eq!(row.len(), 28); } -} -#[test] -fn test_raw_board_boundaries() { - // First row should be all walls + // Test boundaries assert!(RAW_BOARD[0].chars().all(|c| c == '#')); + assert!(RAW_BOARD[RAW_BOARD.len() - 1].chars().all(|c| c == '#')); - // Last row should be all walls - let last_row = RAW_BOARD[RAW_BOARD.len() - 1]; - assert!(last_row.chars().all(|c| c == '#')); - - // First and last character of each row should be walls (except tunnel rows and rows with spaces) - for (i, row) in RAW_BOARD.iter().enumerate() { - if i != 14 && !row.starts_with(' ') { - // Skip tunnel row and rows that start with spaces - assert_eq!(row.chars().next().unwrap(), '#'); - assert_eq!(row.chars().last().unwrap(), '#'); - } - } -} - -#[test] -fn test_raw_board_tunnel_row() { - // Row 14 should have tunnel characters 'T' at the edges + // Test tunnel row let tunnel_row = RAW_BOARD[14]; assert_eq!(tunnel_row.chars().next().unwrap(), 'T'); assert_eq!(tunnel_row.chars().last().unwrap(), 'T'); } #[test] -fn test_raw_board_power_pellets() { - // Power pellets are represented by 'o' - let mut power_pellet_count = 0; - for row in RAW_BOARD.iter() { - power_pellet_count += row.chars().filter(|&c| c == 'o').count(); - } - assert_eq!(power_pellet_count, 4); // Should have exactly 4 power pellets -} - -#[test] -fn test_raw_board_starting_position() { - // Should have a starting position 'X' for Pac-Man - let mut found_starting_position = false; - for row in RAW_BOARD.iter() { - if row.contains('X') { - found_starting_position = true; - break; - } - } - assert!(found_starting_position); -} - -#[test] -fn test_raw_board_ghost_house() { - // The ghost house area should be present (the == characters) - let mut found_ghost_house = false; - for row in RAW_BOARD.iter() { - if row.contains("==") { - found_ghost_house = true; - break; - } - } - assert!(found_ghost_house); -} - -#[test] -fn test_raw_board_symmetry() { - // The board should be roughly symmetrical - let mid_point = RAW_BOARD[0].len() / 2; - - for row in RAW_BOARD.iter() { - let left_half = &row[..mid_point]; - let right_half = &row[mid_point..]; - - // Check that the halves are symmetrical (accounting for the center column) - assert_eq!(left_half.len(), right_half.len()); - } -} - -#[test] -fn test_constants_consistency() { - // Verify that derived constants are calculated correctly - let calculated_pixel_offset = UVec2::new(BOARD_CELL_OFFSET.x * CELL_SIZE, BOARD_CELL_OFFSET.y * CELL_SIZE); - assert_eq!(BOARD_PIXEL_OFFSET, calculated_pixel_offset); - - let calculated_pixel_size = UVec2::new(BOARD_CELL_SIZE.x * CELL_SIZE, BOARD_CELL_SIZE.y * CELL_SIZE); - assert_eq!(BOARD_PIXEL_SIZE, calculated_pixel_size); - - let calculated_canvas_size = UVec2::new( - (BOARD_CELL_SIZE.x + BOARD_CELL_OFFSET.x) * CELL_SIZE, - (BOARD_CELL_SIZE.y + BOARD_CELL_OFFSET.y) * CELL_SIZE, - ); - assert_eq!(CANVAS_SIZE, calculated_canvas_size); +fn test_raw_board_content() { + let power_pellet_count = RAW_BOARD.iter().flat_map(|row| row.chars()).filter(|&c| c == 'o').count(); + assert_eq!(power_pellet_count, 4); + + assert!(RAW_BOARD.iter().any(|row| row.contains('X'))); + assert!(RAW_BOARD.iter().any(|row| row.contains("=="))); } diff --git a/tests/direction.rs b/tests/direction.rs index fb30e00..a7e36b2 100644 --- a/tests/direction.rs +++ b/tests/direction.rs @@ -3,59 +3,29 @@ use pacman::entity::direction::*; #[test] fn test_direction_opposite() { - assert_eq!(Direction::Up.opposite(), Direction::Down); - assert_eq!(Direction::Down.opposite(), Direction::Up); - assert_eq!(Direction::Left.opposite(), Direction::Right); - assert_eq!(Direction::Right.opposite(), Direction::Left); + let test_cases = [ + (Direction::Up, Direction::Down), + (Direction::Down, Direction::Up), + (Direction::Left, Direction::Right), + (Direction::Right, Direction::Left), + ]; + + for (dir, expected) in test_cases { + assert_eq!(dir.opposite(), expected); + } } #[test] fn test_direction_as_ivec2() { - assert_eq!(Direction::Up.as_ivec2(), -IVec2::Y); - assert_eq!(Direction::Down.as_ivec2(), IVec2::Y); - assert_eq!(Direction::Left.as_ivec2(), -IVec2::X); - assert_eq!(Direction::Right.as_ivec2(), IVec2::X); -} + let test_cases = [ + (Direction::Up, -IVec2::Y), + (Direction::Down, IVec2::Y), + (Direction::Left, -IVec2::X), + (Direction::Right, IVec2::X), + ]; -#[test] -fn test_direction_from_ivec2() { - assert_eq!(IVec2::from(Direction::Up), -IVec2::Y); - assert_eq!(IVec2::from(Direction::Down), IVec2::Y); - assert_eq!(IVec2::from(Direction::Left), -IVec2::X); - assert_eq!(IVec2::from(Direction::Right), IVec2::X); -} - -#[test] -fn test_directions_constant() { - assert_eq!(DIRECTIONS.len(), 4); - assert!(DIRECTIONS.contains(&Direction::Up)); - assert!(DIRECTIONS.contains(&Direction::Down)); - assert!(DIRECTIONS.contains(&Direction::Left)); - assert!(DIRECTIONS.contains(&Direction::Right)); -} - -#[test] -fn test_direction_equality() { - assert_eq!(Direction::Up, Direction::Up); - assert_ne!(Direction::Up, Direction::Down); - assert_ne!(Direction::Left, Direction::Right); -} - -#[test] -fn test_direction_clone() { - let dir = Direction::Up; - let cloned = dir; - assert_eq!(dir, cloned); -} - -#[test] -fn test_direction_hash() { - use std::collections::HashMap; - let mut map = HashMap::new(); - map.insert(Direction::Up, "up"); - map.insert(Direction::Down, "down"); - - assert_eq!(map.get(&Direction::Up), Some(&"up")); - assert_eq!(map.get(&Direction::Down), Some(&"down")); - assert_eq!(map.get(&Direction::Left), None); + for (dir, expected) in test_cases { + assert_eq!(dir.as_ivec2(), expected); + assert_eq!(IVec2::from(dir), expected); + } } diff --git a/tests/directional.rs b/tests/directional.rs index ad42ea6..753d615 100644 --- a/tests/directional.rs +++ b/tests/directional.rs @@ -19,7 +19,7 @@ fn mock_animated_texture(id: u32) -> AnimatedTexture { } #[test] -fn test_partial_directions() { +fn test_directional_texture_partial_directions() { let mut textures = HashMap::new(); textures.insert(Direction::Up, mock_animated_texture(1)); @@ -33,18 +33,23 @@ fn test_partial_directions() { } #[test] -fn test_all_directions() { +fn test_directional_texture_all_directions() { let mut textures = HashMap::new(); - textures.insert(Direction::Up, mock_animated_texture(1)); - textures.insert(Direction::Down, mock_animated_texture(2)); - textures.insert(Direction::Left, mock_animated_texture(3)); - textures.insert(Direction::Right, mock_animated_texture(4)); + let directions = [ + (Direction::Up, 1), + (Direction::Down, 2), + (Direction::Left, 3), + (Direction::Right, 4), + ]; + + for (direction, id) in directions { + textures.insert(direction, mock_animated_texture(id)); + } let texture = DirectionalAnimatedTexture::new(textures, HashMap::new()); assert_eq!(texture.texture_count(), 4); - assert!(texture.has_direction(Direction::Up)); - assert!(texture.has_direction(Direction::Down)); - assert!(texture.has_direction(Direction::Left)); - assert!(texture.has_direction(Direction::Right)); + for direction in &[Direction::Up, Direction::Down, Direction::Left, Direction::Right] { + assert!(texture.has_direction(*direction)); + } } diff --git a/tests/game.rs b/tests/game.rs new file mode 100644 index 0000000..374d212 --- /dev/null +++ b/tests/game.rs @@ -0,0 +1,21 @@ +use pacman::constants::RAW_BOARD; +use pacman::map::Map; + +#[test] +fn test_game_map_creation() { + let map = Map::new(RAW_BOARD); + + assert!(map.graph.node_count() > 0); + assert!(!map.grid_to_node.is_empty()); + + // Should find Pac-Man's starting position + let pacman_pos = map.find_starting_position(0); + assert!(pacman_pos.is_some()); +} + +#[test] +fn test_game_score_initialization() { + // This would require creating a full Game instance, but we can test the concept + let map = Map::new(RAW_BOARD); + assert!(map.find_starting_position(0).is_some()); +} diff --git a/tests/graph.rs b/tests/graph.rs index 1c3e247..4b6196d 100644 --- a/tests/graph.rs +++ b/tests/graph.rs @@ -1,5 +1,5 @@ use pacman::entity::direction::Direction; -use pacman::entity::graph::{Graph, Node, Position, Traverser}; +use pacman::entity::graph::{EdgePermissions, Graph, Node, Position, Traverser}; fn create_test_graph() -> Graph { let mut graph = Graph::new(); @@ -19,6 +19,22 @@ fn create_test_graph() -> Graph { graph } +#[test] +fn test_graph_basic_operations() { + let mut graph = Graph::new(); + let node1 = graph.add_node(Node { + position: glam::Vec2::new(0.0, 0.0), + }); + let node2 = graph.add_node(Node { + position: glam::Vec2::new(16.0, 0.0), + }); + + assert_eq!(graph.node_count(), 2); + assert!(graph.get_node(node1).is_some()); + assert!(graph.get_node(node2).is_some()); + assert!(graph.get_node(999).is_none()); +} + #[test] fn test_graph_connect() { let mut graph = Graph::new(); @@ -29,10 +45,8 @@ fn test_graph_connect() { position: glam::Vec2::new(16.0, 0.0), }); - let result = graph.connect(node1, node2, false, None, Direction::Right); - assert!(result.is_ok()); + assert!(graph.connect(node1, node2, false, None, Direction::Right).is_ok()); - // Check that edges were added in both directions let edge1 = graph.find_edge_in_direction(node1, Direction::Right); let edge2 = graph.find_edge_in_direction(node2, Direction::Left); @@ -43,23 +57,18 @@ fn test_graph_connect() { } #[test] -fn test_graph_connect_invalid_nodes() { +fn test_graph_connect_errors() { let mut graph = Graph::new(); let node1 = graph.add_node(Node { position: glam::Vec2::new(0.0, 0.0), }); - // Try to connect to non-existent node - let result = graph.connect(node1, 999, false, None, Direction::Right); - assert!(result.is_err()); - - // Try to connect from non-existent node - let result = graph.connect(999, node1, false, None, Direction::Right); - assert!(result.is_err()); + assert!(graph.connect(node1, 999, false, None, Direction::Right).is_err()); + assert!(graph.connect(999, node1, false, None, Direction::Right).is_err()); } #[test] -fn test_graph_find_edge() { +fn test_graph_edge_permissions() { let mut graph = Graph::new(); let node1 = graph.add_node(Node { position: glam::Vec2::new(0.0, 0.0), @@ -68,56 +77,29 @@ fn test_graph_find_edge() { position: glam::Vec2::new(16.0, 0.0), }); - graph.connect(node1, node2, false, None, Direction::Right).unwrap(); + graph + .add_edge(node1, node2, false, None, Direction::Right, EdgePermissions::GhostsOnly) + .unwrap(); - let edge = graph.find_edge(node1, node2); - assert!(edge.is_some()); - assert_eq!(edge.unwrap().target, node2); - - // Test non-existent edge - assert!(graph.find_edge(node1, 999).is_none()); + let edge = graph.find_edge_in_direction(node1, Direction::Right).unwrap(); + assert_eq!(edge.permissions, EdgePermissions::GhostsOnly); } #[test] -fn test_graph_find_edge_in_direction() { - let mut graph = Graph::new(); - let node1 = graph.add_node(Node { - position: glam::Vec2::new(0.0, 0.0), - }); - let node2 = graph.add_node(Node { - position: glam::Vec2::new(16.0, 0.0), - }); - - graph.connect(node1, node2, false, None, Direction::Right).unwrap(); - - let edge = graph.find_edge_in_direction(node1, Direction::Right); - assert!(edge.is_some()); - assert_eq!(edge.unwrap().target, node2); - - // Test non-existent direction - assert!(graph.find_edge_in_direction(node1, Direction::Up).is_none()); -} - -#[test] -fn test_traverser_set_next_direction() { +fn test_traverser_basic() { let graph = create_test_graph(); let mut traverser = Traverser::new(&graph, 0, Direction::Left, &|_| true); traverser.set_next_direction(Direction::Up); assert!(traverser.next_direction.is_some()); assert_eq!(traverser.next_direction.unwrap().0, Direction::Up); - - // Setting same direction should not change anything - traverser.set_next_direction(Direction::Up); - assert_eq!(traverser.next_direction.unwrap().0, Direction::Up); } #[test] -fn test_traverser_advance_at_node() { +fn test_traverser_advance() { let graph = create_test_graph(); let mut traverser = Traverser::new(&graph, 0, Direction::Right, &|_| true); - // Should start moving in the initial direction traverser.advance(&graph, 5.0, &|_| true); match traverser.position { @@ -128,17 +110,7 @@ fn test_traverser_advance_at_node() { } _ => panic!("Expected to be between nodes"), } -} -#[test] -fn test_traverser_advance_between_nodes() { - let graph = create_test_graph(); - let mut traverser = Traverser::new(&graph, 0, Direction::Right, &|_| true); - - // Move to between nodes - traverser.advance(&graph, 5.0, &|_| true); - - // Advance further traverser.advance(&graph, 3.0, &|_| true); match traverser.position { @@ -150,3 +122,28 @@ fn test_traverser_advance_between_nodes() { _ => panic!("Expected to be between nodes"), } } + +#[test] +fn test_traverser_with_permissions() { + let mut graph = Graph::new(); + let node1 = graph.add_node(Node { + position: glam::Vec2::new(0.0, 0.0), + }); + let node2 = graph.add_node(Node { + position: glam::Vec2::new(16.0, 0.0), + }); + + graph + .add_edge(node1, node2, false, None, Direction::Right, EdgePermissions::GhostsOnly) + .unwrap(); + + // Pacman can't traverse ghost-only edges + let mut traverser = Traverser::new(&graph, node1, Direction::Right, &|edge| { + matches!(edge.permissions, EdgePermissions::All) + }); + + traverser.advance(&graph, 5.0, &|edge| matches!(edge.permissions, EdgePermissions::All)); + + // Should still be at the node since it can't traverse + assert!(traverser.position.is_at_node()); +} diff --git a/tests/helpers.rs b/tests/helpers.rs index 8b0dab6..6831dff 100644 --- a/tests/helpers.rs +++ b/tests/helpers.rs @@ -2,36 +2,18 @@ use glam::{IVec2, UVec2}; use pacman::helpers::centered_with_size; #[test] -fn test_centered_with_size_basic() { - let rect = centered_with_size(IVec2::new(100, 100), UVec2::new(50, 30)); - assert_eq!(rect.origin(), (75, 85)); - assert_eq!(rect.size(), (50, 30)); -} +fn test_centered_with_size() { + let test_cases = [ + ((100, 100), (50, 30), (75, 85)), + ((50, 50), (51, 31), (25, 35)), + ((0, 0), (100, 100), (-50, -50)), + ((-100, -50), (80, 40), (-140, -70)), + ((1000, 1000), (1000, 1000), (500, 500)), + ]; -#[test] -fn test_centered_with_size_odd_dimensions() { - let rect = centered_with_size(IVec2::new(50, 50), UVec2::new(51, 31)); - assert_eq!(rect.origin(), (25, 35)); - assert_eq!(rect.size(), (51, 31)); -} - -#[test] -fn test_centered_with_size_zero_position() { - let rect = centered_with_size(IVec2::new(0, 0), UVec2::new(100, 100)); - assert_eq!(rect.origin(), (-50, -50)); - assert_eq!(rect.size(), (100, 100)); -} - -#[test] -fn test_centered_with_size_negative_position() { - let rect = centered_with_size(IVec2::new(-100, -50), UVec2::new(80, 40)); - assert_eq!(rect.origin(), (-140, -70)); - assert_eq!(rect.size(), (80, 40)); -} - -#[test] -fn test_centered_with_size_large_dimensions() { - let rect = centered_with_size(IVec2::new(1000, 1000), UVec2::new(1000, 1000)); - assert_eq!(rect.origin(), (500, 500)); - assert_eq!(rect.size(), (1000, 1000)); + for ((pos_x, pos_y), (size_x, size_y), (expected_x, expected_y)) in test_cases { + let rect = centered_with_size(IVec2::new(pos_x, pos_y), UVec2::new(size_x, size_y)); + assert_eq!(rect.origin(), (expected_x, expected_y)); + assert_eq!(rect.size(), (size_x, size_y)); + } } diff --git a/tests/map_builder.rs b/tests/map_builder.rs index cfc0f3e..64f9cb9 100644 --- a/tests/map_builder.rs +++ b/tests/map_builder.rs @@ -1,10 +1,9 @@ -use glam::{IVec2, Vec2}; +use glam::Vec2; use pacman::constants::{BOARD_CELL_SIZE, CELL_SIZE}; use pacman::map::Map; fn create_minimal_test_board() -> [&'static str; BOARD_CELL_SIZE.y as usize] { let mut board = [""; BOARD_CELL_SIZE.y as usize]; - // Create a minimal valid board with house doors board[0] = "############################"; board[1] = "#............##............#"; board[2] = "#.####.#####.##.#####.####.#"; @@ -40,37 +39,11 @@ fn create_minimal_test_board() -> [&'static str; BOARD_CELL_SIZE.y as usize] { } #[test] -fn test_find_starting_position_pacman() { +fn test_map_creation() { let board = create_minimal_test_board(); let map = Map::new(board); - let pacman_pos = map.find_starting_position(0); - assert!(pacman_pos.is_some()); - - let pos = pacman_pos.unwrap(); - // Pacman should be found somewhere in the board - assert!(pos.x < BOARD_CELL_SIZE.x); - assert!(pos.y < BOARD_CELL_SIZE.y); -} - -#[test] -fn test_find_starting_position_nonexistent() { - let board = create_minimal_test_board(); - let map = Map::new(board); - - let pos = map.find_starting_position(99); // Non-existent entity - assert!(pos.is_none()); -} - -#[test] -fn test_map_graph_construction() { - let board = create_minimal_test_board(); - let map = Map::new(board); - - // Check that nodes were created assert!(map.graph.node_count() > 0); - - // Check that grid_to_node mapping was created assert!(!map.grid_to_node.is_empty()); // Check that some connections were made @@ -85,17 +58,17 @@ fn test_map_graph_construction() { } #[test] -fn test_map_grid_to_node_mapping() { +fn test_map_starting_positions() { let board = create_minimal_test_board(); let map = Map::new(board); - // Check that Pac-Man's position is mapped - let pacman_pos = map.find_starting_position(0).unwrap(); - let grid_pos = IVec2::new(pacman_pos.x as i32, pacman_pos.y as i32); + let pacman_pos = map.find_starting_position(0); + assert!(pacman_pos.is_some()); + assert!(pacman_pos.unwrap().x < BOARD_CELL_SIZE.x); + assert!(pacman_pos.unwrap().y < BOARD_CELL_SIZE.y); - assert!(map.grid_to_node.contains_key(&grid_pos)); - let node_id = map.grid_to_node[&grid_pos]; - assert!(map.graph.get_node(node_id).is_some()); + let nonexistent_pos = map.find_starting_position(99); + assert_eq!(nonexistent_pos, None); } #[test] @@ -103,7 +76,6 @@ fn test_map_node_positions() { let board = create_minimal_test_board(); let map = Map::new(board); - // Check that node positions are correctly calculated for (grid_pos, &node_id) in &map.grid_to_node { let node = map.graph.get_node(node_id).unwrap(); let expected_pos = Vec2::new((grid_pos.x * CELL_SIZE as i32) as f32, (grid_pos.y * CELL_SIZE as i32) as f32) diff --git a/tests/pacman.rs b/tests/pacman.rs index e893a8b..85d31bb 100644 --- a/tests/pacman.rs +++ b/tests/pacman.rs @@ -24,46 +24,32 @@ fn create_test_graph() -> Graph { } fn create_test_atlas() -> SpriteAtlas { - // Create a minimal test atlas with required tiles let mut frames = HashMap::new(); + let directions = ["up", "down", "left", "right"]; + + for (i, dir) in directions.iter().enumerate() { + frames.insert( + format!("pacman/{dir}_a.png"), + MapperFrame { + x: i as u16 * 16, + y: 0, + width: 16, + height: 16, + }, + ); + frames.insert( + format!("pacman/{dir}_b.png"), + MapperFrame { + x: i as u16 * 16, + y: 16, + width: 16, + height: 16, + }, + ); + } + frames.insert( - "pacman/up_a.png".to_string(), - MapperFrame { - x: 0, - y: 0, - width: 16, - height: 16, - }, - ); - frames.insert( - "pacman/up_b.png".to_string(), - MapperFrame { - x: 16, - y: 0, - width: 16, - height: 16, - }, - ); - frames.insert( - "pacman/down_a.png".to_string(), - MapperFrame { - x: 32, - y: 0, - width: 16, - height: 16, - }, - ); - frames.insert( - "pacman/down_b.png".to_string(), - MapperFrame { - x: 48, - y: 0, - width: 16, - height: 16, - }, - ); - frames.insert( - "pacman/left_a.png".to_string(), + "pacman/full.png".to_string(), MapperFrame { x: 64, y: 0, @@ -71,71 +57,43 @@ fn create_test_atlas() -> SpriteAtlas { height: 16, }, ); - frames.insert( - "pacman/left_b.png".to_string(), - MapperFrame { - x: 80, - y: 0, - width: 16, - height: 16, - }, - ); - frames.insert( - "pacman/right_a.png".to_string(), - MapperFrame { - x: 96, - y: 0, - width: 16, - height: 16, - }, - ); - frames.insert( - "pacman/right_b.png".to_string(), - MapperFrame { - x: 112, - y: 0, - width: 16, - height: 16, - }, - ); - frames.insert( - "pacman/full.png".to_string(), - MapperFrame { - x: 128, - y: 0, - width: 16, - height: 16, - }, - ); let mapper = AtlasMapper { frames }; - // Create a dummy texture (we won't actually render, just test the logic) let dummy_texture = unsafe { std::mem::zeroed() }; SpriteAtlas::new(dummy_texture, mapper) } #[test] -fn test_handle_key_valid_directions() { +fn test_pacman_creation() { + let graph = create_test_graph(); + let atlas = create_test_atlas(); + let pacman = Pacman::new(&graph, 0, &atlas); + + assert!(pacman.traverser.position.is_at_node()); + assert_eq!(pacman.traverser.direction, Direction::Left); +} + +#[test] +fn test_pacman_key_handling() { let graph = create_test_graph(); let atlas = create_test_atlas(); let mut pacman = Pacman::new(&graph, 0, &atlas); - // Test that direction keys are handled correctly - pacman.handle_key(Keycode::Up); - assert!(pacman.traverser.next_direction.is_some() || pacman.traverser.direction == Direction::Up); + let test_cases = [ + (Keycode::Up, Direction::Up), + (Keycode::Down, Direction::Down), + (Keycode::Left, Direction::Left), + (Keycode::Right, Direction::Right), + ]; - pacman.handle_key(Keycode::Down); - assert!(pacman.traverser.next_direction.is_some() || pacman.traverser.direction == Direction::Down); - - pacman.handle_key(Keycode::Left); - assert!(pacman.traverser.next_direction.is_some() || pacman.traverser.direction == Direction::Left); - - pacman.handle_key(Keycode::Right); - assert!(pacman.traverser.next_direction.is_some() || pacman.traverser.direction == Direction::Right); + for (key, expected_direction) in test_cases { + pacman.handle_key(key); + assert!(pacman.traverser.next_direction.is_some() || pacman.traverser.direction == expected_direction); + } } #[test] -fn test_handle_key_invalid_direction() { +fn test_pacman_invalid_key() { let graph = create_test_graph(); let atlas = create_test_atlas(); let mut pacman = Pacman::new(&graph, 0, &atlas); @@ -143,10 +101,7 @@ fn test_handle_key_invalid_direction() { let original_direction = pacman.traverser.direction; let original_next_direction = pacman.traverser.next_direction; - // Test invalid key pacman.handle_key(Keycode::Space); - - // Should not change direction assert_eq!(pacman.traverser.direction, original_direction); assert_eq!(pacman.traverser.next_direction, original_next_direction); } diff --git a/tests/parser.rs b/tests/parser.rs index ebbb030..3171bc2 100644 --- a/tests/parser.rs +++ b/tests/parser.rs @@ -3,36 +3,20 @@ use pacman::map::parser::{MapTileParser, ParseError}; #[test] fn test_parse_character() { - assert!(matches!( - MapTileParser::parse_character('#').unwrap(), - pacman::constants::MapTile::Wall - )); - assert!(matches!( - MapTileParser::parse_character('.').unwrap(), - pacman::constants::MapTile::Pellet - )); - assert!(matches!( - MapTileParser::parse_character('o').unwrap(), - pacman::constants::MapTile::PowerPellet - )); - assert!(matches!( - MapTileParser::parse_character(' ').unwrap(), - pacman::constants::MapTile::Empty - )); - assert!(matches!( - MapTileParser::parse_character('T').unwrap(), - pacman::constants::MapTile::Tunnel - )); - assert!(matches!( - MapTileParser::parse_character('X').unwrap(), - pacman::constants::MapTile::Empty - )); - assert!(matches!( - MapTileParser::parse_character('=').unwrap(), - pacman::constants::MapTile::Wall - )); + let test_cases = [ + ('#', pacman::constants::MapTile::Wall), + ('.', pacman::constants::MapTile::Pellet), + ('o', pacman::constants::MapTile::PowerPellet), + (' ', pacman::constants::MapTile::Empty), + ('T', pacman::constants::MapTile::Tunnel), + ('X', pacman::constants::MapTile::Empty), + ('=', pacman::constants::MapTile::Wall), + ]; + + for (char, _expected) in test_cases { + assert!(matches!(MapTileParser::parse_character(char).unwrap(), _expected)); + } - // Test invalid character assert!(MapTileParser::parse_character('Z').is_err()); } @@ -42,20 +26,12 @@ fn test_parse_board() { assert!(result.is_ok()); let parsed = result.unwrap(); - - // Verify we have tiles assert_eq!(parsed.tiles.len(), BOARD_CELL_SIZE.x as usize); assert_eq!(parsed.tiles[0].len(), BOARD_CELL_SIZE.y as usize); - - // Verify we found house door positions assert!(parsed.house_door[0].is_some()); assert!(parsed.house_door[1].is_some()); - - // Verify we found tunnel ends assert!(parsed.tunnel_ends[0].is_some()); assert!(parsed.tunnel_ends[1].is_some()); - - // Verify we found Pac-Man's starting position assert!(parsed.pacman_start.is_some()); } diff --git a/tests/sprite.rs b/tests/sprite.rs index 9a77687..52efd99 100644 --- a/tests/sprite.rs +++ b/tests/sprite.rs @@ -2,13 +2,12 @@ use pacman::texture::sprite::{AtlasMapper, MapperFrame, SpriteAtlas}; use sdl2::pixels::Color; use std::collections::HashMap; -// Mock texture for testing fn mock_texture() -> sdl2::render::Texture<'static> { unsafe { std::mem::transmute(0usize) } } #[test] -fn test_sprite_atlas_get_tile() { +fn test_sprite_atlas_basic() { let mut frames = HashMap::new(); frames.insert( "test".to_string(), @@ -26,37 +25,12 @@ fn test_sprite_atlas_get_tile() { let tile = atlas.get_tile("test"); assert!(tile.is_some()); - let tile = tile.unwrap(); assert_eq!(tile.pos, glam::U16Vec2::new(10, 20)); assert_eq!(tile.size, glam::U16Vec2::new(32, 64)); assert_eq!(tile.color, None); } -#[test] -fn test_sprite_atlas_get_tile_nonexistent() { - let mapper = AtlasMapper { frames: HashMap::new() }; - let texture = mock_texture(); - let atlas = SpriteAtlas::new(texture, mapper); - - let tile = atlas.get_tile("nonexistent"); - assert!(tile.is_none()); -} - -#[test] -fn test_sprite_atlas_set_color() { - let mapper = AtlasMapper { frames: HashMap::new() }; - let texture = mock_texture(); - let mut atlas = SpriteAtlas::new(texture, mapper); - - assert_eq!(atlas.default_color(), None); - - let color = Color::RGB(255, 0, 0); - atlas.set_color(color); - - assert_eq!(atlas.default_color(), Some(color)); -} - #[test] fn test_sprite_atlas_multiple_tiles() { let mut frames = HashMap::new(); @@ -87,4 +61,18 @@ fn test_sprite_atlas_multiple_tiles() { assert!(atlas.has_tile("tile1")); assert!(atlas.has_tile("tile2")); assert!(!atlas.has_tile("tile3")); + assert!(atlas.get_tile("nonexistent").is_none()); +} + +#[test] +fn test_sprite_atlas_color() { + let mapper = AtlasMapper { frames: HashMap::new() }; + let texture = mock_texture(); + let mut atlas = SpriteAtlas::new(texture, mapper); + + assert_eq!(atlas.default_color(), None); + + let color = Color::RGB(255, 0, 0); + atlas.set_color(color); + assert_eq!(atlas.default_color(), Some(color)); }