Esempio n. 1
0
static void activate(int val)
{
	Entity *e;

	if (self->health == 3)
	{
		e = addTeslaPack(0, 0, "item/tesla_pack_full");

		addToInventory(e);

		self->health = -1;
	}

	else
	{
		e = getInventoryItemByObjectiveName("Tesla Pack");

		if (e != NULL && e->health == 0)
		{
			removeInventoryItemByObjectiveName(e->objectiveName);

			self->health = 0;

			self->thinkTime = 180;
		}
	}

	setChargeState();
}
Esempio n. 2
0
void ControlSystem::pickUpItem() const
{
  if (player_turn_->turn_taken) {
    return;
  }
  GameObject item = getItemAtPos(player_space_->pos);
  if (item.getId()) {
    addToInventory(item);
  }
}
Esempio n. 3
0
static void addStatue(int val)
{
	Entity *e;

	if (self->target == NULL)
	{
		e = getCurrentInventoryItem();

		if (e == NULL || strstr(e->name, "_statue") == NULL)
		{
			runScript("statue_required");
		}

		else
		{
			STRNCPY(self->objectiveName, e->objectiveName, sizeof(e->objectiveName));

			e = addEntity(*e, self->x, self->y);

			self->target = e;

			self->target->x = self->x + self->w / 2;

			self->target->x -= self->target->w / 2;

			self->target->y = self->y - self->target->h;

			self->target->flags |= FLY;

			self->target->touch = NULL;

			self->target->action = &statueWait;

			removeInventoryItemByObjectiveName(e->objectiveName);

			validate();
		}
	}

	else
	{
		e = addEntity(*self->target, 0, 0);

		addToInventory(e);

		self->target->inUse = FALSE;

		self->target = NULL;

		self->objectiveName[0] = '\0';
	}
}
Esempio n. 4
0
static void collectBomb(Entity *other)
{
	Entity *bomb = NULL;

	if (other->type == PLAYER && self->thinkTime <= 0 && other->health > 0)
	{
		if (getInventoryItemByObjectiveName("Bomb") == NULL)
		{
			bomb = addBomb(other->x, other->y, "item/bomb");

			STRNCPY(bomb->objectiveName, "Bomb", sizeof(bomb->objectiveName));

			addToInventory(bomb);
		}

		self->thinkTime = self->maxThinkTime;
	}
}
Esempio n. 5
0
static void collectSpore(Entity *other)
{
	Entity *spore = NULL;

	if (self->thinkTime <= 0 && other->health > 0)
	{
		if (getInventoryItemByObjectiveName("Spore") == NULL)
		{
			spore = addSpore(other->x, other->y, "item/spores");

			STRNCPY(spore->objectiveName, "Spore", sizeof(spore->objectiveName));

			addToInventory(spore);
		}

		self->thinkTime = self->maxThinkTime;
	}
}
Esempio n. 6
0
/**
 * @brief Tries to add an item to a container (in the inventory inv).
 * @param[in] inv The inventory to add the item to.
 * @param[in] item Item to add to inventory (actually a copy of it).
 * @param[in] container Container id.
 * @sa findSpace
 * @sa addToInventory
 */
bool InventoryInterface::tryAddToInventory (Inventory* const inv, const Item* const item, const invDef_t* container)
{
	int x, y;

	inv->findSpace(container, item, &x, &y, nullptr);

	if (x == NONE) {
		assert(y == NONE);
		return false;
	} else {
		const int checkedTo = inv->canHoldItem(container, item->def(), x, y, nullptr);
		if (!checkedTo)
			return false;

		const bool rotated = checkedTo == INV_FITS_ONLY_ROTATED;
		Item itemRotation = *item;
		itemRotation.rotated = rotated;

		return addToInventory(inv, &itemRotation, container, x, y, 1) != nullptr;
	}
}
Esempio n. 7
0
void Hero::search()
{

	std::cout << "Items:\n";
	if (location->getItems().size() == 0)
		std::cout << "The room is empty\n\n";
	else
	{
		std::cout << "You found: ";
		bool hasPrev = false;
		// temp display
		for (Item* item : location->getItems())
		{
			if (hasPrev) cout << ", ";
			std::cout << item->getName();
			addToInventory(item);
			hasPrev = true;
		}

		std::cout << std::endl << std::endl;
	}
	addPerception(1);
}
Esempio n. 8
0
char *loadResources(char *buffer)
{
	int i, startX, startY, type, name, resourceType;
	char *token, *line, itemName[MAX_VALUE_LENGTH], *savePtr2, *savePtr;
	Entity *e;

	savePtr = NULL;

	resourceType = ENTITY_DATA;

	if (key == NULL || value == NULL)
	{
		key = malloc(sizeof(char *) * MAX_PROPS_FILES);
		value = malloc(sizeof(char *) * MAX_PROPS_FILES);

		if (key == NULL || value == NULL)
		{
			showErrorAndExit("Ran out of memory when loading properties");
		}

		for (i=0;i<MAX_PROPS_FILES;i++)
		{
			key[i] = malloc(MAX_VALUE_LENGTH);
			value[i] = malloc(MAX_VALUE_LENGTH);

			if (key[i] == NULL || value[i] == NULL)
			{
				showErrorAndExit("Ran out of memory when loading properties");
			}
		}
	}

	for (i=0;i<MAX_PROPS_FILES;i++)
	{
		key[i][0] = '\0';
		value[i][0] = '\0';
	}

	i = 0;

	name = type = startX = startY = -1;

	e = NULL;

	line = strtok_r(buffer, "\n", &savePtr);

	while (line != NULL)
	{
		if (line[strlen(line) - 1] == '\n')
		{
			line[strlen(line) - 1] = '\0';
		}

		if (line[strlen(line) - 1] == '\r')
		{
			line[strlen(line) - 1] = '\0';
		}

		if (line[0] == '#' || line[0] == '\n')
		{
			line = strtok_r(NULL, "\n", &savePtr);

			continue;
		}

		else if (line[0] == ' ')
		{
			printf("WARNING: Line starts with a space\n");

			#if DEV == 1
				exit(0);
			#endif

			line = strtok_r(NULL, "\n", &savePtr);

			continue;
		}

		sscanf(line, "%s", itemName);

		if (strcmpignorecase(itemName, "MAP_NAME") == 0)
		{
			break;
		}

		else if (strcmpignorecase(itemName, "UPDATE_ENTITY") == 0 || strcmpignorecase(itemName, "REMOVE_ENTITY") == 0)
		{
			break;
		}

		else if (strcmpignorecase(line, "PLAYER_INVENTORY") == 0)
		{
			resourceType = PLAYER_INVENTORY;
		}

		else if (strstr(line, "INVENTORY_INDEX") != NULL)
		{
			sscanf(line, "%*s %d", &startX);

			setInventoryIndex(startX);
		}

		else if (strcmpignorecase(line, "ENTITY_DATA") == 0)
		{
			resourceType = ENTITY_DATA;
		}

		else if (strcmpignorecase(line, "{") == 0)
		{
			i = 0;

			name = type = startX = startY = -1;

			e = NULL;
		}

		else if (strcmpignorecase(line, "}") == 0)
		{
			e = addEntityFromResource(value[type], value[name], startX == -1 ? 0 : atoi(value[startX]), startY == -1 ? 0 : atoi(value[startY]));

			if (e != NULL)
			{
				for (i=0;i<MAX_PROPS_FILES;i++)
				{
					if (strlen(key[i]) > 0)
					{
						setProperty(e, key[i], value[i]);
					}
				}

				if (resourceType == PLAYER_INVENTORY)
				{
					addToInventory(e);
				}
			}

			for (i=0;i<MAX_PROPS_FILES;i++)
			{
				key[i][0] = '\0';

				value[i][0] = '\0';
			}

			i = 0;
		}

		else
		{
			token = strtok_r(line, " ", &savePtr2);

			STRNCPY(key[i], token, MAX_VALUE_LENGTH);

			token = strtok_r(NULL, "\0", &savePtr2);

			if (token != NULL)
			{
				STRNCPY(value[i], token, MAX_VALUE_LENGTH);
			}

			else
			{
				key[i][0] = '\0';
			}

			if (strcmpignorecase(key[i], "TYPE") == 0)
			{
				type = i;
			}

			else if (strcmpignorecase(key[i], "START_X") == 0)
			{
				startX = i;
			}

			else if (strcmpignorecase(key[i], "START_Y") == 0)
			{
				startY = i;
			}

			else if (strcmpignorecase(key[i], "NAME") == 0)
			{
				name = i;
			}

			i++;
		}

		line = strtok_r(NULL, "\n", &savePtr);
	}

	loadInventoryItems();

	return line;
}
Esempio n. 9
0
/**
 * @brief Conditions for moving items between containers.
 * @param[in] inv The inventory to move in.
 * @param[in] from Source container.
 * @param[in] fItem The item to be moved.
 * @param[in] to Destination container.
 * @param[in] tx X coordinate in destination container.
 * @param[in] ty Y coordinate in destination container.
 * @param[in,out] TU pointer to entity available TU at this moment
 * or @c nullptr if TU doesn't matter (outside battlescape)
 * @param[out] uponItem The item fItem is evetually dropped upon
 * @return IA_NOTIME when not enough TU.
 * @return IA_NONE if no action possible.
 * @return IA_NORELOAD if you cannot reload a weapon.
 * @return IA_RELOAD_SWAP in case of exchange of ammo in a weapon.
 * @return IA_RELOAD when reloading.
 * @return IA_ARMOUR when placing an armour on the actor.
 * @return IA_MOVE when just moving an item.
 */
inventory_action_t InventoryInterface::moveInInventory (Inventory* const inv, const invDef_t* from, Item* fItem, const invDef_t* to, int tx, int ty, int* TU, Item**  uponItem)
{
	assert(to);
	assert(from);

	if (uponItem)
		*uponItem = nullptr;

	if (from == to && fItem->getX() == tx && fItem->getY() == ty)
		return IA_NONE;

	int time = from->out + to->in;
	if (from == to) {
		if (from->isFloorDef())
			time = 0;
		else
			time /= 2;
	}

	if (TU && *TU < time)
		return IA_NOTIME;

	assert(inv);

	int checkedTo = INV_DOES_NOT_FIT;
	/* Special case for moving an item within the same container. */
	if (from == to) {
		/* Do nothing if we move inside a scroll container. */
		if (from->scroll)
			return IA_NONE;

		const Container& cont = inv->getContainer(from->id);
		Item* item = nullptr;
		while ((item = cont.getNextItem(item))) {
			if (item != fItem)
				continue;

			if (item->getAmount() <= 1)
				continue;
			checkedTo = inv->canHoldItem(to, item->def(), tx, ty, fItem);
			if (!(checkedTo & INV_FITS))
				return IA_NONE;

			item->setX(tx);
			item->setY(ty);
			if (uponItem)
				*uponItem = item;
			return IA_MOVE;
		}
	}

	/* If weapon is twohanded and is moved from hand to hand do nothing. */
	/* Twohanded weapon are only in CID_RIGHT. */
	if (fItem->def()->fireTwoHanded && to->isLeftDef() && from->isRightDef()) {
		return IA_NONE;
	}

	/* If non-armour moved to an armour slot then abort.
	 * Same for non extension items when moved to an extension slot. */
	if ((to->armour && !fItem->isArmour())
	 || (to->implant && !fItem->def()->implant)
	 || (to->headgear && !fItem->def()->headgear)) {
		return IA_NONE;
	}

	/* Check if the target is a blocked inv-armour and source!=dest. */
	if (to->single)
		checkedTo = inv->canHoldItem(to, fItem->def(), 0, 0, fItem);
	else {
		if (tx == NONE || ty == NONE)
			inv->findSpace(to, fItem, &tx, &ty, fItem);
		/* still no valid location found */
		if (tx == NONE || ty == NONE)
			return IA_NONE;

		checkedTo = inv->canHoldItem(to, fItem->def(), tx, ty, fItem);
	}

	Item* ic;
	bool alreadyRemovedSource = false;
	if (to->armour && from != to && !checkedTo) {
		/* Store x/y origin coordinates of removed (source) item.
		 * When we re-add it we can use this. */
		const int cacheFromX = fItem->getX();
		const int cacheFromY = fItem->getY();

		/* Check if destination/blocking item is the same as source/from item.
		 * In that case the move is not needed -> abort. */
		Item* icTo = inv->getItemAtPos(to, tx, ty);
		if (fItem->def() == icTo->def())
			return IA_NONE;

		/* Actually remove the ammo from the 'from' container. */
		if (!removeFromInventory(inv, from, fItem))
			return IA_NONE;
		else
			/* Removal successful - store this info. */
			alreadyRemovedSource = true;

		Item cacheItem2 = this->cacheItem; /* Save/cache (source) item. The cacheItem is modified in MoveInInventory. */

		/* Move the destination item to the source. */
		moveInInventory(inv, to, icTo, from, cacheFromX, cacheFromY, TU, uponItem);

		/* Reset the cached item (source) (It'll be move to container emptied by destination item later.) */
		this->cacheItem = cacheItem2;
		checkedTo = inv->canHoldItem(to, this->cacheItem.def(), 0, 0, fItem);
	} else if (!checkedTo) {
		/* Get the target-invlist (e.g. a weapon). We don't need to check for
		 * scroll because checkedTo is always true here. */
		ic = inv->getItemAtPos(to, tx, ty);

		if (ic && !to->isEquipDef() && fItem->def()->isLoadableInWeapon(ic->def())) {
			/* A target-item was found and the dragged item (implicitly ammo)
			 * can be loaded in it (implicitly weapon). */
			if (ic->getAmmoLeft() >= ic->def()->ammo && ic->ammoDef() == fItem->def()) {
				/* Weapon already fully loaded with the same ammunition -> abort */
				return IA_NORELOAD;
			}
			time += ic->def()->getReloadTime();
			if (!TU || *TU >= time) {
				if (TU)
					*TU -= time;
				if (ic->getAmmoLeft() >= ic->def()->ammo) {
					/* exchange ammo */
					const Item item(ic->ammoDef());
					/* Put current ammo in place of the new ammo unless floor - there can be more than 1 item */
					const int cacheFromX = from->isFloorDef() ? NONE : fItem->getX();
					const int cacheFromY = from->isFloorDef() ? NONE : fItem->getY();

					/* Actually remove the ammo from the 'from' container. */
					if (!removeFromInventory(inv, from, fItem))
						return IA_NONE;

					/* Add the currently used ammo in place of the new ammo in the "from" container. */
					if (addToInventory(inv, &item, from, cacheFromX, cacheFromY, 1) == nullptr)
						Sys_Error("Could not reload the weapon - add to inventory failed (%s)", invName);

					ic->setAmmoDef(this->cacheItem.def());
					if (uponItem)
						*uponItem = ic;
					return IA_RELOAD_SWAP;
				} else {
					/* Actually remove the ammo from the 'from' container. */
					if (!removeFromInventory(inv, from, fItem))
						return IA_NONE;

					ic->setAmmoDef(this->cacheItem.def());
					/* loose ammo of type ic->m saved on server side */
					ic->setAmmoLeft(ic->def()->ammo);
					if (uponItem)
						*uponItem = ic;
					return IA_RELOAD;
				}
			}
			/* Not enough time -> abort. */
			return IA_NOTIME;
		}

		/* temp container like CID_EQUIP and CID_FLOOR */
		if (ic && to->temp) {
			/* We are moving to a blocked location container but it's the base-equipment floor or a battlescape floor.
			 * We add the item anyway but it'll not be displayed (yet)
			 * This is then used in addToInventory below.*/
			/** @todo change the other code to browse through these things. */
			inv->findSpace(to, fItem, &tx, &ty, fItem);
			if (tx == NONE || ty == NONE) {
				Com_DPrintf(DEBUG_SHARED, "MoveInInventory - item will be added non-visible (%s)\n", invName);
			}
		} else {
			/* Impossible move -> abort. */
			return IA_NONE;
		}
	}

	/* twohanded exception - only CID_RIGHT is allowed for fireTwoHanded weapons */
	if (fItem->def()->fireTwoHanded && to->isLeftDef())
		to = &this->csi->ids[CID_RIGHT];

	switch (checkedTo) {
	case INV_DOES_NOT_FIT:
		/* Impossible move - should be handled above, but add an abort just in case */
		Com_Printf("MoveInInventory: Item doesn't fit into container.");
		return IA_NONE;
	case INV_FITS:
		/* Remove rotated tag */
		fItem->rotated = false;
		break;
	case INV_FITS_ONLY_ROTATED:
		/* Set rotated tag */
		fItem->rotated = true;
		break;
	case INV_FITS_BOTH:
		/* Leave rotated tag as-is */
		break;
	}

	/* Actually remove the item from the 'from' container (if it wasn't already removed). */
	if (!alreadyRemovedSource)
		if (!removeFromInventory(inv, from, fItem))
			return IA_NONE;

	/* successful */
	if (TU)
		*TU -= time;

	assert(this->cacheItem.def());
	ic = addToInventory(inv, &this->cacheItem, to, tx, ty, 1);

	/* return data */
	if (uponItem) {
		assert(ic);
		*uponItem = ic;
	}

	if (to->isArmourDef()) {
		assert(this->cacheItem.isArmour());
		return IA_ARMOUR;
	}

	return IA_MOVE;
}