Пример #1
0
void WorldSession::SendTrainerList(Creature* pCreature)
{
	Trainer * pTrainer = pCreature->GetTrainer();
	//if(pTrainer == 0 || !CanTrainAt(_player, pTrainer)) return;
	if(pTrainer==0)
		return;

	if(!CanTrainAt(_player,pTrainer))
	{
		GossipMenu * pMenu;
		objmgr.CreateGossipMenuForPlayer(&pMenu,pCreature->GetGUID(),pTrainer->Cannot_Train_GossipTextId,_player);
		pMenu->SendTo(_player);
		return;
	}

	WorldPacket data(SMSG_TRAINER_LIST, 5000);
	TrainerSpell * pSpell;
	uint32 Spacer = 0;
	uint32 Count=0;
	uint8 Status;
	string Text;

	data << pCreature->GetGUID();
	data << pTrainer->TrainerType;

	data << uint32(0);
	for(vector<TrainerSpell>::iterator itr = pTrainer->Spells.begin(); itr != pTrainer->Spells.end(); ++itr)
	{
		pSpell = &(*itr);
		Status = TrainerGetSpellStatus(pSpell);
		if( pSpell->pCastRealSpell != NULL )
			data << pSpell->pCastRealSpell->Id;
		else if( pSpell->pLearnSpell )
			data << pSpell->pLearnSpell->Id;
		else
			continue;

		data << Status;
		data << pSpell->Cost;
		data << Spacer;
		data << uint32(pSpell->IsProfession);
		data << uint8(pSpell->RequiredLevel);
		data << pSpell->RequiredSkillLine;
		data << pSpell->RequiredSkillLineValue;
		data << pSpell->RequiredSpell;
		data << Spacer;	//this is like a spell override or something, ex : (id=34568 or id=34547) or (id=36270 or id=34546) or (id=36271 or id=34548)
		data << Spacer;
		++Count;
	}

#ifdef USING_BIG_ENDIAN
	*(uint32*)&data.contents()[12] = swap32(Count);
#else
	*(uint32*)&data.contents()[12] = Count;
#endif
	
	data << pTrainer->UIMessage;
	SendPacket(&data);
}
Пример #2
0
void WorldSession::SendTrainerList(Creature* pCreature)
{
	Trainer* pTrainer = pCreature->GetTrainer();
	//if(pTrainer == 0 || !CanTrainAt(_player, pTrainer)) return;
	if(pTrainer == NULL)
		return;

	if(! _player->CanTrainAt(pTrainer))
		Arcemu::Gossip::Menu::SendSimpleMenu(pCreature->GetGUID(), pTrainer->Cannot_Train_GossipTextId, GetPlayer());
	else
	{
		WorldPacket data(SMSG_TRAINER_LIST, 5000);
		TrainerSpell* pSpell;
		uint32 Spacer = 0;
		uint32 Count = 0;
		uint8 Status;
		string Text;

		data << pCreature->GetGUID();
		data << pTrainer->TrainerType;

		data << uint32(0);
		for(vector<TrainerSpell>::iterator itr = pTrainer->Spells.begin(); itr != pTrainer->Spells.end(); ++itr)
		{
			pSpell = &(*itr);
			Status = TrainerGetSpellStatus(pSpell);
			if(pSpell->pCastRealSpell != NULL)
				data << pSpell->pCastSpell->Id;
			else if(pSpell->pLearnSpell)
				data << pSpell->pLearnSpell->Id;
			else
				continue;

			data << Status;
			data << pSpell->Cost;
			data << Spacer;
			data << uint32(pSpell->IsProfession);
			data << uint8(pSpell->RequiredLevel);
			data << pSpell->RequiredSkillLine;
			data << pSpell->RequiredSkillLineValue;
			data << pSpell->RequiredSpell;
			data << Spacer;	//this is like a spell override or something, ex : (id=34568 or id=34547) or (id=36270 or id=34546) or (id=36271 or id=34548)
			data << Spacer;
			++Count;
		}

		*(uint32*)&data.contents()[12] = Count;

		if(stricmp(pTrainer->UIMessage, "DMSG") == 0)
			data << _player->GetSession()->LocalizedWorldSrv(37);
		else
			data << pTrainer->UIMessage;
		SendPacket(&data);
	}
}
Пример #3
0
void WorldSession::HandleTrainerBuySpellOpcode(WorldPacket& recvPacket)
{
	if(!_player->IsInWorld()) return;
	uint64 Guid;
	uint32 TeachingSpellID;

	recvPacket >> Guid >> TeachingSpellID;
	Creature *pCreature = _player->GetMapMgr()->GetCreature(Guid);
	if(pCreature == 0) return;

	Trainer *pTrainer = objmgr.GetTrainer(pCreature->GetEntry());
	if(pTrainer == 0) return;

	// Find teaching spell index.
	uint32 i;
	for(i = 0; i < pTrainer->SpellCount; ++i)
	{
		if(pTrainer->SpellList[i]->TeachingSpellID == TeachingSpellID)
			break;
	}

	if(i == pTrainer->SpellCount) return;
	TrainerSpell *pSpell = pTrainer->SpellList[i];

	if(TrainerGetSpellStatus(pSpell) > 0) return;
	
	_player->ModUInt32Value(PLAYER_FIELD_COINAGE, -(int32)pSpell->Cost);
	if(pSpell->DeleteSpell)
	{
		// Remove old spell.
		_player->removeSpell(pSpell->DeleteSpell, true, true, pSpell->DeleteSpell);
	}

	// Cast teaching spell on player
	pCreature->CastSpell(_player, pSpell->TeachingSpellID, true);
}
Пример #4
0
void WorldSession::HandleTrainerBuySpellOpcode(WorldPacket & recvPacket)
{
	CHECK_INWORLD_ASSERT;

	////////////////////////////////////////////////////////////////////////////////
	// As of 3.1.3 the client sends this when buying a spell
	//
	// {CLIENT} Packet: (0x01B2) CMSG_TRAINER_BUY_SPELL PacketSize = 12 TimeStamp = 39035859
	// A0 85 00 06 7A 00 30 F1 2D 85 00 00
	//
	// Structure:
	// uint64 GUID     - GUID of the trainer
	// uint32 spellid  - ID of the spell being bought
	////////////////////////////////////////////////////////////////////////////////

	uint64 Guid;
	uint32 TeachingSpellID;

	recvPacket >> Guid >> TeachingSpellID;
	Creature* pCreature = _player->GetMapMgr()->GetCreature(GET_LOWGUID_PART(Guid));

/////////////////////////////////////////// Checks //////////////////////////////////////

	if(pCreature == NULL) return;

	Trainer* pTrainer = pCreature->GetTrainer();
	if(pTrainer == 0)
		return;

	// Check if the trainer offers that spell
	TrainerSpell* pSpell = NULL;
	for(vector<TrainerSpell>::iterator itr = pTrainer->Spells.begin(); itr != pTrainer->Spells.end(); ++itr)
	{
		if((itr->pCastSpell && itr->pCastSpell->Id == TeachingSpellID) ||
		        (itr->pLearnSpell && itr->pLearnSpell->Id == TeachingSpellID))
		{
			pSpell = &(*itr);
		}
	}

	// If the trainer doesn't offer it, this is probably some packet mangling
	if(pSpell == NULL)
	{
		// Disconnecting the player
		sCheatLog.writefromsession(this, "Player %s tried learning none-obtainable spell - Possibly using WPE", _player->GetName());
		this->Disconnect();
		return;
	}

	// We can't learn it
	if(TrainerGetSpellStatus(pSpell) > 0)
		return;

//////////////////////////////////////////// Teaching ////////////////////////////////////

	_player->ModGold(-(int32)pSpell->Cost);

	if(pSpell->pCastSpell)
	{
		_player->CastSpell(_player, pSpell->pCastSpell->Id, true);
	}
	else
	{
/////////////////////////////////////// Showing the learning spellvisuals//////////////
		_player->SendPlaySpellVisual(pCreature->GetGUID(), 0x5B3);
		_player->SendPlaySpellVisual(_player->GetGUID(), 0x16A);
///////////////////////////////////////////////////////////////////////////////////////

		// add the spell itself
		_player->addSpell(pSpell->pLearnSpell->Id);
	}

	if(pSpell->DeleteSpell)
	{
		// Remove old spell.
		if(pSpell->pLearnSpell)
			_player->removeSpell(pSpell->DeleteSpell, true, true, pSpell->pLearnSpell->Id);
		else if(pSpell->pCastSpell)
			_player->removeSpell(pSpell->DeleteSpell, true, true, pSpell->pCastRealSpell->Id);
		else
			_player->removeSpell(pSpell->DeleteSpell, true, false, 0);
	}

	_player->_UpdateSkillFields();

	/////////////////////////////////////////////////////////////////////////////////
	// As of 3.1.3 this is sent after buying the spell
	//
	//
	// {SERVER} Packet: (0x01B3) SMSG_TRAINER_BUY_SUCCEEDED PacketSize = 12 TimeStamp = 39035968
	// A0 85 00 06 7A 00 30 F1 2D 85 00 00
	//
	// structure:
	//
	// uint64 GUID    -  GUID of the trainer
	// uint32 spellid -  ID of the spell we bought
	//////////////////////////////////////////////////////////////////////////////////

	WorldPacket data(SMSG_TRAINER_BUY_SUCCEEDED, 12);

	data << uint64(Guid) << uint32(TeachingSpellID);
	this->SendPacket(&data);
}
Пример #5
0
void WorldSession::SendTrainerList(Creature* pCreature)
{
	Trainer * pTrainer = objmgr.GetTrainer(pCreature->GetEntry());
	if(pTrainer == 0) return;

	WorldPacket data(SMSG_TRAINER_LIST, 5000);
	
	data << pCreature->GetGUID();
	data << pTrainer->TrainerType;
	data << pTrainer->SpellCount;

	TrainerSpell * pSpell;
	uint32 Spacer = 0;
	uint32 * SpellCount = (uint32*)&data.contents()[12];
	uint8 Status;
	int32 RequiredLevel;

	for(uint32 i = 0; i < pTrainer->SpellCount; ++i)
	{
		// We need the info for the teaching spell ;)
		pSpell = pTrainer->SpellList[i];
		RequiredLevel = pSpell->RequiredLevel;

		if(pSpell->RequiredClass != -1)
		{
			// Check class
			if(!(_player->getClassMask() & pSpell->RequiredClass))
			{
				// Hide this spell.
				*SpellCount--;
				continue;
			}
		}

		//Dual Wield
		if(pSpell->SpellID == 674 || pSpell->SpellID == 29651)
		{
			switch(_player->getClass())
			{
			case WARRIOR:
			case HUNTER:
				RequiredLevel = 20;
				break;
			case ROGUE:
				RequiredLevel = 10;
				break;
			default:
				RequiredLevel = -1;
			}
		}

		Status = TrainerGetSpellStatus(pSpell);

		// HACKFIX: dont show already known spells
		if((Status == TRAINER_STATUS_ALREADY_HAVE && _player->getClass() == PALADIN) || RequiredLevel < 0)
		{
			*SpellCount--;
			continue;
		}

		data << pSpell->TeachingSpellID;
		data << Status;		
		data << pSpell->Cost;
		data << Spacer;
		data << pSpell->IsProfession;
		data << (uint8)pSpell->RequiredLevel;

		data << pSpell->RequiredSkillLine;
		data << pSpell->RequiredSkillLineValue;
		data << pSpell->RequiredSpell;

		data << Spacer << Spacer;
	}

	string Text = pTrainer->TalkMessage;
	data << Text;

	SendPacket(&data);
}
Пример #6
0
void WorldSession::HandleTrainerBuySpellOpcode(WorldPacket& recvPacket)
{
	if(!_player->IsInWorld()) return;
	uint64 Guid;
	uint32 TeachingSpellID;

	recvPacket >> Guid >> TeachingSpellID;
	Creature *pCreature = _player->GetMapMgr()->GetCreature(GET_LOWGUID_PART(Guid));
	if(pCreature == 0) return;

	Trainer *pTrainer = pCreature->GetTrainer();
	if(pTrainer == 0 || !CanTrainAt(_player, pTrainer)) return;

	TrainerSpell * pSpell=NULL;
	for(vector<TrainerSpell>::iterator itr = pTrainer->Spells.begin(); itr != pTrainer->Spells.end(); ++itr)
	{
		if( ( itr->pCastRealSpell && itr->pCastRealSpell->Id == TeachingSpellID ) ||
			( itr->pLearnSpell && itr->pLearnSpell->Id == TeachingSpellID ) )
		{
			pSpell = &(*itr);
		}
	}
	
	if(pSpell == NULL)
		return;

	if(TrainerGetSpellStatus(pSpell) > 0) return;
	
	_player->ModUnsigned32Value(PLAYER_FIELD_COINAGE, -(int32)pSpell->Cost);

	if( pSpell->pCastSpell)
	{
		// Cast teaching spell on player
		pCreature->CastSpell(_player, pSpell->pCastSpell, true);
	}

	if( pSpell->pLearnSpell )
	{
		packetSMSG_PLAY_SPELL_VISUAL pck;
		pck.guid = pCreature->GetGUID();
		pck.visualid = 0x5b3;
		_player->OutPacketToSet( SMSG_PLAY_SPELL_VISUAL, sizeof(packetSMSG_PLAY_SPELL_VISUAL), &pck, true );

		pck.guid = _player->GetGUID();
		pck.visualid = 0x16a;
		_player->OutPacketToSet( 0x1F7, sizeof(packetSMSG_PLAY_SPELL_VISUAL), &pck, true );

		// add the spell
		_player->addSpell( pSpell->pLearnSpell->Id );

		uint32 i;
		for( i = 0; i < 3; ++i)
		{
			if(pSpell->pLearnSpell->Effect[i] == SPELL_EFFECT_PROFICIENCY || pSpell->pLearnSpell->Effect[i] == SPELL_EFFECT_LEARN_SPELL ||
				pSpell->pLearnSpell->Effect[i] == SPELL_EFFECT_WEAPON)
			{
				_player->CastSpell(_player, pSpell->pLearnSpell, true);
				break;
			}
		}

		for( i = 0; i < 3; ++i)
		{
			if( pSpell->pLearnSpell->Effect[i] == SPELL_EFFECT_SKILL )
			{
				uint32 skill = pSpell->pLearnSpell->EffectMiscValue[i];
				uint32 val = (pSpell->pLearnSpell->EffectBasePoints[i]+1) * 75;
				if( val > 350 )
					val = 350;

				if( _player->_GetSkillLineMax(skill) >= val )
					return;

				if( skill == SKILL_RIDING )
					_player->_AddSkillLine( skill, val, val );
				else
				{
					if( _player->_HasSkillLine(skill) )
						_player->_ModifySkillMaximum(skill, val);
					else
						_player->_AddSkillLine( skill, 1, val);
				}
			}
		}
	}

	if(pSpell->DeleteSpell)
	{
		// Remove old spell.
		if( pSpell->pLearnSpell )
			_player->removeSpell(pSpell->DeleteSpell, true, true, pSpell->pLearnSpell->Id);
		else if(pSpell->pCastSpell)
			_player->removeSpell(pSpell->DeleteSpell, true, true, pSpell->pCastRealSpell->Id);
		else
			_player->removeSpell(pSpell->DeleteSpell,true,false,0);
	}
}
Пример #7
0
void WorldSession::HandleTrainerBuySpellOpcode(WorldPacket& recvPacket)
{
	CHECK_INWORLD_RETURN;
	uint64 Guid;
	uint32 TeachingSpellID;

	recvPacket >> Guid >> TeachingSpellID;
	Creature* pCreature = _player->GetMapMgr()->GetCreature(GET_LOWGUID_PART(Guid));
	if(pCreature == NULL)
		return;

	Trainer *pTrainer = pCreature->GetTrainer();
	if(pTrainer == NULL || !CanTrainAt(_player, pTrainer))
		return;

	TrainerSpell* pSpell = NULL;
	for(vector<TrainerSpell>::iterator itr = pTrainer->Spells.begin(); itr != pTrainer->Spells.end(); itr++)
	{
		if( ( itr->pCastRealSpell && itr->pCastRealSpell->Id == TeachingSpellID ) ||
			( itr->pLearnSpell && itr->pLearnSpell->Id == TeachingSpellID ) )
		{
			pSpell = &(*itr);
		}
	}
	
	if(pSpell == NULL)
		return;

	if(TrainerGetSpellStatus(pSpell) > 0) return;
	
	_player->ModUnsigned32Value(PLAYER_FIELD_COINAGE, -(int32)pSpell->Cost);

	if( pSpell->pCastSpell)
	{
		// Cast teaching spell on player
		pCreature->CastSpell(_player, pSpell->pCastSpell, true);
	}

	if( pSpell->pLearnSpell )
	{
		packetSMSG_PLAY_SPELL_VISUAL pck;
		pck.guid = pCreature->GetGUID();
		pck.visualid = 0x5b3;
		_player->OutPacketToSet( SMSG_PLAY_SPELL_VISUAL, sizeof(packetSMSG_PLAY_SPELL_VISUAL), &pck, true );

		pck.guid = _player->GetGUID();
		pck.visualid = 0x16a;
		_player->OutPacketToSet( SMSG_PLAY_SPELL_IMPACT, sizeof(packetSMSG_PLAY_SPELL_VISUAL), &pck, true );

		// add the spell
		_player->addSpell( pSpell->pLearnSpell->Id );

		uint32 i;
		for( i = 0; i < 3; ++i)
		{
			if(pSpell->pLearnSpell->Effect[i] == SPELL_EFFECT_PROFICIENCY || pSpell->pLearnSpell->Effect[i] == SPELL_EFFECT_LEARN_SPELL ||
				pSpell->pLearnSpell->Effect[i] == SPELL_EFFECT_WEAPON)
			{
				_player->CastSpell(_player, pSpell->pLearnSpell, true);
				break;
			}
		}

		for( i = 0; i < 3; ++i)
		{
			if( pSpell->pLearnSpell->Effect[i] == SPELL_EFFECT_SKILL )
			{
				uint32 skill = pSpell->pLearnSpell->EffectMiscValue[i];
				uint32 val = (pSpell->pLearnSpell->EffectBasePoints[i]+1) * 75;
				if( val > 350 )
					val = 350;

				if( _player->_GetSkillLineMax(skill) >= val )
					return;

				if( skill == SKILL_RIDING )
					_player->_AddSkillLine( skill, val, val );
				else
				{
					if( _player->_HasSkillLine(skill) )
						_player->_ModifySkillMaximum(skill, val);
					else
						_player->_AddSkillLine( skill, 1, val);
				}
			}
		}
	}

	if(pSpell->DeleteSpell)
	{
		// Remove old spell.
		if( pSpell->pLearnSpell )
			_player->removeSpell(pSpell->DeleteSpell, true, true, pSpell->pLearnSpell->Id);
		else if(pSpell->pCastSpell)
			_player->removeSpell(pSpell->DeleteSpell, true, true, pSpell->pCastRealSpell->Id);
		else
			_player->removeSpell(pSpell->DeleteSpell,true,false,0);
	}
	/////////////////////////////////////////////////////////////////////////////////
	// As of 3.1.3 this is sent after buying the spell
	//
	//
	// {SERVER} Packet: (0x01B3) SMSG_TRAINER_BUY_SUCCEEDED PacketSize = 12 TimeStamp = 39035968
	// A0 85 00 06 7A 00 30 F1 2D 85 00 00
	//
	// structure:
	//
	// uint64 GUID    -  GUID of the trainer
	// uint32 spellid -  ID of the spell we bought
	//////////////////////////////////////////////////////////////////////////////////

	WorldPacket data(SMSG_TRAINER_BUY_SUCCEEDED, 12);

	data << uint64(Guid) << uint32(TeachingSpellID);
	this->SendPacket(&data);
}
Пример #8
0
void WorldSession::HandleTrainerBuySpellOpcode(WorldPacket& recvPacket)
{
	if(!_player->IsInWorld()) return;

    ////////////////////////////////////////////////////////////////////////////////
    // As of 3.1.3 the client sends this when buying a spell
    //
    // {CLIENT} Packet: (0x01B2) CMSG_TRAINER_BUY_SPELL PacketSize = 12 TimeStamp = 39035859
    // A0 85 00 06 7A 00 30 F1 2D 85 00 00 
    //
    // Structure:
    // uint64 GUID     - GUID of the trainer
    // uint32 spellid  - ID of the spell being bought
    ////////////////////////////////////////////////////////////////////////////////

	uint64 Guid;
	uint32 TeachingSpellID;

	recvPacket >> Guid >> TeachingSpellID;
	Creature *pCreature = _player->GetMapMgr()->GetCreature(GET_LOWGUID_PART(Guid));
	
/////////////////////////////////////////// Checks //////////////////////////////////////
    
    if(pCreature == NULL) return;

	Trainer *pTrainer = pCreature->GetTrainer();
	if(pTrainer == NULL || !CanTrainAt(_player, pTrainer)) return;

    // Check if the trainer offers that spell
	TrainerSpell * pSpell = NULL;
	for(vector<TrainerSpell>::iterator itr = pTrainer->Spells.begin(); itr != pTrainer->Spells.end(); ++itr)
	{
		if( ( itr->pCastSpell && itr->pCastSpell->Id == TeachingSpellID ) ||
			( itr->pLearnSpell && itr->pLearnSpell->Id == TeachingSpellID ) )
		{
			pSpell = &(*itr);
		}
	}
	
    // If the trainer doesn't offer it, this is probably some packet mangling
    if(pSpell == NULL){
        // Disconnecting the player
        this->Disconnect();
		return;
    }

    // We can't learn it
	if(TrainerGetSpellStatus(pSpell) > 0) 
        return;

//////////////////////////////////////////// Teaching ////////////////////////////////////
	
	_player->ModUnsigned32Value(PLAYER_FIELD_COINAGE, -(int32)pSpell->Cost);

	if( pSpell->pCastSpell)
	{
        _player->CastSpell( _player, pSpell->pCastSpell->Id, true );
    }
    else
	{
/////////////////////////////////////// Showing the learning spellvisuals//////////////
            packetSMSG_PLAY_SPELL_VISUAL pck;

	        pck.guid = pCreature->GetGUID();
	        pck.visualid = 0x5b3;

	        _player->OutPacketToSet( SMSG_PLAY_SPELL_VISUAL, sizeof(packetSMSG_PLAY_SPELL_VISUAL), &pck, true );

            pck.guid = _player->GetGUID();
	        pck.visualid = 0x16a;

	        _player->OutPacketToSet( SMSG_PLAY_SPELL_IMPACT, sizeof(packetSMSG_PLAY_SPELL_VISUAL), &pck, true );
///////////////////////////////////////////////////////////////////////////////////////
        
        // add the spell itself
		_player->addSpell( pSpell->pLearnSpell->Id );
    }

	if(pSpell->DeleteSpell)
	{
		// Remove old spell.
		if( pSpell->pLearnSpell )
			_player->removeSpell(pSpell->DeleteSpell, true, true, pSpell->pLearnSpell->Id);
		else if(pSpell->pCastSpell)
			_player->removeSpell(pSpell->DeleteSpell, true, true, pSpell->pCastRealSpell->Id);
		else
			_player->removeSpell(pSpell->DeleteSpell,true,false,0);
	}

	_player->_UpdateSkillFields();

    /////////////////////////////////////////////////////////////////////////////////
    // As of 3.1.3 this is sent after buying the spell
    // 
    //
    // {SERVER} Packet: (0x01B3) SMSG_TRAINER_BUY_SUCCEEDED PacketSize = 12 TimeStamp = 39035968
    // A0 85 00 06 7A 00 30 F1 2D 85 00 00 
    // 
    // structure:
    //
    // uint64 GUID    -  GUID of the trainer
    // uint32 spellid -  ID of the spell we bought
    //////////////////////////////////////////////////////////////////////////////////

    WorldPacket data( SMSG_TRAINER_BUY_SUCCEEDED, 12 );

    data << uint64( Guid ) << uint32( TeachingSpellID );
    this->SendPacket( &data );
}
void WorldSession::HandleTrainerBuySpellOpcode(WorldPacket& recvPacket)
{
	if(!_player->IsInWorld()) 
	{ 
		return;
	}
	uint64 Guid;
	uint32 TeachingSpellID;

	recvPacket >> Guid >> TeachingSpellID;
	Creature *pCreature = _player->GetMapMgr()->GetCreature( Guid );
	if(pCreature == 0) 
	{ 
		return;
	}

	Trainer *pTrainer = pCreature->GetTrainer();
	if(pTrainer == 0 || !CanTrainAt(_player, pTrainer)) 
	{ 
		return;
	}

	TrainerSpell * pSpell=NULL;
	for(uint32 itr = 0; itr < pTrainer->SpellCount; ++itr)
	{
		TrainerSpell *t = pTrainer->Spells.GetValue( itr );
		if( ( t->pCastRealSpell && t->pCastRealSpell->Id == TeachingSpellID ) ||
			( t->pLearnSpell && t->pLearnSpell->Id == TeachingSpellID ) )
			pSpell = t;
	}
	
	if(pSpell == NULL)
	{ 
		return;
	}

	if(TrainerGetSpellStatus(pSpell) > 0) 
	{ 
		return;
	}
	
	_player->ModGold( -(int32)pSpell->Cost);

	if( pSpell->pCastSpell)
	{
		// Cast teaching spell on player
//		pCreature->CastSpell(_player, pSpell->pCastSpell, true);
		_player->CastSpell(_player, pSpell->pCastSpell, true); //creature cast might fail due to bad targeting
	}

	//are these required in 3.1.1 ?
/*	packetSMSG_PLAY_SPELL_VISUAL pck;
	pck.guid = pCreature->GetGUID();
	pck.visualid = 0x5b3;
	_player->OutPacketToSet( SMSG_PLAY_SPELL_VISUAL, sizeof(packetSMSG_PLAY_SPELL_VISUAL), &pck, true );*/

	packetSMSG_PLAY_SPELL_IMPACT pck2;
	pck2.guid = _player->GetGUID();
	pck2.visualid = 0x16a;
	_player->OutPacketToSet( SMSG_PLAY_SPELL_IMPACT, sizeof(packetSMSG_PLAY_SPELL_VISUAL), &pck2, true );/**/
	this->OutPacket( SMSG_TRAINER_BUY_SUCCEEDED, 12, recvPacket.contents() );


	if( pSpell->pLearnSpell )
	{
		// add the spell
		if( pSpell->pLearnSpell->Effect[0] != SPELL_EFFECT_LEARN_SPELL &&
			pSpell->pLearnSpell->Effect[1] != SPELL_EFFECT_LEARN_SPELL &&
			pSpell->pLearnSpell->Effect[2] != SPELL_EFFECT_LEARN_SPELL )
			_player->addSpell( pSpell->pLearnSpell->Id );

		uint32 i;
		for( i = 0; i < 3; ++i )
		{
			if( pSpell->pLearnSpell->Effect[i] == SPELL_EFFECT_PROFICIENCY || pSpell->pLearnSpell->Effect[i] == SPELL_EFFECT_WEAPON ||
				( pSpell->pLearnSpell->Effect[i] == SPELL_EFFECT_LEARN_SPELL && pSpell->pLearnSpell->EffectImplicitTargetA[i] != EFF_TARGET_PET ) )  // avoid direct pet teaching
			{
				_player->CastSpell( _player, pSpell->pLearnSpell, true );
				break;
			}
		}

		for( i = 0; i < 3; ++i)
		{
			if( pSpell->pLearnSpell->Effect[i] == SPELL_EFFECT_SKILL )
			{
				uint32 skill = pSpell->pLearnSpell->EffectMiscValue[i];
				uint32 val = (pSpell->pLearnSpell->EffectBasePoints[i]+1) * 75;
				if( val > PLAYER_SKILL_CAP )
					val = PLAYER_SKILL_CAP;
				if( _player->_GetSkillLineMax(skill) >= val )
				{ 
					return;
				}

				if( skill == SKILL_RIDING )
					_player->_AddSkillLine( skill, val, val );
				else
				{
					if( _player->_HasSkillLine(skill) )
						_player->_ModifySkillMaximum(skill, val);
					else
						_player->_AddSkillLine( skill, 1, val);
				}
			}
		}
	}

	if(pSpell->DeleteSpell)
	{
		// Remove old spell.
		if( pSpell->pLearnSpell )
			_player->removeSpell(pSpell->DeleteSpell, true, true, pSpell->pLearnSpell->Id);
		else if(pSpell->pCastSpell)
			_player->removeSpell(pSpell->DeleteSpell, true, true, pSpell->pCastRealSpell->Id);
		else
			_player->removeSpell(pSpell->DeleteSpell,true,false,0);
	}
}