From e1b5e25e852efcf91db1f1c55c0b7004d4aa50ff Mon Sep 17 00:00:00 2001 From: Michael Smith Date: Sat, 13 Nov 2021 15:40:00 +0100 Subject: [PATCH] Dropping items --- src/main.rs | 37 +++++++++++++++++++++++++++++++++++-- 1 file changed, 35 insertions(+), 2 deletions(-) diff --git a/src/main.rs b/src/main.rs index ae93c08..03537cf 100644 --- a/src/main.rs +++ b/src/main.rs @@ -304,6 +304,7 @@ enum Item { Heal, Lightning, Confuse, + Fireball, } enum UseResult { @@ -506,6 +507,11 @@ fn place_objects(room: Rect, map: &Map, objects: &mut Vec) { let mut object = Object::new(x, y, '#', "scroll of lightning bolt", LIGHT_YELLOW, false); object.item = Some(Item::Lightning); object + } else if dice < 0.7 + 0.1 + 0.1 { + // Create a fireball scroll (10% chance) + let mut object = Object::new(x, y, '#', "scroll of fireball", LIGHT_YELLOW, false); + object.item = Some(Item::Fireball); + object } else { // Create a confuse scroll (10% chance) let mut object = Object::new(x, y, '#', "scroll of confusion", LIGHT_YELLOW, false); @@ -823,6 +829,7 @@ fn use_item(inventory_id: usize, tcod: &mut Tcod, game: &mut Game, objects: &mut Heal => cast_heal, Lightning => cast_lightning, Confuse => cast_confuse, + Fireball => cast_fireball, }; match on_use(inventory_id, tcod, game, objects) { UseResult::UsedUp => { @@ -899,7 +906,11 @@ fn cast_confuse( game: &mut Game, objects: &mut [Object], ) -> UseResult { - let monster_id = target_monster(CONFUSE_RANGE, objects, tcod); + game.messages.add( + "Left-click an enemy to confuse it, or right click to cancel.", + LIGHT_CYAN, + ); + let monster_id = target_monster(tcod, game, objects, Some(CONFUSE_RANGE as f32)); if let Some(monster_id) = monster_id { let old_ai = objects[monster_id].ai.take().unwrap_or(Ai::Basic); // Replace the monster's AI with a "confused" one; after @@ -938,7 +949,7 @@ fn cast_fireball( ); let (x, y) = match target_tile(tcod, game, objects, None) { Some(tile_pos) => tile_pos, - None => return UseResult::Canceled, + None => return UseResult::Cancelled, }; game.messages.add( format!( @@ -1025,6 +1036,28 @@ fn target_tile( } } +// Returns a clicked monster inside FOV up to a range, or None if right-clicked +fn target_monster( + tcod: &mut Tcod, + game: &mut Game, + objects: &[Object], + max_range: Option, +) -> Option { + loop { + match target_tile(tcod, game, objects, max_range) { + Some((x, y)) => { + // Return the first clicked monster, otherwise continue looping + for (id, obj) in objects.iter().enumerate() { + if obj.pos() == (x, y) && obj.fighter.is_some() && id != PLAYER { + return Some(id); + } + } + } + None => return None, + } + } +} + fn render_all(tcod: &mut Tcod, game: &mut Game, objects: &[Object], fov_recompute: bool) { if fov_recompute { let player = &objects[PLAYER];