Add new theme for forest map
This commit is contained in:
parent
0e9de911ce
commit
e475a91c19
@ -1,7 +1,8 @@
|
|||||||
use ::rltk::{Point, Rltk, RGB};
|
use ::rltk::{Point, Rltk, RGB};
|
||||||
use ::specs::prelude::*;
|
use ::specs::prelude::*;
|
||||||
|
|
||||||
use crate::{Hidden, Map, Position, Renderable, TileType};
|
use crate::map::tile_glyph;
|
||||||
|
use crate::{Hidden, Map, Position, Renderable};
|
||||||
|
|
||||||
const SHOW_BOUNDARIES: bool = false;
|
const SHOW_BOUNDARIES: bool = false;
|
||||||
|
|
||||||
@ -37,7 +38,7 @@ pub fn render_camera(ecs: &World, ctx: &mut Rltk) {
|
|||||||
if tx > 0 && tx < map_width && ty > 0 && ty < map_height {
|
if tx > 0 && tx < map_width && ty > 0 && ty < map_height {
|
||||||
let idx = map.xy_idx(tx, ty);
|
let idx = map.xy_idx(tx, ty);
|
||||||
if map.revealed_tiles[idx] {
|
if map.revealed_tiles[idx] {
|
||||||
let (glyph, fg, bg) = get_tile_glyph(idx, &*map);
|
let (glyph, fg, bg) = tile_glyph(idx, &*map);
|
||||||
ctx.set(x, y, fg, bg, glyph);
|
ctx.set(x, y, fg, bg, glyph);
|
||||||
}
|
}
|
||||||
} else if SHOW_BOUNDARIES {
|
} else if SHOW_BOUNDARIES {
|
||||||
@ -109,7 +110,7 @@ pub fn render_debug_map(map: &Map, ctx: &mut Rltk) {
|
|||||||
if tx > 0 && tx < map_width && ty > 0 && ty < map_height {
|
if tx > 0 && tx < map_width && ty > 0 && ty < map_height {
|
||||||
let idx = map.xy_idx(tx, ty);
|
let idx = map.xy_idx(tx, ty);
|
||||||
if map.revealed_tiles[idx] {
|
if map.revealed_tiles[idx] {
|
||||||
let (glyph, fg, bg) = get_tile_glyph(idx, &*map);
|
let (glyph, fg, bg) = tile_glyph(idx, &*map);
|
||||||
ctx.set(x, y, fg, bg, glyph);
|
ctx.set(x, y, fg, bg, glyph);
|
||||||
}
|
}
|
||||||
} else if SHOW_BOUNDARIES {
|
} else if SHOW_BOUNDARIES {
|
||||||
@ -126,83 +127,3 @@ pub fn render_debug_map(map: &Map, ctx: &mut Rltk) {
|
|||||||
y += 1;
|
y += 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_tile_glyph(idx: usize, map: &Map) -> (rltk::FontCharType, RGB, RGB) {
|
|
||||||
let mut bg = RGB::from_f32(0., 0., 0.);
|
|
||||||
|
|
||||||
let (glyph, mut fg) = match map.tiles[idx] {
|
|
||||||
TileType::Floor => (rltk::to_cp437('.'), RGB::from_f32(0., 0.5, 0.5)),
|
|
||||||
TileType::WoodFloor => (rltk::to_cp437('.'), RGB::named(rltk::CHOCOLATE)),
|
|
||||||
TileType::Wall => {
|
|
||||||
let x = idx as i32 % map.width;
|
|
||||||
let y = idx as i32 / map.width;
|
|
||||||
(wall_glyph(&*map, x, y), RGB::from_f32(0., 1.0, 0.))
|
|
||||||
}
|
|
||||||
TileType::DownStairs => (rltk::to_cp437('>'), RGB::from_f32(0., 1.0, 1.0)),
|
|
||||||
TileType::Bridge => (rltk::to_cp437('.'), RGB::named(rltk::CHOCOLATE)),
|
|
||||||
TileType::Road => (rltk::to_cp437('~'), RGB::named(rltk::GRAY)),
|
|
||||||
TileType::Grass => (rltk::to_cp437('"'), RGB::named(rltk::GREEN)),
|
|
||||||
TileType::ShallowWater => (rltk::to_cp437('≈'), RGB::named(rltk::CYAN)),
|
|
||||||
TileType::DeepWater => (rltk::to_cp437('≈'), RGB::named(rltk::NAVY_BLUE)),
|
|
||||||
TileType::Gravel => (rltk::to_cp437(';'), RGB::named(rltk::GRAY)),
|
|
||||||
};
|
|
||||||
|
|
||||||
if map.bloodstains.contains(&idx) {
|
|
||||||
bg = RGB::from_f32(0.75, 0., 0.);
|
|
||||||
}
|
|
||||||
|
|
||||||
if !map.visible_tiles[idx] {
|
|
||||||
fg = fg.to_greyscale();
|
|
||||||
|
|
||||||
// Don't show bloodstains out of visual range
|
|
||||||
bg = RGB::from_f32(0., 0., 0.);
|
|
||||||
}
|
|
||||||
|
|
||||||
(glyph, fg, bg)
|
|
||||||
}
|
|
||||||
|
|
||||||
fn wall_glyph(map: &Map, x: i32, y: i32) -> rltk::FontCharType {
|
|
||||||
if x < 1 || x > map.width - 2 || y < 1 || y > map.height - 2 {
|
|
||||||
return 35;
|
|
||||||
}
|
|
||||||
|
|
||||||
let mut mask = 0u8;
|
|
||||||
|
|
||||||
if is_revealed_and_wall(map, x, y - 1) {
|
|
||||||
mask += 1;
|
|
||||||
}
|
|
||||||
if is_revealed_and_wall(map, x, y + 1) {
|
|
||||||
mask += 2;
|
|
||||||
}
|
|
||||||
if is_revealed_and_wall(map, x - 1, y) {
|
|
||||||
mask += 4;
|
|
||||||
}
|
|
||||||
if is_revealed_and_wall(map, x + 1, y) {
|
|
||||||
mask += 8;
|
|
||||||
}
|
|
||||||
|
|
||||||
match mask {
|
|
||||||
0 => 9, // Pillar because we can't see neighbors
|
|
||||||
1 => 186, // Wall only to the north
|
|
||||||
2 => 186, // Wall only to the south
|
|
||||||
3 => 186, // Wall to the north and south
|
|
||||||
4 => 205, // Wall only to the west
|
|
||||||
5 => 188, // Wall to the north and west
|
|
||||||
6 => 187, // Wall to the south and west
|
|
||||||
7 => 185, // Wall to the north, south, and west
|
|
||||||
8 => 205, // Wall only to the east
|
|
||||||
9 => 200, // Wall to the north and east
|
|
||||||
10 => 201, // Wall to the sound and east
|
|
||||||
11 => 204, // Wall to the north, south, and east
|
|
||||||
12 => 205, // Wall to the east and west
|
|
||||||
13 => 202, // Wall to the east, west, and south
|
|
||||||
14 => 203, // Wall to the east, west, and north
|
|
||||||
15 => 206, // ╬ Wall on all sides
|
|
||||||
_ => 35, // We missed one?
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fn is_revealed_and_wall(map: &Map, x: i32, y: i32) -> bool {
|
|
||||||
let idx = map.xy_idx(x, y);
|
|
||||||
map.tiles[idx] == TileType::Wall && map.revealed_tiles[idx]
|
|
||||||
}
|
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
mod themes;
|
||||||
mod tiletype;
|
mod tiletype;
|
||||||
|
|
||||||
use std::collections::HashSet;
|
use std::collections::HashSet;
|
||||||
@ -5,6 +6,7 @@ use std::collections::HashSet;
|
|||||||
use ::rltk::{Algorithm2D, BaseMap, Point, SmallVec};
|
use ::rltk::{Algorithm2D, BaseMap, Point, SmallVec};
|
||||||
use ::serde::{Deserialize, Serialize};
|
use ::serde::{Deserialize, Serialize};
|
||||||
use ::specs::prelude::*;
|
use ::specs::prelude::*;
|
||||||
|
pub use themes::*;
|
||||||
pub use tiletype::{tile_opaque, tile_walkable, TileType};
|
pub use tiletype::{tile_opaque, tile_walkable, TileType};
|
||||||
|
|
||||||
use crate::map::tiletype::tile_cost;
|
use crate::map::tiletype::tile_cost;
|
||||||
|
121
src/map/themes.rs
Normal file
121
src/map/themes.rs
Normal file
@ -0,0 +1,121 @@
|
|||||||
|
use ::rltk::{FontCharType, RGB};
|
||||||
|
|
||||||
|
use super::{Map, TileType};
|
||||||
|
|
||||||
|
pub fn tile_glyph(idx: usize, map: &Map) -> (FontCharType, RGB, RGB) {
|
||||||
|
let (glyph, mut fg, mut bg) = match map.depth {
|
||||||
|
2 => get_forest_glyph(idx, map),
|
||||||
|
_ => get_tile_glyph_default(idx, map),
|
||||||
|
};
|
||||||
|
|
||||||
|
if map.bloodstains.contains(&idx) {
|
||||||
|
bg = RGB::from_f32(0.7, 0., 0.);
|
||||||
|
}
|
||||||
|
|
||||||
|
if !map.visible_tiles[idx] {
|
||||||
|
fg = fg.to_greyscale();
|
||||||
|
bg = RGB::from_f32(0., 0., 0.);
|
||||||
|
}
|
||||||
|
|
||||||
|
(glyph, fg, bg)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn get_forest_glyph(idx: usize, map: &Map) -> (FontCharType, RGB, RGB) {
|
||||||
|
use rltk::to_cp437;
|
||||||
|
|
||||||
|
let bg = RGB::from_f32(0., 0., 0.);
|
||||||
|
|
||||||
|
let (glyph, fg) = match map.tiles[idx] {
|
||||||
|
TileType::Wall => (to_cp437('♣'), RGB::from_f32(0.0, 0.6, 0.0)),
|
||||||
|
TileType::Bridge => (to_cp437('.'), RGB::named(rltk::CHOCOLATE)),
|
||||||
|
TileType::Road => (to_cp437('≡'), RGB::named(rltk::YELLOW)),
|
||||||
|
TileType::Grass => (to_cp437('"'), RGB::named(rltk::GREEN)),
|
||||||
|
TileType::ShallowWater => (to_cp437('~'), RGB::named(rltk::CYAN)),
|
||||||
|
TileType::DeepWater => (to_cp437('~'), RGB::named(rltk::BLUE)),
|
||||||
|
TileType::Gravel => (to_cp437(';'), RGB::from_f32(0.5, 0.5, 0.5)),
|
||||||
|
TileType::DownStairs => (to_cp437('>'), RGB::from_f32(0., 1.0, 1.0)),
|
||||||
|
_ => (to_cp437('"'), RGB::from_f32(0.0, 0.6, 0.0)),
|
||||||
|
};
|
||||||
|
|
||||||
|
(glyph, fg, bg)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn get_tile_glyph_default(idx: usize, map: &Map) -> (rltk::FontCharType, RGB, RGB) {
|
||||||
|
let mut bg = RGB::from_f32(0., 0., 0.);
|
||||||
|
|
||||||
|
let (glyph, mut fg) = match map.tiles[idx] {
|
||||||
|
TileType::Floor => (rltk::to_cp437('.'), RGB::from_f32(0., 0.5, 0.5)),
|
||||||
|
TileType::WoodFloor => (rltk::to_cp437('░'), RGB::named(rltk::CHOCOLATE)),
|
||||||
|
TileType::Wall => {
|
||||||
|
let x = idx as i32 % map.width;
|
||||||
|
let y = idx as i32 / map.width;
|
||||||
|
(wall_glyph(&*map, x, y), RGB::from_f32(0., 1.0, 0.))
|
||||||
|
}
|
||||||
|
TileType::DownStairs => (rltk::to_cp437('>'), RGB::from_f32(0., 1.0, 1.0)),
|
||||||
|
TileType::Bridge => (rltk::to_cp437('.'), RGB::named(rltk::CHOCOLATE)),
|
||||||
|
TileType::Road => (rltk::to_cp437('≡'), RGB::named(rltk::GRAY)),
|
||||||
|
TileType::Grass => (rltk::to_cp437('"'), RGB::named(rltk::GREEN)),
|
||||||
|
TileType::ShallowWater => (rltk::to_cp437('~'), RGB::named(rltk::CYAN)),
|
||||||
|
TileType::DeepWater => (rltk::to_cp437('~'), RGB::named(rltk::NAVY_BLUE)),
|
||||||
|
TileType::Gravel => (rltk::to_cp437(';'), RGB::named(rltk::GRAY)),
|
||||||
|
};
|
||||||
|
|
||||||
|
if map.bloodstains.contains(&idx) {
|
||||||
|
bg = RGB::from_f32(0.75, 0., 0.);
|
||||||
|
}
|
||||||
|
|
||||||
|
if !map.visible_tiles[idx] {
|
||||||
|
fg = fg.to_greyscale();
|
||||||
|
|
||||||
|
// Don't show bloodstains out of visual range
|
||||||
|
bg = RGB::from_f32(0., 0., 0.);
|
||||||
|
}
|
||||||
|
|
||||||
|
(glyph, fg, bg)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn wall_glyph(map: &Map, x: i32, y: i32) -> FontCharType {
|
||||||
|
if x < 1 || x > map.width - 2 || y < 1 || y > map.height - 2 {
|
||||||
|
return 35;
|
||||||
|
}
|
||||||
|
|
||||||
|
let mut mask = 0u8;
|
||||||
|
|
||||||
|
if is_revealed_and_wall(map, x, y - 1) {
|
||||||
|
mask += 1;
|
||||||
|
}
|
||||||
|
if is_revealed_and_wall(map, x, y + 1) {
|
||||||
|
mask += 2;
|
||||||
|
}
|
||||||
|
if is_revealed_and_wall(map, x - 1, y) {
|
||||||
|
mask += 4;
|
||||||
|
}
|
||||||
|
if is_revealed_and_wall(map, x + 1, y) {
|
||||||
|
mask += 8;
|
||||||
|
}
|
||||||
|
|
||||||
|
match mask {
|
||||||
|
0 => 9, // Pillar because we can't see neighbors
|
||||||
|
1 => 186, // Wall only to the north
|
||||||
|
2 => 186, // Wall only to the south
|
||||||
|
3 => 186, // Wall to the north and south
|
||||||
|
4 => 205, // Wall only to the west
|
||||||
|
5 => 188, // Wall to the north and west
|
||||||
|
6 => 187, // Wall to the south and west
|
||||||
|
7 => 185, // Wall to the north, south, and west
|
||||||
|
8 => 205, // Wall only to the east
|
||||||
|
9 => 200, // Wall to the north and east
|
||||||
|
10 => 201, // Wall to the sound and east
|
||||||
|
11 => 204, // Wall to the north, south, and east
|
||||||
|
12 => 205, // Wall to the east and west
|
||||||
|
13 => 202, // Wall to the east, west, and south
|
||||||
|
14 => 203, // Wall to the east, west, and north
|
||||||
|
15 => 206, // ╬ Wall on all sides
|
||||||
|
_ => 35, // We missed one?
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn is_revealed_and_wall(map: &Map, x: i32, y: i32) -> bool {
|
||||||
|
let idx = map.xy_idx(x, y);
|
||||||
|
map.tiles[idx] == TileType::Wall && map.revealed_tiles[idx]
|
||||||
|
}
|
@ -8,6 +8,7 @@ mod distant_exit;
|
|||||||
mod dla;
|
mod dla;
|
||||||
mod door_placement;
|
mod door_placement;
|
||||||
mod drunkard;
|
mod drunkard;
|
||||||
|
mod forest;
|
||||||
mod maze;
|
mod maze;
|
||||||
mod prefab_builder;
|
mod prefab_builder;
|
||||||
mod room_based_spawner;
|
mod room_based_spawner;
|
||||||
@ -39,6 +40,7 @@ use distant_exit::DistantExit;
|
|||||||
use dla::DLABuilder;
|
use dla::DLABuilder;
|
||||||
use door_placement::DoorPlacement;
|
use door_placement::DoorPlacement;
|
||||||
use drunkard::DrunkardsWalkBuilder;
|
use drunkard::DrunkardsWalkBuilder;
|
||||||
|
use forest::forest_builder;
|
||||||
use maze::MazeBuilder;
|
use maze::MazeBuilder;
|
||||||
use prefab_builder::PrefabBuilder;
|
use prefab_builder::PrefabBuilder;
|
||||||
use room_based_spawner::RoomBasedSpawner;
|
use room_based_spawner::RoomBasedSpawner;
|
||||||
@ -342,6 +344,7 @@ pub fn level_builder(
|
|||||||
rltk::console::log(format!("Depth: {}", new_depth));
|
rltk::console::log(format!("Depth: {}", new_depth));
|
||||||
match new_depth {
|
match new_depth {
|
||||||
1 => town_builder(new_depth, rng, width, height),
|
1 => town_builder(new_depth, rng, width, height),
|
||||||
|
2 => forest_builder(new_depth, rng, width, height),
|
||||||
_ => random_builder(new_depth, rng, width, height),
|
_ => random_builder(new_depth, rng, width, height),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
26
src/map_builders/forest.rs
Normal file
26
src/map_builders/forest.rs
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
use ::rltk::RandomNumberGenerator;
|
||||||
|
|
||||||
|
use super::{
|
||||||
|
AreaStartingPosition, BuilderChain, CellularAutomataBuilder, CullUnreachable, DistantExit,
|
||||||
|
VoronoiSpawning, XStart, YStart,
|
||||||
|
};
|
||||||
|
|
||||||
|
pub fn forest_builder(
|
||||||
|
new_depth: i32,
|
||||||
|
_rng: &mut RandomNumberGenerator,
|
||||||
|
width: i32,
|
||||||
|
height: i32,
|
||||||
|
) -> BuilderChain {
|
||||||
|
let mut chain = BuilderChain::new(new_depth, width, height, "Into the Woods");
|
||||||
|
|
||||||
|
chain
|
||||||
|
.start_with(CellularAutomataBuilder::new())
|
||||||
|
.with(AreaStartingPosition::new(XStart::Center, YStart::Center))
|
||||||
|
.with(CullUnreachable::new())
|
||||||
|
.with(AreaStartingPosition::new(XStart::Left, YStart::Center));
|
||||||
|
|
||||||
|
// Setup an exit and spawn mobs
|
||||||
|
chain.with(VoronoiSpawning::new()).with(DistantExit::new());
|
||||||
|
|
||||||
|
chain
|
||||||
|
}
|
@ -53,8 +53,10 @@ impl TownBuilder {
|
|||||||
let doors = self.add_doors(rng, build_data, &mut buildings, wall_gap_y);
|
let doors = self.add_doors(rng, build_data, &mut buildings, wall_gap_y);
|
||||||
self.add_paths(build_data, &doors);
|
self.add_paths(build_data, &doors);
|
||||||
|
|
||||||
let exit_idx = build_data.map.xy_idx(build_data.width - 5, wall_gap_y);
|
for y in wall_gap_y - 3..wall_gap_y + 4 {
|
||||||
|
let exit_idx = build_data.map.xy_idx(build_data.width - 2, y);
|
||||||
build_data.map.tiles[exit_idx] = TileType::DownStairs;
|
build_data.map.tiles[exit_idx] = TileType::DownStairs;
|
||||||
|
}
|
||||||
|
|
||||||
let building_size = self.sort_buildings(&buildings);
|
let building_size = self.sort_buildings(&buildings);
|
||||||
self.building_factory(rng, build_data, &buildings, &building_size);
|
self.building_factory(rng, build_data, &buildings, &building_size);
|
||||||
|
Loading…
Reference in New Issue
Block a user