diff options
author | Guillaume Pasquet <dev@etenil.net> | 2019-11-21 19:54:38 +0000 |
---|---|---|
committer | Guillaume Pasquet <dev@etenil.net> | 2019-11-21 19:54:38 +0000 |
commit | 538008cbdc8ec8a873e62a8b991201fda5762d63 (patch) | |
tree | d9dab5a34ac13d4393ca4531807e455cf5af828a | |
parent | b53947f191ad6ffc9b72890abb916a44f581c0c3 (diff) |
Fog of war! Inneficient and buggy but works
-rw-r--r-- | src/entities.rs | 27 | ||||
-rw-r--r-- | src/main.rs | 6 | ||||
-rw-r--r-- | src/state.rs | 13 | ||||
-rw-r--r-- | src/tiling.rs | 24 |
4 files changed, 55 insertions, 15 deletions
diff --git a/src/entities.rs b/src/entities.rs index b3cdf34..430e37a 100644 --- a/src/entities.rs +++ b/src/entities.rs @@ -22,6 +22,8 @@ pub trait Entity { fn is_dirty(&self) -> bool;
/// Declare the entity clean
fn clean(&mut self);
+ fn visibility(&mut self, visible: bool);
+ fn is_visible(&self) -> bool;
}
#[derive(Clone)]
@@ -39,12 +41,19 @@ pub struct Character { luck: i32,
xp: i32,
tile: Tile,
+ visible: bool,
}
pub trait Enemy {
- fn new(class: String, health: i32, attack: i32, dodge: i32, luck: i32,
- location: Point, tile_str: &'static str)
- -> Self;
+ fn new(
+ class: String,
+ health: i32,
+ attack: i32,
+ dodge: i32,
+ luck: i32,
+ location: Point,
+ tile_str: &'static str,
+ ) -> Self;
fn set_tile(&mut self, tile: Tile);
}
@@ -103,6 +112,14 @@ impl Entity for Character { fn clean(&mut self) {
self.dirty = false;
}
+
+ fn visibility(&mut self, visible: bool) {
+ self.visible = visible;
+ }
+
+ fn is_visible(&self) -> bool {
+ self.visible
+ }
}
impl Enemy for Character {
@@ -129,6 +146,7 @@ impl Enemy for Character { previous_location: location,
tile: Tile::from(TileType::Character(tile_str)),
dirty: false,
+ visible: false,
}
}
@@ -160,9 +178,10 @@ impl Player for Character { previous_location: (0, 0),
tile: Tile::new(
TileType::Player,
- true, // player is visible by default
+ true, // player is visible by default
),
dirty: false,
+ visible: true,
}
}
diff --git a/src/main.rs b/src/main.rs index 5acbbef..e45701a 100644 --- a/src/main.rs +++ b/src/main.rs @@ -42,15 +42,13 @@ fn main() { let _raw = RawScreen::into_raw_mode(); - state.render_level(); - let input = input(); let mut reader = input.read_sync(); loop { - // update + state.render_player(); + state.render_level(); state.render_entities(); - state.render_player(); state.render_ui(); diff --git a/src/state.rs b/src/state.rs index 9939226..805e9e9 100644 --- a/src/state.rs +++ b/src/state.rs @@ -6,6 +6,8 @@ use crate::entities::{Character, Entity, Player}; use crate::tiling::{tile_to_str, Tile, TileGrid, TileType}; use crate::world::{apply_movement, Dungeon, Generatable, Level, Movement}; +const PLAYER_SIGHT: usize = 5; + pub struct State { pub player: Character, dungeon: Dungeon, @@ -48,7 +50,7 @@ impl State { } fn render_entity(&self, entity: &dyn Entity) { - if !entity.is_dirty() { + if !entity.is_visible() || !entity.is_dirty() { return; } let dirt = entity.previous_location(); @@ -71,8 +73,13 @@ impl State { } } - pub fn render_player(&self) { - self.render_entity(&self.player) + pub fn render_player(&mut self) { + self.render_entity(&self.player); + + self.grid + .as_mut() + .unwrap() + .clear_fog_of_war(self.player.location(), PLAYER_SIGHT); } fn ui_state_position(&self) -> MoveTo { diff --git a/src/tiling.rs b/src/tiling.rs index c79d6ef..b7c2bc6 100644 --- a/src/tiling.rs +++ b/src/tiling.rs @@ -25,15 +25,23 @@ impl Tile { pub fn get_type(&self) -> &TileType { &self.tile_type } + + pub fn is_visible(&self) -> bool { + self.visible + } + + pub fn visibility(&mut self, visible: bool) { + self.visible = visible; + } } impl From<TileType> for Tile { fn from(tile_type: TileType) -> Self { Tile { tile_type, - visible: true, // <--- TODO: this set the default beaviour - // - true: all tiles of world and entities will be drawn - // - false: only draw tiles visible for the player + visible: false, // <--- TODO: this set the default beaviour + // - true: all tiles of world and entities will be drawn + // - false: only draw tiles visible for the player } } } @@ -94,10 +102,18 @@ impl TileGrid { pub fn ysize(&self) -> usize { self.ysize } + + pub fn clear_fog_of_war(&mut self, center: &(usize, usize), radius: usize) { + for x in 0.max(center.0 - radius)..center.0 + radius { + for y in 0.max(center.1 - radius)..center.1 + radius { + self.grid[y][x].visibility(true) + } + } + } } pub fn tile_to_str(tile: &Tile) -> &str { - if tile.visible { + if tile.is_visible() { match tile.tile_type { TileType::Floor => ".", TileType::Wall => "#", |