Example #1
0
void Wand::onEvent(Event* const event) {
	if (event->id() == ReceivedItems::ID) {
		ReceivedItems* e = static_cast<ReceivedItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			map<const string, const data::Wand*>::const_iterator w = data::Wand::wands().find(i->second.name());
			if (w == data::Wand::wands().end())
				continue; // not a wand
			if (i->second.beatitude() == BEATITUDE_UNKNOWN) {
				// beatify, but it's not that important
				Beatify b(i->first, 10);
				EventBus::broadcast(&b);
			}
			if (w->second->properties() & PROPERTY_RANDOM_APPEARANCE)
				_engrave_test_wand_key = i->first;
		}
	} else if (event->id() == WantItems::ID) {
		WantItems* e = static_cast<WantItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			map<const string, const data::Wand*>::const_iterator w = data::Wand::wands().find(i->second.name());
			if (w == data::Wand::wands().end())
				continue; // not a wand
			i->second.want(i->second.count());
		}
	}
}
Example #2
0
/* methods */
void Amulet::onEvent(Event * const event) {
	if (event->id() == ChangedInventoryItems::ID) {
		ChangedInventoryItems* e = static_cast<ChangedInventoryItems*> (event);
		for (set<unsigned char>::iterator i = e->keys().begin(); i != e->keys().end(); ++i) {
			Item item = Inventory::itemAtKey(*i);
			if (item.beatitude() != CURSED && item.beatitude() != BEATITUDE_UNKNOWN && data::Amulet::amulets().find(item.name()) != data::Amulet::amulets().end()) {
				if (item.name().find("strangulation") != string::npos && item.name().find("restful") != string::npos)
					_amulet_key = *i;
				break;
			}
		}
		//todo: determine best amulet
	} else if (event->id() == ReceivedItems::ID) {
		ReceivedItems* e = static_cast<ReceivedItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (i->second.beatitude() != BEATITUDE_UNKNOWN || data::Amulet::amulets().find(i->second.name()) == data::Amulet::amulets().end())
				continue; // known beatitude or not an amulet
			else if (i->second.beatitude() == BEATITUDE_UNKNOWN && data::Amulet::amulets().find(i->second.name()) != data::Amulet::amulets().end()) {
				Beatify b(i->first, 175);
				EventBus::broadcast(&b);
			} else if (i->second.beatitude() != CURSED && data::Amulet::amulets().find(i->second.name()) != data::Amulet::amulets().end()) {
				if (i->second.name().find("strangulation") != string::npos && i->second.name().find("restful") != string::npos)
					_amulet_key = i->first;
			}
		}
	} else if (event->id() == WantItems::ID) {
		Debug::info() << "WantItems appeared, wearing?" << endl;
		WantItems* e = static_cast<WantItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (wantItem(i->second))
				i->second.want(i->second.count());
		}
	}
}
Example #3
0
void Weapon::onEvent(event::Event* const event) {
	if (event->id() == ChangedInventoryItems::ID) {
		ChangedInventoryItems* e = static_cast<ChangedInventoryItems*> (event);
		for (set<unsigned char>::iterator k = e->keys().begin(); k != e->keys().end(); ++k) {
			const Item& item = Inventory::itemAtKey(*k);
			if (item.count() <= 0) {
				/* we lost this item */
				_range_weapons.erase(*k);
				_melee_weapons.erase(*k);
				continue;
			}
			map<const string, const data::Weapon*>::const_iterator w = data::Weapon::weapons().find(item.name());
			if (w == data::Weapon::weapons().end())
				continue; // not a weapon
			int score = calculateWeaponScore(item, w->second);
			if (isRangedWeapon(w->second))
				_range_weapons[*k] = score;
			else
				_melee_weapons[*k] = score;

		}
		setBestWeapons();
	} else if (event->id() == ReceivedItems::ID) {
		ReceivedItems* e = static_cast<ReceivedItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			map<const string, const data::Weapon*>::const_iterator w = data::Weapon::weapons().find(i->second.name());
			if (w == data::Weapon::weapons().end())
				continue; // not a weapon
			int score = calculateWeaponScore(i->second, w->second);
			if (isRangedWeapon(w->second)) {
				_range_weapons[i->first] = score;
			} else {
				_melee_weapons[i->first] = score;
				if (i->second.beatitude() == BEATITUDE_UNKNOWN) {
					Beatify b(i->first, 175);
					EventBus::broadcast(&b);
				}
			}
		}
		setBestWeapons();
	} else if (event->id() == WantItems::ID) {
		WantItems* e = static_cast<WantItems*> (event);
//		if (e->dropping() || Saiph::encumbrance() < BURDENED) {
			/* dropping items or we're burdened (which means don't loot weapons) */
			for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
				if (e->dropping()) {
					if (_range_weapons.find(i->first) != _range_weapons.end() || _melee_weapons.find(i->first) != _melee_weapons.end()) {
						/* don't drop weapons in one of our lists */
						i->second.want(i->second.count());
					}
				} else {
					/* looting, is this better than what we got? */
					if (betterThanWhatWeGot(i->second))
						i->second.want(i->second.count());
				}
			}
//		}
	}
}
Example #4
0
void Health::onEvent(event::Event* const event) {
	if (event->id() == ChangedInventoryItems::ID) {
		ChangedInventoryItems* e = static_cast<ChangedInventoryItems*> (event);
		for (set<unsigned char>::iterator k = e->keys().begin(); k != e->keys().end(); ++k) {
			map<unsigned char, Item>::iterator i = Inventory::items().find(*k);
			if (*k == _unihorn_key) {
				if (i == Inventory::items().end() || i->second.beatitude() == CURSED || data::UnicornHorn::unicornHorns().find(i->second.name()) == data::UnicornHorn::unicornHorns().end()) {
					_unihorn_key = ILLEGAL_ITEM;
					continue;
				}
			} else if (*k == _lizard_key) {
				if (i == Inventory::items().end()) {
					_lizard_key = ILLEGAL_ITEM;
					continue;
				}
				map<const string, const data::Corpse*>::const_iterator c = data::Corpse::corpses().find(i->second.name());
				if (c == data::Corpse::corpses().end() || !(c->second->effects() & EAT_EFFECT_CURE_STONING)) {
					_lizard_key = ILLEGAL_ITEM;
					continue;
				}
			}
		}
	} else if (event->id() == ReceivedItems::ID) {
		ReceivedItems* e = static_cast<ReceivedItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (data::UnicornHorn::unicornHorns().find(i->second.name()) != data::UnicornHorn::unicornHorns().end()) {
				if (i->second.beatitude() == BEATITUDE_UNKNOWN) {
					Beatify b(i->first, 175);
					EventBus::broadcast(&b);
				} else if (i->second.beatitude() != CURSED) {
					map<unsigned char, Item>::iterator u = Inventory::items().find(_unihorn_key);
					if (u == Inventory::items().end() || u->second.beatitude() == UNCURSED)
						_unihorn_key = i->first;
				}
				continue;
			}
			map<const string, const data::Corpse*>::const_iterator c = data::Corpse::corpses().find(i->second.name());
			if (c != data::Corpse::corpses().end() && (c->second->effects() & EAT_EFFECT_CURE_STONING)) {
				_lizard_key = i->first;
				continue;
			}
		}
	} else if (event->id() == WantItems::ID) {
		WantItems* e = static_cast<WantItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (i->second.beatitude() != CURSED && data::UnicornHorn::unicornHorns().find(i->second.name()) != data::UnicornHorn::unicornHorns().end()) {
				/* let's pick up all non-cursed unihorns */
				i->second.want(i->second.count());
				continue;
			}
			map<const string, const data::Corpse*>::const_iterator c = data::Corpse::corpses().find(i->second.name());
			if (c != data::Corpse::corpses().end() && (c->second->effects() & EAT_EFFECT_CURE_STONING)) {
				/* let's pick up all lizard corpses */
				i->second.want(i->second.count());
				continue;
			}
		}
	}
}
Example #5
0
void Armor::onEvent(event::Event * const event) {
	if (event->id() == ChangedInventoryItems::ID) {
		ChangedInventoryItems* e = static_cast<ChangedInventoryItems*> (event);
		for (set<unsigned char>::iterator k = e->keys().begin(); k != e->keys().end(); ++k) {
			if (betterThanCurrent(Inventory::itemAtKey(*k)))
				_put_on.insert(*k);
			else
				_put_on.erase(*k);
		}
	} else if (event->id() == ReceivedItems::ID) {
		ReceivedItems* e = static_cast<ReceivedItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (data::Armor::armors().find(i->second.name()) == data::Armor::armors().end())
				continue; // not armor
			if (i->second.beatitude() != BEATITUDE_UNKNOWN) {
				/* known beatitude, should we wear it? */
				if (i->second.beatitude() != CURSED && betterThanCurrent(i->second))
					_put_on.insert(i->first); // it's not cursed and (possibly) better than what we're wearing
				else
					_put_on.erase(i->first);
				continue;
			}
			Beatify b(i->first, 175);
			EventBus::broadcast(&b);
		}
	} else if (event->id() == WantItems::ID) {
		WantItems* e = static_cast<WantItems*> (event);
		if (Saiph::encumbrance() >= BURDENED) {
			/* burdened and beatifying, (and is on a stash): pick up */
			if (World::shortestPath(ALTAR).cost() < UNPASSABLE) {
				if (Saiph::encumbrance() < STRESSED) {
					if (e->safeStash()) {
						for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
							if (betterThanCurrent(i->second))
								i->second.want(i->second.count());
						}
					}
				}
				/* burdened and not beatifying: stash */
			} else if (e->safeStash()) {
				loopTimeout = World::turn() + 10;
			}
			/* not burdened */
		} else {
			/* and not on safe stash: pick up */
			if (!e->safeStash() && loopTimeout <= World::turn()) {
				/* ^ this also means 'drop at every safe stash if not burdened' */
				/* TODO: to avoid this, check whether on upstair, without stashing */
				for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
					if (betterThanCurrent(i->second))
						i->second.want(i->second.count());
				}
			}
		}
	}
}
Example #6
0
void Donate::onEvent(Event* const event) {
	if (event->id() == WantItems::ID) {
		/* we want gold to donate to priests */
		WantItems* e = static_cast<WantItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (i->second.name() == "gold piece")
				i->second.want(i->second.count());
		}
	}
}
Example #7
0
void Lamp::onEvent(event::Event * const event) {
	if (event->id() == ChangedInventoryItems::ID) {
		/* inventory changed, find lamp */
		findLamp();
	} else if (event->id() == ReceivedItems::ID) {
		/* received items, find lamp */
		findLamp();
	} else if (event->id() == WantItems::ID) {
		WantItems* e = static_cast<WantItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (data::Lamp::lamps().find(i->second.name()) != data::Lamp::lamps().end())
				i->second.want(i->second.count());
		}
	}
}
Example #8
0
/* methods */
void DiggingTool::onEvent(Event* const event) {
	if (event->id() == ChangedInventoryItems::ID || event->id() == ReceivedItems::ID) {
		findDigger();
	} else if (event->id() == WantItems::ID) {
		WantItems* e = static_cast<WantItems*> (event);
		int key;
		int score;

		// WantItems is called once per page while dropping, but the ranking needs to see the whole list...
		rankDiggers(key, score, (e->dropping() ? NULL : &Inventory::items()), (e->dropping() ? &Inventory::items() : &e->items()));

		if (key >= 0 && e->items().find(key) != e->items().end()) {
			Item& item = e->items()[(unsigned char)key];
			item.want(min(1, item.count()));
		}
	}
}
Example #9
0
void Quest::onEvent(event::Event* const event) {
	if (event->id() == WantItems::ID) {
		WantItems* e = static_cast<WantItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (i->second.name() == "silver bell" || i->second.name() == "Bell of Opening") {
				_seen_bell = true;
				i->second.want(i->second.count());
			} else if (i->second.name() == artifacts[Saiph::role()]) {
				_seen_arti = true;
				i->second.want(i->second.count());
			}

			if (_status != QUEST_STATUS_COMPLETED && _seen_bell && _seen_arti)
				setStatus(_portal_level, QUEST_STATUS_COMPLETED);
		}
	}
}
Example #10
0
File: Shop.cpp Project: Paiev/saiph
void Shop::onEvent(event::Event* const event) {
	if (event->id() == WantItems::ID) {
		WantItems* e = static_cast<WantItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (data::Pickaxe::pickaxes().find(i->second.name()) == data::Pickaxe::pickaxes().end())
				continue;

			int near = nearShop(Saiph::position());

			if (_shopping && near == THRESHOLD) {
				// drop them all
				// setting count to 0 prevents any other analyzer from overriding
				i->second.count(0);
			} else if (near == IN_SHOP) {
				// a pick in a doorway is a problem and should be picked up even if shopping
				i->second.want(i->second.count());
			}
		}
	}
}
Example #11
0
/* methods */
void Amulet::onEvent(Event* const event) {
	if (event->id() == ChangedInventoryItems::ID) {
		ChangedInventoryItems* e = static_cast<ChangedInventoryItems*> (event);
		map<unsigned char, Item> k;
		for (set<unsigned char>::iterator i = e->keys().begin(); i != e->keys().end(); ++i) {
			Item item = Inventory::itemAtKey(*i);
			k.insert(pair<unsigned char, Item>(*i, item));
		}
		_amulet_key = bestAmulet(k);
	} else if (event->id() == ReceivedItems::ID) {
		ReceivedItems* e = static_cast<ReceivedItems*> (event);
		_amulet_key = bestAmulet((e->items()));
	} else if (event->id() == WantItems::ID) {
		WantItems* e = static_cast<WantItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (wantItem(i->second))
				i->second.want(i->second.count());
		}
	}
}
Example #12
0
void Door::onEvent(Event* const event) {
	if (event->id() == ChangedInventoryItems::ID) {
		/* inventory changed, see if we lost our unlocking device or got a new/better one */
		if (Inventory::items().find(_unlock_tool_key) == Inventory::items().end())
			_unlock_tool_key = 0; // darn, we lost our unlocking device
		ChangedInventoryItems* e = static_cast<ChangedInventoryItems*> (event);
		for (set<unsigned char>::iterator k = e->keys().begin(); k != e->keys().end(); ++k) {
			map<unsigned char, Item>::iterator i = Inventory::items().find(*k);
			if (i != Inventory::items().end() && wantItem(i->second))
				_unlock_tool_key = *k; // better key than what we currently got
		}
	} else if (event->id() == ReceivedItems::ID) {
		ReceivedItems* e = static_cast<ReceivedItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (wantItem(i->second))
				_unlock_tool_key = i->first; // better key than what we currently got
		}
	} else if (event->id() == WantItems::ID) {
		WantItems* e = static_cast<WantItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if ((e->dropping() && _unlock_tool_key != ILLEGAL_ITEM && i->first == _unlock_tool_key) || wantItem(i->second))
				i->second.want(i->second.count());
		}
	} else if (event->id() == ShopDetected::ID) {
		ShopDetected* e = static_cast<ShopDetected*> (event);
		stack<Point> ps;
		for (int x = e->ul().col(); x <= e->lr().col(); ++x) {
			ps.push(Point(e->ul().row() - 1, x));
			ps.push(Point(e->lr().row() + 1, x));
		}
		for (int y = e->ul().row() - 1; y <= e->lr().row() + 1; ++y) {
			ps.push(Point(y, e->ul().col() - 1));
			ps.push(Point(y, e->lr().col() + 1));
		}
		for (; !ps.empty(); ps.pop()) {
			if (World::level().tile(ps.top()).symbol() != CLOSED_DOOR)
				continue;
			World::level().setDungeonSymbolValue(ps.top(), getDoorFlags(ps.top()) | DOOR_IS_SHOP);
		}
	}
}
Example #13
0
void Armor::onEvent(event::Event * const event) {
	if (event->id() == ChangedInventoryItems::ID) {
		ChangedInventoryItems* e = static_cast<ChangedInventoryItems*> (event);
		for (set<unsigned char>::iterator k = e->keys().begin(); k != e->keys().end(); ++k) {
			if (betterThanCurrent(Inventory::itemAtKey(*k)))
				_put_on.insert(*k);
			else
				_put_on.erase(*k);
		}
	} else if (event->id() == ReceivedItems::ID) {
		ReceivedItems* e = static_cast<ReceivedItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (data::Armor::armors().find(i->second.name()) == data::Armor::armors().end())
				continue; // not armor
			if (i->second.beatitude() != BEATITUDE_UNKNOWN) {
				/* known beatitude, should we wear it? */
				if (i->second.beatitude() != CURSED && betterThanCurrent(i->second))
					_put_on.insert(i->first); // it's not cursed and (possibly) better than what we're wearing
				else
					_put_on.erase(i->first);
				continue;
			}
			Beatify b(i->first, 175);
			EventBus::broadcast(&b);
		}
	} else if (event->id() == WantItems::ID) {
		WantItems* e = static_cast<WantItems*> (event);
		if (e->safeStash() && World::shortestPath(ALTAR).cost() >= UNPASSABLE) {
			/* on safe stash and can't path to altar, drop */
		} else if (Saiph::encumbrance() < BURDENED && (!e->safeStash() || World::shortestPath(ALTAR).cost() < UNPASSABLE)) {
			/* we're not burdened and not on a safe stash or we can't reach an altar, loot armor */
			/* if we are on a safe stash and can't reach an altar then we will drop armor */
			for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
				if (betterThanCurrent(i->second))
					i->second.want(i->second.count());
			}
		}
	}
}
Example #14
0
void Beatitude::onEvent(event::Event* const event) {
	if (event->id() == Beatify::ID) {
		Beatify* e = static_cast<Beatify*> (event);
		set<unsigned char>::iterator b = _beatify.find(e->key());
		_beatify.insert(e->key());
		if (e->priority() > _max_priority)
			_max_priority = e->priority();
	} else if (event->id() == WantItems::ID && World::level().tile().symbol() == ALTAR) {
		/* looting or picking up items at an altar */
		WantItems* e = static_cast<WantItems*> (event);
		if (e->dropping()) {
			for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
				if (i->second.beatitude() != BEATITUDE_UNKNOWN)
					continue; // know beatitude already
				/* should drop this item, force it by setting count to 0 */
				i->second.count(0);
			}
			_beatify.clear();
			_max_priority = ILLEGAL_PRIORITY;
		}
	}
}
Example #15
0
void Health::onEvent(event::Event * const event) {
	if (event->id() == ChangedInventoryItems::ID) {
		ChangedInventoryItems* e = static_cast<ChangedInventoryItems*> (event);
		for (set<unsigned char>::iterator k = e->keys().begin(); k != e->keys().end(); ++k) {
			map<unsigned char, Item>::iterator i = Inventory::items().find(*k);
			if (*k == _unihorn_key) {
				if (i == Inventory::items().end() || i->second.beatitude() == CURSED || data::UnicornHorn::unicornHorns().find(i->second.name()) == data::UnicornHorn::unicornHorns().end()) {
					_unihorn_key = ILLEGAL_ITEM;
					continue;
				}
			} else if (*k == _lizard_key) {
				if (i == Inventory::items().end()) {
					_lizard_key = ILLEGAL_ITEM;
					continue;
				}
				map<const string, const data::Corpse*>::const_iterator c = data::Corpse::corpses().find(i->second.name());
				if (c == data::Corpse::corpses().end() || !(c->second->effects() & EAT_EFFECT_CURE_STONING)) {
					_lizard_key = ILLEGAL_ITEM;
					continue;
				}
			}
		}
	} else if (event->id() == ReceivedItems::ID) {
		ReceivedItems* e = static_cast<ReceivedItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (data::UnicornHorn::unicornHorns().find(i->second.name()) != data::UnicornHorn::unicornHorns().end()) {
				if (i->second.beatitude() == BEATITUDE_UNKNOWN) {
					Beatify b(i->first, 175);
					EventBus::broadcast(&b);
				} else if (i->second.beatitude() != CURSED) {
					map<unsigned char, Item>::iterator u = Inventory::items().find(_unihorn_key);
					if (u == Inventory::items().end() || u->second.beatitude() == UNCURSED)
						_unihorn_key = i->first;
				}
				continue;
			}
			map<const string, const data::Corpse*>::const_iterator c = data::Corpse::corpses().find(i->second.name());
			if (c != data::Corpse::corpses().end() && (c->second->effects() & EAT_EFFECT_CURE_STONING)) {
				_lizard_key = i->first;
				continue;
			}
		}
	} else if (event->id() == WantItems::ID) {
		WantItems* e = static_cast<WantItems*> (event);
		for (map<unsigned char, Item>::iterator i = e->items().begin(); i != e->items().end(); ++i) {
			if (i->second.beatitude() != CURSED && data::UnicornHorn::unicornHorns().find(i->second.name()) != data::UnicornHorn::unicornHorns().end()) {
				/* non-cursed unihorn */
				/* if we want to limit amount of unihorns, do it here, check inventory how many we got */
				int unihornNum = 0;
				for (map<unsigned char, Item>::iterator i2 = e->items().begin(); i2 != e->items().end(); ++i2) {
					if (i2->second.beatitude() != CURSED && data::UnicornHorn::unicornHorns().find(i->second.name()) != data::UnicornHorn::unicornHorns().end())
						unihornNum++;
				}
				/* keep at least 3 on hand */
				if (unihornNum < 3)
					i->second.want(i->second.count());
				continue;
			}
			map<const string, const data::Corpse*>::const_iterator c = data::Corpse::corpses().find(i->second.name());
			if (c != data::Corpse::corpses().end() && (c->second->effects() & EAT_EFFECT_CURE_STONING)) {
				/* lizard corpse */
				/* if we want to limit amount of lizard corpses, do it here, check inventory how many we got */
				int lizardNum = 0;
				for (map<unsigned char, Item>::iterator i2 = e->items().begin(); i2 != e->items().end(); ++i2) {
					map<const string, const data::Corpse*>::const_iterator c2 = data::Corpse::corpses().find(i2->second.name());
					if (c != data::Corpse::corpses().end() && (c->second->effects() & EAT_EFFECT_CURE_STONING))
						lizardNum++;
				}
				if (lizardNum < 3)
					i->second.want(i->second.count());
				continue;
			}
		}
	}
}