dawn/notes/
dawn/src/
dawn/src/docs/
/**************************************************************************/
// magic_ob.cpp - spells/skills from Oblivion source
/***************************************************************************
 * The Dawn of Time v1.69r (c)1997-2004 Michael Garratt                    *
 * >> A number of people have contributed to the Dawn codebase, with the   *
 *    majority of code written by Michael Garratt - www.dawnoftime.org     *
 * >> To use this source code, you must fully comply with all the licenses *
 *    in licenses.txt... In particular, you may not remove this copyright  *
 *    notice.                                                              *
 ***************************************************************************
 * >> Original Diku Mud copyright (c)1990, 1991 by Sebastian Hammer,       *
 *    Michael Seifert, Hans Henrik St{rfeldt, Tom Madsen, & Katja Nyboe.   *
 * >> Merc Diku Mud improvements copyright (C) 1992, 1993 by Michael       *
 *    Chastain, Michael Quan, and Mitchell Tse.                            *
 * >> ROM 2.4 is copyright 1993-1995 Russ Taylor and has been brought to   *
 *    you by the ROM consortium: Russ Taylor(rtaylor@pacinfo.com),         *
 *    Gabrielle Taylor(gtaylor@pacinfo.com) & Brian Moore(rom@rom.efn.org) *
 * >> Oblivion 1.2 is copyright 1996 Wes Wagner                            *
 **************************************************************************/
#include "include.h" // dawn standard includes

#include "magic.h"

// Prototypes
DECLARE_DO_FUN(do_look);
DECLARE_DO_FUN(do_bug);
bool check_cold_shield( int level, char_data *ch, char_data *victim);
bool check_fire_shield( int level, char_data *ch, char_data *victim);
bool is_aff_fire_shield( char_data *ch, char_data *victim );
bool is_aff_cold_shield( char_data *ch, char_data *victim );
bool check_skin( char_data *ch, char_data *victim);

/**************************************************************************/
// by Airius WWW 
void send_hue_mess(char *clmess, char *clcode, char_data *ch, char_data *victim)
{
	char buf[MSL];
	char_data	*vch;
	char_data   *vch_next;
	
	// to character
	victim->printlnf( "%sA %s hue strikes you!`x", clcode, clmess);
	
	// to room
	sprintf(buf, "%sA %s hue strikes %s!`x", clcode,
		clmess, victim->short_descr);
    for ( vch = ch->in_room->people; vch; vch = vch_next )
	{
        vch_next=vch->next_in_room;
		// dont affect unseen mobs
		if ( IS_NPC(vch) && IS_SET(vch->act, ACT_IS_UNSEEN)){
			continue;
		}

		if (vch->in_room == NULL)
			continue;
		if ( vch->in_room == ch->in_room )
		{
			if ( vch != victim )
			{
				vch->printlnf( "%s", buf );
			}
			continue;
		}
	}
	
}
/**************************************************************************/
// by Airius WWW 
void strike_with_hue( int sn, int level, char_data *ch, char_data *victim)
{
	int dtoss;
	ROOM_INDEX_DATA *pRoomIndex;
	AFFECT_DATA af;
	
	dtoss=dice(1,7);
	switch (dtoss)
	{
	case 1 :
		send_hue_mess("red", "`r", ch, victim);
		damage_spell(ch, victim, saves_spell( level, victim, DAM_LIGHT) ?
			50 : 25, sn, DAM_LIGHT, true);
		break;
	case 2 :
		send_hue_mess("orange", "`R", ch, victim);
		damage_spell(ch, victim, saves_spell( level, victim, DAM_ENERGY) ? 
			100 : 50, sn, DAM_ENERGY, true);
		break;
	case 3 :
		send_hue_mess("yellow", "`Y", ch, victim);
		damage_spell(ch, victim, saves_spell( level, victim, DAM_FIRE) ? 
			150 : 75, sn, DAM_FIRE, true);
		break;
	case 4 :
		send_hue_mess("green", "`g", ch, victim);
		if(!saves_spell(level, victim, DAM_POISON))
		{
			af.where     = WHERE_AFFECTS;
			af.type      = sn;
			af.level     = level;
			af.duration  = level;
			af.location  = APPLY_ST;
			af.modifier  = -4;
			af.bitvector = AFF_POISON;
			affect_join( victim, &af );
			victim->println("You feel very sick.");
			act("$n looks very ill.",victim,NULL,NULL,TO_ROOM);
		}
		else
			damage_spell(ch, victim, 20, sn, DAM_POISON, true);
		break;
	case 5 :
		send_hue_mess("blue", "`b", ch, victim);
		if ( victim->in_room == NULL
			|| IS_SET(victim->in_room->room_flags, ROOM_NO_RECALL)
			|| ( victim != ch && IS_SET(victim->imm_flags,IMM_SUMMON))
			|| ( !IS_NPC(ch) && victim->fighting != NULL )
			|| ( victim != ch
			&& ( saves_spell( level - 5, victim,DAM_OTHER))))
		{
			break;
		}
		
		pRoomIndex = get_random_room(victim);
		
		if (victim != ch)
			victim->println("You have been teleported!");
		
		act( "$n vanishes!", victim, NULL, NULL, TO_ROOM );
		char_from_room( victim );
		char_to_room( victim, pRoomIndex );
		act( "$n slowly fades into existence.", victim, NULL, NULL, TO_ROOM );
		do_look( victim, "auto" );
		break;
	case 6 :
		send_hue_mess("indigo", "`M", ch, victim);
		if (saves_spell(level,victim,DAM_OTHER)
			||  IS_SET(victim->imm_flags,IMM_MAGIC))
		{
			if (victim != ch)
				ch->println("Nothing seemed to happen.");
			victim->println("You feel momentarily lethargic.");
			break;
		}
		
		if (IS_AFFECTED(victim,AFF_HASTE))
		{
			if (!check_dispel(level,victim, gsn_haste ))
			{
				if (victim!= ch){
					ch->println("Spell failed.");
				}
				return;
			}			
			act("$n is moving less quickly.",victim,NULL,NULL,TO_ROOM);
			return;
		}		
		
		af.where     = WHERE_AFFECTS;
		af.type      = sn;
		af.level     = level;
		af.duration  = level/2;
		af.location  = APPLY_QU;
		af.modifier  = -1 - (level/5);
		af.bitvector = AFF_SLOW;
		affect_join( victim, &af );
		victim->println("You feel yourself slowing d o w n...");
		act("$n starts to move in slow motion.",victim,NULL,NULL,TO_ROOM);
		break;
	case 7 :
		send_hue_mess("violet", "`m", ch, victim);
		damage_spell(ch, victim, saves_spell( level, victim, DAM_NEGATIVE) ? 200 : 150, sn, DAM_NEGATIVE, true);
		break;
	}
	return;
}
/**************************************************************************/
//  By Wynn
SPRESULT spell_animal_essence( int sn, int level, char_data *ch, void *vo, int )
{
	char_data 	*victim = (char_data *) vo;
	AFFECT_DATA	af;
	
	if ( !IS_SET( victim->affected_by, AFF_FLYING ))
	{
		if ( !IS_SET( ch->in_room->room_flags, ROOM_NOFLY	)){
			af.where		= WHERE_AFFECTS;
			af.type			= sn;
			af.level		= level;
			af.duration		= level/2;
			af.location		= APPLY_NONE;
			af.modifier		= 0;
			af.bitvector	= AFF_FLYING;
			affect_to_char( victim, &af );
			victim->println( "Your feet rise off the ground." );
			act( "$n's feet rise off the ground.", ch, NULL, victim, TO_NOTVICT );
		}
	}
	else
		victim->println("You already can fly.");

	if ( !IS_SET( victim->affected_by, AFF_DETECT_HIDDEN ))
	{
		af.where 	 = WHERE_AFFECTS;
		af.type		 = sn;
		af.level	 = level;
		af.duration  = level/2;
		af.location  = APPLY_NONE;
		af.modifier  = 0;
		af.bitvector = AFF_DETECT_HIDDEN;
		affect_to_char( victim, &af );
		victim->println("Your awareness improves.");
	}
	else
		victim->println("You are as alert as you're ever going to be.");
	
	if ( !IS_SET( victim->affected_by, AFF_DETECT_INVIS ))
	{
		af.where		= WHERE_AFFECTS;
		af.type			= sn;
		af.level		= level;
		af.duration		= level/2;
		af.location		= APPLY_NONE;
		af.modifier		= 0;
		af.bitvector	= AFF_DETECT_INVIS;
		affect_to_char( victim, &af );
		victim->println("Your eyes tingle.");
	}
	else
		victim->println("You can already see the invisible.");

	if ( !is_affected( victim, gsn_augment_hearing ))
	{
		af.where		= WHERE_AFFECTS;
		af.type			= gsn_augment_hearing;
		af.level		= level;
		af.duration		= level/5;
		af.location		= APPLY_NONE;
		af.modifier		= 0;
		af.bitvector	= 0;
		affect_to_char( victim, &af );
		victim->println("Your hearing is greatly augmented.");
	}
	else
		victim->println("Your hearing is already augmented.");

	ch->println("Ok.");
	return FULL_MANA;
}

/**************************************************************************/
// by Airius WWW + Jarren Update
SPRESULT spell_barkskin( int sn, int level, char_data *ch, void *vo,int )
{
	char_data *victim = (char_data *) vo;
	AFFECT_DATA af;
	
	if(check_skin( ch, victim ))
		return HALF_MANA;
	
	af.where     = WHERE_AFFECTS;
	af.type      = sn;
	af.level     = level;
	af.duration  = level;
	af.location  = APPLY_AC;
	af.modifier  = -40;
	af.bitvector = 0;
	affect_to_char( victim, &af );
	act( "$n's skin turns to bark.", victim, NULL, NULL, TO_ROOM );
	victim->println("Your skin turns to bark.");
	af.where	 = WHERE_VULN;
	af.location  = APPLY_NONE;
	af.modifier  = 0;
	af.bitvector = VULN_FIRE;
	affect_to_char( victim, &af );
	
	return FULL_MANA;
}

/**************************************************************************/
// Airius WWW + Jarren Update
SPRESULT spell_chill_shield( int, int level, char_data *ch, void *vo,int  )
{
	char_data *victim = (char_data *) vo;
	AFFECT_DATA af;
	
	if ( is_aff_cold_shield( ch, victim ))
		return HALF_MANA;
	
	else if ( check_fire_shield(level, ch, victim))
		return FULL_MANA;

	af.where     = WHERE_AFFECTS;
	af.type      = gsn_chill_shield;
	af.level     = level;
	if (victim == ch)
		af.duration  = level/5;
	else
		af.duration  = level/10;
	af.location  = APPLY_NONE;
	af.modifier  = 0;
	af.bitvector = 0;
	affect_to_char( victim, &af );
	af.where	  = WHERE_RESIST;
	af.bitvector = RES_FIRE;
	affect_to_char( victim, &af );
	af.where	  = WHERE_VULN;
	af.bitvector = VULN_COLD;
	victim->println("You are surrounded by an icy aura.");
	act("$n is surrounded by an icy aura.",victim,NULL,NULL,TO_ROOM);
	if ( ch != victim )
		ch->println("Ok.");
	return FULL_MANA;
}

/**************************************************************************/
// by Airius WWW
SPRESULT spell_cone_cold( int sn, int level, char_data *ch, void *, int  )
{
	char_data	*vch;
	char_data	*vch_next;
	int			dam;
	AFFECT_DATA af;

	dam = dice( level , 3 )+50;

	af.where		= WHERE_AFFECTS;
	af.type			= sn;
	af.level		= level;
	af.duration		= level;
	af.location		= APPLY_ST;
	af.modifier		= -level/3;
	af.bitvector	= 0;

	ch->println("You send forth a cone of cold!");
	act( "$n places out his hands and blasts forth a cone of cold!",ch, NULL, NULL, TO_ROOM );

    for ( vch = ch->in_room->people; vch; vch = vch_next )
	{
        vch_next=vch->next_in_room;
		// dont affect unseen mobs
		if ( IS_NPC(vch) && IS_SET(vch->act, ACT_IS_UNSEEN)){
			continue;
		}

		if (vch->in_room == NULL)
			continue;
		if ( vch->in_room == ch->in_room )
		{
			if ( vch != ch
			&& ( IS_NPC( ch ) ? !IS_NPC( vch ) : IS_NPC( vch )))
			{
		        damage_spell( ch, vch, saves_spell( level, vch, DAMTYPE(sn)) ? dam /2 : dam, sn, DAMTYPE(sn), true );
				if(!saves_spell(level,vch, DAMTYPE(sn)))
				{
					affect_join( vch, &af );
					vch->printf( "The cold seeps into your bones." );
				}
			}
			continue;
		}
	}
	return FULL_MANA;
}

/**************************************************************************/
// Airius WWW
SPRESULT spell_create_buffet( int , int level, char_data *ch, void *,int )
{
	OBJ_DATA *mushroom=NULL;
	int counter=0;
	
	for(counter=0; counter< number_fuzzy(level/5)+1; counter++)
	{
		mushroom = create_object( get_obj_index( OBJ_VNUM_MUSHROOM ));
		mushroom->value[0] = number_fuzzy(level) / 2;
		mushroom->value[1] = number_fuzzy(level);
		mushroom->timer = number_fuzzy((number_fuzzy(number_fuzzy((ch->level))+10)));
		obj_to_room( mushroom, ch->in_room );
	}
	if(counter){
		act( FORMATF("$p suddenly appears (x%d).", counter), ch, mushroom, NULL, TO_ROOM );
	}
	return FULL_MANA;
}

/**************************************************************************/
// Airius WWW
SPRESULT spell_drain_blade( int sn, int level, char_data *ch, void *vo, int  )
{
	OBJ_DATA *obj;
	AFFECT_DATA af;
	
	obj=(OBJ_DATA *) vo;
	
	
	if(IS_GOOD(ch))
	{
		ch->println("You are far too nice to use such evil magic.");
		return NO_MANA;
	}
	
	if(!IS_EVIL(ch))
	{
		ch->println("You are not quite wicked enough to do that.");
		return NO_MANA;
	}
	if(obj->item_type != ITEM_WEAPON)
	{
		ch->println("You can only target sharp weapons.");
		return NO_MANA;
	}
	else
	{
		if( obj->value[0] == WEAPON_WHIP
			||  obj->value[0] == WEAPON_EXOTIC )
		{
			act( "Your spell had no effect on $p.", ch, obj, NULL, TO_CHAR );
			return HALF_MANA;
		}
		else
		{
			if(IS_WEAPON_STAT(obj,WEAPON_VAMPIRIC))
			{
				ch->println("That weapon is already quite evil.");
				return HALF_MANA;
			}
			if(IS_OBJ_STAT(obj,OBJEXTRA_BLESS))
			{
				ch->println("That weapon is too holy to be touched by your majiks.");
				return FULL_MANA;
			}
			if(!IS_OBJ_STAT(obj,OBJEXTRA_EVIL))
				SET_BIT(obj->extra_flags, OBJEXTRA_EVIL);
			if(!IS_OBJ_STAT(obj,OBJEXTRA_ANTI_GOOD))
				SET_BIT(obj->extra_flags, OBJEXTRA_ANTI_GOOD);
			if(!IS_OBJ_STAT(obj,OBJEXTRA_ANTI_NEUTRAL))
				SET_BIT(obj->extra_flags, OBJEXTRA_ANTI_NEUTRAL);
			
			af.where    = WHERE_WEAPON;
			af.type     = sn;
			af.level    = level/2;
			af.duration = level/2;
			af.location = APPLY_NONE;
			af.modifier = 0;
			af.bitvector= WEAPON_VAMPIRIC;
			affect_to_obj(obj, &af);
			
			act("$p becomes dark and evil.",ch,obj,NULL,TO_ALL);
			return FULL_MANA;
		}
	}
	return FULL_MANA;
}

/**************************************************************************/
// Airius WWW
SPRESULT spell_empower_blade( int sn, int level, char_data *ch, void *vo, int  )
{
	OBJ_DATA *obj;
	AFFECT_DATA af;
	
	obj=(OBJ_DATA *) vo;
	
	if(obj->item_type != ITEM_WEAPON)
	{
		ch->println("You can only target sharp weapons.");
		return NO_MANA;
	}
	else
	{
		if(    obj->value[0] == WEAPON_WHIP
			|| obj->value[0] == WEAPON_EXOTIC ) {
			act( "Your spell had no effect on $p.", ch, obj, NULL, TO_CHAR );
			return HALF_MANA;
		}
		else
		{
			if(IS_WEAPON_STAT(obj,WEAPON_SHOCKING))
			{
				ch->println("That weapon is already imbued with power.");
				return HALF_MANA;
			}
			
			af.where    = WHERE_WEAPON;
			af.type     = sn;
			af.level    = level/2;
			af.duration = level;
			af.location = APPLY_NONE;
			af.modifier = 0;
			af.bitvector= WEAPON_SHOCKING;
			affect_to_obj(obj, &af);
			
			act("$p sparks with electricity.",ch,obj,NULL,TO_ALL);
			return FULL_MANA;
		}
	}
	return FULL_MANA;
}


/**************************************************************************/
// Airius WWW
SPRESULT spell_flame_blade( int sn, int level, char_data *ch, void *vo, int  )
{
	OBJ_DATA *obj;
	AFFECT_DATA af;
	
	obj=(OBJ_DATA *) vo;
	
	if(obj->item_type != ITEM_WEAPON)
	{
		ch->println("You can only target sharp weapons.");
		return NO_MANA;
	}
	else
	{
		if( obj->value[0] == WEAPON_WHIP
			||  obj->value[0] == WEAPON_EXOTIC ) {
			act( "Your spell had no effect on $p.", ch, obj, NULL, TO_CHAR );
			return HALF_MANA;
		}
		else
		{
			if(IS_WEAPON_STAT(obj,WEAPON_FLAMING))
			{
				ch->println("That weapon is already flaming.");
				return HALF_MANA;
			}
			if(IS_WEAPON_STAT(obj,WEAPON_FROST))
			{
				ch->println("That weapon is too cold to accept the magic.");
				return FULL_MANA;
			}
			
			af.where    = WHERE_WEAPON;
			af.type     = sn;
			af.level    = level/2;
			af.duration = level;
			af.location = APPLY_NONE;
			af.modifier = 0;
			af.bitvector= WEAPON_FLAMING;
			affect_to_obj(obj, &af);
			
			act("$p gets a fiery aura.",ch,obj,NULL,TO_ALL);
			return FULL_MANA;
		}
	}
	return FULL_MANA;
}

/**************************************************************************/
// Airius WWW + Jarren Update
SPRESULT spell_fire_shield( int sn, int level, char_data *ch, void *vo,int  )
{
	char_data *victim = (char_data *) vo;
	AFFECT_DATA af;
	
	if ( is_aff_fire_shield( ch, victim ))
		return HALF_MANA;
	
	else if ( check_cold_shield(level, ch, victim))
		return FULL_MANA;
	
	af.where     = WHERE_AFFECTS;
	af.type      = sn;
	af.level     = level;
	if (victim == ch)
		af.duration  = level/5;
	else
		af.duration  = level/10;
	af.location  = APPLY_NONE;
	af.modifier  = 0;
	af.bitvector = 0;
	affect_to_char( victim, &af );
	af.where	  = WHERE_RESIST;
	af.bitvector = RES_COLD;
	affect_to_char( victim, &af );
	af.where	  = WHERE_VULN;
	af.bitvector = VULN_FIRE;
	victim->println("You are surrounded by a fire shield.");
	act("$n is surrounded by a fire shield.",victim,NULL,NULL,TO_ROOM);
	if ( ch != victim )
		ch->println("Ok.");
	return FULL_MANA;
}

/**************************************************************************/
// Airius WWW
SPRESULT spell_frost_blade( int sn, int level, char_data *ch, void *vo, int  )
{
	OBJ_DATA *obj;
	AFFECT_DATA af;
	
	obj=(OBJ_DATA *) vo;
	
	if(obj->item_type != ITEM_WEAPON)
	{
		ch->println("You can only target sharp weapons.");
		return NO_MANA;
	}
	else
	{
		if(    obj->value[0] == WEAPON_WHIP
			|| obj->value[0] == WEAPON_EXOTIC ) {
			act( "Your spell had no effect on $p.", ch, obj, NULL, TO_CHAR );
			return HALF_MANA;
		}
		else
		{
			if(IS_WEAPON_STAT(obj,WEAPON_FROST))
			{
				ch->println("That weapon is already wickedly cold.");
				return HALF_MANA;
			}
			if(IS_WEAPON_STAT(obj,WEAPON_FLAMING))
			{
				ch->println("That weapon is too hot to accept the magic.");
				return FULL_MANA;
			}
			
			af.where    = WHERE_WEAPON;
			af.type     = sn;
			af.level    = level/2;
			af.duration = level;
			af.location = APPLY_NONE;
			af.modifier = 0;
			af.bitvector= WEAPON_FROST;
			affect_to_obj(obj, &af);
			
			act("$p grows wickedly cold.",ch,obj,NULL,TO_ALL);
			return FULL_MANA;
		}
	}
	return FULL_MANA;
}


/**************************************************************************/
// by Airius WWW 
SPRESULT spell_holy_aura( int sn, int level, char_data *ch, void *vo, int  )
{
	char_data *victim = (char_data *) vo;
	AFFECT_DATA af;
	
	if ( !IS_IMMORTAL(ch) && (!IS_GOOD(victim) || !IS_GOOD(ch)))
	{
		if(ch == victim)
		{
			ch->println("You are not holy enough to cast this spell.");
			return NO_MANA;
		}

		ch->println("They are too unrighteous!");
		return HALF_MANA;
	}
	
	if(!is_affected(victim,sn))
	{
		af.where      = WHERE_AFFECTS;
		af.type		  = sn;
		af.level	  = level;
		af.duration	  = level/5;
		af.location	  = APPLY_AC;
		af.bitvector  = 0;
		af.modifier	  = -level;
		affect_to_char( victim, &af);
		af.where	  = WHERE_RESIST;
		af.modifier	  = 0;
		af.location	  = APPLY_NONE;
		af.bitvector  = RES_NEGATIVE;
		affect_to_char( victim, &af);
		victim->println("You are surrounded by a golden aura.");
		act("$n is surrounded with a gold aura.", ch, NULL, victim, TO_NOTVICT);
	}
	else
	{
		if(ch == victim)
			ch->println("You are already protected by divine magic.");
		else
			ch->println("They are already protected.");
		return HALF_MANA;
	}
	
	return FULL_MANA;
}

/**************************************************************************/
SPRESULT spell_ice_storm( int sn, int level, char_data *ch, void *, int  )
{
	char_data	*vch;
	char_data	*vch_next;
	int			dam;
	AFFECT_DATA af;
	
	dam = 150;
	
	af.where     = WHERE_AFFECTS;
	af.type      = sn;
	af.level     = level;
	af.duration  = level/10;
	af.location  = APPLY_QU;
	af.modifier  = -1 - (level/5);
	af.bitvector = AFF_SLOW;
	
	ch->println("You conjure up an ice storm!");
	act( "$n raises $s hands and an ice storm appears from nowhere!",ch, NULL, NULL, TO_ROOM );
	
    for ( vch = ch->in_room->people; vch; vch = vch_next )
	{
        vch_next=vch->next_in_room;
		// dont affect unseen mobs
		if ( IS_NPC(vch) && IS_SET(vch->act, ACT_IS_UNSEEN)){
			continue;
		}

		if (vch->in_room == NULL)
			continue;

		if ( vch->in_room == ch->in_room )
		{
			if ( vch != ch
				&& ( IS_NPC( ch ) ? !IS_NPC( vch ) : IS_NPC( vch ) ) )
			{
				damage_spell( ch, vch, saves_spell( level, vch, DAMTYPE(sn)) ? dam /2 : dam, sn, DAMTYPE(sn), true );
				if(!saves_spell(level,vch, DAMTYPE(sn)))
				{
					affect_join( vch, &af );
					vch->println("You get covered in ice and have a hard time moving.");
					act("$n is covered in ice.",vch,NULL,NULL,TO_ROOM);
				}
			}
			continue;
		}
	}
	return FULL_MANA;
}


/**************************************************************************/
// by Airius  WWW 
SPRESULT spell_illusions_grandeur( int sn, int level, char_data *ch, void *vo, int )
{
	char_data *victim = (char_data *) vo;
	AFFECT_DATA af;

	if ( is_affected( victim, gsn_strength_of_the_land )) {
		ch->println("Spell failed.");
		return HALF_MANA;
	}
	
	if(!is_affected(victim,sn))
	{
		af.where		= WHERE_AFFECTS;
		af.type			= sn;
		af.level		= level;
		af.duration		= level/10;
		af.location		= APPLY_HIT;
		af.modifier		= level;
		af.bitvector	= 0;
		affect_to_char( victim, &af );
		victim->println("You appear mightier than you are!");
		act( "$n grows in stature and appears quite mighty now!", victim, NULL, NULL, TO_ROOM );
	}
	else
	{
		victim->println("You are having delusions of grandeur now.");
		return HALF_MANA;
	}
	return FULL_MANA;
}

/**************************************************************************/
// by Airius 
SPRESULT spell_improved_phantasm( int sn, int level, char_data *ch, void *vo, int )
{
	char_data *victim = (char_data *) vo;
	int dam;
	
	dam = dice(level, 9);
	if(saves_spell( level, victim, DAMTYPE(sn)))
		dam = dam/3;
	damage_spell( ch, victim, dam, sn, DAMTYPE(sn), true);
	return FULL_MANA;
}

/**************************************************************************/
SPRESULT spell_induce_sleep( int, int, char_data *ch, void *vo, int )
{
	char_data *victim = (char_data *) vo;
	
	if(ch==victim)
	{
		ch->println("You put yourself to sleep.");
		ch->is_trying_sleep=true;
		ch->position=POS_SLEEPING;
		act( "$n goes quietly to sleep.", ch, NULL, NULL, TO_ROOM );
	}
	
	if(IS_NPC(victim))
	{
		ch->println("You cannot put to sleep unwilling creatures.");
		return FULL_MANA;
	}
	
	if(victim->is_trying_sleep)
	{
		victim->println("You drift off into dreamland.");
		victim->position=POS_SLEEPING;
		act( "$n goes quietly to sleep.", victim, NULL, NULL, TO_ROOM );
		return FULL_MANA;
	}
	
	ch->println("You cannot put to sleep others so unwilling.");
	
	return FULL_MANA;
}

/**************************************************************************/
// by Airius
SPRESULT spell_magic_resistance( int sn, int level, char_data *, void *vo, int )
{
	char_data *victim = (char_data *) vo;
	AFFECT_DATA af;
	
	if(!is_affected(victim,sn))
	{
		af.where		= WHERE_RESIST;
		af.type			= sn;
		af.level		= level;
		af.duration		= level/10+1;
		af.location 	= APPLY_NONE;
		af.modifier 	= 0;
		af.bitvector	= RES_MAGIC;
		affect_to_char(victim, &af);
		victim->println("You are protected from magic.");
	}
	else
	{
		victim->println("You are already protected from magic.");
		return HALF_MANA;
	}
	return FULL_MANA;
}

/**************************************************************************/
// by Airius
SPRESULT spell_phantasmal_force( int sn, int level, char_data *ch, void *vo, int )
{
	char_data *victim = (char_data *) vo;
	int dam;
	
	dam = dice(level, 4);
	if(saves_spell( level, victim, DAMTYPE(sn)))
		dam = 0;
	damage_spell( ch, victim, dam, sn, DAMTYPE(sn), true);
	return FULL_MANA;
}

/**************************************************************************/
// by Airius WWW 
SPRESULT spell_prismatic_spray( int sn, int level, char_data *ch, void *, int )
{
	char_data	*vch;
	char_data   *vch_next;
	int number_hits;
	int i;
	
	ch->println("You put out your hands and send forth a dazzling pristmatic spray!");
	act( "$n raises $s hands and sends out a dazzling prismatic spray!",ch, NULL, NULL, TO_ROOM );
	
    for ( vch = ch->in_room->people; vch; vch = vch_next )
	{
        vch_next=vch->next_in_room;

		// dont affect unseen mobs
		if ( IS_NPC(vch) && IS_SET(vch->act, ACT_IS_UNSEEN)){
			continue;
		}

		if (vch->in_room == NULL)
			continue;

		if ( vch->in_room == ch->in_room )
		{
			if ( vch != ch && ( IS_NPC( ch ) ? !IS_NPC( vch ) : IS_NPC( vch ) ) )
			{
				if(dice(1,8)==8)
					number_hits=2;	else number_hits=1;
				if(dice(1,8)==8)
					number_hits+=2; else number_hits+=1;
				for(i=1; i<=number_hits; i+=1)
				{
					strike_with_hue(sn,level,ch,vch);
				}
			}
			continue;
		}
	}
	return FULL_MANA;
}

/**************************************************************************/
// by Airius 
SPRESULT spell_protection_fire( int sn, int level, char_data *, void *vo, int  )
{
	char_data *victim = (char_data *) vo;
	AFFECT_DATA af;
	
	if(!is_affected(victim,sn))
	{
		af.where		= WHERE_RESIST;
		af.type			= sn;
		af.level		= level;
		af.duration		= level/2;
		af.location 	= APPLY_NONE;
		af.modifier 	= 0;
		af.bitvector	= RES_FIRE;
		affect_to_char(victim, &af);
		victim->println("You are protected from flames.");
	}
	else
	{
		victim->println("You are already protected from fire.");
		return HALF_MANA;
	}
	return FULL_MANA;
}

/**************************************************************************/
// by Airius
SPRESULT spell_protection_cold( int sn, int level, char_data *, void *vo, int  )
{
	char_data *victim = (char_data *) vo;
	AFFECT_DATA af;
	
	if(!is_affected(victim,sn))
	{
		af.where		= WHERE_RESIST;
		af.type			= sn;
		af.level		= level;
		af.duration		= level/2;
		af.location 	= APPLY_NONE;
		af.modifier 	= 0;
		af.bitvector	= RES_COLD;
		affect_to_char(victim, &af);
		victim->println("You are protected from cold.");
	}
	else
	{
		victim->println("You are already protected from cold.");
		return HALF_MANA;
	}
	return FULL_MANA;
}

/**************************************************************************/
// by Airius 
SPRESULT spell_protection_lightning( int sn, int level, char_data *, void *vo, int  )
{
	char_data *victim = (char_data *) vo;
	AFFECT_DATA af;
	
	if(!is_affected(victim,sn))
	{
		af.where		= WHERE_RESIST;
		af.type			= sn;
		af.level		= level;
		af.duration		= level/2;
		af.location 	= APPLY_NONE;
		af.modifier 	= 0;
		af.bitvector	= RES_LIGHTNING;
		affect_to_char(victim, &af);
		victim->println("You are protected from lightning.");
	}
	else
	{
		victim->println("You are already protected from lightning.");
		return HALF_MANA;
	}
	return FULL_MANA;
}

/**************************************************************************/
// by Airius 
SPRESULT spell_poison_immunity( int sn, int level, char_data *, void *vo, int  )
{
	char_data *victim = (char_data *) vo;
	AFFECT_DATA af;
	
	if(!is_affected(victim,sn))
	{
		af.where		= WHERE_IMMUNE;
		af.type			= sn;
		af.level		= level;
		af.duration		= level/4+10;
		af.location 	= APPLY_NONE;
		af.modifier 	= 0;
		af.bitvector	= IMM_POISON;
		affect_to_char(victim, &af);
		victim->println("You are immune to all forms of poison.");
	}
	else
	{
		victim->println("You are already immune to poison.");
		return HALF_MANA;
	}
	return FULL_MANA;
}


/**************************************************************************/
// by Wynn
SPRESULT spell_poison_rain( int sn, int level, char_data *ch, void *, int  )
{
	char_data	*vch;
	char_data       *vch_next;
	int			 dam;
	AFFECT_DATA af;
	
	if ( !IS_OUTSIDE( ch ) )
	{
		ch->println("You must be out of doors.");
		return NO_MANA;
	}
	
	if ( ch->in_room->sector_type == SECT_CAVE )
	{
		ch->println("You can't make it rain here.");
		return NO_MANA;
	}

	dam = dice( level , 8 );
	
	af.where	 = WHERE_AFFECTS;
	af.type		 = gsn_poison;
	af.level	 = level;
	af.duration  = level;
	af.location  = APPLY_ST;
	af.modifier  = -4;
	af.bitvector = AFF_POISON;
	
	ch->println("A burning rain falls on your enemy's heads!");
	act( "$n brings forth a rain of poison!", ch, NULL, NULL, TO_ROOM );
	
    for ( vch = ch->in_room->people; vch; vch = vch_next )
	{
        vch_next=vch->next_in_room;
		// dont affect unseen mobs
		if ( IS_NPC(vch) && IS_SET(vch->act, ACT_IS_UNSEEN)){
			continue;
		}

		if (vch->in_room == NULL)
			continue;
		if ( vch->in_room == ch->in_room )
		{
			if ( vch != ch
				&& ( IS_NPC( ch ) ? !IS_NPC( vch ) : IS_NPC( vch ) )
				&& !HAS_CLASSFLAG(vch, CLASSFLAG_POISON_IMMUNITY))
			{
				damage_spell( ch, vch, saves_spell( level, vch, DAMTYPE(sn) ) ? dam /2 : dam, sn, DAMTYPE(sn), true );
				if(!saves_spell(level,vch, DAMTYPE(sn)))
					affect_join( vch, &af );
			}
			continue;
		}
	}
	
	return FULL_MANA;
}

/**************************************************************************/
// by Wynn
SPRESULT spell_rage ( int sn, int level, char_data *ch, void *vo, int )
{
	char_data	*victim = (char_data *)	vo;
	AFFECT_DATA	af;
	
	if ( is_affected( victim, sn ))
	{
		if (victim == ch)
			ch->println("You are already enraged.");
		else
			act("$N is already enraged.",ch,NULL,victim,TO_CHAR);
		return HALF_MANA;
	}
	
	af.where		= WHERE_AFFECTS;
	af.type			= sn;
	af.level	 	= level;
	af.duration		= level / 4;
	af.location		= APPLY_DAMROLL;
	af.modifier		= level / 5;
	af.bitvector	= 0;
	affect_to_char( victim, &af );
	
	af.location = APPLY_AC;
	af.modifier = level*3;
	affect_to_char( victim, &af );
	
	af.location = APPLY_HIT;
	af.modifier = level/2;
	affect_to_char( victim, &af );
	victim->hit = UMIN( victim->hit + level*2, victim->max_hit );
	update_pos( victim );
	
	if (ch != victim ){
		act("$N appears to be filled with rage.",ch,NULL,victim,TO_CHAR);
	}
	victim->println("You feel enraged!");
	return FULL_MANA;
}

/**************************************************************************/
SPRESULT spell_regeneration( int sn, int level, char_data *ch, void *vo, int )
{
	char_data 	*victim = (char_data *) vo;
	AFFECT_DATA	af;

	if (IS_AFFECTED( victim, AFF_REGENERATION ))
	{
		if(ch==victim)
			ch->println("You are already healing at an accelerated rate.");
		else
			ch->println("They are already regenerating.");
		return HALF_MANA;
	}

	af.where		= WHERE_AFFECTS;
	af.type			= sn;
	af.level	 	= level;
	af.duration		= level / 4;
	af.location		= APPLY_NONE;
	af.modifier		= 0;
	af.bitvector	= AFF_REGENERATION;
	affect_to_char( victim, &af );

	if(victim==ch)
		ch->println("You feel more vibrant!!!");
	else
	{
		victim->println("You feel more vibrant!!!");
		ch->println("Ok.");
	}

	return FULL_MANA;
}

/**************************************************************************/
// contributed by Wynn, Modified by Airius
SPRESULT spell_rejuvinate( int, int level, char_data *ch, void *vo, int  )
{
	char_data 	*victim = (char_data *) vo;

	victim->hit = victim->max_hit;
	update_pos( victim );
	victim->println("You feel rejuvinated...");
	if ( ch != victim )
		ch->println("Ok.");
	if ( is_affected( victim, gsn_curse ) )
	{
		affect_strip( victim, gsn_curse );
		victim->println("A warm feeling fills your body.");
		act( "$N looks better.", ch, NULL, victim, TO_NOTVICT );
	}

	if ( is_affected( victim, gsn_poison ) )
	{
		affect_strip( victim, gsn_poison );
		victim->println("You feel better.");
	}
	// boost movement points
	victim->move = UMIN( victim->move + level/2, victim->max_move );
	// restore tiredness
	if(!IS_NPC(victim) && victim->pcdata->tired!=-1)
	{
		victim->pcdata->tired-=level/10+2;
		if(victim->pcdata->tired<0)
			victim->pcdata->tired=0;
		victim->println("You feel less tired.");
	}
	return FULL_MANA;
}

/**************************************************************************/
// by Airius
SPRESULT spell_resist_poison( int sn, int level, char_data *, void *vo, int )
{
	char_data *victim = (char_data *) vo;
	AFFECT_DATA af;

	if(!is_affected(victim,sn))
	{
		af.where		= WHERE_RESIST;
		af.type			= sn;
		af.level		= level;
		af.duration		= level/4+10;
		af.location 	= APPLY_NONE;
		af.modifier 	= 0;
		af.bitvector	= RES_POISON;
		affect_to_char(victim, &af);
		victim->println("You are protected from all forms of poison.");
	}
	else
	{
		victim->println("You are already protected from poison.");
		return HALF_MANA;
	}

	return FULL_MANA;
}

/**************************************************************************/
// Airius WWW
SPRESULT spell_rune_edge( int sn, int level, char_data *ch, void *vo, int )
{
	OBJ_DATA *obj;
	AFFECT_DATA af;

	obj=(OBJ_DATA *) vo;

	if(obj->item_type != ITEM_WEAPON)
	{
		ch->println("You can only target sharp weapons.");
		return NO_MANA;
	}
	else
	{
		if(obj->value[0]!=WEAPON_SWORD && obj->value[0]!=WEAPON_DAGGER
			&& obj->value[0]!=WEAPON_STAFF && obj->value[0]!=WEAPON_AXE
			&& obj->value[0]!=WEAPON_POLEARM && obj->value[0]!=WEAPON_EXOTIC)
			return HALF_MANA;
		else
		{
			if(IS_WEAPON_STAT(obj,WEAPON_SHARP)||IS_WEAPON_STAT(obj,WEAPON_VORPAL))
			{
				ch->println("That weapon is already quite sharp.");
				return HALF_MANA;
			}
			
			af.where    = WHERE_WEAPON;
			af.type     = sn;
			af.level    = level/2;
			af.duration = level;
			af.location = APPLY_NONE;
			af.modifier = 0;
			af.bitvector= WEAPON_SHARP;
			affect_to_obj(obj, &af);
			act("$p looks newly honed.",ch,obj,NULL,TO_ALL);
			return FULL_MANA;
		}
	}
	return FULL_MANA;
}

/**************************************************************************/
// Airius WWW
SPRESULT spell_runic_blade( int sn, int level, char_data *ch, void *vo, int )
{
	OBJ_DATA *obj;
	AFFECT_DATA af;

	obj=(OBJ_DATA *) vo;

	if(obj->item_type != ITEM_WEAPON)
	{
		ch->println("You can only target sharp weapons.");
		return NO_MANA;
	}
	else
	{
		if(    obj->value[0] == WEAPON_WHIP
			|| obj->value[0] == WEAPON_EXOTIC ) {
			act( "Your spell had no effect on $p.", ch, obj, NULL, TO_CHAR );
			return HALF_MANA;
		}
		else
		{
		  if(IS_WEAPON_STAT(obj,WEAPON_VORPAL) || IS_WEAPON_STAT(obj,WEAPON_SHARP))
		  {
			ch->println("That weapon is already magically sharp.");
			return HALF_MANA;
		  }

		  af.where    = WHERE_WEAPON;
		  af.type     = sn;
		  af.level    = level/2;
		  af.duration = level;
		  af.location = APPLY_NONE;
		  af.modifier = 0;
		  af.bitvector= WEAPON_VORPAL;
		  affect_to_obj(obj, &af);

		  act("$p gleams with magical strength.",ch,obj,NULL,TO_ALL);
		  return FULL_MANA;
		}
	}
	return FULL_MANA;
}

/**************************************************************************/
// Airius WWW
SPRESULT spell_true_sight( int sn, int level, char_data *ch, void *vo, int )
{
	char_data *victim = (char_data *) vo;
	AFFECT_DATA af;

	if( !is_affected( victim, sn ))
	{
		af.where		= WHERE_IMMUNE;
		af.type			= sn;
		af.level		= level;
		af.duration		= level/2;
		af.location 	= APPLY_NONE;
		af.modifier		= 0;
		af.bitvector	= IMM_ILLUSION;
		affect_to_char(victim, &af);
		victim->println("You see more clearly now.");

		if ( !IS_SET( victim->affected_by, AFF_DETECT_HIDDEN ))
		{
			af.where		= WHERE_AFFECTS;
			af.type			= sn;
			af.level		= level;
			af.duration		= level/2;
			af.location		= APPLY_NONE;
			af.modifier		= 0;
			af.bitvector	= AFF_DETECT_HIDDEN;
			affect_to_char( victim, &af );
			victim->println("Your awareness improves.");
		}
		else
			victim->println("You can already detect hidden.");

		if ( !IS_SET( victim->affected_by, AFF_DETECT_INVIS ))
		{
			af.where		= WHERE_AFFECTS;
			af.type			= sn;
			af.level		= level;
			af.duration		= level/2;
			af.location		= APPLY_NONE;
			af.modifier		= 0;
			af.bitvector	= AFF_DETECT_INVIS;
			affect_to_char( victim, &af );
			victim->println("Your eyes tingle.");
		}
		else
			victim->println("You can already see the invisible.");
	}
	else
	{
		if(victim!=ch)
			ch->println("They can already see clearly.");
		else
			ch->println("You can already see clearly.");
		return HALF_MANA;
	}

	ch->println("Ok.");

	return FULL_MANA;
}

/**************************************************************************/
// Airius WWW
SPRESULT spell_vampiric_touch( int sn, int level, char_data *ch, void *vo, int )
{
	char_data *victim = (char_data *) vo;
	int dam;
	int temp_hps;
	
	if(ch==victim)
	{
		ch->println("You cannot target yourself!");
		return NO_MANA;
	}

	if ( IS_ICIMMORTAL(victim)){
		act( "$n doesn't appear to be even slightly affected by your magic.", victim, NULL, NULL, TO_ROOM );
		return FULL_MANA;
	}
	
	dam=dice(level, 7)/abs(4+ch->alliance);
	
	if(saves_spell(level, victim, DAMTYPE(sn))){
		dam /= 2;
	}
	temp_hps=victim->hit;
    damage_spell(ch, victim, dam, sn, DAMTYPE(sn), true);
	if(victim->hit<-10) victim->hit=-10;
	
	//gives caster victims hps
	if(victim){	// at most you can get 40 hp per cast
		ch->hit+=UMIN(number_range(25,40), temp_hps-victim->hit);
	}
	return FULL_MANA;
}

/**************************************************************************/
// by Airius 
SPRESULT spell_wizard_eye( int , int level, char_data *ch, void *vo, int  )
{
	char_data	*victim = (char_data *) vo;
	char		buf[MSL];
	int			chance, random, i;
	bool		saved = false;
    char_data	*pMob;

	if (( victim = get_char_world( ch, target_name )) == NULL
	 ||   victim == ch
	 ||   victim->in_room == NULL
	 ||	  IS_OOC(victim)
	 ||   IS_SET(victim->in_room->room_flags, ROOM_PRIVATE)
	 ||   IS_SET(victim->in_room->room_flags, ROOM_ANTIMAGIC )
	 ||   IS_SET(victim->in_room->room_flags, ROOM_SOLITARY)
	 ||   IS_SET(victim->in_room->room_flags, ROOM_NOSCRY)
	 ||   IS_SET(victim->in_room->area->area_flags, AREA_NOSCRY)
	 ||   (!IS_NPC(victim) && victim->level >= LEVEL_IMMORTAL )) { // NOT trust
		ch->println("You failed.");
		return FULL_MANA;
	}

	if(	IS_SET(victim->imm_flags, IMM_SCRY)	 
		|| (IS_SET(victim->res_flags, RES_SCRY) && number_range(1,3)!=1) )
	{
		ch->println("You failed.");
		return FULL_MANA;
	}

	if ( is_affected( victim, gsn_detect_scry )) {
		chance = 50 - (( ch->level - victim->level ) * 3 );
		random = number_range( 1, 100);
		if ( chance >= random )
			victim->println("You feel someone watching you.");
		if (( chance /= 5 ) >= random )
			act( "$n is observing you.", ch, NULL, victim, TO_VICT );
	}

	if ( victim->mirage )
	{
		for ( i=0; i < victim->level; i += 20 )
		{
			if ( saves_spell( level, victim, DAM_ILLUSION)) saved = true;
		}
	}

	if (saved)
	{
		char	buf2[MSL];

		sprintf( buf, "%d look", victim->mirage );

		pMob = create_mobile( limbo_mob_index_data, 0 );

		sprintf(buf2, "%s is standing here.", victim->short_descr );
		replace_string(pMob->long_descr, buf2 );
		pMob->level = 1;
		pMob->max_hit = 1;
		pMob->hit = 1;
		pMob->timer = 1;
	    char_to_room( pMob, get_room_index( victim->mirage ));
		do_at( ch, buf );
		extract_char( pMob, true );
	}
	else
	{
		sprintf(buf, "'%s' look", target_name);
		do_at(ch, buf);
	}

	return FULL_MANA;
}

/**************************************************************************/
// By Bonhomme
SPRESULT spell_chaos_lace( int sn, int level, char_data *ch, void *vo, int )
{
    OBJ_DATA *obj = (OBJ_DATA *) vo;
    AFFECT_DATA *paf;
    AFFECT_DATA *paf_next;
    int result, fail;

    if ( !CAN_WEAR( obj, OBJWEAR_TORSO) &&
         !CAN_WEAR( obj, OBJWEAR_HEAD) &&
         !CAN_WEAR( obj, OBJWEAR_LEGS) &&
         !CAN_WEAR( obj, OBJWEAR_WIELD) )
      {
        ch->println("Chaos lace works only on torso armor, leggings, helmets, and weapons.");
        return NO_MANA;
      }

// Some objects are impossible to lace

	if ( IS_SET( obj->extra2_flags, OBJEXTRA2_NOCHAOS ))
	{
		act("$p weirds out completely!",ch,obj,NULL,TO_CHAR);
		act("$p weirds out completely!",ch,obj,NULL,TO_ROOM);
		extract_obj(obj);
		return FULL_MANA;
	}

    if (obj->wear_loc != -1) {
        ch->println("The item must be carried to be enchanted.");
        return NO_MANA;
    }
// Only one weird enchant per item 

    if (obj->chaos || IS_SET(obj->extra_flags,OBJEXTRA_CHAOS)) {
        ch->println("That item is already as wierd as it can get!");
        return HALF_MANA;
    }

// Items with attitudes don't like weirdness, and resist it 

    if ( (IS_OBJ_STAT(obj,OBJEXTRA_ANTI_EVIL)) ||
         (IS_OBJ_STAT(obj,OBJEXTRA_ANTI_GOOD)) ||
         (IS_OBJ_STAT(obj,OBJEXTRA_ANTI_NEUTRAL)) ) {
       fail = 50;
       fail += (level - obj->level);
       result = number_percent();
       if (result < fail) {
            act("$p weirds out completely!",ch,obj,NULL,TO_CHAR);
            act("$p weirds out completely!",ch,obj,NULL,TO_ROOM);
            extract_obj(obj);
            return FULL_MANA;
       }
       REMOVE_BIT(obj->extra_flags,OBJEXTRA_ANTI_GOOD);
       REMOVE_BIT(obj->extra_flags,OBJEXTRA_ANTI_EVIL);
       REMOVE_BIT(obj->extra_flags,OBJEXTRA_ANTI_NEUTRAL);
    }

// weirdness ruins all flags

    obj->no_affects=true;
    for (paf = obj->affected; paf != NULL; paf = paf_next)
    {
       paf_next = paf->next;
       free_affect(paf);
    }
    obj->affected = NULL;
    obj->extra_flags = 0;

    obj->chaos = true;

    act("$p suddenly looks rather weird.",ch,obj,NULL,TO_CHAR);
    act("$p suddenly looks rather weird.",ch,obj,NULL,TO_ROOM);
    SET_BIT(obj->extra_flags,OBJEXTRA_CHAOS);
	SET_BIT( obj->extra_flags, OBJEXTRA_MAGIC );
	obj->timer=UMIN(obj->timer, number_range(600, 15000));

	// Add affects, often bad, depending on what type item this is 
    paf = new_affect();
    paf->where       = WHERE_OBJEXTRA;
    paf->type        = sn;
    paf->level       = ch->level;
    paf->duration    = -1;
    paf->bitvector   = 0;

    if ( CAN_WEAR(obj, OBJWEAR_TORSO) ) {
       if (number_percent() <= 60) {
          paf->location = APPLY_HIT;
          paf->modifier = (((number_percent() % 6) - 3) * 10);
          paf->next     = obj->affected;
          obj->affected = paf;
       }
       else {
          paf->location = APPLY_ST;
          paf->modifier = ((number_percent() % 6) - 3) * 2 ;
          paf->next     = obj->affected;
          obj->affected = paf;
       }
    }
    if ( CAN_WEAR(obj, OBJWEAR_HEAD) ) {
       if (number_percent() <= 60) {
          paf->location = APPLY_MANA;
          paf->modifier = (((number_percent() % 6) - 3) * 10);
          paf->next     = obj->affected;
          obj->affected = paf;
       }
       else if (number_percent() <= 50) {
          paf->location = APPLY_IN;
          paf->modifier = ((number_percent() % 6) - 3) * 2;
          paf->next     = obj->affected;
          obj->affected = paf;
       }
       else {
          paf->location = APPLY_ME;
          paf->modifier = ((number_percent() % 6) - 3) * 2;
          paf->next     = obj->affected;
          obj->affected = paf;
       }
    }
    if ( CAN_WEAR(obj, OBJWEAR_LEGS) ) {
       if (number_percent() <= 60) {
          paf->location = APPLY_MOVE;
          paf->modifier = (((number_percent() % 6) - 3) * 10);
          paf->next     = obj->affected;
          obj->affected = paf;
       }
       else {
          paf->location = APPLY_CO;
          paf->modifier = ((number_percent() % 6) - 3) * 2;
          paf->next     = obj->affected;
          obj->affected = paf;
       }
    }

// weird weapons are weird, and have three different 10% chances;
// they can easily wind up with no affect, though still weird 

    if ( CAN_WEAR(obj, OBJWEAR_WIELD) ) {
       if (number_percent() <= 10) {
          paf->location = APPLY_HIT;
          paf->modifier = (((number_percent() % 6) - 3) * 10);
          paf->next     = obj->affected;
          obj->affected = paf;
       }
       else if (number_percent() <= 10) {
          paf->location = APPLY_ST;
          paf->modifier = ((number_percent() % 6) - 3) * 2;
          paf->next     = obj->affected;
          obj->affected = paf;
       }
       else if (number_percent() <= 10) {
          paf->location = APPLY_QU;
          paf->modifier = ((number_percent() % 6) - 3) * 2;
          paf->next     = obj->affected;
          obj->affected = paf;
       }
    }

    return FULL_MANA;
}

/**************************************************************************/
// By Bonhomme
SPRESULT spell_mithril_glaze( int sn, int level, char_data *ch, void *vo, int )
{
    OBJ_DATA *obj = (OBJ_DATA *) vo;
    OBJ_DATA *mit, *mit_next;
    AFFECT_DATA *paf;
	
	
    if(!CAN_WEAR( obj, OBJWEAR_ABOUT) ){
		ch->println( "You can only apply a mithril glaze to objects which are worn about the body." );
		return NO_MANA;
	}

	if (obj->wear_loc != -1){
		ch->println( "The item must be carried to be glazed." );
        return NO_MANA;
    }
	/*
	* Have to put (at least some) mithril items in manually until
	* someone gets around to fixing obj->pIndexData->material ;)
	*/
    for ( mit = ch->carrying; mit != NULL; mit = mit_next)
    {
        mit_next = mit->next_content;
        if	((mit->wear_loc == -1) &&
			( !strcmp( mit->pIndexData->material, "mithril" )))
		{
			break;
		}
    }
    if (mit == NULL)
	{
		ch->println( "You must have a mithril item to be consumed by this spell." );
        return NO_MANA;
    }
    if (ch->pcdata->tired > 16)
	{
		ch->println( "You are not well-rested enough to cast this spell just now. Have a nap first." );
		return NO_MANA;
    }
	
    act("$p effervesces into a mithril cloud...",ch,mit,NULL,TO_CHAR);
    act("$p effervesces into a mithril cloud...",ch,mit,NULL,TO_ROOM);
    extract_obj(mit);
    if ( number_percent() <= 40 ) {
        act("Which settles on $p and sets it aflame!",ch,obj,NULL,TO_CHAR);
        act("Which settles on $p and sets it aflame!",ch,obj,NULL,TO_ROOM);
        extract_obj(obj);
    }else{
        ch->mana = 0;
        ch->pcdata->tired += 60;
        ch->pcdata->condition[COND_THIRST] = 0;
        ch->pcdata->condition[COND_HUNGER] = 0;
        act("Which slowly condenses at your command upon $p.",ch,obj,NULL,TO_CHAR);
        act("Which slowly condenses upon $p.",ch,obj,NULL,TO_ROOM);
    }

	// success, get the template affects on to the object if their is no local affects
	affects_from_template_to_obj(obj); 

    for ( paf = obj->affected; paf; paf = paf->next ) {
        if ( !str_cmp( skill_table[paf->type].name, "mithril glaze" ) ) {
            paf->modifier+= dice(level / 3, 3);
            paf->level = UMIN(LEVEL_HERO, obj->level + 5); 
            obj->level = UMIN(LEVEL_HERO, obj->level + 5);
            if ( ch->mana == 0 ){
				return ALL_MANA;
			}else{
				return FULL_MANA;
			}
        }
    }
    paf = new_affect();
    paf->where       = WHERE_OBJEXTRA;
    paf->type        = sn;
    paf->level       = UMIN(LEVEL_HERO, obj->level + 5);
    paf->duration    = -1;
    paf->bitvector   = 0;
    paf->location    = APPLY_MANA;
    paf->modifier    = dice(level / 3, 3);
    paf->next        = obj->affected;
    obj->level       = UMIN(LEVEL_HERO, obj->level + 5);
    obj->affected    = paf;
	SET_BIT( obj->extra_flags, OBJEXTRA_MAGIC );
	if ( ch->mana == 0 ){
		return ALL_MANA;
	}else{
		return FULL_MANA;
	}
}

/**************************************************************************/
// By Bonhomme 
SPRESULT spell_extension( int sn, int level, char_data *ch, void *vo, int )
{
    OBJ_DATA *obj = (OBJ_DATA *) vo;
    AFFECT_DATA *paf, *afpaf;

    if (obj->wear_loc != -1)
	{
		ch->println("The item must be carried to be extended.");
        return NO_MANA;
    }
    for ( afpaf = paf = obj->affected; paf != NULL; paf = paf->next ) {
        if ( paf->duration < 0 )
                continue;
        if ( afpaf->duration < 0 ) {
                afpaf = paf;
                continue;
        }
        if ( afpaf->duration > paf->duration )
                afpaf = paf;
    }
    if ( ( afpaf != NULL ) && ( afpaf->duration > 0 ) ) {
        afpaf->duration += dice(((ch->pcdata->learned[sn] * level)/1000), 10);
        if ( afpaf->duration > 9999 )
            afpaf->duration = 9999;
        ch->printlnf( "The %s affect seems steadier.", skill_table[afpaf->type].name );
    }
    else
	{
		act("You couldn't find any effect on $p to extend.",ch,obj,NULL,TO_CHAR);
		return HALF_MANA;
	}
	return FULL_MANA;
}

/**************************************************************************/
SPRESULT spell_wrath( int sn, int level, char_data *ch, void *vo, int )
{
	AFFECT_DATA af;
	char_data *victim;

	victim=(char_data *) vo;

	if ( !IS_IMMORTAL(ch))
	{
		if(!IS_EVIL(ch))
		{
			ch->println("You must be evil to wield such magic.");
			return NO_MANA;
		}

		if(IS_EVIL(victim))
		{
			ch->println("You may not cast that against those who are evilly aligned.");
			return HALF_MANA;
		}
	}

	if(!saves_spell( level, victim, DAMTYPE(sn)) )
	{
	    af.where     = WHERE_AFFECTS;
	    af.type      = sn;
	    af.level     = level;
	    af.duration  = level/5;
	    af.location  = APPLY_HIT;
	    af.modifier  = (-level / 4) - 15;
	    af.bitvector = 0;
	    affect_join( victim, &af );
	    victim->println("You feel a force of great ill invade your soul.");
	    act("$n drops to $s knees in horror.",victim,NULL,NULL,TO_ROOM);
	    return FULL_MANA;
	}
	else
	{          
		act("$n shivers against a great force, but it passes.",victim,NULL,NULL,TO_ROOM);
		victim->println("You feel a great ill, but it passes.");
		return FULL_MANA;
	}
	return FULL_MANA;
}
/**************************************************************************/