From d0b0a84984fe70b4d233c7debcf0189d8a6c0893 Mon Sep 17 00:00:00 2001 From: Timothy Warren Date: Mon, 29 Nov 2021 14:39:15 -0500 Subject: [PATCH] Add item to reveal current map, completes section 3.5 --- src/components.rs | 3 +++ src/inventory_system.rs | 19 +++++++++++++++++-- src/main.rs | 25 ++++++++++++++++++++++++- src/saveload_system.rs | 2 ++ src/spawner.rs | 19 +++++++++++++++++++ 5 files changed, 65 insertions(+), 3 deletions(-) diff --git a/src/components.rs b/src/components.rs index 1aedea1..c9fbb53 100644 --- a/src/components.rs +++ b/src/components.rs @@ -196,6 +196,9 @@ pub struct HungerClock { #[derive(Component, Debug, Serialize, Deserialize, Clone)] pub struct ProvidesFood {} +#[derive(Component, Debug, Serialize, Deserialize, Clone)] +pub struct MagicMapper {} + // Serialization helper code. We need to implement ConvertSaveLoad for each type that contains an // Entity. diff --git a/src/inventory_system.rs b/src/inventory_system.rs index 1460932..dc7dab9 100644 --- a/src/inventory_system.rs +++ b/src/inventory_system.rs @@ -1,5 +1,5 @@ use crate::components::*; -use crate::{game_log::GameLog, particle_system::ParticleBuilder, Map}; +use crate::{game_log::GameLog, particle_system::ParticleBuilder, Map, RunState}; use rltk::RGB; use specs::prelude::*; @@ -50,7 +50,7 @@ impl<'a> System<'a> for ItemUseSystem { type SystemData = ( ReadExpect<'a, Entity>, WriteExpect<'a, GameLog>, - ReadExpect<'a, Map>, + WriteExpect<'a, Map>, Entities<'a>, WriteStorage<'a, WantsToUseItem>, ReadStorage<'a, Name>, @@ -68,6 +68,8 @@ impl<'a> System<'a> for ItemUseSystem { ReadStorage<'a, Position>, ReadStorage<'a, ProvidesFood>, WriteStorage<'a, HungerClock>, + ReadStorage<'a, MagicMapper>, + WriteExpect<'a, RunState>, ); #[allow(clippy::cognitive_complexity)] @@ -93,6 +95,8 @@ impl<'a> System<'a> for ItemUseSystem { positions, provides_food, mut hunger_clocks, + magic_mapper, + mut runstate, ) = data; for (entity, useitem) in (&entities, &wants_use).join() { @@ -207,6 +211,17 @@ impl<'a> System<'a> for ItemUseSystem { } } + // If its a magic mapper... + match magic_mapper.get(useitem.item) { + None => {} + Some(_) => { + used_item = true; + gamelog.append("The map is revealed to you!"); + + *runstate = RunState::MagicMapReveal { row: 0 }; + } + } + // If the item heals, apply the healing match healing.get(useitem.item) { None => {} diff --git a/src/main.rs b/src/main.rs index d6fc39a..ba452ab 100644 --- a/src/main.rs +++ b/src/main.rs @@ -63,6 +63,9 @@ pub enum RunState { NextLevel, ShowRemoveItem, GameOver, + MagicMapReveal { + row: i32, + }, } pub struct State { @@ -160,7 +163,13 @@ impl GameState for State { RunState::PlayerTurn => { self.run_systems(); self.ecs.maintain(); - newrunstate = RunState::MonsterTurn; + + match *self.ecs.fetch::() { + RunState::MagicMapReveal { .. } => { + newrunstate = RunState::MagicMapReveal { row: 0 } + } + _ => newrunstate = RunState::MonsterTurn, + } } RunState::MonsterTurn => { self.run_systems(); @@ -296,6 +305,19 @@ impl GameState for State { self.goto_next_level(); newrunstate = RunState::PreRun; } + RunState::MagicMapReveal { row } => { + let mut map = self.ecs.fetch_mut::(); + for x in 0..MAP_WIDTH { + let idx = map.xy_idx(x as i32, row); + map.revealed_tiles[idx] = true; + } + + if row as usize == MAP_HEIGHT - 1 { + newrunstate = RunState::MonsterTurn; + } else { + newrunstate = RunState::MagicMapReveal { row: row + 1 }; + } + } } { @@ -487,6 +509,7 @@ fn main() -> rltk::BError { ParticleLifetime, HungerClock, ProvidesFood, + MagicMapper, ); gs.ecs.insert(SimpleMarkerAllocator::::new()); diff --git a/src/saveload_system.rs b/src/saveload_system.rs index b84b006..856146e 100644 --- a/src/saveload_system.rs +++ b/src/saveload_system.rs @@ -78,6 +78,7 @@ pub fn save_game(ecs: &mut World) { ParticleLifetime, HungerClock, ProvidesFood, + MagicMapper, ); } @@ -162,6 +163,7 @@ pub fn load_game(ecs: &mut World) { ParticleLifetime, HungerClock, ProvidesFood, + MagicMapper, ); } diff --git a/src/spawner.rs b/src/spawner.rs index ed98564..10d1af2 100644 --- a/src/spawner.rs +++ b/src/spawner.rs @@ -50,6 +50,7 @@ fn room_table(map_depth: i32) -> RandomTable { .add("Longsword", map_depth - 1) .add("Tower Shield", map_depth - 1) .add("Rations", 10) + .add("Magic Mapping Scroll", 2) } /// fills a room with stuff! @@ -99,6 +100,7 @@ pub fn spawn_room(ecs: &mut World, room: &Rect, map_depth: i32) { "Longsword" => longsword(ecs, x, y), "Tower Shield" => tower_shield(ecs, x, y), "Rations" => rations(ecs, x, y), + "Magic Mapping Scroll" => magic_mapping_scroll(ecs, x, y), _ => {} } } @@ -299,3 +301,20 @@ fn rations(ecs: &mut World, x: i32, y: i32) { .marked::>() .build(); } + +fn magic_mapping_scroll(ecs: &mut World, x: i32, y: i32) { + ecs.create_entity() + .with(Position { x, y }) + .with(Renderable { + glyph: rltk::to_cp437(')'), + fg: RGB::named(rltk::CYAN3), + bg: RGB::named(rltk::BLACK), + render_order: 2, + }) + .with(Name::from("Scroll of Magic Mapping")) + .with(Item {}) + .with(MagicMapper {}) + .with(Consumable {}) + .marked::>() + .build(); +}