Go Back   EQEmulator Home > EQEmulator Forums > Archives > Archive::Development > Archive::Development

Archive::Development Archive area for Development's posts that were moved here after an inactivity period of 90 days.

Reply
 
Thread Tools Display Modes
  #31  
Old 08-24-2004, 09:53 AM
Branks
Sarnak
 
Join Date: May 2004
Posts: 58
Default

scorp also has a ton of custom code i believe so it may not work the same with this, however if it does and he feels like sharing that would be great! if not no biggy i'll eventually get it done or someone else will.
Reply With Quote
  #32  
Old 08-24-2004, 02:45 PM
Branks
Sarnak
 
Join Date: May 2004
Posts: 58
Default

updated the code from my last post it seems while testing none of us ever decided to use canni, manastones etc or heal a pet so it was causing some problems we apparently didnt see, sorry ill try to be a lil more carefull testing next time.

anyway uh updated it so self target only spells no longer crit(manastone-canni-etc) and fixed the heal messages a lil but currently group heals dont display a message- also fixed something else i cant think of atm.
Reply With Quote
  #33  
Old 08-28-2004, 06:49 AM
Branks
Sarnak
 
Join Date: May 2004
Posts: 58
Default

dont use old manaburn or lifeburn code, remove them and use the new stuff posted below, this will allow the buff from manaburn to take hold and not allow manaburn groups however the buff stacking system doesnt seem to work with it currently- also this method allows pvp checks and you dont have to modify the spell value.

also updated the previous code for zone/spells.cpp to include a few more things and updated it since i learned a little more of the way spells are handled. case SE_CurrentHP that is.

added code to place a cap on pvp damage of 70% for a single spell like live used to be, if you want it 40% like live is currently youll have to do it yourself.

added cleric fury and fury of magic mastery, im not too sure of the exact values of these AAs so i just guessed that its a little behind the other versions.

also added quick damage, quick evacuation and spell casting deftness. i think theres another spell haste AA but cant think of it currently. will update whenever i do

also swarm pets are still killing exsisting pets and i have yet to find a way around this but im working on it.

zone/spells.cpp right below case SE_CurrentHP youll find
case: SE_CurrentHPOnce- replace exsisting with this-

Code:
			case SE_CurrentHPOnce:	// used in buffs usually, see Courage
			{
#ifdef SPELL_EFFECT_SPAM
				snprintf(effect_desc, _EDLEN, "Current Hitpoints Once: %+i", effect_value);
#endif
				//Dook- added manaburn, lifeburn
				if(spell_id==2751)
				{
					int r=MakeRandomInt(0,10);
					if(r>=9)
					{
						effect_value+=((caster->GetMana())*2.4)*-1;
						caster->SetMana(0);
						entity_list.MessageClose(caster,false,75,0,"%s delivers a critical blast! (%d)",caster->GetName(),((effect_value)*(-1)));
						caster->Message(0,"You deliver a critical blast! (%d)", ((effect_value)*(-1)));
					}
					else
					{
						effect_value+=((caster->GetMana())*1.8)*-1;
						caster->SetMana(0);
					}
				}
				if(spell_id==2755)
				{
					effect_value+=(caster->GetHP())*-1;
					caster->SetHP(caster->CalcMaxHP()/4);
				}
				ChangeHP(caster, effect_value, spell_id, buffslot);
				break;
			}
then in zone/attack.cpp do a search for "cut all pvp" and alter the exsisting code to be-

Code:
	if (amount < 0)
	{
		// cut all PVP spell damage to 2/3 -solar
		if(other && this->IsClient() && other->IsClient() && this != other)
			amount = (int) (amount * 0.67f);
		//Dook- Added 70% single blow max damage	--pvp dmg cap
		if(other && this->IsClient() && other->IsClient())
		{
			int pcmaxdmg=(((this->CalcMaxHP())*0.7)*(-1));
			if(amount<pcmaxdmg)
				amount=pcmaxdmg;
		}
		this->Damage(other, abs(amount), spell_id, 231, false, buffslot, iBuffTic);
		return true;
	}
then in zone/spells.capp again do a search for "we know our" and alter exsisting code to look like this-

Code:
	// we know our mana cost now
	casting_spell_mana = mana_cost;

	//Dook- Casting Haste
	if((IsClient)&&(spell_id != 13)&&(slot != 9)&&(slot != 10)&&(cast_time >= 4000))
	{
		int dur=spells[spell_id].buffduration;
		int dmg;
		for (int i = 0; i < EFFECT_COUNT; i++)
		{
			if (spells[spell_id].effectid[i] == SE_CurrentHP)
			{
				dmg = CalcSpellEffectValue(spell_id, i, GetCasterLevel());
				break;
			}   
		}
		Client *c=this->CastToClient();
		if(IsEffectInSpell(spell_id, SE_Succor))	//Dook- Quick Evac
		{
			uint8 qe=c->GetAA(42);
			if(qe==1){cast_time=(cast_time*0.90);}
			if(qe==2){cast_time=(cast_time*0.75);}
			if(qe==3){cast_time=(cast_time*0.50);}
		}
		if((IsEffectInSpell(spell_id,SE_CurrentHPOnce))||
			(IsEffectInSpell(spell_id,SE_CurrentHP))&&(dmg<=0))
		{
			uint8 qd=c->GetAA(44);
			if(qd==1){cast_time=(cast_time*0.98);}
			if(qd==2){cast_time=(cast_time*0.95);}
			if(qd==3){cast_time=(cast_time*0.90);}
		}
		if(IsBeneficialSpell(spell_id)&&(dur > 0))
		{
			uint8 deft=c->GetAA(27);
			if(deft==1){cast_time=(cast_time*0.95);}
			if(deft==2){cast_time=(cast_time*0.85);}
			if(deft==3){cast_time=(cast_time*0.75);}
		}
		else if(cast_time <= 0)
		{
			cast_time = 0;
		}
	}

	orgcasttime = cast_time;

	// cast time is 0, just finish it right now and be done with it
	if(cast_time == 0)
thats all for now.
Reply With Quote
  #34  
Old 09-02-2004, 03:32 AM
Branks
Sarnak
 
Join Date: May 2004
Posts: 58
Default

updated my little checklist of whats broken in my first post, you dont need to do anything with that i simply did it in hopes that someone will pick one of the none working one and start hacking at it with me.

also updated the flurry code from an earlier post, the part in client_process.cpp due to the message being displayed at incorrect times such as when the target was out of range and the skill triggered.

updated SE_CurrentHP in spells.cpp from an earlier post due to something allowing a warrior to get an exceptional heal....only happened onces and i dont really know why but i cleaned it up a little and it hasnt happened since.

updated the lifetap code in attack.cpp from an earlier post due to once again something without the skill got the benefit and a necro pet this time had an exceptional heal... anyone see something obviously wrong im missing?

so! ive spent a ton of time with swarm pets and and have yet to get them perfect, so im posting the progress ive made with them currently in hopes that someone will help finish up, the current minor issues are commented in the code for things like incorrect textures/models or details i dont know of them, the only magor issue at the moment is that after the swarm pets despawn if you had a pet already you no longer see the pet in the group window or in the pet information window, however all command line instructions work perfectly still, this one is driving me insane as ive tried just about everything i believe to be possible. also since this isnt exactly finished im not removing my comment or custom pets i threw in for fun.

wake the dead and doppelganger, these both require getting textures from pop+ which ive been unable to do and havent spent much time looking into yet. so doppelganger only trys to reproduce the primary item slot from the caster and i just gave it a kedge robe for the time being.

wake the dead, again with the textures thing, it works out nicely for NPC corpses but its far from perfect with clients.

fading memories and escape, the invisibility effect on these isnt working correctly since i dont yet understand how to make a client use their hide skill by code, and when i just flagged the player invisable the effect doesnt fade thus every mob in the zone cons indifferent after the skill had been used, as a temporary solution i added the spell improved invis to the skills and plan on coming back to this later, also when i know for sure if fading memories uses 900 mana or only checks that the player has 900 mana.

rampage...well it works perfectly, but i added an area message to it just as i did with flurry, just cause well i think its more fun that way~

ae taunt... see rampage

the god swarm pets i havent been able to get much information on, i know the shaman swarm pets from god proc a 640 poison based DD however i havent been able to figure out what spell this is.

swarm of decay, again with the freakin texture thing, their bows are not the correct model, i also had to guess as to their attack animation speed since it seems no one has seen it enough to remember.

anyway i think thats the magority of it and instead of posting the code per skill im just lumping it all together here, also keep in mind this is a work in progress so dont expect perfection with this just yet.

zone\MobAI.cpp search for "Mob::AI_Process" then scroll down a few lines till you see the bit saying "if (CombatRange(target))" then ABOVE THAT LINE add.

Code:
		if((GetBodyType()==63)&&(GetClass()==4)
			&&(attack_timer->Check())&&(IsAttackAllowed(target)))
		{	//Dook- Swarm Pets -Swarm of Decay
			if(Dist(*target)<=100)
			{
				FaceTarget(target);
				DoAnim(20, 9);
				int dmg=MakeRandomInt(50,200);
				target->Damage(this, dmg, 0xffff, 0x07, true);
			}
			return;
		}

		if((GetBodyType()==63)&&(GetRace()==89)&&(IsAttackAllowed(target))
			&&(attack_timer->Check())&&(Dist(*target)<=100))
		{
			//Dook- Servant of Ro castin Bolt of Lava
			CastSpell(3005,target->GetID(),9,3000,0,0,0);
			return;
		}

		if((GetBodyType()==63)&&(GetRace()==127)&&(IsAttackAllowed(target))
			&&(attack_timer->Check())&&(CombatRange(target))&&(GetClass()==90)
			&&(MakeRandomInt(0,10)>=9))
		{
			CastSpell(1638,target->GetID(),9,0,0,0,0);
		}

		if((GetBodyType()==63)&&(GetRace()==120)&&(IsAttackAllowed(target))
			&&(attack_timer->Check())&&(CombatRange(target))&&(GetClass()==91)
			&&(MakeRandomInt(0,10)>=9))
		{
			//Dook- ToDo Add GoD shaman swarm puppy proc here
		}
now on to zone\entity.cpp do a search for "EntityList::GetFreeID" then ABOVE THAT LINE add the following.

Code:
Mob* EntityList::GetMobInZoneByRange(Mob *client, int type, int range)	//Dook- AA skills
{
	if(type==1)		//Dook- find a corpse within range
	{
		LinkedListIterator<Corpse*> iterator(corpse_list);
		iterator.Reset();
		Mob* corp;
		while(iterator.MoreElements())
		{
			corp = iterator.GetData();
			if(corp->Dist(*client)<=range)
			{
				return iterator.GetData();
			}
			iterator.Advance();
		}
		return 0;
	}
	if(type==2)		//Dook- todo add mob by range here
	{
		return 0;
	}
}

void EntityList::WipeHateAll(Mob *client)		//Dook- FM, Escape and such
{
	LinkedListIterator<Mob*> iterator(mob_list);
	Mob *agroed;
	
	for(iterator.Reset(); iterator.MoreElements(); iterator.Advance())
	{
		agroed = iterator.GetData();
		if(agroed->IsNPC())
		{
			agroed->RemoveFromHateList(client);
		}
	}	
}

void EntityList::AETaunt(Mob *client)	//Dook- AE Taunt of course..
{		//Dook- no horse no players
	LinkedListIterator<Mob*> iterator(mob_list);
	Mob *taunte;	
	for(iterator.Reset(); iterator.MoreElements(); iterator.Advance())
	{
		taunte = iterator.GetData();
		if((taunte->Dist(*client) <= 30)&&(client->IsAttackAllowed(taunte))&&(taunte != client)
			&&(taunte->IsNPC())&&(taunte->GetRace() != 216))
		{
			Mob* hated=taunte->GetHateTop();
			int hate=0;
			if(hated)
			{
				hate=taunte->GetHateAmount(hated);
				taunte->SetHate(client,(hate+100));
			}
			else
			{
				taunte->AddToHateList(client,100);
			}
		}
	}	
}

void EntityList::AEAttack(Mob *attacker, float dist)	//Dook- Rampage and stuff
{		//Dook- Will need tweaking, currently no pets or players or horses
	LinkedListIterator<Mob*> iterator(mob_list);
	Mob *curmob;
	
	for(iterator.Reset(); iterator.MoreElements(); iterator.Advance())
	{
		curmob = iterator.GetData();
		if((curmob->Dist(*attacker) <= dist)&&(attacker->IsAttackAllowed(curmob))&&(curmob != attacker)
			&&(curmob->IsNPC())&&(curmob->GetRace() != 216))
			attacker->Attack(curmob,13);
	}	
}
then on to zone\entity.h do a search for "GetMobByNpcTypeID" then above or below it, doesnt really matter add the following.

Code:
	Mob*	GetMobInZoneByRange(Mob* client, int type, int range);//Dook- For AA skills etc
	void	WipeHateAll(Mob* client);					//Dook- Escape and Fading Memories etc
	void	AETaunt(Mob* client);						//Dook- AE Taunt of course
	void	AEAttack(Mob *attacker, float dist);		//Dook- Rampage and such
then on to zone\mob.cpp and do a search for
"attack_timer_dw = new Timer(2000);" then below this line add the following.

Code:
	swarm_timer = new Timer(0);		//Dook- swarm pets
	swarm_timer->Disable();
then in mob.cpp still search for "safe_delete(spellend_timer);" and on the line below it add.
Code:
	safe_delete(swarm_timer);			//Dook- swarm pets
then still in moc.cpp do a search for "Mob* Mob::GetOwnerOrSelf" and replace exsisting with this.
Code:
Mob* Mob::GetOwnerOrSelf() {
	if (!GetOwnerID())
		return this;
	Mob* owner = entity_list.GetMob(this->GetOwnerID());
	if (!owner) {
		SetOwnerID(0);
	}
	else if (owner->GetPetID() == this->GetID()) {
		return owner;
	}
    else if (owner->GetFamiliarID() == this->GetID()) {
        return owner;
    }
	else if (this->GetBodyType() == 63) {			//Dook- swarm pets
		return owner;
	}
	else {
		SetOwnerID(0);
	}
	return this;
}
still in mob.cpp right below the code we just did you should see "Mob* Mob::GetOwner" replace exsisting with this.

Code:
Mob* Mob::GetOwner() {
	Mob* owner = entity_list.GetMob(this->GetOwnerID());
	if (owner && owner->GetPetID() == this->GetID()) {

		return owner;
	}
    if (owner && owner->GetFamiliarID() == this->GetID())
    {
        return owner;
    }
	if(this->GetBodyType() == 63)	//Dook- Swarm Pets
	{
		return owner;
	}
	this->SetOwnerID(0);
	return 0;
}
now move over to zone\mob.h and search for "spellend_timer"
and right below this add.
Code:
	Timer*	swarm_timer;     //Dook- swarm pets
now move to zone\npc.cpp and search for "if (p_depop)" and replace exsisting with.
Code:
    if (p_depop)
    {
        Mob* owner = entity_list.GetMob(this->ownerid);
        if((owner != 0)&&(this->GetBodyType() != 63))	//Dook- Swarm Pets
        {
            owner->SetPetID(0);
			this->ownerid = 0;
            this->petid = 0;
        }
		if(this->GetBodyType() ==63)			//Dook- Swarm Pets
		{
			this->ownerid = 0;
			this->petid = 0;
		}
        return false;
    }
then move to zone\spdat.h and search for "SE_StackingCommand_Block" and alter that area to look like this.
Code:
#define SE_StackingCommand_Block	148
#define SE_StackingCommand_Overwrite 149
#define SE_DeathSave				150
#define SE_TemporaryPets			152	//Dook- Swarm Pets
#define SE_BalanceHP				153	// Divine Arbitration
#define SE_DispelDetrimental		154
#define SE_IllusionCopy				156	// Deception
#define SE_SpellDamageShield		157	// Petrad's Protection
#define SE_Reflect					158
#define SE_AllStats					159	// Aura of Destruction
#define SE_FadingMemories			194	//Dook- ....
#define SE_Blank					254
#define SE_WakeTheDead				299	//Dook- ....
#define SE_Doppelganger				300	//Dook- ...
then on to zone\spells.cpp and search for "Mob::SpellProcess" and add the bit at the bottom so that it looks like this.
Code:
void Mob::SpellProcess()
{
	// check the rapid recast prevention timer
	if(delaytimer == true && spellend_timer->Check())
	{
		spellend_timer->Disable();
		delaytimer = false;
		return;
	}

	// a timed spell is finished casting
	if (casting_spell_id != 0 && spellend_timer->Check())
	{
		spellend_timer->Disable();
		delaytimer = false;
		CastedSpellFinished(casting_spell_id, casting_spell_targetid, casting_spell_slot, casting_spell_mana, casting_spell_inventory_slot);
	}

	//Dook- swarm pets
	if((swarm_timer->Check()) && (GetBodyType() == 63))
	{
		Depop();
		swarm_timer->Disable();
	}
}
then still in spells.cpp search for "The basic types of spells" and move 3 or so lines up and alter it so it looks like this.
Code:
	if(IsEffectInSpell(spell_id, SE_TemporaryPets))			//Dook- swarm pet
	{
		target_id = this->GetID();
	}


/*
	solar: The basic types of spells:
making a second post now as the next bit is huge and i think im nearing the end of this post.
Reply With Quote
  #35  
Old 09-02-2004, 05:58 AM
Branks
Sarnak
 
Join Date: May 2004
Posts: 58
Default

lovely time for the forums to crash.
so anyway still in spells.cpp now do a search for
"case SE_StackingCommand_Block:" and on the line below it and all this.

Code:
			case SE_TemporaryPets:			//Dook- swarms and wards
				{
					Mob* c=CastToClient();
					Mob* targ=c->GetTarget();
					if(!targ)
					{
						targ=c;
					}
					int tim=spell.unknown[12];
					int time=tim*1000;
					NPCType* npc_type = new NPCType;
					memset(npc_type, 0, sizeof(NPCType));
					strcpy(npc_type->name, CastToClient()->GetName());
					strcat(npc_type->name, "'s_pet");
					npc_type->level = 59;
					npc_type->race = 127;
					npc_type->class_ = 1;
					npc_type->runspeed = 1.25f; 
					npc_type->min_dmg = 1;
					npc_type->max_dmg = 50;
					npc_type->walkspeed = 0.7f;
					npc_type->bodytype = 63;	//Dook- claimed 63 for swarm pets
					npc_type->max_hp = 100;
					npc_type->cur_hp = npc_type->max_hp;
					npc_type->gender = 2;
					switch(spell_id) {
					case 2272:
						{//listed as wrath of xuzl but i dont
						}//think this is in game
						break;
					case 3265:		//3265-67 servant of ro
						{
							npc_type->level = 61;
							npc_type->race = 89;
							npc_type->texture = 2;
							npc_type->max_dmg = 150;
							npc_type->max_hp = 100;
							npc_type->walkspeed = 0;
							npc_type->runspeed = 0; 
							npc_type->cur_hp = npc_type->max_hp;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
						}
						break;
					case 3266:
						{
							npc_type->level = 61;
							npc_type->race = 89;
							npc_type->texture = 2;
							npc_type->max_dmg = 150;
							npc_type->max_hp = 100;
							npc_type->walkspeed = 0;
							npc_type->runspeed = 0; 
							npc_type->cur_hp = npc_type->max_hp;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
						}
						break;
					case 3267:
						{
							npc_type->level = 61;
							npc_type->race = 89;
							npc_type->texture = 2;
							npc_type->max_dmg = 150;
							npc_type->max_hp = 100;
							npc_type->walkspeed = 0;
							npc_type->runspeed = 0; 
							npc_type->cur_hp = npc_type->max_hp;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
						}
						break;
					case 3283:		//3283-85 spirit call
						{
							npc_type->race = 120;
							npc_type->texture = 4;
							npc_type->max_hp = 2050;
							npc_type->cur_hp = npc_type->max_hp;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							npcc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							entity_list.AddNPC(npcc);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
							npcc->AddToHateList(targ,1000,1000);
							npcc->swarm_timer->Start(time);
						}
						break;
					case 3284:
						{
							npc_type->race = 120;
							npc_type->texture = 4;
							npc_type->max_hp = 2050;
							npc_type->cur_hp = npc_type->max_hp;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							NPC* npcd = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							npcc->SetOwnerID(c->GetID());
							npcd->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							entity_list.AddNPC(npcc);
							entity_list.AddNPC(npcd);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
							npcc->AddToHateList(targ,1000,1000);
							npcc->swarm_timer->Start(time);
							npcd->AddToHateList(targ,1000,1000);
							npcd->swarm_timer->Start(time);
						}
						break;
					case 3285:
						{
							npc_type->race = 120;
							npc_type->texture = 4;
							npc_type->max_hp = 2050;
							npc_type->cur_hp = npc_type->max_hp;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							NPC* npcd = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							NPC* npce = new NPC(npc_type, 0,
								c->GetX()+10, c->GetY()+10,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							npcc->SetOwnerID(c->GetID());
							npcd->SetOwnerID(c->GetID());
							npce->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							entity_list.AddNPC(npcc);
							entity_list.AddNPC(npcd);
							entity_list.AddNPC(npce);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
							npcc->AddToHateList(targ,1000,1000);
							npcc->swarm_timer->Start(time);
							npcd->AddToHateList(targ,1000,1000);
							npcd->swarm_timer->Start(time);
							npce->AddToHateList(targ,1000,1000);
							npce->swarm_timer->Start(time);
						}
						break;
					case 3286:		//3286-88 host of the elements
						{
							npc_type->race = 75;
							npc_type->texture = 0;
							npc_type->size = 3;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							NPC* npcd = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							NPC* npce = new NPC(npc_type, 0,
								c->GetX()+10, c->GetY()+10,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							npcc->SetOwnerID(c->GetID());
							npcd->SetOwnerID(c->GetID());
							npce->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							entity_list.AddNPC(npcc);
							entity_list.AddNPC(npcd);
							entity_list.AddNPC(npce);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
							npcc->AddToHateList(targ,1000,1000);
							npcc->swarm_timer->Start(time);
							npcd->AddToHateList(targ,1000,1000);
							npcd->swarm_timer->Start(time);
							npce->AddToHateList(targ,1000,1000);
							npce->swarm_timer->Start(time);
						}
						break;
					case 3287:
						{
							npc_type->race = 75;
							npc_type->texture = 0;
							npc_type->size = 3;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							NPC* npcd = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							NPC* npce = new NPC(npc_type, 0,
								c->GetX()+10, c->GetY()+10,
								c->GetZ(), c->GetHeading());
							NPC* npcf = new NPC(npc_type, 0,
								c->GetX()-10, c->GetY()+10,
								c->GetZ(), c->GetHeading());
							NPC* npcg = new NPC(npc_type, 0,
								c->GetX()+10, c->GetY()-10,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							npcc->SetOwnerID(c->GetID());
							npcd->SetOwnerID(c->GetID());
							npce->SetOwnerID(c->GetID());
							npcf->SetOwnerID(c->GetID());
							npcg->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							entity_list.AddNPC(npcc);
							entity_list.AddNPC(npcd);
							entity_list.AddNPC(npce);
							entity_list.AddNPC(npcf);
							entity_list.AddNPC(npcg);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
							npcc->AddToHateList(targ,1000,1000);
							npcc->swarm_timer->Start(time);
							npcd->AddToHateList(targ,1000,1000);
							npcd->swarm_timer->Start(time);
							npce->AddToHateList(targ,1000,1000);
							npce->swarm_timer->Start(time);
							npcf->AddToHateList(targ,1000,1000);
							npcf->swarm_timer->Start(time);
							npcg->AddToHateList(targ,1000,1000);
							npcg->swarm_timer->Start(time);
						}
						break;
					case 3288:
						{
							npc_type->race = 75;
							npc_type->texture = 0;
							npc_type->size = 3;
							if(CastToClient()->GetGM())
							{
								npc_type->race = 95;
								npc_type->size = 3;
								npc_type->gender = 2;
								npc_type->texture = 0;
								npc_type->max_dmg = 200;
							}
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							NPC* npcd = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							NPC* npce = new NPC(npc_type, 0,
								c->GetX()+10, c->GetY()+10,
								c->GetZ(), c->GetHeading());
							NPC* npcf = new NPC(npc_type, 0,
								c->GetX()-10, c->GetY()+10,
								c->GetZ(), c->GetHeading());
							NPC* npcg = new NPC(npc_type, 0,
								c->GetX()+10, c->GetY()-10,
								c->GetZ(), c->GetHeading());
							NPC* npch = new NPC(npc_type, 0,
								c->GetX()-10, c->GetY()-10,
								c->GetZ(), c->GetHeading());
							NPC* npci = new NPC(npc_type, 0,
								c->GetX()+8, c->GetY()+8,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							npcc->SetOwnerID(c->GetID());
							npcd->SetOwnerID(c->GetID());
							npce->SetOwnerID(c->GetID());
							npcf->SetOwnerID(c->GetID());
							npcg->SetOwnerID(c->GetID());
							npch->SetOwnerID(c->GetID());
							npci->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							entity_list.AddNPC(npcc);
							entity_list.AddNPC(npcd);
							entity_list.AddNPC(npce);
							entity_list.AddNPC(npcf);
							entity_list.AddNPC(npcg);
							entity_list.AddNPC(npch);
							entity_list.AddNPC(npci);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
							npcc->AddToHateList(targ,1000,1000);
							npcc->swarm_timer->Start(time);
							npcd->AddToHateList(targ,1000,1000);
							npcd->swarm_timer->Start(time);
							npce->AddToHateList(targ,1000,1000);
							npce->swarm_timer->Start(time);
							npcf->AddToHateList(targ,1000,1000);
							npcf->swarm_timer->Start(time);
							npcg->AddToHateList(targ,1000,1000);
							npcg->swarm_timer->Start(time);
							npch->AddToHateList(targ,1000,1000);
							npch->swarm_timer->Start(time);
							npci->AddToHateList(targ,1000,1000);
							npci->swarm_timer->Start(time);
						}
						break;
					case 3292:		//3292-94 call of xuzl
						{
							npc_type->equipment[7] = 62;
							npc_type->gender = 0;
							npc_type->texture = 4;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
						}
						break;
					case 3293:
						{
							npc_type->equipment[7] = 62;
							npc_type->gender = 0;
							npc_type->texture = 4;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							npcc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							entity_list.AddNPC(npcc);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
							npcc->AddToHateList(targ,1000,1000);
							npcc->swarm_timer->Start(time);
						}
						break;
					case 3294:
						{
							npc_type->equipment[7] = 62;
							npc_type->gender = 0;
							npc_type->texture = 4;
							if(CastToClient()->GetGM())
							{
								npc_type->race = 66;
								npc_type->gender = 2;
								npc_type->texture = 1;
								npc_type->max_dmg = 200;
								npc_type->size = 5;
							}
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							NPC* npcd = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							npcc->SetOwnerID(c->GetID());
							npcd->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							entity_list.AddNPC(npcc);
							entity_list.AddNPC(npcd);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
							npcc->AddToHateList(targ,1000,1000);
							npcc->swarm_timer->Start(time);
							npcd->AddToHateList(targ,1000,1000);
							npcd->swarm_timer->Start(time);
						}
						break;
					case 3495:
						{//another that i dont think is in game
						}
						break;
					case 3633:		//call of the mistwalker
						{//some say invis man with epic, most say wolf /shrug
							npc_type->race = 120;
							npc_type->texture = 4;
							npc_type->max_dmg = 94;
							npc_type->gender = 2;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 3634:		//call of the dark knight
						{
							npc_type->equipment[7] = 145;
							npc_type->max_dmg = 94;
							npc_type->gender = 0;
							//custom for Mog
							if(CastToClient()->GetGM())	//for Mog
							{
								strcpy(npc_type->name, CastToClient()->GetName());
								strcat(npc_type->name, "'s_Minion");
								npc_type->race = 367;
								npc_type->gender = 2;
								npc_type->equipment[7] = 145;
								npc_type->equipment[8] = 145;
								npc_type->texture = 4;
								npc_type->max_dmg = 1500;
								npc_type->min_dmg = 500;
							}
							//custom for Mog
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 3635:			//call of faith
						{	//dunno
							npc_type->equipment[7] = 62;
							npc_type->gender = 0;
							npc_type->max_dmg = 94;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 3636:			//call of battle
						{	//invis war epic
							npc_type->equipment[7] = 141;
							npc_type->equipment[8] = 142;
							npc_type->max_dmg = 94;
							npc_type->gender = 0;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 3637:			//call of the beast
						{	//wtf are the bst epic textures =/
							npc_type->equipment[7] = 431;
							npc_type->equipment[8] = 431;
							npc_type->max_dmg = 94;
							npc_type->gender = 0;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 3638:			//call of wu
						{	//cant be right, can barely see it
							npc_type->equipment[7] = 159;
							npc_type->equipment[8] = 159;
							npc_type->max_dmg = 94;
							npc_type->gender = 0;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 3639:			//call of rizlona
						{
							npc_type->equipment[7] = 148;
							npc_type->gender = 0;
							npc_type->max_dmg = 94;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 3640:			//call of the assassin
						{	//unsure on this one also
							npc_type->equipment[7] = 140;
							npc_type->gender = 0;
							npc_type->max_dmg = 94;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 3649:			//call of time  
						{	//again no textures
							//needs correct weapon
							//someone said sol ro spear?
							npc_type->min_dmg = 100;
							npc_type->max_dmg = 415;
							npc_type->equipment[7] = 431;
							npc_type->equipment[8] = 431;
							npc_type->gender = 0;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 3807:			//trickster's calling
						{//not a clue what this is
							npc_type->max_dmg = 90;
							npc_type->gender = 0;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 3869:			//ancient call
						{	//no clue
							//needs correct weapon
							npc_type->min_dmg = 100;
							npc_type->max_dmg = 415;
							npc_type->equipment[7] = 431;
							npc_type->equipment[8] = 431;
							npc_type->gender = 0;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 3870:			//call of the tempest
						{	//need to make this despawn when disengaged
							//and limit one per fight
							//without a timer
							npc_type->min_dmg = 100;
							npc_type->max_dmg = 330;
							npc_type->race = 75;
							npc_type->texture = 3;
							npc_type->gender = 2;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 4460:			//anguish of torment
						{//again clueless
							npc_type->max_dmg = 90;
							npc_type->gender = 0;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 4490:			//stone animation
						{//......
							npc_type->max_dmg = 90;
							npc_type->gender = 0;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 4564:					//4564-66 swarm of fear/swarm of decay
						{//cant find the stonewood compound bow texture
							npc_type->equipment[7] = 4;
							npc_type->gender = 2;
							npc_type->race = 367;
							npc_type->texture = 1;
							npc_type->walkspeed = 0;
							npc_type->runspeed = 0;
							npc_type->class_ = 4;
							npc_type->max_hp = 1025;
							npc_type->cur_hp = npc_type->max_hp;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
						}
						break;
					case 4565:
						{
							npc_type->equipment[7] = 4;
							npc_type->gender = 2;
							npc_type->race = 367;
							npc_type->texture = 1;
							npc_type->walkspeed = 0;
							npc_type->runspeed = 0;
							npc_type->class_ = 4;
							npc_type->max_hp = 1025;
							npc_type->cur_hp = npc_type->max_hp;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
						}
						break;
					case 4566:
						{
							npc_type->equipment[7] = 4;
							npc_type->gender = 2;
							npc_type->race = 367;
							npc_type->texture = 1;
							npc_type->walkspeed = 0;
							npc_type->runspeed = 0;
							npc_type->class_ = 4;
							npc_type->max_hp = 1025;
							npc_type->cur_hp = npc_type->max_hp;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							npcc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							entity_list.AddNPC(npcc);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
							npcc->AddToHateList(targ,1000,1000);
							npcc->swarm_timer->Start(time);
						}
						break;
					case 4568:				//call of discord
						{//no idea what this is
							npc_type->max_dmg = 90;
							npc_type->gender = 0;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 4569:			//call of chaos
						{//la la la
							npc_type->max_dmg = 90;
							npc_type->gender = 0;
							NPC* npc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npc);
							npc->AddToHateList(targ,1000,1000);
							npc->swarm_timer->Start(time);
						}
						break;
					case 4790:	//4790-4794=Exquisite Benediction
						break;
					case 4791://heard they cast aura of restoration
						break;
					case 4792:
						break;
					case 4793:
						break;
					case 4794:
						break;
					case 4796:	//4796-4800=Nature's Boon
						break;
					case 4797:
						break;
					case 4798:
						break;
					case 4799:
						break;
					case 4800:
						break;
					case 4826:		//Spirit Call 4
						{//should have a 640 poison DD proc
							npc_type->race = 120;
							npc_type->gender = 2;
							npc_type->texture = 1;
							npc_type->max_hp = 2050;
							npc_type->min_dmg = 80;
							npc_type->max_dmg = 140;
							npc_type->class_ = 91;
							sprintf(npc_type->npc_attacks, "E");
							npc_type->cur_hp = npc_type->max_hp;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
						}
						break;
					case 4827:		//Sprit Call 5
						{//should have a 640 poison DD proc
							npc_type->race = 120;
							npc_type->gender = 2;
							npc_type->texture = 1;
							npc_type->max_hp = 2050;
							npc_type->min_dmg = 80;
							npc_type->max_dmg = 140;
							npc_type->class_ = 91;
							sprintf(npc_type->npc_attacks, "E");
							npc_type->cur_hp = npc_type->max_hp;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							npcc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							entity_list.AddNPC(npcc);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
							npcc->AddToHateList(targ,1000,1000);
							npcc->swarm_timer->Start(time);
						}
						break;
					case 4828://Call of the Ancient 4828-4832
						break;
					case 4829:
						break;
					case 4830:
						break;
					case 4831:
						break;
					case 4832:
						break;
					case 4836://4836-4840 = Flaming ward of Ro
						break;
					case 4837:
						break;
					case 4838:
						break;
					case 4839:
						break;
					case 4840:
						break;
					case 5110:		//5110-5111 wrth of xuzl
						{	//Useing class 90 for their proc
							npc_type->equipment[7] = 62;
							npc_type->gender = 0;
							npc_type->texture = 4;
							npc_type->min_dmg = 80;
							npc_type->max_dmg = 140;
							npc_type->class_ = 90;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
						}
						break;
					case 5111:
						{
							npc_type->equipment[7] = 62;
							npc_type->gender = 0;
							npc_type->texture = 4;
							npc_type->min_dmg = 80;
							npc_type->max_dmg = 140;
							npc_type->class_ = 90;
							NPC* npca = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcb = new NPC(npc_type, 0,
								c->GetX()-5, c->GetY()+5,
								c->GetZ(), c->GetHeading());
							NPC* npcc = new NPC(npc_type, 0,
								c->GetX()+5, c->GetY()-5,
								c->GetZ(), c->GetHeading());
							safe_delete(npc_type);
							npca->SetOwnerID(c->GetID());
							npcb->SetOwnerID(c->GetID());
							npcc->SetOwnerID(c->GetID());
							entity_list.AddNPC(npca);
							entity_list.AddNPC(npcb);
							entity_list.AddNPC(npcc);
							npca->AddToHateList(targ,1000,1000);
							npca->swarm_timer->Start(time);
							npcb->AddToHateList(targ,1000,1000);
							npcb->swarm_timer->Start(time);
							npcc->AddToHateList(targ,1000,1000);
							npcc->swarm_timer->Start(time);
						}
						break;
					case 5156://Call of Nexona..not a clue
						break;
					default:
						{
							c->Message(0,"Unknown pet!");
							cout<<"Unknown Temporary Pet in Spell "<<spell_id<<endl;
							safe_delete(npc_type);
						}
					}
					targ->AddToHateList(c, 1, 0);
				}
				break;

			case SE_Doppelganger:
				{
					NPCType* npc_type = new NPCType;
					memset(npc_type, 0, sizeof(NPCType));
					strcpy(npc_type->name, caster->GetName());
					strcat(npc_type->name, "'s_image");
					npc_type->level = (caster->GetLevel());
					npc_type->race = (caster->GetRace());
					npc_type->class_ = (caster->GetClass());
					npc_type->luclinface = caster->CastToClient()->GetFace();
					npc_type->walkspeed = 0.7f;
					npc_type->size = (caster->GetSize());
					npc_type->runspeed = 1.25f;
					npc_type->bodytype = 63;
					npc_type->texture = 14;
					npc_type->gender = (caster->GetGender());
					npc_type->AC = (caster->GetAC());
					npc_type->equipment[7] = caster->GetEquipmentMaterial(7);//primary
					if(spell_id==4552)
					{
						npc_type->max_hp = (caster->CalcMaxHP())/2;
						npc_type->min_dmg = 1;
						npc_type->max_dmg = 1;
					}
					if(spell_id==4553)
					{
						npc_type->min_dmg = 1;
						npc_type->max_dmg = 150;
						npc_type->max_hp = (caster->CalcMaxHP());
					}
					if(spell_id==4554)
					{
						npc_type->min_dmg = 1;
						npc_type->max_dmg = 150;
						npc_type->max_hp = ((caster->CalcMaxHP())*1.3);
						npc_type->npc_spells_id = 5;
					}
					npc_type->cur_hp = npc_type->max_hp;
					NPC* npc = new NPC(npc_type, 0,
						caster->GetX(), caster->GetY(),
						caster->GetZ(), caster->GetHeading());
					npc->swarm_timer->Start(600000);
					safe_delete(npc_type);
					entity_list.AddNPC(npc);
					Mob* targ=caster->GetTarget();
					if((targ)&&(targ != caster))
					{
						int hate=hate_list.GetEntHate(caster);
						targ->AddToHateList(npc,hate+100);
						npc->AddToHateList(targ,1);
					}
				}
				break;

			case SE_FadingMemories:		//Dook- escape etc
				{
					entity_list.WipeHateAll(this);
					SpellOnTarget(1406,this);
				}
				break;

			case SE_WakeTheDead:		//Dook- Wake the Dead
				{
					Mob* corpse=entity_list.GetMobInZoneByRange(caster, 1, 20);
					Mob* c=caster;
					Mob* targ=caster->GetTarget();
					if(!targ)
					{
						targ=caster;
					}
					if(!corpse)
					{
						caster->Message(0,"Could not find the dead!");
						break;
					}
					else
					{
						NPCType* npc_type = new NPCType;
						memset(npc_type, 0, sizeof(NPCType));
						strcpy(npc_type->name, c->GetName());
						strcat(npc_type->name, "'s_pet");
						npc_type->level = corpse->GetLevel();
						npc_type->race = corpse->GetRace();
						npc_type->class_ = corpse->GetClass();
						npc_type->runspeed = 1.25f; 
						npc_type->min_dmg = 50;
						npc_type->max_dmg = 300;
						npc_type->walkspeed = 0.7f;
						npc_type->bodytype = 63;//Dook- useing swarm timer for this
						npc_type->max_hp = 5000;
						npc_type->cur_hp = npc_type->max_hp;
						npc_type->gender = corpse->GetGender();
						npc_type->texture = corpse->GetTexture();
						npc_type->helmtexture = corpse->GetHelmTexture();
						npc_type->equipment[7] = corpse->GetEquipmentMaterial(7);
						npc_type->equipment[8] = corpse->GetEquipmentMaterial(8);
						NPC* npc = new NPC(npc_type, 0,
							c->GetX()+5, c->GetY()+5,
							c->GetZ(), c->GetHeading());
						safe_delete(npc_type);
						npc->SetOwnerID(c->GetID());
						entity_list.AddNPC(npc);
						npc->AddToHateList(targ,1000,1000);
						if(spell_id==3268)
							npc->swarm_timer->Start(60000);
						if(spell_id==3269)
							npc->swarm_timer->Start(75000);
						if(spell_id==3270)
							npc->swarm_timer->Start(90000);
					}
				}
				break;
well i think thats all of it but not too sure, if i find ive left anything out ill update. anyway i could really use some help finishing this up so if you see anything wrong with it please post, also i do understand theres other ways that might have been nicer or better than this but this is the current state im at, help is always appreciated and if you simply want to fill me in on some of the details im missing can do so here or on my server which ive left up basicly 24/7.
Reply With Quote
  #36  
Old 09-02-2004, 10:56 AM
monalin crusader
Hill Giant
 
Join Date: May 2004
Posts: 238
Default

I havent checked your post in awhile, and so breifly skimming over it i didnt notice if you had figured out how to get aa_timers to work.
I've been working on some code to get that working right but in all my testing I cannot find any type of logic behind the aa_timer table in my db. It randomly changes when you click an aa and has nothing to do with timeing. It also does not change when a button or something is pressed. I'm still investigateing if i can find out whats going on i can let you know how i fixed the problem nearly all the code is fixed cept about one line of logic i think.

Hopefully i will find out soon i'm hopeing lay hands or harm touch will give me some clue. Even though they're not aa's theres a way that they go about triggering off. (Not really sure if that works either hehe) anyways back to codeing. Also after i get this tackled i'll start helping you with the aa's since people on my server want em working.
Reply With Quote
  #37  
Old 09-02-2004, 11:30 AM
monalin crusader
Hill Giant
 
Join Date: May 2004
Posts: 238
Default

Ok after some further investigation heres what i've found. Its still not working just like i want but i'm getting closer.

The way that aa_timers is working atm is:

When the effect first goes off it sets begin < end
If you click it again it sets begin = end

it rotates in this cycle and does not go down in time.
The way i have this working now it will go off every other time

So i was looking in database::UpdateTimersClientConnected(int32 charid)

and heres what i found

Code:
	if (!RunQuery(query, MakeAnyLenString(&query, "update aa_timers set end=(UNIX_TIMESTAMP(now())+(end-begin)),begin=UNIX_TIMESTAMP(now()) where charid=%i",charid), errbuf))
correct me if i'm wrong but the way they have it increases both end and begin and not only begin so no matter what they will have the same difference. Cant think of a way to fix it because i've got to go do some homework. Almost there though if u can think of a fix before i get back post it.
Reply With Quote
  #38  
Old 09-02-2004, 11:52 AM
Draupner
Hill Giant
 
Join Date: Jul 2004
Location: In my basement
Posts: 131
Default

I had AA timers workin perfect, but I lost all the code :(
Reply With Quote
  #39  
Old 09-03-2004, 03:35 AM
fathernitwit
Developer
 
Join Date: Jul 2004
Posts: 773
Default

just to let you guys know.
I have been working with cofruben on a persistent timer which he needs for adventure stuff. The result is something which can easily be used for AAs.

Right now it automatically takes care of all the database stuff, you just use it like the current timer class, basically, and it is preserved across zones. I dont know/care how the aa_timers stuff worked, because it was kinda klumsy if you ask me.

When cofruben gets done testing it, I will hook you up with a patch that should apply to 7-31 CVS... these timers are currently in 5.8, so they will be around for sure.
Reply With Quote
  #40  
Old 09-03-2004, 08:07 AM
monalin crusader
Hill Giant
 
Join Date: May 2004
Posts: 238
Default

Yeah it was set up really wird but i've figured it all out now once i do a little more work today it will be working. Got it down now where the only problem i'm having is the values it sets in aa_timers wont increase over time like it should but thats easy enough to fix i should have my source posted here by the end of today i would think.

**EDIT**

Its working now all timers for aa's should be working i will release the source when i get home from work in like 3 hours. Dont have time to do it atm.
Reply With Quote
  #41  
Old 09-03-2004, 12:18 PM
Branks
Sarnak
 
Join Date: May 2004
Posts: 58
Default

oh sweet im excited to see what you guys came up with, i kinda gave up on the current timers also since the more i looked into it the more it seems to be a simple rapid recast prevention thing than an actual timer, one of you two please say yalls system allows reenabling the button server side. currently the client does timers on its own to reenable the buttons which id like to have adjustable by the server op if possible. also monalin from what ive seen the timers in the DB arent meant to change constantly their simply there to check if current time hasnt passed the time when the timer was supposed to expire however the current system also only checks during zone changes. and fathernitwit would you mind filling me in on how much of this is broken in 5.8? im rather curious and just want a simple answer like "little different" or "omg start over" although i dont see how much of it can be broken other than actually recognizing an AA activation request, anyway thats just something ive been wondering about and one of the reasons i asked about the jr dev thing. anyway thanks again for work with the timers! guess ill spend the night playing with the monk AE attack skill as that one sounds kinda challenging.

also either of you happen to have a link to a decent code optimization tutorial or anything as i think i know enough to start working on good habbits and i still get nervous about tampering with the constantly run processes.
Reply With Quote
  #42  
Old 09-03-2004, 12:42 PM
monalin crusader
Hill Giant
 
Join Date: May 2004
Posts: 238
Default

Ok finnaly heres the source code.

client_process.cpp line 5251

before // try to send all packets that weren't send before
add

Code:
		database.UpdateTimersClientConnected(CharacterID());
database.h line 124
add

Code:
	bool    AATimerTest(int32 charid, int32 ability);
database.cpp line 2213

after #ifdef ZONE
add

Code:
bool Database::AATimerTest(int32 charid, int32 ability){
	char errbuf[MYSQL_ERRMSG_SIZE];
    char *query = 0;
    MYSQL_RES *result;
	MYSQL_ROW row;
	
	if (RunQuery(query, MakeAnyLenString(&query, "SELECT begin-end from aa_timers WHERE charid=%i AND ability=%i", charid, ability), errbuf, &result)) {
		while( ( row = mysql_fetch_row(result) ) ){

			LogFile->write(EQEMuLog::Error, "Database::AATimerTest begin-end=%i for ability: %i and charid: %i",atoi(row[0]),ability,charid);

			if(atoi(row[0]) >= 0){
				LogFile->write(EQEMuLog::Error, "Database::AATimerTest begin <= end");
				return false;
			}
			else{
				return true;
				LogFile->write(EQEMuLog::Error, "Database::AATimerTest begin >= end");
			}

		}
		mysql_free_result(result);
	}
	else
		LogFile->write(EQEMuLog::Error, "Database::AATimerTest query '%s' %s", query, errbuf);	

	safe_delete_array(query);
}
and right before that function
where it has

void Database::UpdateTimersClientConnected(int32 charid)

change that function to

Code:
void Database::UpdateTimersClientConnected(int32 charid){
	char errbuf[MYSQL_ERRMSG_SIZE];
    char *query = 0;
	if (!RunQuery(query, MakeAnyLenString(&query, "update aa_timers set begin=UNIX_TIMESTAMP(now()) where charid=%i",charid), errbuf)) {
		LogFile->write(EQEMuLog::Error, "UpdateAATimers query '%s' %s", query, errbuf);
	}
	safe_delete_array(query);
}
client.cpp line 3271

after int targ;
add

Code:
 if(database.AATimerTest(CastToClient()->character_id,activate) == 0){
client.cpp line 4955 (about)

after safe_delete(outapp);
add

Code:
   }
   else
	CastToClient()->Message(0,"You cannot cast this spell at this time.");
And i think thats about it i might have forgotten something i dont think i did let me know if it works for you guys too i've tested it on my server and it works so if it doesnt work on yours.

if(code != "works)"{
Message(1,"I probly forgot something.");
}
else if (code == "works"){
Message(1,"enjoy ");
}

and branks
Quote:
also either of you happen to have a link to a decent code optimization tutorial or anything as i think i know enough to start working on good habbits and i still get nervous about tampering with the constantly run processes.
I dont know, i'm 17 and i taught myself everything i know. I believe you might be able to edit the aa timers in game by just messing with the db a little i'm not sure how it works i can look into it i hadent really thought of changing it much but i dont think it would be impossible.

**EDIT** dont emptry your aa_timers table it bugs you, also the errors you get in zone.exe mean nothign they're for me to debugg.

**EDIT** UPDATE THIS PLEASE

new AATimerTest function should be

Code:
bool Database::AATimerTest(int32 charid, int32 ability){
	char errbuf[MYSQL_ERRMSG_SIZE];
    char *query = 0;
    MYSQL_RES *result;
	MYSQL_ROW row;
	
	if (RunQuery(query, MakeAnyLenString(&query, "SELECT begin-end from aa_timers WHERE charid=%i AND ability=%i", charid, ability), errbuf, &result)) {
		while( ( row = mysql_fetch_row(result) ) ){

			LogFile->write(EQEMuLog::Error, "Database::AATimerTest begin-end=%i for ability: %i and charid: %i",atoi(row[0]),ability,charid);

			if(atoi(row[0]) >= 0){
				LogFile->write(EQEMuLog::Error, "Database::AATimerTest begin <= end");
				return false;
			}
			else if(row[0] == "NULL"){
				 time_t timestamp=time(NULL);
				 UpdateAATimers(charid,timestamp,timestamp,ability);
				 return true;
			}
			else{
				LogFile->write(EQEMuLog::Error, "Database::AATimerTest begin >= end");
			}

		}
		mysql_free_result(result);
	}
	else{
      LogFile->write(EQEMuLog::Error, "Database::AATimerTest query '%s' %s", query, errbuf);    
	  }

	safe_delete_array(query);
}
it was found to be not adding new timers under certian conditions, with the help of Branks we came up with this it solved his problem he created when he emptied his aa_timer table.
Reply With Quote
  #43  
Old 09-03-2004, 02:10 PM
Branks
Sarnak
 
Join Date: May 2004
Posts: 58
Default

worked out great! but... i was getting one of the errors from it although it was working fine so i decided maybe it didnt like the current numbers that were in the DB so i emptied my aa_timers table and then nothing worked, so it needs a function to handle if there is no table currntly there. working on this now and still trying to track down how to reenable the button when the timer expires.

edit: monalin just noticed the last part, the timers are easily changed they are set in client.cpp above and below the code you added, its the timermod which is in each case, their in seconds. and im self taught also and slowly getting better. also what i meant about the reuse thing was that id like to trackdown whatever it is thats sent to the client to let the client know the skill is avaliable, instead of the button appearing gray while its actually useable, this happens during zoneing currently but not without so its in here somewhere...
Reply With Quote
  #44  
Old 09-03-2004, 02:15 PM
monalin crusader
Hill Giant
 
Join Date: May 2004
Posts: 238
Default

Oh, explain please i'm confused that shouldnt be causing problems since i just created a new character and when i did that it added the values to db just as if it had been blank. It shouldnt be causing any problems. Maybe i forgot to add something in there, did u just empty it or did u delete it, and what errors are you getting.

Oh and the errors are just in there because, u can remove them really i had that in there when i was trying to find out what the hell was going on with the aa_timers table. Those Errors really mean nothing just lets me know what was commingo ut of hte function when i would call it.

Quote:
also what i meant about the reuse thing was that id like to trackdown whatever it is thats sent to the client to let the client know the skill is avaliable, instead of the button appearing gray while its actually useable, this happens during zoneing currently but not without so its in here somewhere...
They had it updateing the database only when it zoned they put the UpdateTimersClientConnected(charid) in wrong place it was only getting called on login or zone.
Reply With Quote
  #45  
Old 09-03-2004, 02:20 PM
Branks
Sarnak
 
Join Date: May 2004
Posts: 58
Default

uh it kept saying begin <= end in the zone window which i assumed it shouldnt have been so i emptied the aa_timers table and rebooted the server.

and since then it wont work im playing with it now though, it may have been some of my other code that caused this as i have a lot thats not posted im playing with.
Reply With Quote
Reply


Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off

Forum Jump

   

All times are GMT -4. The time now is 06:21 PM.


 

Everquest is a registered trademark of Daybreak Game Company LLC.
EQEmulator is not associated or affiliated in any way with Daybreak Game Company LLC.
Except where otherwise noted, this site is licensed under a Creative Commons License.
       
Powered by vBulletin®, Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Template by Bluepearl Design and vBulletin Templates - Ver3.3