示例#1
0
文件: wizard.c 项目: mtadd/angband
bool wiz_create_item_subaction(menu_type *m, const ui_event *e, int oid)
{
	object_kind **choices = menu_priv(m);
	object_kind *kind = choices[oid];

	object_type *i_ptr;
	object_type object_type_body;

	if (e->type != EVT_SELECT)
		return TRUE;


	/* Get local object */
	i_ptr = &object_type_body;

	/* Create the item */
	object_prep(i_ptr, kind, p_ptr->depth, RANDOMISE);

	/* Apply magic (no messages, no artifacts) */
	apply_magic(i_ptr, p_ptr->depth, FALSE, FALSE, FALSE);

	/* Mark as cheat, and where created */
	i_ptr->origin = ORIGIN_CHEAT;
	i_ptr->origin_depth = p_ptr->depth;

	if (kind->tval == TV_GOLD)
		make_gold(i_ptr, p_ptr->depth, kind->sval);

	/* Drop the object from heaven */
	drop_near(cave, i_ptr, 0, p_ptr->py, p_ptr->px, TRUE);

	return FALSE;
}
示例#2
0
文件: wizard.c 项目: mtadd/angband
/*
 * Create lots of items.
 */
static void wiz_test_kind(int tval)
{
	int py = p_ptr->py;
	int px = p_ptr->px;
	int sval;

	object_type object_type_body;
	object_type *i_ptr = &object_type_body;

	for (sval = 0; sval < 255; sval++)
	{
		object_kind *kind = lookup_kind(tval, sval);
		if (!kind) continue;

		/* Create the item */
		object_prep(i_ptr, kind, p_ptr->depth, RANDOMISE);

		/* Apply magic (no messages, no artifacts) */
		apply_magic(i_ptr, p_ptr->depth, FALSE, FALSE, FALSE);

		/* Mark as cheat, and where created */
		i_ptr->origin = ORIGIN_CHEAT;
		i_ptr->origin_depth = p_ptr->depth;

		if (tval == TV_GOLD)
			make_gold(i_ptr, p_ptr->depth, sval);

		/* Drop the object from heaven */
		drop_near(cave, i_ptr, 0, py, px, TRUE);
	}

	msg("Done.");
}
示例#3
0
static bool _create_arrows(void)
{
    int             item, slot;
    object_type  forge;

    item_tester_hook = _create_ammo_p;
    if (!get_item(&item, "Convert which item? ", "You have no item to convert.", USE_INVEN | USE_FLOOR)) 
        return FALSE;

    object_prep(&forge, lookup_kind(TV_ARROW, m_bonus(1, p_ptr->lev)+ 1));
    forge.number = (byte)rand_range(5, 10);
    apply_magic(&forge, p_ptr->lev, AM_NO_FIXED_ART);
    obj_identify(&forge);
    forge.discount = 99;

    msg_print("You make some ammo.");
    if (item >= 0)
    {
        inven_item_increase(item, -1);
        inven_item_describe(item);
        inven_item_optimize(item);
    }
    else
    {
        floor_item_increase(0 - item, -1);
        floor_item_describe(0 - item);
        floor_item_optimize(0 - item);
    }

    slot = inven_carry(&forge);
    if (slot >= 0) 
        autopick_alter_item(slot, FALSE);
    return TRUE;
}
示例#4
0
/*
 * Auxilliary Wizard routine for creating objects
 *
 * Hack -- this routine always makes a "dungeon object", and applies
 * magic to it, and attempts to decline cursed items. XXX XXX XXX
 */
static void wiz_create_item_aux(int k_idx)
{
	int py = p_ptr->py;
	int px = p_ptr->px;
		
	object_type *i_ptr;
	object_type object_type_body;
		
	/* Get local object */
	i_ptr = &object_type_body;
	
	/* Create the item */
	object_prep(i_ptr, k_idx);
		
	/* Apply magic (no messages, no artefacts) */
	apply_magic(i_ptr, p_ptr->depth, FALSE, FALSE, FALSE, FALSE);
	
	// apply the autoinscription (if any)
	apply_autoinscription(i_ptr);
	
	if (i_ptr->tval == TV_ARROW) i_ptr->number = 24;
	
	/* Drop the object from heaven */
	drop_near(i_ptr, -1, py, px);
}
示例#5
0
文件: wizard2.c 项目: naota/hengband
/*!
 * @brief 任意のベースアイテム生成のメインルーチン /
 * Wizard routine for creating objects		-RAK-
 * @return なし
 * @details
 * Heavily modified to allow magification and artifactification  -Bernd-
 *
 * Note that wizards cannot create objects on top of other objects.
 *
 * Hack -- this routine always makes a "dungeon object", and applies
 * magic to it, and attempts to decline cursed items.
 */
static void wiz_create_item(void)
{
	object_type	forge;
	object_type *q_ptr;

	int k_idx;


	/* Save the screen */
	screen_save();

	/* Get object base type */
	k_idx = wiz_create_itemtype();

	/* Restore the screen */
	screen_load();


	/* Return if failed */
	if (!k_idx) return;

	if (k_info[k_idx].gen_flags & TRG_INSTA_ART)
	{
		int i;

		/* Artifactify */
		for (i = 1; i < max_a_idx; i++)
		{
			/* Ignore incorrect tval */
			if (a_info[i].tval != k_info[k_idx].tval) continue;

			/* Ignore incorrect sval */
			if (a_info[i].sval != k_info[k_idx].sval) continue;

			/* Create this artifact */
			(void)create_named_art(i, p_ptr->y, p_ptr->x);

			/* All done */
			msg_print("Allocated(INSTA_ART).");

			return;
		}
	}

	/* Get local object */
	q_ptr = &forge;

	/* Create the item */
	object_prep(q_ptr, k_idx);

	/* Apply magic */
	apply_magic(q_ptr, dun_level, AM_NO_FIXED_ART);

	/* Drop the object from heaven */
	(void)drop_near(q_ptr, -1, p_ptr->y, p_ptr->x);

	/* All done */
	msg_print("Allocated.");
}
示例#6
0
/**
 * Attempt to make an object
 *
 * \param c is the current dungeon level.
 * \param j_ptr is the object struct to be populated.
 * \param lev is the creation level of the object (not necessarily == depth).
 * \param good is whether the object is to be good
 * \param great is whether the object is to be great
 * \param value is the value to be returned to the calling function
 *
 * Returns the whether or not creation worked.
 */
bool make_object(struct cave *c, object_type *j_ptr, int lev, bool good,
	bool great, s32b *value)
{
	int base, art, div;
	object_kind *kind;

	/* Base level and artifact chance for the object */
	if (great) {
		art = ART_GREAT;
		base = lev + 10 + m_bonus(5, lev);
	} else if (good) {
		art = ART_GOOD;
		base = lev + 5 + m_bonus(5, lev);
	} else {
		art = ART_NORMAL;
		base = lev;
	}

	/* Small hack to bring artifact frequencies at low depths in line with V */
	div = 9 - p_ptr->depth;
	if (div < 1)
		div = 1;

	/* Try to make an artifact */
	if (one_in_(art * div)) {
		if (make_artifact(j_ptr, lev)) {
			if (value)
				*value = object_value_real(j_ptr, 1, FALSE, TRUE);
			return TRUE;
		}
	}

	/* Get the object, prep it and apply magic */
	kind = get_obj_num(base, good || great);
	if (!kind) return FALSE;
	object_prep(j_ptr, kind, base, RANDOMISE);
	apply_magic(j_ptr, base, FALSE, good, great);

	/* Generate multiple items */
	if (kind->gen_mult_prob >= randint1(100))
		j_ptr->number = randcalc(kind->stack_size, lev, RANDOMISE);

	if (j_ptr->number >= MAX_STACK_SIZE)
		j_ptr->number = MAX_STACK_SIZE - 1;

	/* Return value, increased for uncursed out-of-depth objects */
	if (value)
		*value = object_value_real(j_ptr, j_ptr->number, FALSE, TRUE);

	if (!cursed_p(j_ptr->flags) && (kind->alloc_min > c->depth)) {
		if (value) *value = (kind->alloc_min - c->depth) * (*value / 5);
	}

	return TRUE;
}
示例#7
0
文件: obj-make.c 项目: fizzix/angband
/**
 * Attempt to make an object
 *
 * \param c is the current dungeon level.
 * \param lev is the creation level of the object (not necessarily == depth).
 * \param good is whether the object is to be good
 * \param great is whether the object is to be great
 * \param extra_roll is whether we get an extra roll in apply_magic()
 * \param value is the value to be returned to the calling function
 * \param tval is the desired tval, or 0 if we allow any tval
 *
 * \return a pointer to the newly allocated object, or NULL on failure.
 */
struct object *make_object(struct chunk *c, int lev, bool good, bool great,
						   bool extra_roll, s32b *value, int tval)
{
	int base;
	struct object_kind *kind;
	struct object *new_obj;

	/* Try to make a special artifact */
	if (one_in_(good ? 10 : 1000)) {
		new_obj = make_artifact_special(lev);
		if (new_obj) {
			if (value) *value = object_value_real(new_obj, 1, false);
			return new_obj;
		}

		/* If we failed to make an artifact, the player gets a good item */
		good = true;
	}

	/* Base level for the object */
	base = (good ? (lev + 10) : lev);

	/* Try to choose an object kind */
	kind = get_obj_num(base, good || great, tval);
	if (!kind)
		return NULL;

	/* Make the object, prep it and apply magic */
	new_obj = object_new();
	object_prep(new_obj, kind, lev, RANDOMISE);
	if (one_in_(20) && tval_is_wearable(new_obj)) {
		apply_curse(new_obj, &lev);
	}
	apply_magic(new_obj, lev, true, good, great, extra_roll);
	apply_curse_knowledge(new_obj);

	/* Generate multiple items */
	if (kind->gen_mult_prob >= randint1(100))
		new_obj->number = randcalc(kind->stack_size, lev, RANDOMISE);

	if (new_obj->number > z_info->stack_size)
		new_obj->number = z_info->stack_size;

	/* Get the value */
	if (value)
		*value = object_value_real(new_obj, new_obj->number, false);

	/* Boost of 20% per level OOD for uncursed objects */
	if ((!new_obj->curses) && (kind->alloc_min > c->depth)) {
		if (value) *value += (kind->alloc_min - c->depth) * (*value / 5);
	}

	return new_obj;
}
示例#8
0
/*
 * Helper function for monster_death -
 * Intended only to drop Morgoth's special artifacts
 */
static void mon_drop_chosen_objects(monster_type *m_ptr)
{
	object_type *i_ptr;
	object_type object_type_body;

	/* Get local object */
	i_ptr = &object_type_body;

	/* Mega-Hack -- Prepare to make "Grond" */
	object_prep(i_ptr, lookup_kind(TV_HAFTED, SV_GROND));

	/* Mega-Hack -- Mark this item as "Grond" */
	i_ptr->art_num = ART_GROND;

	/* Mega-Hack -- Actually create "Grond" */
	apply_magic(i_ptr, -1, TRUE, TRUE, TRUE, FALSE);

	/* Remember history */
	object_history(i_ptr, ORIGIN_MORGOTH, 0);

	/* Drop it in the dungeon */
	drop_near(i_ptr, -1, m_ptr->fy, m_ptr->fx);

	/* Get local object */
	i_ptr = &object_type_body;

	/* Mega-Hack -- Prepare to make "Morgoth's crown" */
	object_prep(i_ptr, lookup_kind(TV_CROWN, SV_MORGOTH));

	/* Mega-Hack -- Mark this item as "Morgoth" */
	i_ptr->art_num = ART_MORGOTH;

	/* Mega-Hack -- Actually create "Morgoth" */
	apply_magic(i_ptr, -1, TRUE, TRUE, TRUE, FALSE);

	/* Remember history */
	object_history(i_ptr, ORIGIN_MORGOTH, 0);

	/* Drop it in the dungeon */
	drop_near(i_ptr, -1, m_ptr->fy, m_ptr->fx);
}
示例#9
0
/**
 * Attempt to make an object
 *
 * \param c is the current dungeon level.
 * \param lev is the creation level of the object (not necessarily == depth).
 * \param good is whether the object is to be good
 * \param great is whether the object is to be great
 * \param extra_roll is whether we get an extra roll in apply_magic()
 * \param value is the value to be returned to the calling function
 * \param tval is the desired tval, or 0 if we allow any tval
 *
 * \return a pointer to the newly allocated object, or NULL on failure.
 */
struct object *make_object(struct chunk *c, int lev, bool good, bool great,
						   bool extra_roll, s32b *value, int tval)
{
	int base;
	object_kind *kind;
	struct object *new_obj;

	/* Try to make a special artifact */
	if (one_in_(good ? 10 : 1000)) {
		new_obj = make_artifact_special(lev);
		if (new_obj) {
			if (value) *value = object_value_real(new_obj, 1, FALSE, TRUE);
			return new_obj;
		}

		/* If we failed to make an artifact, the player gets a good item */
		good = TRUE;
	}

	/* Base level for the object */
	base = (good ? (lev + 10) : lev);

	/* Try to choose an object kind */
	kind = get_obj_num(base, good || great, tval);
	if (!kind)
		return NULL;

	/* Make the object, prep it and apply magic */
	new_obj = object_new();
	object_prep(new_obj, kind, lev, RANDOMISE);
	apply_magic(new_obj, lev, TRUE, good, great, extra_roll);

	/* Generate multiple items */
	if (kind->gen_mult_prob >= randint1(100))
		new_obj->number = randcalc(kind->stack_size, lev, RANDOMISE);

	if (new_obj->number > z_info->stack_size)
		new_obj->number = z_info->stack_size;

	/* Return value, increased for uncursed out-of-depth objects */
	if (value)
		*value = object_value_real(new_obj, new_obj->number, FALSE, TRUE);

	/* This seems to imply objects get less value from being > 1 but < 5
	 * levels out of depth - should it be *value +=... - NRM */
	if (!cursed_p(new_obj->flags) && (kind->alloc_min > c->depth)) {
		if (value) *value = (kind->alloc_min - c->depth) * (*value / 5);
	}

	return new_obj;
}
示例#10
0
/*
 * Attempt to make an object (normal or good/great)
 *
 * This routine plays nasty games to generate the "special artifacts".
 *
 * We assume that the given object has been "wiped".
 */
bool make_object(object_type *j_ptr, int lev, bool good, bool great)
{
	int k_idx, base;
	object_kind *k_ptr;

	/* Try to make a special artifact */
	if (one_in_(good ? 10 : 1000))
	{
		if (make_artifact_special(j_ptr, lev)) return TRUE;
		/* If we failed to make an artifact, the player gets a great item */
		good = great = TRUE;
	}

	/* Base level for the object */
	base = (good ? (lev + 10) : lev);

	/* Get the object */
	k_idx = get_obj_num(base, good || great);
	if (!k_idx) return FALSE;

	/* Prepare the object */
	object_prep(j_ptr, &k_info[k_idx], lev, RANDOMISE);

	/* Apply magic (allow artifacts) */
	apply_magic(j_ptr, lev, TRUE, good, great);


	/* Generate multiple items */
	k_ptr = &k_info[j_ptr->k_idx];

	if (k_ptr->gen_mult_prob >= 100 ||
	    k_ptr->gen_mult_prob >= randint1(100))
	{
		j_ptr->number = randcalc(k_ptr->stack_size, lev, RANDOMISE);
	}


	/* Notice "okay" out-of-depth objects */
	if (!cursed_p(j_ptr) && (k_info[j_ptr->k_idx].level > p_ptr->depth))
	{
		/* Rating increase */
		rating += (k_info[j_ptr->k_idx].alloc_min - p_ptr->depth);

		/* Cheat -- peek at items */
		if (OPT(cheat_peek)) object_mention(j_ptr);
	}

	return TRUE;
}
示例#11
0
/**
 * Creates the onbject a mimic is imitating.
 */
void mon_create_mimicked_object(struct chunk *c, struct monster *mon, int index)
{
	struct object *obj;
	struct object_kind *kind = mon->race->mimic_kinds->kind;
	struct monster_mimic *mimic_kind;
	int i = 1;
	bool dummy = true;

	/* Pick a random object kind to mimic */
	for (mimic_kind = mon->race->mimic_kinds;
		 mimic_kind;
		 mimic_kind = mimic_kind->next, i++) {
		if (one_in_(i)) {
			kind = mimic_kind->kind;
		}
	}

	if (tval_is_money_k(kind)) {
		obj = make_gold(player->depth, kind->name);
	} else {
		obj = object_new();
		object_prep(obj, kind, mon->race->level, RANDOMISE);
		apply_magic(obj, mon->race->level, true, false, false, false);
		obj->number = 1;
		obj->origin = ORIGIN_DROP_MIMIC;
		obj->origin_depth = player->depth;
	}

	obj->mimicking_m_idx = index;
	mon->mimicked_obj = obj;

	/* Put the object on the floor if it goes, otherwise no mimicry */
	if (floor_carry(c, mon->fy, mon->fx, obj, &dummy)) {
		list_object(c, obj);
	} else {
		/* Clear the mimicry */
		obj->mimicking_m_idx = 0;
		mon->mimicked_obj = NULL;

		/* Give the object to the monster if appropriate */
		if (rf_has(mon->race->flags, RF_MIMIC_INV)) {
			monster_carry(c, mon, obj);
		} else {
			/* Otherwise delete the mimicked object */
			object_delete(&obj);
		}
	}
}
示例#12
0
文件: obj-make.c 项目: Dasaan/angband
/**
 * Attempt to make an object
 *
 * \param c is the current dungeon level.
 * \param j_ptr is the object struct to be populated.
 * \param lev is the creation level of the object (not necessarily == depth).
 * \param good is whether the object is to be good
 * \param great is whether the object is to be great
 * \param value is the value to be returned to the calling function
 * \param tval is the desired tval, or 0 if we allow any tval
 *
 * Returns the whether or not creation worked.
 */
bool make_object(struct cave *c, object_type *j_ptr, int lev, bool good,
	bool great, bool extra_roll, s32b *value, int tval)
{
	int base;
	object_kind *kind;

	/* Try to make a special artifact */
	if (one_in_(good ? 10 : 1000)) {
		if (make_artifact_special(j_ptr, lev)) {
			if (value) *value = object_value_real(j_ptr, 1, FALSE, TRUE);
			return TRUE;
		}

		/* If we failed to make an artifact, the player gets a good item */
		good = TRUE;
	}

	/* Base level for the object */
	base = (good ? (lev + 10) : lev);

	/* Get the object, prep it and apply magic */
	kind = get_obj_num(base, good || great, tval);
	if (!kind) return FALSE;
	object_prep(j_ptr, kind, lev, RANDOMISE);
	apply_magic(j_ptr, lev, TRUE, good, great, extra_roll);

	/* Generate multiple items */
	if (kind->gen_mult_prob >= randint1(100))
		j_ptr->number = randcalc(kind->stack_size, lev, RANDOMISE);

	if (j_ptr->number >= MAX_STACK_SIZE)
		j_ptr->number = MAX_STACK_SIZE - 1;

	/* Return value, increased for uncursed out-of-depth objects */
	if (value)
		*value = object_value_real(j_ptr, j_ptr->number, FALSE, TRUE);

	if (!cursed_p(j_ptr->flags) && (kind->alloc_min > c->depth)) {
		if (value) *value = (kind->alloc_min - c->depth) * (*value / 5);
	}

	return TRUE;
}
示例#13
0
//Helper function to get the complete artifacts name.
QString MakeObjectDialog::get_object_display_name(int o_idx)
{
    object_type object_type_body;
    object_type *o_ptr = &object_type_body;

    /* Make fake artifact */
    o_ptr = &object_type_body;
    o_ptr->object_wipe();
    object_prep(o_ptr, o_idx);

    //  This is necessary to keep the game from freezing on dragon armor
    object_level = k_info[o_idx].k_level;

    apply_magic(o_ptr, k_info[o_idx].k_level, FALSE, FALSE, FALSE, FALSE);
    o_ptr->mark_fully_known(TRUE);

    object_level = p_ptr->depth;

    return (object_desc(o_ptr, ODESC_BASE | ODESC_SPOIL));
}
示例#14
0
static bool _create_shots(void)
{
    int         x, y, dir, slot;
    cave_type  *c_ptr;
    object_type forge;

    if (!get_rep_dir(&dir, FALSE)) 
        return FALSE;

    y = py + ddy[dir];
    x = px + ddx[dir];
    c_ptr = &cave[y][x];

    if (!have_flag(f_info[get_feat_mimic(c_ptr)].flags, FF_CAN_DIG))
    {
        msg_print("You need pile of rubble.");
        return FALSE;
    }

    if (!cave_have_flag_grid(c_ptr, FF_CAN_DIG) || !cave_have_flag_grid(c_ptr, FF_HURT_ROCK))
    {
        msg_print("You failed to make ammo.");
        return FALSE;
    }

    object_prep(&forge, lookup_kind(TV_SHOT, m_bonus(1, p_ptr->lev) + 1));
    forge.number = (byte)rand_range(15,30);
    apply_magic(&forge, p_ptr->lev, AM_NO_FIXED_ART);
    obj_identify(&forge);
    forge.discount = 99;

    msg_print("You make some ammo.");

    slot = inven_carry(&forge);
    if (slot >= 0) 
        autopick_alter_item(slot, FALSE);

    cave_alter_feat(y, x, FF_HURT_ROCK);
    p_ptr->update |= PU_FLOW;
    return TRUE;
}
示例#15
0
/*
 * Wizard routine for creating objects
 *
 * Note that wizards cannot create objects on top of other objects.
 *
 * Hack -- this routine always makes a "dungeon object", and applies
 * magic to it, and attempts to decline cursed items. XXX XXX XXX
 */
static void wiz_create_item(void)
{
	int py = p_ptr->py;
	int px = p_ptr->px;

	object_type *i_ptr;
	object_type object_type_body;

	int k_idx;


	/* Save screen */
	screen_save();

	/* Get object base type */
	k_idx = wiz_create_itemtype();

	/* Load screen */
	screen_load();


	/* Return if failed */
	if (!k_idx) return;

	/* Get local object */
	i_ptr = &object_type_body;

	/* Create the item */
	object_prep(i_ptr, k_idx);

	/* Apply magic (no messages, no artifacts) */
	apply_magic(i_ptr, p_ptr->depth, FALSE, FALSE, FALSE);

	/* Drop the object from heaven */
	drop_near(i_ptr, -1, py, px);

	/* All done */
	msg_print("Allocated.");
}
示例#16
0
static bool _create_bolts(void)
{
    int             item, slot;
    object_type  forge;

    item_tester_hook = _create_ammo_p;
    if (!get_item(&item, "Convert which item? ", "You have no item to convert.", USE_INVEN | USE_FLOOR)) 
        return FALSE;

    /* Note: You won't ever get Steel Bolts this way since I:18:1 is shared with 
       by Bolts and Steel Bolts and lookup_kind() picks the first match in k_info.txt.
       However, getting Steel from Bones/Junk would be a bit odd anyway ... */
    object_prep(&forge, lookup_kind(TV_BOLT, m_bonus(1, p_ptr->lev)+ 1));
    forge.number = (byte)rand_range(4, 8);
    apply_magic(&forge, p_ptr->lev, AM_NO_FIXED_ART);
    obj_identify(&forge);
    forge.discount = 99;

    msg_print("You make some ammo.");
    if (item >= 0)
    {
        inven_item_increase(item, -1);
        inven_item_describe(item);
        inven_item_optimize(item);
    }
    else
    {
        floor_item_increase(0 - item, -1);
        floor_item_describe(0 - item);
        floor_item_optimize(0 - item);
    }

    slot = inven_carry(&forge);
    if (slot >= 0) 
        autopick_alter_item(slot, FALSE);
    return TRUE;
}
示例#17
0
/*
 * Handle the "death" of a monster.
 *
 * Disperse treasures centered at the monster location based on the
 * various flags contained in the monster flags fields.
 *
 * Check for "Quest" completion when a quest monster is killed.
 *
 * Note that only the player can induce "monster_death()" on Uniques or quest monsters.
 *
 * Note that monsters can now carry objects, and when a monster dies,
 * it drops all of its objects, which may disappear in crowded rooms.
 */
void monster_death(int m_idx, int who)
{
	int i, j, y, x;

	int dump_item = 0;
	int dump_gold = 0;

	int number_drops = 0;
	int total = 0;

	bool questlevel = FALSE;
	bool completed = FALSE;
	bool fixedquest = FALSE;
	bool writenote = TRUE;
	bool need_stairs = FALSE;

	s16b set_object_level;

	s16b this_o_idx, next_o_idx = 0;

	monster_type *m_ptr = &mon_list[m_idx];

	monster_race *r_ptr = &r_info[m_ptr->r_idx];

	bool visible = (m_ptr->ml || (r_ptr->flags1 & (RF1_UNIQUE)));

	bool chest = (r_ptr->flags1 & (RF1_DROP_CHEST)) ? TRUE : FALSE;
	bool good = (r_ptr->flags1 & (RF1_DROP_GOOD)) ? TRUE : FALSE;
	bool great = (r_ptr->flags1 & (RF1_DROP_GREAT)) ? TRUE : FALSE;

	bool do_gold = (!(r_ptr->flags1 & (RF1_ONLY_ITEM)));
	bool do_item = (!(r_ptr->flags1 & (RF1_ONLY_GOLD)));

	int force_coin = get_coin_type(r_ptr);

	object_type *i_ptr;
	object_type object_type_body;

	/* Get the location */
	y = m_ptr->fy;
	x = m_ptr->fx;

	/* Drop objects being carried */
	for (this_o_idx = m_ptr->hold_o_idx; this_o_idx; this_o_idx = next_o_idx)
	{
		object_type *o_ptr;

		/* Get the object */
		o_ptr = &o_list[this_o_idx];

		/*Remove the mark to hide when monsters carry this object*/
		o_ptr->ident &= ~(IDENT_HIDE_CARRY);

		/* Get the next object */
		next_o_idx = o_ptr->next_o_idx;

		/* Paranoia */
		o_ptr->held_m_idx = 0;

		/* Get local object */
		i_ptr = &object_type_body;

		/* Copy the object */
		object_copy(i_ptr, o_ptr);

		/* Delete the object */
		delete_object_idx(this_o_idx);

		/* Drop it */
		drop_near(i_ptr, -1, y, x);
	}

	/* Forget objects */
	m_ptr->hold_o_idx = 0;

	/* Mega-Hack -- drop "winner" treasures */
	if (r_ptr->flags1 & (RF1_DROP_CHOSEN))
	{
		/* Get local object */
		i_ptr = &object_type_body;

		/* Mega-Hack -- Prepare to make "Grond" */
		object_prep(i_ptr, lookup_kind(TV_HAFTED, SV_GROND));

		/* Mega-Hack -- Mark this item as "Grond" */
		i_ptr->art_num = ART_GROND;

		/* Mega-Hack -- Actually create "Grond" */
		apply_magic(i_ptr, -1, TRUE, TRUE, TRUE, FALSE);

		/* Remember history */
		object_history(i_ptr, ORIGIN_MORGOTH, 0);

		/* Drop it in the dungeon */
		drop_near(i_ptr, -1, y, x);

		/* Get local object */
		i_ptr = &object_type_body;

		/* Mega-Hack -- Prepare to make "Morgoth's crown" */
		object_prep(i_ptr, lookup_kind(TV_CROWN, SV_MORGOTH));

		/* Mega-Hack -- Mark this item as "Morgoth" */
		i_ptr->art_num = ART_MORGOTH;

		/* Mega-Hack -- Actually create "Morgoth" */
		apply_magic(i_ptr, -1, TRUE, TRUE, TRUE, FALSE);

		/* Remember history */
		object_history(i_ptr, ORIGIN_MORGOTH, 0);

		/* Drop it in the dungeon */
		drop_near(i_ptr, -1, y, x);
	}


	/* Determine how much we can drop */
	if ((r_ptr->flags1 & (RF1_DROP_60)) && (rand_int(100) < 60)) number_drops++;
	if ((r_ptr->flags1 & (RF1_DROP_90)) && (rand_int(100) < 90)) number_drops++;
	if (r_ptr->flags1 & (RF1_DROP_1D2)) number_drops += damroll(1, 2);
	if (r_ptr->flags1 & (RF1_DROP_2D2)) number_drops += damroll(2, 2);
	if (r_ptr->flags1 & (RF1_DROP_3D2)) number_drops += damroll(3, 2);
	if (r_ptr->flags1 & (RF1_DROP_4D2)) number_drops += damroll(4, 2);

	/* Hack -- handle creeping coins */
	coin_type = force_coin;

	/* Average dungeon and monster levels */
	set_object_level = object_level = (effective_depth(p_ptr->depth) + r_ptr->level) / 2;

	/* Drop some objects */
	for (j = 0; j < number_drops; j++)
	{
		bool interesting = FALSE;

		/* Re-set the object level */
		object_level = set_object_level;

		/* Get local object */
		i_ptr = &object_type_body;

		/* Wipe the object */
		object_wipe(i_ptr);

		/* work on the "too much junk" problem, large drops sometimes are less items with a "boost". */
		if ((randint(750) < (number_drops * number_drops)) && (!(r_ptr->flags1 & (RF1_UNIQUE))))
		{
			interesting = TRUE;
			number_drops -= 5;
			object_level += 5;

			/*Boundry Control*/
			if (number_drops < 0) number_drops = 0;
			if (object_level > MAX_DEPTH) object_level = MAX_DEPTH;
		}

		/* Make Gold */
		if (do_gold && (!chest) && (!do_item || (rand_int(100) < 70)))
		{
			/* Make some gold */
			if (!make_gold(i_ptr)) continue;

			/* Assume seen XXX XXX XXX */
			dump_gold++;
		}

		/* Make Object */
		else
		{
			if (chest)
			{
				if (!make_object(i_ptr, good, great, DROP_TYPE_CHEST, FALSE)) continue;
			}

			/* Make an object */
			else if (!make_object(i_ptr, good, great, DROP_TYPE_UNTHEMED, interesting)) continue;

			/* Remember history */
			if (visible) object_history(i_ptr, ORIGIN_DROP_KNOWN, m_ptr->r_idx);
			else object_history(i_ptr, ORIGIN_DROP_UNKNOWN, 0);

			/* Assume seen XXX XXX XXX */
			dump_item++;
		}

		/* Drop it in the dungeon */
		drop_near(i_ptr, -1, y, x);
	}

	/* Re-set the object level */
	object_level = set_object_level;

	/*If marked for a bonus item, create it and drop it */
	if (m_ptr->mflag & (MFLAG_BONUS_ITEM))
	{
		bool this_good = good;
		bool this_great = great;
		bool this_chest = chest;
		bool interesting = FALSE;

		char o_name[80];

		/* Get local object */
		i_ptr = &object_type_body;

		/* Wipe the object */
		object_wipe(i_ptr);

		if (one_in_(50)) this_chest = TRUE;
		if (one_in_(15)) this_great = TRUE;
		if (one_in_(5)) this_good = TRUE;
		if ((!this_good) && (!this_great) && (!this_chest))
		{
			object_level += 5;
			if (object_level > MAX_DEPTH) object_level = MAX_DEPTH;
			interesting = TRUE;
		}

		if (this_chest)
		{
			while (!make_object(i_ptr, TRUE, TRUE, DROP_TYPE_CHEST, FALSE)) continue;
		}

		/* Make an object */
		else while (!make_object(i_ptr, this_good, this_good, DROP_TYPE_UNTHEMED, interesting)) continue;

		/* Remember history */
		if (visible) object_history(i_ptr, ORIGIN_DROP_KNOWN, m_ptr->r_idx);
		else object_history(i_ptr, ORIGIN_DROP_UNKNOWN, 0);

		object_desc(o_name, sizeof(o_name), i_ptr, ODESC_PREFIX | ODESC_FULL);

		/* Drop it in the dungeon */
		drop_near(i_ptr, -1, y, x);


	}

	/* Reset the object level */
	object_level = effective_depth(p_ptr->depth);

	/* Reset "coin" type */
	coin_type = 0;

	/* Take note of any dropped treasure */
	if (visible && (dump_item || dump_gold))
	{
		/* Take notes on treasure */
		lore_treasure(m_idx, dump_item, dump_gold);
	}

	/* Update monster list window */
	p_ptr->redraw |= (PR_MONLIST);

	/* Count incomplete quests */
	for (i = 0; i < z_info->q_max; i++)
	{
		quest_type *q_ptr = &q_info[i];

		/*
		 * Hack - don't count if player didn't kill, or on a town level
		 * This assumes only a player can kill quest monsters!!!!!
		 * This line is also ugly coding. :)
		 */
		if (((who != SOURCE_PLAYER) && (who != SOURCE_TRAP)) || (!p_ptr->depth)) continue;

		/* Quest level? */
		if ((q_ptr->active_level == p_ptr->depth) && (p_ptr->depth > 0))
		{
			/* One on the level */
			questlevel = TRUE;

			/* Require "Quest Monsters" */
			if 	(q_ptr->mon_idx == m_ptr->r_idx)
			{
				char race_name[80];

				/* Get the monster race name (singular)*/
				monster_desc_race(race_name, sizeof(race_name), q_ptr->mon_idx);

				/* Mark kills */
				q_ptr->cur_num++;

				/* Redraw quest indicator */
				p_ptr->redraw |= (PR_QUEST_ST);

				/* Completed quest? */
				if (q_ptr->cur_num == q_ptr->max_num)
				{
					/* Mark complete */
					q_ptr->active_level = 0;

					/* Mark fixed quests */
					if ((q_ptr->q_type == QUEST_FIXED) ||
						(q_ptr->q_type == QUEST_FIXED_U))
						fixedquest = TRUE;

					if (q_ptr->q_type == QUEST_GUARDIAN) need_stairs = TRUE;

					/* One complete */
					completed = TRUE;

					/*make a note of the completed quest, but not for fixed or
				     * fixed unique quests
					 */
					if ((adult_take_notes) && (!fixedquest))
					{
						char note[120];

						/* Multiple quest monsters */
						if (q_ptr->max_num > 1)
						{
							plural_aux(race_name, sizeof(race_name));
						}

						if (r_ptr->flags1 & (RF1_UNIQUE))
						{
							/*write note*/
							if monster_nonliving(r_ptr)
								sprintf(note, "Quest: Destroyed %s", race_name);
							else sprintf(note, "Quest: Killed %s", race_name);
						}

						else
						{
							/* Write note */
							if monster_nonliving(r_ptr)
示例#18
0
/**
 * Apply magic to an item or turn it into an artifact. -Bernd-
 */
static void wiz_reroll_item(object_type * o_ptr)
{
    object_type *i_ptr;
    object_type object_type_body;

    char ch;

    bool changed = FALSE;


    /* Hack -- leave artifacts alone */
    if (artifact_p(o_ptr))
        return;


    /* Get local object */
    i_ptr = &object_type_body;

    /* Copy the object */
    object_copy(i_ptr, o_ptr);


    /* Main loop. Ask for magification and artifactification */
    while (TRUE) {
        /* Display full item debug information */
        wiz_display_item(i_ptr);

        /* Ask wizard what to do. */
        if (!get_com("[a]ccept, [n]ormal, [g]ood, [e]xcellent? ", &ch)) {
            changed = FALSE;
            break;
        }

        /* Create/change it! */
        if (ch == 'A' || ch == 'a') {
            changed = TRUE;
            break;
        }

        /* Apply normal magic, but first clear object */
        else if (ch == 'n' || ch == 'N') {
            object_prep(i_ptr, o_ptr->k_idx, RANDOMISE);
            apply_magic(i_ptr, p_ptr->depth, FALSE, FALSE, FALSE);
        }

        /* Apply good magic, but first clear object */
        else if (ch == 'g' || ch == 'g') {
            object_prep(i_ptr, o_ptr->k_idx, RANDOMISE);
            apply_magic(i_ptr, p_ptr->depth, FALSE, TRUE, FALSE);
        }

        /* Apply great magic, but first clear object */
        else if (ch == 'e' || ch == 'e') {
            object_prep(i_ptr, o_ptr->k_idx, RANDOMISE);
            apply_magic(i_ptr, p_ptr->depth, FALSE, TRUE, TRUE);
        }
    }


    /* Notice change */
    if (changed) {
        /* Apply changes */
        object_copy(o_ptr, i_ptr);

        /* Recalculate bonuses */
        p_ptr->update |= (PU_BONUS);

        /* Combine / Reorder the pack (later) */
        p_ptr->notice |= (PN_COMBINE | PN_REORDER);

        /* Redraw stuff */
        p_ptr->redraw |= (PR_INVEN | PR_EQUIP);
    }
}
示例#19
0
bool quest_poison_gen_hook(char *fmt)
{
	int cy = 1, cx = 1, x, y, try = 10000, r_idx;
	bool (*old_get_mon_num_hook)(int r_idx);

	if (cquest.status != QUEST_STATUS_TAKEN) return FALSE;
	if (p_ptr->wilderness_y != wild_locs[cquest.data[0]][0]) return FALSE;
	if (p_ptr->wilderness_x != wild_locs[cquest.data[0]][1]) return FALSE;
	if (p_ptr->wild_mode) return FALSE;

	/* Find a good position */
	while (try)
	{
		/* Get a random spot */
		cy = randint(cur_hgt - 24) + 22;
		cx = randint(cur_wid - 34) + 32;

		/* Is it a good spot ? */
		if (cave_empty_bold(cy, cx)) break;

		/* One less try */
		try--;
	}

	/* Place the baddies */

	/* Backup the old hook */
	old_get_mon_num_hook = get_mon_num_hook;

	/* Require "okay" monsters */
	get_mon_num_hook = create_molds_hook;

	/* Prepare allocation table */
	get_mon_num_prep();

	/* Pick a monster, using the level calculation */
	for (x = cx - 25; x <= cx + 25; x++)
		for (y = cy - 25; y <= cy + 25; y++)
		{
			if (!in_bounds(y, x)) continue;

			if (distance(cy, cx, y, x) > 25) continue;

			if (magik(80) && ((cave[y][x].feat == FEAT_DEEP_WATER) || (cave[y][x].feat == FEAT_SHAL_WATER))) cave_set_feat(y, x, FEAT_TAINTED_WATER);

			if (distance(cy, cx, y, x) > 10) continue;

			if (magik(60))
			{
				int m_idx;

				r_idx = get_mon_num(30);
				m_idx = place_monster_one(y, x, r_idx, 0, FALSE, MSTATUS_ENEMY);

				/* Sometimes make it up some levels */
				if (magik(80) && m_idx)
				{
					monster_type *m_ptr = &m_list[m_idx];

					if (m_ptr->level < p_ptr->lev)
					{
						m_ptr->exp = MONSTER_EXP(m_ptr->level + randint(p_ptr->lev - m_ptr->level));
						monster_check_experience(m_idx, TRUE);
					}
				}
			}
		}

	/* Reset restriction */
	get_mon_num_hook = old_get_mon_num_hook;

	/* Prepare allocation table */
	get_mon_num_prep();

	return FALSE;
}
bool quest_poison_finish_hook(char *fmt)
{
	object_type forge, *q_ptr;
	s32b q_idx;

	q_idx = get_next_arg(fmt);

	if (q_idx != QUEST_POISON) return FALSE;

	c_put_str(TERM_YELLOW, "The water is clean again! Thank you so much.", 8, 0);
	c_put_str(TERM_YELLOW, "The beautiful Mallorns are safe. Take this as a proof of our gratitude.", 9, 0);

	q_ptr = &forge;
	object_prep(q_ptr, lookup_kind(TV_DRAG_ARMOR, SV_DRAGON_BLUE));
	q_ptr->found = OBJ_FOUND_REWARD;
	q_ptr->number = 1;
	q_ptr->name2 = EGO_ELVENKIND;
	apply_magic(q_ptr, 1, FALSE, FALSE, FALSE);
	object_aware(q_ptr);
	object_known(q_ptr);
	q_ptr->ident |= IDENT_STOREB;
	(void)inven_carry(q_ptr, FALSE);

	/* Continue the plot */
	*(quest[q_idx].plot) = QUEST_NULL;

	del_hook(HOOK_QUEST_FINISH, quest_poison_finish_hook);
	process_hooks_restart = TRUE;

	return TRUE;
}
示例#20
0
/*
 * Apply magic to an item or turn it into an artifact. -Bernd-
 */
static void wiz_reroll_item(object_type *o_ptr)
{
	object_type forge;
	object_type *q_ptr;

	char ch;

	bool changed = FALSE;

	/* Hack -- leave normal artifacts alone */
	if ((o_ptr->flags3 & TR3_INSTA_ART) &&
		(o_ptr->activate > 128)) return;

	/* Get local object */
	q_ptr = &forge;

	/* Copy the object */
	object_copy(q_ptr, o_ptr);


	/* Main loop. Ask for magification and artifactification */
	while (TRUE)
	{
		/* Display full item debug information */
		wiz_display_item(q_ptr);

		/* Ask wizard what to do. */
		if (!get_com("[a]ccept, [w]orthless, [n]ormal, [e]xcellent, [s]pecial? ", &ch))
		{
		}

		/* Create/change it! */
		if (ch == 'A' || ch == 'a')
		{
			changed = TRUE;
			break;
		}

		switch (ch)
		{
			/* Apply bad magic, but first clear object */
			case 'w': case 'W':
			{
				object_prep(q_ptr, o_ptr->k_idx);
				apply_magic(q_ptr, p_ptr->depth, 0, OC_FORCE_BAD, FALSE);
				break;
			}
			/* Apply normal magic, but first clear object */
			case 'n': case 'N':
			{
				object_prep(q_ptr, o_ptr->k_idx);
				apply_magic(q_ptr, p_ptr->depth, 0, OC_NORMAL, FALSE);
				break;
			}
			/* Apply great magic, but first clear object */
			case 'e': case 'E':
			{
				object_prep(q_ptr, o_ptr->k_idx);
				apply_magic(q_ptr, p_ptr->depth, 30, OC_FORCE_GOOD, FALSE);
				break;
			}
			case 's': case 'S':
			{
				object_prep(q_ptr, o_ptr->k_idx);

				/* Make a random artifact */
				(void)create_artifact(q_ptr, FALSE, FALSE);
				break;
			}
		}
	}


	/* Notice change */
	if (changed)
	{
		/* Restore the position information */
		q_ptr->iy = o_ptr->iy;
		q_ptr->ix = o_ptr->ix;
		q_ptr->next_o_idx = o_ptr->next_o_idx;
		q_ptr->marked = o_ptr->marked;

		/* Apply changes */
		object_copy(o_ptr, q_ptr);

		/* Recalculate bonuses */
		p_ptr->update |= (PU_BONUS);

		/* Combine / Reorder the pack (later) */
		p_ptr->notice |= (PN_COMBINE | PN_REORDER);

		/* Window stuff */
		p_ptr->window |= (PW_INVEN | PW_EQUIP | PW_SPELL | PW_PLAYER | PW_PLAYRES);
	}
}
示例#21
0
/**
 * Attempts to place a copy of the given monster at the given position in
 * the dungeon.
 *
 * All of the monster placement routines eventually call this function. This
 * is what actually puts the monster in the dungeon (i.e., it notifies the cave
 * and sets the monsters position). The dungeon loading code also calls this
 * function directly.
 *
 * `origin` is the item origin to use for any monster drops (e.g. ORIGIN_DROP,
 * ORIGIN_DROP_PIT, etc.) The dungeon loading code calls this with origin = 0,
 * which prevents the monster's drops from being generated again.
 *
 * Returns the m_idx of the newly copied monster, or 0 if the placement fails.
 */
s16b place_monster(struct chunk *c, int y, int x, struct monster *mon,
				   byte origin)
{
	s16b m_idx;
	struct monster *new_mon;

	assert(square_in_bounds(c, y, x));
	assert(!square_monster(c, y, x));

	/* Get a new record */
	m_idx = mon_pop(c);
	if (!m_idx) return 0;

	/* Copy the monster */
	new_mon = cave_monster(c, m_idx);
	memcpy(new_mon, mon, sizeof(struct monster));

	/* Set the ID */
	new_mon->midx = m_idx;

	/* Set the location */
	c->squares[y][x].mon = new_mon->midx;
	new_mon->fy = y;
	new_mon->fx = x;
	assert(square_monster(c, y, x) == new_mon);

	update_mon(new_mon, c, true);

	/* Hack -- Count the number of "reproducers" */
	if (rf_has(new_mon->race->flags, RF_MULTIPLY)) num_repro++;

	/* Count racial occurrences */
	new_mon->race->cur_num++;

	/* Create the monster's drop, if any */
	if (origin)
		(void)mon_create_drop(c, new_mon, origin);

	/* Make mimics start mimicking */
	if (origin && new_mon->race->mimic_kinds) {
		struct object *obj;
		struct object_kind *kind = new_mon->race->mimic_kinds->kind;
		struct monster_mimic *mimic_kind;
		int i = 1;

		/* Pick a random object kind to mimic */
		for (mimic_kind = new_mon->race->mimic_kinds; mimic_kind; 
				mimic_kind = mimic_kind->next, i++) {
			if (one_in_(i)) kind = mimic_kind->kind;
		}

		if (tval_is_money_k(kind)) {
			obj = make_gold(player->depth, kind->name);
		} else {
			obj = object_new();
			object_prep(obj, kind, new_mon->race->level, RANDOMISE);
			apply_magic(obj, new_mon->race->level, true, false, false, false);
			obj->number = 1;
			obj->origin = ORIGIN_DROP_MIMIC;
			obj->origin_depth = player->depth;
		}

		obj->mimicking_m_idx = m_idx;
		new_mon->mimicked_obj = obj;

		/* Put the object on the floor if it goes, otherwise no mimicry */
		if (floor_carry(c, y, x, obj, false)) {
			list_object(c, obj);
		} else {
			/* Clear the mimicry */
			obj->mimicking_m_idx = 0;
			new_mon->mimicked_obj = NULL;

			/* Give the object to the monster if appropriate */
			if (rf_has(new_mon->race->flags, RF_MIMIC_INV)) {
				monster_carry(c, new_mon, obj);
			} else {
				/* Otherwise delete the mimicked object */
				object_delete(&obj);
			}
		}
	}

	/* Result */
	return m_idx;
}
/*
 * Allocates some objects (using "place" and "type")
 */
static void alloc_object(int set, int typ, int num)
{
    int y = 0, x = 0, k;

    /* A small level has few objects. */
    num = MAX(1, num * cur_hgt * cur_wid / (MAX_HGT*MAX_WID));

    /* Diligent players should be encouraged to explore more! */
    if (typ == ALLOC_TYP_OBJECT || typ == ALLOC_TYP_GOLD)
        num = num * (625 + virtue_current(VIRTUE_DILIGENCE)) / 625;

    for (k = 0; k < num; k++)
    {
        object_type forge;
        int         k_idx;

        if (!_get_loc(set, &x, &y))
        {
            if (cheat_room)
                msg_print("Warning! Could not place object!");

            return;
        }

        switch (typ)
        {
        case ALLOC_TYP_RUBBLE:
            place_rubble(y, x);
            cave[y][x].info &= ~(CAVE_FLOOR);
            break;

        case ALLOC_TYP_TRAP:
            place_trap(y, x);
            cave[y][x].info &= ~(CAVE_FLOOR);
            break;

        case ALLOC_TYP_GOLD:
            place_gold(y, x);
            break;

        case ALLOC_TYP_OBJECT:
            /* Comment: Monsters drop objects at (ML + DL)/2. In practice,
               this means that your best drops are just laying on the ground,
               and this encourages recall scumming for end game resources such
               as wands of rockets. Note: Vaults are not affected and we want
               to encourage these! Room templates need some thought ... */
            if (base_level > 31)
            {
               int n = base_level - 30;
               object_level = 30 + n/2 + randint1(n/2);
            }
            else
                object_level = base_level; /* paranoia */
            place_object(y, x, 0L);
            object_level = base_level;
            break;

        case ALLOC_TYP_FOOD:
            if (prace_is_(RACE_ENT))
                k_idx = lookup_kind(TV_POTION, SV_POTION_WATER);
            else
                k_idx = lookup_kind(TV_FOOD, SV_FOOD_RATION);
            object_prep(&forge, k_idx);
            obj_make_pile(&forge);
            drop_near(&forge, -1, y, x);
            break;

        case ALLOC_TYP_LIGHT:
            if (one_in_(3))
                k_idx = lookup_kind(TV_FLASK, SV_FLASK_OIL);
            else
                k_idx = lookup_kind(TV_LITE, SV_LITE_LANTERN);
            object_prep(&forge, k_idx);
            apply_magic(&forge, dun_level, 0);
            obj_make_pile(&forge);
            drop_near(&forge, -1, y, x);
            break;

        case ALLOC_TYP_RECALL:
            k_idx = lookup_kind(TV_SCROLL, SV_SCROLL_WORD_OF_RECALL);
            object_prep(&forge, k_idx);
            /*obj_make_pile(&forge);*/
            drop_near(&forge, -1, y, x);
            break;

        case ALLOC_TYP_SKELETON:
            k_idx = lookup_kind(TV_CORPSE, SV_SKELETON);
            object_prep(&forge, k_idx);
            apply_magic(&forge, dun_level, 0);
            drop_near(&forge, -1, y, x);
            break;
        }
    }
}
示例#23
0
void WizardModeDialog::wiz_winners_kit(void)
{
    if (!character_dungeon) return;

    if (game_mode == GAME_NPPMORIA)
    {
        // Make 2 rings of speed
        int k_idx = lookup_kind(TV_RING, SV_RING_SPEED);
        object_type object_type_body;
        object_type *i_ptr = &object_type_body;
        i_ptr->object_wipe();
        if (k_idx)
        {
            object_prep(i_ptr, k_idx);
            apply_magic(i_ptr, k_info[k_idx].k_level, FALSE, TRUE, TRUE, TRUE);
            i_ptr->number = 2;
            i_ptr->mark_fully_known(TRUE);
            object_history(i_ptr, ORIGIN_CHEAT, 0);
            if(inven_carry(i_ptr) < 0)
            {
                drop_near(i_ptr, -1, p_ptr->py, p_ptr->px);
            }
        }
        //Give an amulet of the magi;
        k_idx = lookup_kind(TV_AMULET, SV_AMULET_THE_MAGI);
        if (k_idx)
        {
            i_ptr->object_wipe();
            object_prep(i_ptr, k_idx);
            apply_magic(i_ptr, k_info[k_idx].k_level, FALSE, TRUE, TRUE, TRUE);
            i_ptr->mark_fully_known(TRUE);
            object_history(i_ptr, ORIGIN_CHEAT, 0);
            if(inven_carry(i_ptr) < 0)
            {
                drop_near(i_ptr, -1, p_ptr->py, p_ptr->px);
            }
        }
        //boots of speed
        k_idx = lookup_kind(TV_BOOTS, SV_PAIR_OF_SOFT_LEATHER_BOOTS);
        int ego_num = lookup_ego(TV_BOOTS, SV_PAIR_OF_SOFT_LEATHER_BOOTS, "speed");
        if (k_idx && ego_num)
        {
            i_ptr->object_wipe();
            object_prep(i_ptr, k_idx);
            i_ptr->ego_num = ego_num;
            a_m_aux_2(i_ptr, k_info[k_idx].k_level, 2);
            apply_ego_item_magic(i_ptr, k_info[k_idx].k_level);
            i_ptr->to_a = 25;
            i_ptr->mark_fully_known(TRUE);
            object_history(i_ptr, ORIGIN_CHEAT, 0);
            if(inven_carry(i_ptr) < 0)
            {
                drop_near(i_ptr, -1, p_ptr->py, p_ptr->px);
            }
        }
        // Robe of Resistance
        k_idx = lookup_kind(TV_SOFT_ARMOR, SV_ROBE);
        ego_num = lookup_ego(TV_SOFT_ARMOR, SV_ROBE, "resistance");
        if (k_idx && ego_num)
        {
            i_ptr->object_wipe();
            object_prep(i_ptr, k_idx);
            i_ptr->ego_num = ego_num;
            a_m_aux_2(i_ptr, k_info[k_idx].k_level, 2);
            apply_ego_item_magic(i_ptr, k_info[k_idx].k_level);
            i_ptr->to_a = 25;
            i_ptr->mark_fully_known(TRUE);
            object_history(i_ptr, ORIGIN_CHEAT, 0);
            if(inven_carry(i_ptr) < 0)
            {
                drop_near(i_ptr, -1, p_ptr->py, p_ptr->px);
            }
        }
        // super-charged holy avenger dagger
        k_idx = lookup_kind(TV_SWORD, SV_DAGGER);
        ego_num = lookup_ego(TV_SWORD, SV_DAGGER, "holy avenger");
        if (k_idx && ego_num)
        {
            i_ptr->object_wipe();
            object_prep(i_ptr, k_idx);
            i_ptr->ego_num = ego_num;
            a_m_aux_1(i_ptr, k_info[k_idx].k_level, 2);
            apply_ego_item_magic(i_ptr, k_info[k_idx].k_level);
            i_ptr->to_a = i_ptr->to_h = i_ptr->to_d = 25;
            i_ptr->dd = i_ptr->ds = 9;
            i_ptr->mark_fully_known(TRUE);
            object_history(i_ptr, ORIGIN_CHEAT, 0);
            if(inven_carry(i_ptr) < 0)
            {
                drop_near(i_ptr, -1, p_ptr->py, p_ptr->px);
            }
        }
        // crown of the magi
        k_idx = lookup_kind(TV_CROWN, SV_SILVER_CROWN);
        ego_num = lookup_ego(TV_CROWN, SV_SILVER_CROWN, "magi");
        if (k_idx && ego_num)
        {
            i_ptr->object_wipe();
            object_prep(i_ptr, k_idx);
            i_ptr->ego_num = ego_num;
            a_m_aux_2(i_ptr, k_info[k_idx].k_level, 2);
            apply_ego_item_magic(i_ptr, k_info[k_idx].k_level);
            i_ptr->to_a = 25;
            i_ptr->mark_fully_known(TRUE);
            object_history(i_ptr, ORIGIN_CHEAT, 0);
            if(inven_carry(i_ptr) < 0)
            {
                drop_near(i_ptr, -1, p_ptr->py, p_ptr->px);
            }
        }
        // super charged gloves of slaying
        k_idx = lookup_kind(TV_GLOVES, SV_SET_OF_LEATHER_GLOVES);
        ego_num = lookup_ego(TV_GLOVES, SV_SET_OF_LEATHER_GLOVES, "slaying");
        if (k_idx && ego_num)
        {
            i_ptr->object_wipe();
            object_prep(i_ptr, k_idx);
            i_ptr->ego_num = ego_num;
            a_m_aux_2(i_ptr, k_info[k_idx].k_level, 2);
            apply_ego_item_magic(i_ptr, k_info[k_idx].k_level);
            i_ptr->to_a = i_ptr->to_h = i_ptr->to_d = 25;
            i_ptr->mark_fully_known(TRUE);
            object_history(i_ptr, ORIGIN_CHEAT, 0);
            if(inven_carry(i_ptr) < 0)
            {
                drop_near(i_ptr, -1, p_ptr->py, p_ptr->px);
            }
        }
        //finally the Phial
        if (TRUE)
        {
            i_ptr->object_wipe();
            if (wiz_alloc_artifact(i_ptr, 1))
            {
                object_history(i_ptr, ORIGIN_CHEAT, 0);
                identify_object(i_ptr, true);
                if(inven_carry(i_ptr) < 0)
                {
                    drop_near(i_ptr, -1, p_ptr->py, p_ptr->px);
                }
            }
        }

        handle_stuff();
        this->accept();
        return;

    }

    else if (game_mode != GAME_NPPANGBAND) return;

    int artis[] = {
        47,     // RINGIL
        124,    // CUBRAGOL
        13,     // NARYA
        14,     // NENYA
        10,     // ELESSAR
        12,     // GEM OF AMON SUL
        38,     // BLADETUNDER
        113,    // COLANNON
        33,     // THORIN
        110,    // NUMENOR
        129,    // CAMBELEG
        127,    // FEANOR
        0
    };

    object_type obj;
    object_type *o_ptr = &obj;

    for (int i = 0; artis[i]; i++)
    {
        o_ptr->object_wipe();
        if (!wiz_alloc_artifact(o_ptr, artis[i])) continue;
        object_history(o_ptr, ORIGIN_CHEAT, 0);
        identify_object(o_ptr, true);
        if (inven_carry(o_ptr) < 0)
        {
            drop_near(o_ptr, -1, p_ptr->py, p_ptr->px);
        }
        QString name = object_desc(o_ptr, ODESC_PREFIX | ODESC_FULL);
        message("Allocated " + name);
    }

    //Some amazing ammo;
    int k_idx = lookup_kind(TV_BOLT, SV_AMMO_MITHRIL);
    int ego_num = lookup_ego(TV_BOLT, SV_AMMO_MITHRIL, "holy might");
    if (k_idx && ego_num)
    {
        o_ptr->object_wipe();
        object_prep(o_ptr, k_idx);
        o_ptr->ego_num = ego_num;
        a_m_aux_1(o_ptr, k_info[k_idx].k_level, 2);
        apply_ego_item_magic(o_ptr, k_info[k_idx].k_level);
        o_ptr->to_h = 99;
        o_ptr->to_d = 99;
        o_ptr->dd = 25;
        o_ptr->ds = 25;
        o_ptr->number = 99;
        o_ptr->mark_fully_known(TRUE);
        object_history(o_ptr, ORIGIN_CHEAT, 0);
        if(inven_carry(o_ptr) < 0)
        {
            drop_near(o_ptr, -1, p_ptr->py, p_ptr->px);
        }
    }

    handle_stuff();

    this->accept();
}
示例#24
0
文件: wizard2.c 项目: naota/hengband
/*!
 * @brief アイテムの質を選択して再生成する /
 * Apply magic to an item or turn it into an artifact. -Bernd-
 * @param o_ptr 再生成の対象となるアイテム情報の参照ポインタ
 * @return なし
 */
static void wiz_reroll_item(object_type *o_ptr)
{
	object_type forge;
	object_type *q_ptr;

	char ch;

	bool changed = FALSE;


	/* Hack -- leave artifacts alone */
	if (object_is_artifact(o_ptr)) return;


	/* Get local object */
	q_ptr = &forge;

	/* Copy the object */
	object_copy(q_ptr, o_ptr);


	/* Main loop. Ask for magification and artifactification */
	while (TRUE)
	{
		/* Display full item debug information */
		wiz_display_item(q_ptr);

		/* Ask wizard what to do. */
		if (!get_com("[a]ccept, [w]orthless, [c]ursed, [n]ormal, [g]ood, [e]xcellent, [s]pecial? ", &ch, FALSE))
		{
			/* Preserve wizard-generated artifacts */
			if (object_is_fixed_artifact(q_ptr))
			{
				a_info[q_ptr->name1].cur_num = 0;
				q_ptr->name1 = 0;
			}

			changed = FALSE;
			break;
		}

		/* Create/change it! */
		if (ch == 'A' || ch == 'a')
		{
			changed = TRUE;
			break;
		}

		/* Preserve wizard-generated artifacts */
		if (object_is_fixed_artifact(q_ptr))
		{
			a_info[q_ptr->name1].cur_num = 0;
			q_ptr->name1 = 0;
		}

		switch(ch)
		{
			/* Apply bad magic, but first clear object */
			case 'w': case 'W':
			{
				object_prep(q_ptr, o_ptr->k_idx);
				apply_magic(q_ptr, dun_level, AM_NO_FIXED_ART | AM_GOOD | AM_GREAT | AM_CURSED);
				break;
			}
			/* Apply bad magic, but first clear object */
			case 'c': case 'C':
			{
				object_prep(q_ptr, o_ptr->k_idx);
				apply_magic(q_ptr, dun_level, AM_NO_FIXED_ART | AM_GOOD | AM_CURSED);
				break;
			}
			/* Apply normal magic, but first clear object */
			case 'n': case 'N':
			{
				object_prep(q_ptr, o_ptr->k_idx);
				apply_magic(q_ptr, dun_level, AM_NO_FIXED_ART);
				break;
			}
			/* Apply good magic, but first clear object */
			case 'g': case 'G':
			{
				object_prep(q_ptr, o_ptr->k_idx);
				apply_magic(q_ptr, dun_level, AM_NO_FIXED_ART | AM_GOOD);
				break;
			}
			/* Apply great magic, but first clear object */
			case 'e': case 'E':
			{
				object_prep(q_ptr, o_ptr->k_idx);
				apply_magic(q_ptr, dun_level, AM_NO_FIXED_ART | AM_GOOD | AM_GREAT);
				break;
			}
			/* Apply special magic, but first clear object */
			case 's': case 'S':
			{
				object_prep(q_ptr, o_ptr->k_idx);
				apply_magic(q_ptr, dun_level, AM_GOOD | AM_GREAT | AM_SPECIAL);

				/* Failed to create artifact; make a random one */
				if (!object_is_artifact(q_ptr)) create_artifact(q_ptr, FALSE);
				break;
			}
		}
		q_ptr->iy = o_ptr->iy;
		q_ptr->ix = o_ptr->ix;
		q_ptr->next_o_idx = o_ptr->next_o_idx;
		q_ptr->marked = o_ptr->marked;
	}


	/* Notice change */
	if (changed)
	{
		/* Apply changes */
		object_copy(o_ptr, q_ptr);

		/* Recalculate bonuses */
		p_ptr->update |= (PU_BONUS);

		/* Combine / Reorder the pack (later) */
		p_ptr->notice |= (PN_COMBINE | PN_REORDER);

		/* Window stuff */
		p_ptr->window |= (PW_INVEN | PW_EQUIP | PW_SPELL | PW_PLAYER);
	}
}
示例#25
0
bool wiz_create_item_subaction(menu_type * m, const ui_event * e, int oid)
{
	int *choices = menu_priv(m);

	object_type *i_ptr;
	object_type object_type_body;

	/* Artifacts */
	if (choose_artifact) {
		int i;
		int o_idx;
		artifact_type *a_ptr = &a_info[choices[oid]];

		/* Get the artifact info */
		//a_ptr = &a_info[choices[oid]];

		/* Ignore "empty" artifacts */
		if (!a_ptr->name)
			return TRUE;

		/* Get local object */
		i_ptr = &object_type_body;

		/* Wipe the object */
		object_wipe(i_ptr);

		/* Acquire the "kind" index */
		o_idx = lookup_kind(a_ptr->tval, a_ptr->sval);

		/* Create the base object */
		object_prep(i_ptr, o_idx, RANDOMISE);

		/* Mark the object as an artifact. */
		i_ptr->name1 = choices[oid];

		/* Extract the fields */
		i_ptr->pval = a_ptr->pval;
		i_ptr->ac = a_ptr->ac;
		i_ptr->dd = a_ptr->dd;
		i_ptr->ds = a_ptr->ds;
		i_ptr->to_a = a_ptr->to_a;
		i_ptr->to_h = a_ptr->to_h;
		i_ptr->to_d = a_ptr->to_d;
		i_ptr->weight = a_ptr->weight;

		of_copy(i_ptr->flags_obj, a_ptr->flags_obj);
		cf_copy(i_ptr->flags_curse, a_ptr->flags_curse);

		for (i = 0; i < MAX_P_RES; i++)
			i_ptr->percent_res[i] = a_ptr->percent_res[i];
		for (i = 0; i < A_MAX; i++)
			i_ptr->bonus_stat[i] = a_ptr->bonus_stat[i];
		for (i = 0; i < MAX_P_BONUS; i++)
			i_ptr->bonus_other[i] = a_ptr->bonus_other[i];
		for (i = 0; i < MAX_P_SLAY; i++)
			i_ptr->multiple_slay[i] = a_ptr->multiple_slay[i];
		for (i = 0; i < MAX_P_BRAND; i++)
			i_ptr->multiple_brand[i] = a_ptr->multiple_brand[i];


		/* Transfer the activation information. */
		if (a_ptr->effect)
			i_ptr->effect = a_ptr->effect;
	}
	/* Regular objects */
	else {
		object_kind *kind = &k_info[choices[oid]];

		if (e->type != EVT_SELECT)
			return TRUE;

		/* Get local object */
		i_ptr = &object_type_body;

		/* Wipe the object */
		object_wipe(i_ptr);

		/* Create the item */
		object_prep(i_ptr, kind->kidx, RANDOMISE);

		/* Apply magic (no messages, no artifacts) */
		apply_magic(i_ptr, p_ptr->danger, FALSE, FALSE, FALSE);

		/* Hack -- Since treasure objects are not effected by apply_magic, they
		 * need special processing. */
		if (i_ptr->tval == TV_GOLD) {
			i_ptr->pval = kind->cost / 2 + randint1((kind->cost + 1) / 2);
		}

		/* Mark as cheat, and where created */
		i_ptr->origin = ORIGIN_CHEAT;
		i_ptr->origin_z = chunk_list[p_ptr->stage].z_pos;
		i_ptr->origin_y = chunk_list[p_ptr->stage].y_pos;
		i_ptr->origin_x = chunk_list[p_ptr->stage].x_pos;

	}

	/* Drop from heaven */
	drop_near(i_ptr, -1, p_ptr->py, p_ptr->px, TRUE);

	/* All done */
	msg("Allocated.");

	return FALSE;
}
示例#26
0
文件: mon-make.c 项目: seebs/angband
/**
 * Creates a specific monster's drop, including any drops specified
 * in the monster.txt file.
 *
 * Returns TRUE if anything is created, FALSE if nothing is.
 */
static bool mon_create_drop(struct monster *m_ptr, byte origin)
{
	struct monster_drop *drop;

	bool great, good, gold_ok, item_ok;
    bool extra_roll = FALSE;
	bool any = FALSE;

	int number = 0, level, j, monlevel;

	object_type *i_ptr;
	object_type object_type_body;
	
	assert(m_ptr);

	great = (rf_has(m_ptr->race->flags, RF_DROP_GREAT));
	good = great || (rf_has(m_ptr->race->flags, RF_DROP_GOOD));
	gold_ok = (!rf_has(m_ptr->race->flags, RF_ONLY_ITEM));
	item_ok = (!rf_has(m_ptr->race->flags, RF_ONLY_GOLD));

	/* Determine how much we can drop */
	if (rf_has(m_ptr->race->flags, RF_DROP_20) && randint0(100) < 20) number++;
	if (rf_has(m_ptr->race->flags, RF_DROP_40) && randint0(100) < 40) number++;
	if (rf_has(m_ptr->race->flags, RF_DROP_60) && randint0(100) < 60) number++;
	if (rf_has(m_ptr->race->flags, RF_DROP_4)) number += rand_range(2, 6);
	if (rf_has(m_ptr->race->flags, RF_DROP_3)) number += rand_range(2, 4);
	if (rf_has(m_ptr->race->flags, RF_DROP_2)) number += rand_range(1, 3);
	if (rf_has(m_ptr->race->flags, RF_DROP_1)) number++;

    /* Give added bonus for unique monters */
    monlevel = m_ptr->race->level;
    if (rf_has(m_ptr->race->flags, RF_UNIQUE)){
        monlevel = MIN(monlevel + 15, monlevel * 2);
        extra_roll = TRUE;
    }
    
	/* Take the best of (average of monster level and current depth)
	   and (monster level) - to reward fighting OOD monsters */
	level = MAX((monlevel + p_ptr->depth) / 2, monlevel);
    level = MIN(level, 100);

	/* Specified drops */
	for (drop = m_ptr->race->drops; drop; drop = drop->next) {
		if ((unsigned int)randint0(100) >= drop->percent_chance)
			continue;

		i_ptr = &object_type_body;
		if (drop->artifact) {
			object_prep(i_ptr, objkind_get(drop->artifact->tval,
				drop->artifact->sval), level, RANDOMISE);
			i_ptr->artifact = drop->artifact;
			copy_artifact_data(i_ptr, i_ptr->artifact);
			i_ptr->artifact->created = 1;
		} else {
			object_prep(i_ptr, drop->kind, level, RANDOMISE);
			apply_magic(i_ptr, level, TRUE, good, great, extra_roll);
		}

		i_ptr->origin = origin;
		i_ptr->origin_depth = p_ptr->depth;
		i_ptr->origin_xtra = m_ptr->race->ridx;
		i_ptr->number = randint0(drop->max - drop->min) + drop->min;
		if (monster_carry(m_ptr, i_ptr))
			any = TRUE;
	}

	/* Make some objects */
	for (j = 0; j < number; j++) {
		i_ptr = &object_type_body;
		object_wipe(i_ptr);

		if (gold_ok && (!item_ok || (randint0(100) < 50))) {
			make_gold(i_ptr, level, SV_GOLD_ANY);
		} else {
			if (!make_object(cave, i_ptr, level, good,
                great, extra_roll, NULL, 0)) continue;
		}

		i_ptr->origin = origin;
		i_ptr->origin_depth = p_ptr->depth;
		i_ptr->origin_xtra = m_ptr->race->ridx;
		if (monster_carry(m_ptr, i_ptr))
			any = TRUE;
	}

	return any;
}
示例#27
0
/*
 * Wizard routine for creating objects		-RAK-
 * Heavily modified to allow magification and artifactification  -Bernd-
 *
 * Note that wizards cannot create objects on top of other objects.
 *
 * Hack -- this routine always makes a "dungeon object", and applies
 * magic to it, and attempts to decline cursed items.
 */
static void wiz_create_item(void)
{
	int py = p_ptr->py;
	int px = p_ptr->px;
/*	int i;*/

	object_type	forge;
	object_type *q_ptr;
	object_kind *k_ptr;

	int k_idx;


	/* Save the screen */
	screen_save();

	/* Get object base type */
	k_idx = wiz_create_itemtype();

	/* Restore the screen */
	screen_load();


	/* Return if failed */
	if (!k_idx) return;

	/* Get local object */
	q_ptr = &forge;

	/* Create the item */
	object_prep(q_ptr, k_idx);

	k_ptr = &k_info[k_idx];

/*
	if (k_ptr->flags3 & TR3_INSTA_ART)
	{*/
		/* Find the "special" artifact this object belongs to */
/*		for (i = 1; i < max_a_idx; i++)
		{
			artifact_type *a_ptr = &a_info[i];*/

			/* Skip "empty" artifacts */
/*			if (!a_ptr->name) continue;

			if ((a_ptr->tval == k_ptr->tval) && (a_ptr->sval == k_ptr->sval))
			{*/
				/* found it */
/*				create_named_art(i, py, px);*/

				/* All done */
/*				msg_print("Allocated.");

				return;
			}
		}
	}
	else
	{*/
		/* Apply magic */
		apply_magic(q_ptr, p_ptr->depth, 0, 0, FALSE);
/*	}*/

	/* Drop the object from heaven */
	(void)drop_near(q_ptr, -1, py, px);

	/* All done */
	msg_print("Allocated.");
}
示例#28
0
文件: wizard.c 项目: mtadd/angband
/*
 * Apply magic to an item or turn it into an artifact. -Bernd-
 */
static void wiz_reroll_item(object_type *o_ptr)
{
	object_type *i_ptr;
	object_type object_type_body;

	struct keypress ch;

	bool changed = FALSE;


	/* Hack -- leave artifacts alone */
	if (o_ptr->artifact) return;


	/* Get local object */
	i_ptr = &object_type_body;

	/* Copy the object */
	object_copy(i_ptr, o_ptr);


	/* Main loop. Ask for magification and artifactification */
	while (TRUE)
	{
		/* Display full item debug information */
		wiz_display_item(i_ptr, TRUE);

		/* Ask wizard what to do. */
		if (!get_com("[a]ccept, [n]ormal, [g]ood, [e]xcellent? ", &ch))
			break;

		/* Create/change it! */
		if (ch.code == 'A' || ch.code == 'a')
		{
			changed = TRUE;
			break;
		}

		/* Apply normal magic, but first clear object */
		else if (ch.code == 'n' || ch.code == 'N')
		{
			object_prep(i_ptr, o_ptr->kind, p_ptr->depth, RANDOMISE);
			apply_magic(i_ptr, p_ptr->depth, FALSE, FALSE, FALSE);
		}

		/* Apply good magic, but first clear object */
		else if (ch.code == 'g' || ch.code == 'G')
		{
			object_prep(i_ptr, o_ptr->kind, p_ptr->depth, RANDOMISE);
			apply_magic(i_ptr, p_ptr->depth, FALSE, TRUE, FALSE);
		}

		/* Apply great magic, but first clear object */
		else if (ch.code == 'e' || ch.code == 'E')
		{
			object_prep(i_ptr, o_ptr->kind, p_ptr->depth, RANDOMISE);
			apply_magic(i_ptr, p_ptr->depth, FALSE, TRUE, TRUE);
		}
	}


	/* Notice change */
	if (changed)
	{
		/* Mark as cheat */
		i_ptr->origin = ORIGIN_CHEAT;

		/* Restore the position information */
		i_ptr->iy = o_ptr->iy;
		i_ptr->ix = o_ptr->ix;
		i_ptr->next_o_idx = o_ptr->next_o_idx;
		i_ptr->marked = o_ptr->marked;

		/* Apply changes */
		object_copy(o_ptr, i_ptr);

		/* Recalculate bonuses */
		p_ptr->update |= (PU_BONUS);

		/* Combine / Reorder the pack (later) */
		p_ptr->notice |= (PN_COMBINE | PN_REORDER | PN_SORT_QUIVER);

		/* Window stuff */
		p_ptr->redraw |= (PR_INVEN | PR_EQUIP );
	}
}
示例#29
0
/**
 * Creates a specific monster's drop, including any drops specified
 * in the monster.txt file.
 *
 * Returns true if anything is created, false if nothing is.
 */
static bool mon_create_drop(struct chunk *c, struct monster *mon, byte origin)
{
	struct monster_drop *drop;

	bool great, good, gold_ok, item_ok;
    bool extra_roll = false;
	bool any = false;

	int number = 0, level, j, monlevel;

	struct object *obj;

	assert(mon);

	great = (rf_has(mon->race->flags, RF_DROP_GREAT));
	good = great || (rf_has(mon->race->flags, RF_DROP_GOOD));
	gold_ok = (!rf_has(mon->race->flags, RF_ONLY_ITEM));
	item_ok = (!rf_has(mon->race->flags, RF_ONLY_GOLD));

	/* Determine how much we can drop */
	number = mon_create_drop_count(mon->race, false);

    /* Give added bonus for unique monters */
    monlevel = mon->race->level;
    if (rf_has(mon->race->flags, RF_UNIQUE)) {
        monlevel = MIN(monlevel + 15, monlevel * 2);
        extra_roll = true;
    }

	/* Take the best of (average of monster level and current depth)
	   and (monster level) - to reward fighting OOD monsters */
	level = MAX((monlevel + player->depth) / 2, monlevel);
    level = MIN(level, 100);

	/* Morgoth currently drops all artifacts with the QUEST_ART flag */
	if (rf_has(mon->race->flags, RF_QUESTOR) && (mon->race->level == 100)) {
		/* Search all the artifacts */
		for (j = 1; j < z_info->a_max; j++) {
			struct artifact *art = &a_info[j];
			struct object_kind *kind = lookup_kind(art->tval, art->sval);
			if (!kf_has(kind->kind_flags, KF_QUEST_ART)) {
				continue;
			}

			/* Allocate by hand, prep, apply magic */
			obj = mem_zalloc(sizeof(*obj));
			object_prep(obj, kind, 100, RANDOMISE);
			obj->artifact = art;
			copy_artifact_data(obj, obj->artifact);
			obj->artifact->created = true;

			/* Set origin details */
			obj->origin = origin;
			obj->origin_depth = player->depth;
			obj->origin_race = mon->race;
			obj->number = 1;

			/* Try to carry */
			if (monster_carry(c, mon, obj)) {
				any = true;
			} else {
				obj->artifact->created = false;
				object_wipe(obj);
				mem_free(obj);
			}
		}
	}

	/* Specified drops */
	for (drop = mon->race->drops; drop; drop = drop->next) {
		if ((unsigned int)randint0(100) >= drop->percent_chance)
			continue;

		/* Allocate by hand, prep, apply magic */
		obj = mem_zalloc(sizeof(*obj));
		object_prep(obj, drop->kind, level, RANDOMISE);
		apply_magic(obj, level, true, good, great, extra_roll);

		/* Set origin details */
		obj->origin = origin;
		obj->origin_depth = player->depth;
		obj->origin_race = mon->race;
		obj->number = randint0(drop->max - drop->min) + drop->min;

		/* Try to carry */
		if (monster_carry(c, mon, obj)) {
			any = true;
		} else {
			object_wipe(obj);
			mem_free(obj);
		}
	}

	/* Make some objects */
	for (j = 0; j < number; j++) {
		if (gold_ok && (!item_ok || (randint0(100) < 50))) {
			obj = make_gold(level, "any");
		} else {
			obj = make_object(c, level, good, great, extra_roll, NULL, 0);
			if (!obj) continue;
		}

		/* Set origin details */
		obj->origin = origin;
		obj->origin_depth = player->depth;
		obj->origin_race = mon->race;

		/* Try to carry */
		if (monster_carry(c, mon, obj)) {
			any = true;
		} else {
			obj->artifact->created = false;
			object_wipe(obj);
			mem_free(obj);
		}
	}

	return any;
}
示例#30
0
文件: mon-make.c 项目: seebs/angband
/**
 * Attempts to place a copy of the given monster at the given position in
 * the dungeon.
 *
 * All of the monster placement routines eventually call this function. This
 * is what actually puts the monster in the dungeon (i.e., it notifies the cave
 * and sets the monsters position). The dungeon loading code also calls this
 * function directly.
 *
 * `origin` is the item origin to use for any monster drops (e.g. ORIGIN_DROP,
 * ORIGIN_DROP_PIT, etc.) The dungeon loading code calls this with origin = 0,
 * which prevents the monster's drops from being generated again.
 *
 * Returns the m_idx of the newly copied monster, or 0 if the placement fails.
 */
s16b place_monster(int y, int x, monster_type *mon, byte origin)
{
	s16b m_idx;
	monster_type *m_ptr;

	assert(cave_in_bounds(cave, y, x));
	assert(!cave_monster_at(cave, y, x));

	/* Get a new record */
	m_idx = mon_pop();
	if (!m_idx) return 0;

	/* Copy the monster */
	m_ptr = cave_monster(cave, m_idx);
	COPY(m_ptr, mon, monster_type);

	/* Set the ID */
	m_ptr->midx = m_idx;

	/* Set the location */
	cave->m_idx[y][x] = m_ptr->midx;
	m_ptr->fy = y;
	m_ptr->fx = x;
	assert(cave_monster_at(cave, y, x) == m_ptr);

	update_mon(m_ptr, TRUE);

	/* Hack -- Count the number of "reproducers" */
	if (rf_has(m_ptr->race->flags, RF_MULTIPLY)) num_repro++;

	/* Count racial occurrences */
	m_ptr->race->cur_num++;

	/* Create the monster's drop, if any */
	if (origin)
		(void)mon_create_drop(m_ptr, origin);

	/* Make mimics start mimicking */
	if (origin && m_ptr->race->mimic_kinds) {
		object_type *i_ptr;
		object_type object_type_body;
		object_kind *kind = m_ptr->race->mimic_kinds->kind;
		struct monster_mimic *mimic_kind;
		int i = 1;
		
		/* Pick a random object kind to mimic */
		for (mimic_kind = m_ptr->race->mimic_kinds; mimic_kind; 
				mimic_kind = mimic_kind->next, i++) {
			if (one_in_(i)) kind = mimic_kind->kind;
		}

		i_ptr = &object_type_body;

		if (kind->tval == TV_GOLD) {
			make_gold(i_ptr, p_ptr->depth, kind->sval);
		} else {
			object_prep(i_ptr, kind, m_ptr->race->level, RANDOMISE);
			apply_magic(i_ptr, m_ptr->race->level, TRUE, FALSE, FALSE, FALSE);
			i_ptr->number = 1;
		}

		i_ptr->origin = origin;
		i_ptr->mimicking_m_idx = m_idx;
		m_ptr->mimicked_o_idx = floor_carry(cave, y, x, i_ptr);
	}

	/* Result */
	return m_idx;
}