basic equippables
This commit is contained in:
parent
595ec61332
commit
8d04c40389
8 changed files with 330 additions and 36 deletions
|
|
@ -84,6 +84,33 @@ impl SufferDamage {
|
|||
#[derive(Component, Debug, Serialize, Deserialize, Clone)]
|
||||
pub struct Item {}
|
||||
|
||||
#[derive(PartialEq, Copy, Clone, Serialize, Deserialize)]
|
||||
pub enum EquipmentSlot {
|
||||
Melee,
|
||||
Shield,
|
||||
}
|
||||
|
||||
#[derive(Component, ConvertSaveload, Clone)]
|
||||
pub struct MeleePowerBonus {
|
||||
pub amount: i32,
|
||||
}
|
||||
|
||||
#[derive(Component, ConvertSaveload, Clone)]
|
||||
pub struct DefenceBonus {
|
||||
pub amount: i32,
|
||||
}
|
||||
|
||||
#[derive(Component, Serialize, Deserialize, Clone)]
|
||||
pub struct Equippable {
|
||||
pub slot: EquipmentSlot,
|
||||
}
|
||||
|
||||
#[derive(Component, ConvertSaveload, Clone)]
|
||||
pub struct Equipped {
|
||||
pub owner: Entity,
|
||||
pub slot: EquipmentSlot,
|
||||
}
|
||||
|
||||
#[derive(Component, Debug, Serialize, Deserialize, Clone)]
|
||||
pub struct Cursed {}
|
||||
|
||||
|
|
@ -131,6 +158,11 @@ pub struct WantsToDropItem {
|
|||
pub item: Entity,
|
||||
}
|
||||
|
||||
#[derive(Component, Debug, ConvertSaveload)]
|
||||
pub struct WantsToRemoveItem {
|
||||
pub item: Entity,
|
||||
}
|
||||
|
||||
#[derive(Component, Debug, ConvertSaveload)]
|
||||
pub struct WantsToUseItem {
|
||||
pub item: Entity,
|
||||
|
|
|
|||
46
src/gui.rs
46
src/gui.rs
|
|
@ -1,6 +1,6 @@
|
|||
use super::{
|
||||
gamelog, rex_assets::RexAssets, CombatStats, InBackpack, Map, Name, Player, Point, Position, RunState, State,
|
||||
Viewshed,
|
||||
gamelog, rex_assets::RexAssets, CombatStats, Equipped, InBackpack, Map, Name, Player, Point, Position, RunState,
|
||||
State, Viewshed,
|
||||
};
|
||||
use rltk::{Rltk, VirtualKeyCode, RGB};
|
||||
use specs::prelude::*;
|
||||
|
|
@ -202,6 +202,48 @@ pub fn drop_item_menu(gs: &mut State, ctx: &mut Rltk) -> (ItemMenuResult, Option
|
|||
}
|
||||
}
|
||||
|
||||
pub fn remove_item_menu(gs: &mut State, ctx: &mut Rltk) -> (ItemMenuResult, Option<Entity>) {
|
||||
let player_entity = gs.ecs.fetch::<Entity>();
|
||||
let names = gs.ecs.read_storage::<Name>();
|
||||
let backpack = gs.ecs.read_storage::<Equipped>();
|
||||
let entities = gs.ecs.entities();
|
||||
|
||||
let inventory = (&backpack, &names).join().filter(|item| item.0.owner == *player_entity);
|
||||
let count = inventory.count();
|
||||
|
||||
let mut y = (25 - (count / 2)) as i32;
|
||||
ctx.draw_box(15, y - 2, 31, (count + 3) as i32, RGB::named(rltk::WHITE), RGB::named(rltk::BLACK));
|
||||
ctx.print_color(18, y - 2, RGB::named(rltk::YELLOW), RGB::named(rltk::BLACK), "Remove what?");
|
||||
ctx.print_color(18, y + count as i32 + 1, RGB::named(rltk::YELLOW), RGB::named(rltk::BLACK), "ESC to cancel");
|
||||
|
||||
let mut equippable: Vec<Entity> = Vec::new();
|
||||
let mut j = 0;
|
||||
for (entity, _pack, name) in (&entities, &backpack, &names).join().filter(|item| item.1.owner == *player_entity) {
|
||||
ctx.set(17, y, RGB::named(rltk::WHITE), RGB::named(rltk::BLACK), rltk::to_cp437('('));
|
||||
ctx.set(18, y, RGB::named(rltk::YELLOW), RGB::named(rltk::BLACK), 97 + j as rltk::FontCharType);
|
||||
ctx.set(19, y, RGB::named(rltk::WHITE), RGB::named(rltk::BLACK), rltk::to_cp437(')'));
|
||||
|
||||
ctx.print(21, y, &name.name.to_string());
|
||||
equippable.push(entity);
|
||||
y += 1;
|
||||
j += 1;
|
||||
}
|
||||
|
||||
match ctx.key {
|
||||
None => (ItemMenuResult::NoResponse, None),
|
||||
Some(key) => match key {
|
||||
VirtualKeyCode::Escape => (ItemMenuResult::Cancel, None),
|
||||
_ => {
|
||||
let selection = rltk::letter_to_option(key);
|
||||
if selection > -1 && selection < count as i32 {
|
||||
return (ItemMenuResult::Selected, Some(equippable[selection as usize]));
|
||||
}
|
||||
(ItemMenuResult::NoResponse, None)
|
||||
}
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
pub fn ranged_target(gs: &mut State, ctx: &mut Rltk, range: i32, aoe: i32) -> (ItemMenuResult, Option<Point>) {
|
||||
let player_entity = gs.ecs.fetch::<Entity>();
|
||||
let player_pos = gs.ecs.fetch::<Point>();
|
||||
|
|
|
|||
|
|
@ -1,7 +1,8 @@
|
|||
use super::{
|
||||
gamelog, CombatStats, Confusion, Consumable, Cursed, Destructible, InBackpack, InflictsDamage, MagicMapper, Map,
|
||||
Name, ParticleBuilder, Point, Position, ProvidesHealing, RunState, SufferDamage, WantsToDropItem,
|
||||
WantsToPickupItem, WantsToUseItem, AOE, DEFAULT_PARTICLE_LIFETIME, LONG_PARTICLE_LIFETIME,
|
||||
gamelog, CombatStats, Confusion, Consumable, Cursed, Destructible, Equippable, Equipped, InBackpack,
|
||||
InflictsDamage, MagicMapper, Map, Name, ParticleBuilder, Point, Position, ProvidesHealing, RunState, SufferDamage,
|
||||
WantsToDropItem, WantsToPickupItem, WantsToRemoveItem, WantsToUseItem, AOE, DEFAULT_PARTICLE_LIFETIME,
|
||||
LONG_PARTICLE_LIFETIME,
|
||||
};
|
||||
use specs::prelude::*;
|
||||
|
||||
|
|
@ -59,6 +60,9 @@ impl<'a> System<'a> for ItemUseSystem {
|
|||
WriteStorage<'a, Confusion>,
|
||||
ReadStorage<'a, MagicMapper>,
|
||||
WriteExpect<'a, RunState>,
|
||||
ReadStorage<'a, Equippable>,
|
||||
WriteStorage<'a, Equipped>,
|
||||
WriteStorage<'a, InBackpack>,
|
||||
);
|
||||
|
||||
fn run(&mut self, data: Self::SystemData) {
|
||||
|
|
@ -81,6 +85,9 @@ impl<'a> System<'a> for ItemUseSystem {
|
|||
mut confused,
|
||||
magic_mapper,
|
||||
mut runstate,
|
||||
equippable,
|
||||
mut equipped,
|
||||
mut backpack,
|
||||
) = data;
|
||||
|
||||
for (entity, wants_to_use) in (&entities, &wants_to_use).join() {
|
||||
|
|
@ -153,6 +160,48 @@ impl<'a> System<'a> for ItemUseSystem {
|
|||
}
|
||||
}
|
||||
|
||||
// EQUIPMENT
|
||||
let item_equippable = equippable.get(wants_to_use.item);
|
||||
match item_equippable {
|
||||
None => {}
|
||||
Some(can_equip) => {
|
||||
let target_slot = can_equip.slot;
|
||||
let target = targets[0];
|
||||
|
||||
// Room any items target has in item's slot
|
||||
let mut to_unequip: Vec<Entity> = Vec::new();
|
||||
for (item_entity, already_equipped, _name) in (&entities, &equipped, &names).join() {
|
||||
if already_equipped.owner == target && already_equipped.slot == target_slot {
|
||||
to_unequip.push(item_entity);
|
||||
if target == *player_entity {
|
||||
gamelog::Logger::new()
|
||||
.append("You unequip the")
|
||||
.item_name_n(&item_being_used.name)
|
||||
.period()
|
||||
.log();
|
||||
}
|
||||
}
|
||||
}
|
||||
for item in to_unequip.iter() {
|
||||
equipped.remove(*item);
|
||||
backpack.insert(*item, InBackpack { owner: target }).expect("Unable to insert backpack");
|
||||
}
|
||||
|
||||
// Wield the item
|
||||
equipped
|
||||
.insert(wants_to_use.item, Equipped { owner: target, slot: target_slot })
|
||||
.expect("Unable to insert equipped component");
|
||||
backpack.remove(wants_to_use.item);
|
||||
if target == *player_entity {
|
||||
gamelog::Logger::new()
|
||||
.append("You equip the")
|
||||
.item_name_n(&item_being_used.name)
|
||||
.period()
|
||||
.log();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// HEALING ITEM
|
||||
let item_heals = provides_healing.get(wants_to_use.item);
|
||||
match item_heals {
|
||||
|
|
@ -339,3 +388,22 @@ impl<'a> System<'a> for ItemDropSystem {
|
|||
wants_drop.clear();
|
||||
}
|
||||
}
|
||||
|
||||
pub struct ItemRemoveSystem {}
|
||||
|
||||
impl<'a> System<'a> for ItemRemoveSystem {
|
||||
#[allow(clippy::type_complexity)]
|
||||
type SystemData =
|
||||
(Entities<'a>, WriteStorage<'a, WantsToRemoveItem>, WriteStorage<'a, Equipped>, WriteStorage<'a, InBackpack>);
|
||||
|
||||
fn run(&mut self, data: Self::SystemData) {
|
||||
let (entities, mut wants_remove, mut equipped, mut backpack) = data;
|
||||
|
||||
for (entity, to_remove) in (&entities, &wants_remove).join() {
|
||||
equipped.remove(to_remove.item);
|
||||
backpack.insert(to_remove.item, InBackpack { owner: entity }).expect("Unable to insert backpack");
|
||||
}
|
||||
|
||||
wants_remove.clear();
|
||||
}
|
||||
}
|
||||
|
|
|
|||
34
src/main.rs
34
src/main.rs
|
|
@ -48,6 +48,7 @@ pub enum RunState {
|
|||
MonsterTurn,
|
||||
ShowInventory,
|
||||
ShowDropItem,
|
||||
ShowRemoveItem,
|
||||
ShowTargeting { range: i32, item: Entity, aoe: i32 },
|
||||
MainMenu { menu_selection: gui::MainMenuSelection },
|
||||
SaveGame,
|
||||
|
|
@ -71,8 +72,10 @@ impl State {
|
|||
inventory_system.run_now(&self.ecs);
|
||||
let mut item_use_system = ItemUseSystem {};
|
||||
item_use_system.run_now(&self.ecs);
|
||||
let mut drop_system = ItemDropSystem {};
|
||||
drop_system.run_now(&self.ecs);
|
||||
let mut item_drop_system = ItemDropSystem {};
|
||||
item_drop_system.run_now(&self.ecs);
|
||||
let mut item_remove_system = ItemRemoveSystem {};
|
||||
item_remove_system.run_now(&self.ecs);
|
||||
let mut melee_system = MeleeCombatSystem {};
|
||||
melee_system.run_now(&self.ecs);
|
||||
let mut damage_system = DamageSystem {};
|
||||
|
|
@ -87,6 +90,7 @@ impl State {
|
|||
let player = self.ecs.read_storage::<Player>();
|
||||
let backpack = self.ecs.read_storage::<InBackpack>();
|
||||
let player_entity = self.ecs.fetch::<Entity>();
|
||||
let equipped = self.ecs.read_storage::<Equipped>();
|
||||
|
||||
let mut to_delete: Vec<Entity> = Vec::new();
|
||||
for entity in entities.join() {
|
||||
|
|
@ -105,6 +109,12 @@ impl State {
|
|||
should_delete = false;
|
||||
}
|
||||
}
|
||||
let eq = equipped.get(entity);
|
||||
if let Some(eq) = eq {
|
||||
if eq.owner == *player_entity {
|
||||
should_delete = false;
|
||||
}
|
||||
}
|
||||
|
||||
if should_delete {
|
||||
to_delete.push(entity);
|
||||
|
|
@ -280,6 +290,21 @@ impl GameState for State {
|
|||
}
|
||||
}
|
||||
}
|
||||
RunState::ShowRemoveItem => {
|
||||
let result = gui::remove_item_menu(self, ctx);
|
||||
match result.0 {
|
||||
gui::ItemMenuResult::Cancel => new_runstate = RunState::AwaitingInput,
|
||||
gui::ItemMenuResult::NoResponse => {}
|
||||
gui::ItemMenuResult::Selected => {
|
||||
let item_entity = result.1.unwrap();
|
||||
let mut intent = self.ecs.write_storage::<WantsToRemoveItem>();
|
||||
intent
|
||||
.insert(*self.ecs.fetch::<Entity>(), WantsToRemoveItem { item: item_entity })
|
||||
.expect("Unable to insert intent");
|
||||
new_runstate = RunState::PlayerTurn;
|
||||
}
|
||||
}
|
||||
}
|
||||
RunState::ShowTargeting { range, item, aoe } => {
|
||||
let result = gui::ranged_target(self, ctx, range, aoe);
|
||||
match result.0 {
|
||||
|
|
@ -397,6 +422,10 @@ fn main() -> rltk::BError {
|
|||
gs.ecs.register::<WantsToMelee>();
|
||||
gs.ecs.register::<SufferDamage>();
|
||||
gs.ecs.register::<Item>();
|
||||
gs.ecs.register::<Equippable>();
|
||||
gs.ecs.register::<Equipped>();
|
||||
gs.ecs.register::<MeleePowerBonus>();
|
||||
gs.ecs.register::<DefenceBonus>();
|
||||
gs.ecs.register::<Cursed>();
|
||||
gs.ecs.register::<ProvidesHealing>();
|
||||
gs.ecs.register::<InflictsDamage>();
|
||||
|
|
@ -407,6 +436,7 @@ fn main() -> rltk::BError {
|
|||
gs.ecs.register::<InBackpack>();
|
||||
gs.ecs.register::<WantsToPickupItem>();
|
||||
gs.ecs.register::<WantsToDropItem>();
|
||||
gs.ecs.register::<WantsToRemoveItem>();
|
||||
gs.ecs.register::<WantsToUseItem>();
|
||||
gs.ecs.register::<Consumable>();
|
||||
gs.ecs.register::<Destructible>();
|
||||
|
|
|
|||
|
|
@ -1,4 +1,7 @@
|
|||
use super::{gamelog, CombatStats, Name, ParticleBuilder, Position, SufferDamage, WantsToMelee};
|
||||
use super::{
|
||||
gamelog, CombatStats, DefenceBonus, Equipped, MeleePowerBonus, Name, ParticleBuilder, Position, SufferDamage,
|
||||
WantsToMelee,
|
||||
};
|
||||
use specs::prelude::*;
|
||||
|
||||
pub struct MeleeCombatSystem {}
|
||||
|
|
@ -13,6 +16,9 @@ impl<'a> System<'a> for MeleeCombatSystem {
|
|||
WriteStorage<'a, SufferDamage>,
|
||||
WriteExpect<'a, ParticleBuilder>,
|
||||
ReadStorage<'a, Position>,
|
||||
ReadStorage<'a, Equipped>,
|
||||
ReadStorage<'a, DefenceBonus>,
|
||||
ReadStorage<'a, MeleePowerBonus>,
|
||||
);
|
||||
|
||||
fn run(&mut self, data: Self::SystemData) {
|
||||
|
|
@ -25,6 +31,9 @@ impl<'a> System<'a> for MeleeCombatSystem {
|
|||
mut inflict_damage,
|
||||
mut particle_builder,
|
||||
positions,
|
||||
equipped,
|
||||
defence_bonuses,
|
||||
melee_power_bonuses,
|
||||
) = data;
|
||||
|
||||
for (entity, wants_melee, name, stats) in (&entities, &wants_melee, &names, &combat_stats).join() {
|
||||
|
|
@ -37,18 +46,20 @@ impl<'a> System<'a> for MeleeCombatSystem {
|
|||
}
|
||||
|
||||
let target_name = names.get(wants_melee.target).unwrap();
|
||||
let pos = positions.get(wants_melee.target);
|
||||
if let Some(pos) = pos {
|
||||
particle_builder.request(
|
||||
pos.x,
|
||||
pos.y,
|
||||
rltk::RGB::named(rltk::ORANGE),
|
||||
rltk::RGB::named(rltk::BLACK),
|
||||
rltk::to_cp437('‼'),
|
||||
150.0,
|
||||
);
|
||||
|
||||
let mut offensive_bonus = 0;
|
||||
for (_item_entity, power_bonus, equipped_by) in (&entities, &melee_power_bonuses, &equipped).join() {
|
||||
if equipped_by.owner == entity {
|
||||
offensive_bonus += power_bonus.amount;
|
||||
}
|
||||
}
|
||||
let damage = i32::max(0, stats.power - target_stats.defence);
|
||||
let mut defensive_bonus = 0;
|
||||
for (_item_entity, defence_bonus, equipped_by) in (&entities, &defence_bonuses, &equipped).join() {
|
||||
if equipped_by.owner == wants_melee.target {
|
||||
defensive_bonus += defence_bonus.amount;
|
||||
}
|
||||
}
|
||||
let damage = i32::max(0, (stats.power + offensive_bonus) - (target_stats.defence + defensive_bonus));
|
||||
|
||||
if damage == 0 {
|
||||
if entity == *player_entity {
|
||||
|
|
@ -96,6 +107,17 @@ impl<'a> System<'a> for MeleeCombatSystem {
|
|||
.period()
|
||||
.log();
|
||||
}
|
||||
let pos = positions.get(wants_melee.target);
|
||||
if let Some(pos) = pos {
|
||||
particle_builder.request(
|
||||
pos.x,
|
||||
pos.y,
|
||||
rltk::RGB::named(rltk::ORANGE),
|
||||
rltk::RGB::named(rltk::BLACK),
|
||||
rltk::to_cp437('‼'),
|
||||
150.0,
|
||||
);
|
||||
}
|
||||
SufferDamage::new_damage(&mut inflict_damage, wants_melee.target, damage);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -35,20 +35,30 @@ pub fn try_move_player(delta_x: i32, delta_y: i32, ecs: &mut World) {
|
|||
}
|
||||
|
||||
if !map.blocked[destination_idx] {
|
||||
// TODO: Refactor
|
||||
let mut tile_content = "You see ".to_string();
|
||||
let names = ecs.read_storage::<Name>();
|
||||
// Push every entity name in the pile to a vector of strings
|
||||
let mut item_names: Vec<String> = Vec::new();
|
||||
let mut some = false;
|
||||
for entity in map.tile_content[destination_idx].iter() {
|
||||
if let Some(name) = names.get(*entity) {
|
||||
if tile_content != "You see " {
|
||||
tile_content.push_str(", ");
|
||||
}
|
||||
tile_content.push_str(&name.name);
|
||||
let item_name = &name.name;
|
||||
item_names.push(item_name.to_string());
|
||||
some = true;
|
||||
}
|
||||
}
|
||||
if tile_content != "You see " {
|
||||
tile_content.push_str(".");
|
||||
gamelog::Logger::new().append(tile_content).log()
|
||||
// If some names were found, append. Logger = logger is necessary
|
||||
// makes logger called a mutable self. It's not the most efficient
|
||||
// but it happens infrequently enough (once per player turn at most)
|
||||
// that it shouldn't matter.
|
||||
if some {
|
||||
let mut logger = gamelog::Logger::new().append("You see a");
|
||||
for i in 0..item_names.len() {
|
||||
if i > 0 && i < item_names.len() {
|
||||
logger = logger.append(", a");
|
||||
}
|
||||
logger = logger.item_name_n(&item_names[i]);
|
||||
}
|
||||
logger.period().log();
|
||||
}
|
||||
pos.x = min((MAPWIDTH as i32) - 1, max(0, pos.x + delta_x));
|
||||
pos.y = min((MAPHEIGHT as i32) - 1, max(0, pos.y + delta_y));
|
||||
|
|
@ -127,6 +137,7 @@ pub fn player_input(gs: &mut State, ctx: &mut Rltk) -> RunState {
|
|||
VirtualKeyCode::G => get_item(&mut gs.ecs),
|
||||
VirtualKeyCode::I => return RunState::ShowInventory,
|
||||
VirtualKeyCode::D => return RunState::ShowDropItem,
|
||||
VirtualKeyCode::R => return RunState::ShowRemoveItem,
|
||||
VirtualKeyCode::Escape => return RunState::SaveGame,
|
||||
_ => {
|
||||
return RunState::AwaitingInput;
|
||||
|
|
|
|||
|
|
@ -58,6 +58,10 @@ pub fn save_game(ecs: &mut World) {
|
|||
SufferDamage,
|
||||
WantsToMelee,
|
||||
Item,
|
||||
Equippable,
|
||||
Equipped,
|
||||
MeleePowerBonus,
|
||||
DefenceBonus,
|
||||
Cursed,
|
||||
Consumable,
|
||||
Destructible,
|
||||
|
|
@ -71,6 +75,7 @@ pub fn save_game(ecs: &mut World) {
|
|||
WantsToPickupItem,
|
||||
WantsToUseItem,
|
||||
WantsToDropItem,
|
||||
WantsToRemoveItem,
|
||||
SerializationHelper
|
||||
);
|
||||
}
|
||||
|
|
@ -135,6 +140,10 @@ pub fn load_game(ecs: &mut World) {
|
|||
SufferDamage,
|
||||
WantsToMelee,
|
||||
Item,
|
||||
Equippable,
|
||||
Equipped,
|
||||
MeleePowerBonus,
|
||||
DefenceBonus,
|
||||
Cursed,
|
||||
Consumable,
|
||||
Destructible,
|
||||
|
|
@ -148,6 +157,7 @@ pub fn load_game(ecs: &mut World) {
|
|||
WantsToPickupItem,
|
||||
WantsToUseItem,
|
||||
WantsToDropItem,
|
||||
WantsToRemoveItem,
|
||||
SerializationHelper
|
||||
);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
use super::{
|
||||
random_table::RandomTable, BlocksTile, CombatStats, Confusion, Consumable, Cursed, Destructible, InflictsDamage,
|
||||
Item, MagicMapper, Monster, Name, Player, Position, ProvidesHealing, Ranged, Rect, Renderable, SerializeMe,
|
||||
Viewshed, AOE, MAPWIDTH,
|
||||
random_table::RandomTable, BlocksTile, CombatStats, Confusion, Consumable, Cursed, DefenceBonus, Destructible,
|
||||
EquipmentSlot, Equippable, InflictsDamage, Item, MagicMapper, MeleePowerBonus, Monster, Name, Player, Position,
|
||||
ProvidesHealing, Ranged, Rect, Renderable, SerializeMe, Viewshed, AOE, MAPWIDTH,
|
||||
};
|
||||
use rltk::{console, RandomNumberGenerator, RGB};
|
||||
use specs::prelude::*;
|
||||
|
|
@ -116,6 +116,11 @@ pub fn spawn_room(ecs: &mut World, room: &Rect, map_depth: i32) {
|
|||
"goblin" => goblin(ecs, x, y),
|
||||
"goblin chieftain" => goblin_chieftain(ecs, x, y),
|
||||
"orc" => orc(ecs, x, y),
|
||||
// Equipment
|
||||
"dagger" => dagger(ecs, x, y),
|
||||
"shortsword" => shortsword(ecs, x, y),
|
||||
"buckler" => buckler(ecs, x, y),
|
||||
"shield" => shield(ecs, x, y),
|
||||
// Potions
|
||||
"weak health potion" => weak_health_potion(ecs, x, y),
|
||||
"health potion" => health_potion(ecs, x, y),
|
||||
|
|
@ -149,14 +154,19 @@ fn mob_table(map_depth: i32) -> RandomTable {
|
|||
.add("orc", 2 + map_depth);
|
||||
}
|
||||
|
||||
// 25 potions : 10 scrolls : 2 cursed scrolls
|
||||
fn item_table(_map_depth: i32) -> RandomTable {
|
||||
// 6 equipment : 10 potions : 10 scrolls : 2 cursed scrolls
|
||||
fn item_table(map_depth: i32) -> RandomTable {
|
||||
return RandomTable::new()
|
||||
// Equipment
|
||||
.add("dagger", 2)
|
||||
.add("shortsword", map_depth - 1)
|
||||
.add("buckler", 2)
|
||||
.add("shield", 1)
|
||||
// Potions
|
||||
.add("weak health potion", 20)
|
||||
.add("health potion", 5)
|
||||
.add("weak health potion", 7)
|
||||
.add("health potion", 3)
|
||||
// Scrolls
|
||||
.add("fireball scroll", 1)
|
||||
.add("fireball scroll", map_depth - 1)
|
||||
.add("cursed fireball scroll", 1)
|
||||
.add("confusion scroll", 2)
|
||||
.add("magic missile scroll", 5)
|
||||
|
|
@ -337,3 +347,72 @@ fn cursed_magic_map_scroll(ecs: &mut World, x: i32, y: i32) {
|
|||
.marked::<SimpleMarker<SerializeMe>>()
|
||||
.build();
|
||||
}
|
||||
|
||||
// EQUIPMENT
|
||||
fn dagger(ecs: &mut World, x: i32, y: i32) {
|
||||
ecs.create_entity()
|
||||
.with(Position { x, y })
|
||||
.with(Renderable {
|
||||
glyph: rltk::to_cp437('/'),
|
||||
fg: RGB::named(rltk::GREY),
|
||||
bg: RGB::named(rltk::BLACK),
|
||||
render_order: 2,
|
||||
})
|
||||
.with(Name { name: "dagger".to_string() })
|
||||
.with(Item {})
|
||||
.with(Equippable { slot: EquipmentSlot::Melee })
|
||||
.with(MeleePowerBonus { amount: 1 })
|
||||
.marked::<SimpleMarker<SerializeMe>>()
|
||||
.build();
|
||||
}
|
||||
fn shortsword(ecs: &mut World, x: i32, y: i32) {
|
||||
ecs.create_entity()
|
||||
.with(Position { x, y })
|
||||
.with(Renderable {
|
||||
glyph: rltk::to_cp437('/'),
|
||||
fg: RGB::named(rltk::GREY),
|
||||
bg: RGB::named(rltk::BLACK),
|
||||
render_order: 2,
|
||||
})
|
||||
.with(Name { name: "shortsword".to_string() })
|
||||
.with(Item {})
|
||||
.with(Equippable { slot: EquipmentSlot::Melee })
|
||||
.with(MeleePowerBonus { amount: 2 })
|
||||
.marked::<SimpleMarker<SerializeMe>>()
|
||||
.build();
|
||||
}
|
||||
|
||||
fn buckler(ecs: &mut World, x: i32, y: i32) {
|
||||
ecs.create_entity()
|
||||
.with(Position { x, y })
|
||||
.with(Renderable {
|
||||
glyph: rltk::to_cp437('('),
|
||||
fg: RGB::named(rltk::GREY),
|
||||
bg: RGB::named(rltk::BLACK),
|
||||
render_order: 2,
|
||||
})
|
||||
.with(Name { name: "buckler".to_string() })
|
||||
.with(Item {})
|
||||
.with(DefenceBonus { amount: 1 })
|
||||
.with(Equippable { slot: EquipmentSlot::Shield })
|
||||
.marked::<SimpleMarker<SerializeMe>>()
|
||||
.build();
|
||||
}
|
||||
|
||||
fn shield(ecs: &mut World, x: i32, y: i32) {
|
||||
ecs.create_entity()
|
||||
.with(Position { x, y })
|
||||
.with(Renderable {
|
||||
glyph: rltk::to_cp437('('),
|
||||
fg: RGB::named(rltk::GREY),
|
||||
bg: RGB::named(rltk::BLACK),
|
||||
render_order: 2,
|
||||
})
|
||||
.with(Name { name: "shield".to_string() })
|
||||
.with(Item {})
|
||||
.with(DefenceBonus { amount: 2 })
|
||||
.with(MeleePowerBonus { amount: -1 })
|
||||
.with(Equippable { slot: EquipmentSlot::Shield })
|
||||
.marked::<SimpleMarker<SerializeMe>>()
|
||||
.build();
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue