Beispiel #1
0
void CTeam::rewardSharing(CRewardSharing * reward)
{
	// if there is a reward add the new it
	if ( _RewardSharing )
	{
		_RewardSharing->addReward(reward,this);
	}
	// otherwise, create a new one
	else
	{
		_RewardSharing = reward;
		for (list<CEntityId>::const_iterator it = _TeamMembers.begin() ; it != _TeamMembers.end() ; ++it)
		{
			CCharacter * user = PlayerManager.getOnlineChar( (*it) );
			if (user )
			{
				CMessage msgout ("IMPULSION_ID");
				msgout.serial ((CEntityId&)(*it));
				CBitMemStream bms;
				
				if (!GenericMsgManager.pushNameToStream ("TEAM:SHARE_OPEN", bms))
					nlstopex (("Missing TEAM:SHARE_OPEN in msg.xml"));
				msgout.serialBufferWithSize ((uint8*)bms.buffer(), bms.length());
				sendMessageViaMirror ( NLNET::TServiceId((*it).getDynamicId()), msgout);
			}
		}
		_RewardSharing->resetCandidates(this);
	}
}// CTeam::rewardSharing
//-----------------------------------------------
//	chat
//
//-----------------------------------------------
void CClientChatManager::chat( const ucstring& strIn, bool isChatTeam )
{
	// Truncate to 255 chars max (because of server restriction)
	ucstring	str= strIn.substr(0,255);

	// send str to IOS
	CBitMemStream bms;
	string msgType;

	if (isChatTeam)
	{
		if (NLGUI::CDBManager::getInstance()->getDbProp("SERVER:GROUP:0:PRESENT")->getValueBool())
			msgType = "STRING:CHAT_TEAM";
		else
			return;		// don't display team chat message if there is no team chat
	}
	else
		msgType = "STRING:CHAT";

	if( GenericMsgHeaderMngr.pushNameToStream(msgType,bms) )
	{
		bms.serial( str );
		NetMngr.push( bms );
		//nlinfo("impulseCallBack : %s %s sent", msgType.c_str(), str.toString().c_str());
	}
	else
	{
		nlwarning("<CClientChatManager::chat> unknown message name : %s", msgType.c_str());
	}

	if (UserEntity != NULL) UserEntity->setAFK(false);

} // chat //
Beispiel #3
0
// ***************************************************************************
void CGuildManager::launchAscensor()
{
	// Start the huge list exchange
	Ascensors.start();

	// Increment session id
	Ascensors.incrementSessionID();

	// Send request of the first page to the server specifying the session id
	CBitMemStream out;
	if(GenericMsgHeaderMngr.pushNameToStream("GUILD:FIRST_ASCENSOR_PAGE", out))
	{
		uint16 session = Ascensors.getSessionID();
		out.serial(session);
		NetMngr.push(out);
		//nlinfo("impulseCallBack : GUILD:FIRST_ASCENSOR_PAGE %d sent",session);
	}
	else
	{
		nlwarning("impulseCallBack : unknown message name : 'GUILD:FIRST_ASCENSOR_PAGE'.");
	}

	// Start Ascensor Interface
	CInterfaceManager *pIM = CInterfaceManager::getInstance();
	CGroupContainer *pAC = dynamic_cast<CGroupContainer*>(pIM->getElementFromId(WIN_ASCENSOR));
	if (pAC == NULL) return;
	pAC->setActive(true);
	pIM->setTopWindow(pAC);
}
/*
 * Push one change to the stream
 */
void	CCDBSynchronised::pushDelta( CBitMemStream& s, CCDBStructNodeLeaf *node, uint32& bitsize )
{
	TCDBDataIndex index = node->getDataIndex();

	// Test if the property type is valid.
	if ( node->type() > ICDBStructNode::UNKNOWN && node->type() < ICDBStructNode::Nb_Prop_Type )
	{
		// Serialize the Property Value according to the Property Type.
		uint64 value;
		value = (uint64)_DataContainer.getValue64( index );
		//_DataContainer.archiveCurrentValue( index );

		if ( node->type() == ICDBStructNode::TEXT )
		{
			s.serialAndLog2( value, 32 );
			bitsize += 32;
			if ( VerboseDatabase )
				nldebug( "CDB: Pushing value %"NL_I64"d (TEXT-32) for index %d prop %s", (sint64)value, index, node->buildTextId().toString().c_str() );
		}
		else
		{
			s.serialAndLog2( value, (uint)node->type() );
			bitsize += (uint32)node->type();
			if ( VerboseDatabase )
				nldebug( "CDB: Pushing value %"NL_I64"d (%u bits) for index %d prop %s", (sint64)value, (uint32)node->type(), index, node->buildTextId().toString().c_str() );
		}
	}
	else
		nlwarning("CCDBStructNodeLeaf::writeDelta : Property Type Unknown ('%d') -> not serialized.", (uint)node->type());
}
	void execute (CCtrlBase * /* pCaller */, const std::string &/* sParams */)
	{
		CInterfaceManager	*pIM= CInterfaceManager::getInstance();

		// Copy SERVER DB to Local selection
		uint32	outpostSheet= 0;
		CCDBNodeLeaf	*node= NLGUI::CDBManager::getInstance()->getDbProp("LOCAL:TARGET:CONTEXT_MENU:OUTPOST");
		if(node)	outpostSheet= node->getValue32();
		node= NLGUI::CDBManager::getInstance()->getDbProp("UI:TEMP:OUTPOST:BOT_SELECTION");
		if(node)	node->setValue32(outpostSheet);

		// Send a msg to server
		if(outpostSheet)
		{
			string	sMsg= "OUTPOST:SELECT";
			CBitMemStream out;
			if(GenericMsgHeaderMngr.pushNameToStream(sMsg, out))
			{
				//nlinfo("impulseCallBack : %s %d sent", sMsg.c_str(), outpostSheet);
				out.serial(outpostSheet);
				NetMngr.push(out);
			}
			else
			{
				nlwarning("command : unknown message name : '%s'.", sMsg.c_str());
			}
		}
	}
//-----------------------------------------------
//	setChatMode
//
//-----------------------------------------------
void CClientChatManager::setChatMode(CChatGroup::TGroupType group, TChanID dynamicChannelId)
{
	uint8 mode = group;
	 // mode really changed ?
	if (mode == _ChatMode && dynamicChannelId==_ChatDynamicChannelId) return;

	// Chat team don't need swap mode
	if (group != CChatGroup::team)
	{
		CBitMemStream bms;
		string msgType = "STRING:CHAT_MODE";
		if( GenericMsgHeaderMngr.pushNameToStream(msgType,bms) )
		{
			bms.serial( mode );
			bms.serial( dynamicChannelId );
			NetMngr.push( bms );
			//nlinfo("impulseCallBack : %s %d sent", msgType.c_str(), mode);
		}
		else
		{
			nlwarning("<CClientChatManager::setChatMode> unknown message name : STRING:CHAT_MODE");
		}
	}

	// update cache
	_ChatMode = mode;
	_ChatDynamicChannelId = dynamicChannelId;

	if (UserEntity != NULL) UserEntity->setAFK(false);

} // filter //
//-----------------------------------------------
//	tell
//
//-----------------------------------------------
void CClientChatManager::tell( const string& receiverIn, const ucstring& strIn )
{
	// Truncate to 255 chars max (because of server restriction)
	string		receiver= receiverIn.substr(0,255);
	ucstring	str= strIn.substr(0,255);

	// *** send str
	CBitMemStream bms;
	string msgType = "STRING:TELL";
	if( GenericMsgHeaderMngr.pushNameToStream(msgType,bms) )
	{
		bms.serial( receiver );
		bms.serial( str );
		NetMngr.push( bms );
		//nlinfo("impulseCallBack : %s %s %s sent", msgType.c_str(), receiver.c_str(), str.toString().c_str());
	}
	else
	{
		nlwarning("<CClientChatManager::tell> unknown message name : STRING:TELL");
	}


	// *** manage list of last telled people
	// remove the telled people from list (if present)
	std::list<ucstring>::iterator it = _TellPeople.begin();
	while(it != _TellPeople.end())
	{
		if (*it == ucstring(receiver))
		{
			it = _TellPeople.erase(it);
			nlassert(_NumTellPeople != 0);
			-- _NumTellPeople;
		}
		else
		{
			++it;
		}
	}

	// readd to back of the list (most recent telled people)
	_TellPeople.push_back(receiver);
	++ _NumTellPeople;

	// if too much people, remove the older one
	if (_NumTellPeople > _MaxNumTellPeople)
	{
		-- _NumTellPeople;
		_TellPeople.pop_front();
	}

	// tell => the user is no more AFK.
	if (UserEntity != NULL) UserEntity->setAFK(false);

} // tell //
Beispiel #8
0
void	CImpulseDecoder::decode(CBitMemStream &inbox, TPacketNumber receivedPacket, TPacketNumber receivedAck, TPacketNumber nextSentPacket, vector<CLFECOMMON::CAction *> &actions)
{
	uint				level;

	for (level=0; level<3; ++level)
	{
		TPacketNumber	*lAck;
		uint			channel;

		switch (level)
		{
		case 0: lAck = _LastAck0; channel = 0; break;
		case 1: lAck = _LastAck1; channel = receivedPacket&1; break;
		case 2: lAck = _LastAck2; channel = receivedPacket&3; break;
		}

		bool			keep = true;
		bool			checkOnce = false;
		uint			num = 0;

		TPacketNumber	lastAck = lAck[channel];

		for(;;)
		{
			bool	next;
			inbox.serial(next);

			if (!next)
				break;

			if (!checkOnce)
			{
				checkOnce = true;
				keep = (receivedAck >= lAck[channel]);
				if (keep)
					lAck[channel] = nextSentPacket;
			}

			++num;
			CAction	*action = CActionFactory::getInstance()->unpack(inbox, false);

			if (keep)
			{
				actions.push_back(action);
				nlinfo("CLIMPD: received new impulsion %d (len=%u) at level %d (channel %d)", action->Code, CActionFactory::getInstance()->size(action), level, channel, num, (keep) ? "" : " (discarded)", lastAck, nextSentPacket);
			}
			else
			{
				nlinfo("CLIMPD: discarded action %d (len=%u) at level %d (channel %d)", action->Code, CActionFactory::getInstance()->size(action), level, channel, num, (keep) ? "" : " (discarded)", lastAck, nextSentPacket);
				CActionFactory::getInstance()->remove(action);
			}
		}

		if (checkOnce)
			nldebug("CLIMPD: at level %d (channel %d), %d actions%s (ReceivedAck=%d/lastAck=%d/nextSentPacket=%d)", level, channel, num, (keep) ? "" : " (discarded)", receivedAck, lastAck, nextSentPacket);
	}
}
//-----------------------------------------------
//	filter
//
//-----------------------------------------------
void CClientChatManager::filter( uint8 filter )
{
	CBitMemStream bms;
	string msgType = "STRING:FILTER";
	if( GenericMsgHeaderMngr.pushNameToStream(msgType,bms) )
	{
		bms.serial( filter );
		NetMngr.push( bms );
		//nlinfo("impulseCallBack : %s %d sent", msgType.c_str(), filter);
	}
	else
	{
		nlwarning("<CClientChatManager::filter> unknown message name : STRING:FILTER");
	}

	if (UserEntity != NULL) UserEntity->setAFK(false);

} // filter //
Beispiel #10
0
// ***************************************************************************
void	COutpostManager::endPvpJoinProposal(bool bNeutral, OUTPOSTENUMS::TPVPSide pvpSide)
{
	// send msg
	string sMsg= "OUTPOST:SIDE_CHOSEN";
	CBitMemStream out;
	if(GenericMsgHeaderMngr.pushNameToStream(sMsg, out))
	{
		//nlinfo("impulseCallBack : %s %d %s sent", sMsg.c_str(), bNeutral, OUTPOSTENUMS::toString(pvpSide).c_str());
		out.serial(bNeutral);
		uint8 sideAsInt = (uint8)pvpSide;
		out.serial(sideAsInt);
		NetMngr.push(out);
	}
	else
	{
		nlwarning("command : unknown message name : '%s'.", sMsg.c_str());
	}

	// Abort any timer
	_EndTickForPvpJoinProposal= 0;
}
	void execute (CCtrlBase * /* pCaller */, const std::string &/* sParams */)
	{
		CInterfaceManager	*pIM= CInterfaceManager::getInstance();

		// read current outpost sheet
		uint32	outpostSheet= 0;
		CCDBNodeLeaf	*node= NLGUI::CDBManager::getInstance()->getDbProp("SERVER:OUTPOST_SELECTED:SHEET", false);
		if(node)
			outpostSheet= node->getValue32();

		// read wanted GMT attack period
		uint8	wantedAttHour= 0;
		node= NLGUI::CDBManager::getInstance()->getDbProp("UI:TEMP:OUTPOST:DECLARE_WAR_ATTACK_PERIOD", false);
		if(node)
			wantedAttHour= (uint8)node->getValue32();

		// read result Att Period Time (NB: for final server check: ensure that the user will get what it sees)
		uint32	startAttackTime= 0;
		node= NLGUI::CDBManager::getInstance()->getDbProp("UI:TEMP:OUTPOST:DECLARE_WAR_ACK_TIME_RANGE_ATT", false);
		if(node)
			startAttackTime= node->getValue32();

		// send a DECLARE_WAR_VALIDATE message to server
		string	sMsg= "OUTPOST:DECLARE_WAR_VALIDATE";
		CBitMemStream out;
		if(GenericMsgHeaderMngr.pushNameToStream(sMsg, out))
		{
			//nlinfo("impulseCallBack : %s %d %d %d sent", sMsg.c_str(), outpostSheet, wantedAttHour, startAttackTime);
			out.serial(outpostSheet);
			out.serial(wantedAttHour);
			out.serial(startAttackTime);
			NetMngr.push(out);
		}
		else
		{
			nlwarning("command : unknown message name : '%s'.", sMsg.c_str());
		}

	}
//-----------------------------------------------
//	readDelta
//
//-----------------------------------------------
void CCDBSynchronised::readDelta( NLMISC::TGameCycle gc, CBitMemStream& s, TCDBBank bank )
{
	nldebug("Update DB");

	if( _Database == 0 )
	{
		nlwarning("<CCDBSynchronised::readDelta> the database has not been initialized");
		return;
	}

	//displayBitStream2( f, f.getPosInBit(), f.getPosInBit() + 64 );
	uint16 propertyCount = 0;
	s.serial( propertyCount );

	if ( VerboseDatabase )
		nlinfo( "CDB: Reading delta (%hu changes)", propertyCount );
	NbDatabaseChanges += propertyCount;

	for( uint i=0; i!=propertyCount; ++i )
	{
		_Database->readAndMapDelta( gc, s, bank );
	}

	/*// Read "client only" property changes
	bool hasCOPropChanges;
	s.serialBit( hasCOPropChanges );
	if ( hasCOPropChanges )
	{
		uint32 nbCOPropChanges;
		s.serial( nbCOPropChanges, 4 );
		if ( nbCOPropChanges == 15 )
		{
			s.serial( nbCOPropChanges );
		}
		for ( uint i=0; i!=nbCOPropChanges; ++i )
		{
			string propName; //TEMP
			sint64 value; //TEMP
			s.serial( propName );
			s.serial( value );
			setProp( propName, value );
		}
	}*/

} // readDelta //
Beispiel #13
0
//-----------------------------------------------
//	readDelta
//-----------------------------------------------
void CCDBNodeLeaf::readDelta(TGameCycle gc, CBitMemStream & f )
{
	// If the property Type is valid.
	if(_Type > UNKNOWN && _Type < Nb_Prop_Type)
	{
		// Read the Property Value according to the Property Type.
		uint64 recvd = 0;
		uint bits;
		if (_Type == TEXT)
			bits = 32;
		else if (_Type <= I64)
			bits = _Type;
		else
			bits = _Type - 64;
		f.serial(recvd, bits);


		// if the DB update is older than last DB update, abort (but after the read!!)
		if(gc<_LastChangeGC)
			return;

		// bkup _oldProperty
		_oldProperty = _Property;

		// setup new one
		_Property = (sint64)recvd;

		// if signed
		if (! ((_Type == TEXT) || (_Type <= I64)))
		{
			// extend bit sign
			sint64 mask = (((sint64)1)<<bits)-(sint64)1;
			if( (_Property >> (bits-1))==1 )
			{
				_Property |= ~mask;
			}
		}
Beispiel #14
0
//---------------------------------------------------
// leagueJoinProposal :
//---------------------------------------------------
void CTeamManager::joinLeagueProposal( CCharacter * leader, const CEntityId &targetId)
{
	//check already done
	nlassert(leader);

	const NLMISC::CEntityId &leaderId = leader->getId();
	if (targetId == leaderId )
	{
		CCharacter::sendDynamicSystemMessage( leader->getId(),"INVALID_LEAGUE_TARGET" );
		return;
	}

	// get targeted player
	CCharacter *invitedPlayer = PlayerManager.getOnlineChar( targetId );
	if ( invitedPlayer == NULL )
	{
		CCharacter::sendDynamicSystemMessage( leader->getId(),"INVALID_LEAGUE_TARGET" );
		return;
	}
	
	// god player are forbidden to team
	if (leader->godMode() || invitedPlayer->godMode())
	{
		nlwarning("<CTeamManager joinLeagueProposal> Player %s invited %s, but at least on of them is god, forbidden", 
			leaderId.toString().c_str(),
			targetId.toString().c_str());
		CCharacter::sendDynamicSystemMessage( leader->getId(),"TEAM_GOD_FORBIDDEN" );
		return;
	}

	TInviteRetCode code = isLeagueInvitableBy(invitedPlayer,leader);
	if ( code == AlreadyInvited )
	{
		CCharacter::sendDynamicSystemMessage( leader->getId(),"LEAGUE_ALREADY_INVITED" );
		return;
	}
	else if ( code == AlreadyInLeague )
	{
		CTeam * team = getRealTeam( invitedPlayer->getTeamId() );
		CCharacter::sendDynamicSystemMessage( leader->getId(),"LEAGUE_ALREADY_IN_LEAGUE" );
		return;
	}
	else if ( code == NotLeader )
	{
		CTeam * team = getRealTeam( invitedPlayer->getTeamId() );
		joinLeagueProposal(leader, team->getLeader());
		return;
	}
	else if ( code == CantInvite )
	{
		CCharacter::sendDynamicSystemMessage( leader->getId(),"LEAGUE_INVITOR_NOT_LEADER" );
		return;
	}

	/// the invitor must not be in the ignore list of the target
	if(invitedPlayer->hasInIgnoreList(leaderId))
	{
		SM_STATIC_PARAMS_1( params1, STRING_MANAGER::player );
		params1[0].setEIdAIAlias( targetId, CAIAliasTranslator::getInstance()->getAIAlias( targetId) );
		// Use the standard "player declines your offer". Don't use specific message because
		// maybe not a good idea to inform a player that someone ignores him
		CCharacter::sendDynamicSystemMessage( leaderId, "TEAM_DECLINE", params1 );
		return;
	}

	//set the target's invitor
	invitedPlayer->setLeagueInvitor(leaderId);

	CEntityId msgTargetEId = targetId;
	
	//send the appropriate string to the client
	SM_STATIC_PARAMS_1(params, STRING_MANAGER::player);
	params[0].setEIdAIAlias( leaderId, CAIAliasTranslator::getInstance()->getAIAlias(leaderId) );
	uint32 txt = STRING_MANAGER::sendStringToClient(TheDataset.getDataSetRow(targetId), "LEAGUE_PROPOSAL", params );
	
	CMessage msgout( "IMPULSION_ID" );
	msgout.serial( const_cast<CEntityId&>(msgTargetEId) );
	CBitMemStream bms;
	nlverify ( GenericMsgManager.pushNameToStream( "PVP_CHALLENGE:INVITATION", bms) );
	bms.serial( txt );
	msgout.serialBufferWithSize((uint8*)bms.buffer(), bms.length());
	sendMessageViaMirror( NLNET::TServiceId(msgTargetEId.getDynamicId()), msgout );

	params[0].setEIdAIAlias( targetId, CAIAliasTranslator::getInstance()->getAIAlias( targetId ) );
	PHRASE_UTILITIES::sendDynamicSystemMessage(leader->getEntityRowId(), "LEAGUE_INVITE", params);
	
	leader->updateTarget();	
}
//-----------------------------------------------
//	getString
//
//-----------------------------------------------
ucstring CClientChatManager::getString( CBitMemStream& bms, ucstring& ucstr )
{

	// deal with parameters
	uint32 dynParamIdx = 0;
	bool dynParamSearch = true;
	char chTmp[1024];
	while( dynParamSearch )
	{
		// search if a parameter exists in the string
		sprintf(chTmp,"$%d",dynParamIdx);
		ucstring ucstrTmp( chTmp );
		ucstring::size_type idx = ucstr.find(ucstrTmp);

		// if there's a parameter in the string
		if( idx != ucstring::npos )
		{
			char c = (char)ucstr[idx+ucstrTmp.size()];
			switch( c )
			{
				// parameter is an entry in the dynamic database
				case 'e':
				{
					bool huff;
					bms.serialBit(huff);
					const ucstring dynStr("???");
					if( huff )
					{
						nldebug("<CClientChatManager::getString> receiving huffman dynamic parameter in static string");
//						#ifdef OLD_STRING_SYSTEM
//							_DynamicDB.decodeString( dynStr, bms );
//						#endif
					}
					else
					{
						//if( (sint32)bms.length()*8 - bms.getPosInBit() >= 32 )
						{
							uint32 nameIndex;
							bms.serial(nameIndex);
//							#ifdef OLD_STRING_SYSTEM
//								dynStr = _DynamicDB.getDynamicStringInfos(nameIndex)->Str;
//							#endif
						}
					}
					ucstr.replace( idx, ucstrTmp.size()+1, dynStr );
				}
				break;

				// parameter is a string
				case 's':
				{
					string dynStr;
					bms.serial( dynStr );
					ucstring ucDynStr(dynStr);
					ucstr.replace( idx, ucstrTmp.size()+1, ucDynStr );
				}
				break;

				// parameter is an unsigned integer
				case 'u':
				{
					uint32 nb;
					bms.serial( nb );
					ucstr.replace( idx, ucstrTmp.size()+1, ucstring(toString(nb)) );
				}
				break;
				/*
				case 'u':
				{
					uint i = idx + strTmp.size() + 1;
					string bitCountStr;
					while( isdigit(str[i]) )
					{
						bitCountStr += str[i];
						i++;
					}
					nlassert( !bitCountStr.empty() );
					uint32 bitCount;
					fromString(bitCountStr, bitCount);
					nlassert( bitCount <= 64 );
					uint64 nb;
					bms.serial( nb, bitCount );
					str.replace( idx, strTmp.size() + 1 + bitCountStr.size(), toString(nb) );
				}
				break;
				*/
				// parameter is a signed integer
				case 'i':
				{
					sint32 nb;
					bms.serial( nb );
					ucstr.replace( idx, ucstrTmp.size()+1, ucstring(toString(nb)) );
				}
				break;
				/*
				case 'i':
				{
					uint i = idx + strTmp.size() + 1;
					string bitCountStr;
					while( isdigit(str[i]) )
					{
						bitCountStr += str[i];
						i++;
					}
					nlassert( !bitCountStr.empty() );
					uint32 bitCount;
					fromString(bitCountStr, bitCount);
					nlassert( bitCount <= 64 );
					uint64 nb;
					bms.serial( nb, bitCount );
					str.replace( idx, strTmp.size() + 1 + bitCountStr.size(), toString(nb) );
				}
				break;
				*/

				// parameter is a float
				case 'f':
				{
					float nb;
					bms.serial( nb );
					ucstr.replace( idx, ucstrTmp.size()+1, ucstring(toString(nb)) );
				}
				break;

				// parameter type is unknown
				default :
				{
					nlwarning("<CClientChatManager::getString> The dynamic type %c is unknown",c);
				}
			}
			dynParamIdx++;
		}
		else
		{
			dynParamSearch = false;
		}
	};

	return ucstr;

} // getString //
//-----------------------------------------------
//	writeDelta
//
//-----------------------------------------------
bool CCDBSynchronised::writeDelta( CBitMemStream& s, uint32 maxBitSize )
{
	//if ( ! _DataStructRoot ) // nlwarning("<CCDBSynchronised::writeDelta> the database has not been initialized");
	//	return;

	// Test the changed property count and make room to store the number of property pushed (poked later)
	uint origChangedPropertyCount = getChangedPropertyCount();
	if ( origChangedPropertyCount == 0 )
		return false;
	uint bitposOfNbChanges = s.getPosInBit();
	uint32 dummy = 0;
	s.serial( dummy, CDBChangedPropertyCountBitSize ); // optimising s.reserveBits( CDBChangedPropertyCountBitSize )

	// Browse changes and write them
	uint32 bitsize = CDBChangedPropertyCountBitSize; // initialize with the size of the reserved bits for the number of changes
	TCDBDataIndex dataIndex;
	while ( ((dataIndex = _DataContainer.getFirstChanged()) != CDB_LAST_CHANGED)
			&& (bitsize < maxBitSize) )
	{
		// Retrieve the structure node corresponding to the index
		ICDBStructNode *node = CCDBStructBanks::instance()->getNodeFromDataIndex( _Bank, dataIndex );
		nlassert( node );

		if ( node->isAtomic() ) // counts for 1 change
		{
#ifdef NL_DEBUG
			nlassert( dynamic_cast<CCDBStructNodeBranch*>(node) ); // should not be leaf because the main tracker pushes the atom group index for atomic leaves
#endif
			// Build and push the binary atom id
			ICDBStructNode::CBinId binId;
			(static_cast<CCDBStructNodeBranch*>(node))->buildBinIdFromLeaf( binId );
			bitsize += binId.writeToBitMemStream( s );
			//nlinfo( "CDB/ATOM: Written bin id %s", binId.toString().c_str() );
			//_DataContainer.displayAtomChanges( node->getDataIndex() );

			// Make room to store the atom bitfield
			uint bitposOfAtomBitfield = s.getPosInBit();
			uint indexInAtom = 0;
			node->foreachLeafCall( cbNop, indexInAtom, NULL ); // count the number of siblings
			uint nbAtomElements = indexInAtom;
			s.reserveBits( nbAtomElements );
			bitsize += nbAtomElements;
			//nlinfo( "CDB/ATOM: Reserved %u bits (%d)", nbAtomElements, s.getPosInBit()-bitposOfAtomBitfield );

			// Browse the siblings of the atom node, and push the deltas for the properties marked as changes, updating the bitfield
			TPushAtomChangeStruct arg;
			arg.CdbSync = this;
			arg.BitSize = &bitsize;
			arg.S = &s;
			arg.AtomBitfield.resize( nbAtomElements );
			indexInAtom = 0;
			node->foreachLeafCall( cbPushDeltaOfLeafInAtomIfChanged, indexInAtom, (void*)&arg );
			
			// Fill the placeholder with the bitfield
			s.pokeBits( arg.AtomBitfield, bitposOfAtomBitfield );
			if ( VerboseDatabase )
			{
				nldebug( "CDB/ATOM: Bitfield: %s", arg.AtomBitfield.toString().c_str() );
			}

			// Pop the changes out of the tracker
			TCDBDataIndex atomGroupIndex = node->getDataIndex();
			TCDBDataIndex leafDataIndex;
			while ( (leafDataIndex = _DataContainer.popChangedIndexInAtom( atomGroupIndex )) != CDB_LAST_CHANGED );
		}
		else
		{
#ifdef NL_DEBUG
			nlassert( dynamic_cast<CCDBStructNodeLeaf*>(node) );
#endif

			// Push the binary property id
			bitsize += static_cast<CCDBStructNodeLeaf*>(node)->binLeafId().writeToBitMemStream( s );

			// Push the value
			pushDelta( s, static_cast<CCDBStructNodeLeaf*>(node), bitsize );
		}

		_DataContainer.popFirstChanged();
	}

	// Fill the placeholder with the number of changes
	uint32 nbChanges = origChangedPropertyCount - getChangedPropertyCount();
	s.poke( nbChanges, bitposOfNbChanges, CDBChangedPropertyCountBitSize );
	//s.displayStream( "writeDelta" );
	NbDatabaseChanges += nbChanges;

	// Check if all has been popped
	_DataContainer.quickCleanChanges();

	_NotSentYet = false;

#ifdef TRACE_SET_VALUE
	if ( VerboseDatabase )
		nldebug( "%u: CDB: Delta pushed (%u changes written, %u remaining)", CTickEventHandler::getGameCycle(), nbChanges, getChangedPropertyCount() );
#endif

	return true;
} // writeDelta //
Beispiel #17
0
//---------------------------------------------------
// CTeam addCharacter
//---------------------------------------------------
void CTeam::addCharacter(CCharacter *newCharacter)
{
	// check already done
	nlassert(newCharacter);

	// init new character DB
//	newCharacter->_PropertyDatabase.setProp( "USER:TEAM_MEMBER", 1 );
	CBankAccessor_PLR::getUSER().setTEAM_MEMBER(newCharacter->_PropertyDatabase, true);
//	newCharacter->_PropertyDatabase.setProp( "USER:TEAM_LEADER", 0 );
	CBankAccessor_PLR::getUSER().setTEAM_LEADER(newCharacter->_PropertyDatabase, false);
//	newCharacter->_PropertyDatabase.setProp( "GROUP:LEADER_INDEX", 0 );
	CBankAccessor_PLR::getGROUP().setLEADER_INDEX(newCharacter->_PropertyDatabase, 0);

	if ( _TeamMembers.size() == 1 )
	{
		_SuccessorId = newCharacter->getId();
//		newCharacter->_PropertyDatabase.setProp( "GROUP:SUCCESSOR_INDEX", -1  );
		CBankAccessor_PLR::getGROUP().setSUCCESSOR_INDEX(newCharacter->_PropertyDatabase, 0xf);
	}
	else
	{
//		newCharacter->_PropertyDatabase.setProp( "GROUP:SUCCESSOR_INDEX", 1  );
		CBankAccessor_PLR::getGROUP().setSUCCESSOR_INDEX(newCharacter->_PropertyDatabase, 1);
	}
	
	// update all member's DB
//	char buffer[256];
	uint position = (uint)_TeamMembers.size()-1;
	uint i =0;
	for (std::list<CEntityId>::const_iterator it = _TeamMembers.begin() ; it != _TeamMembers.end() ; ++it)
	{
		uint8 hp, sap, stamina;
		uint32 nameId;
		CCharacter* character = PlayerManager.getOnlineChar( (*it) );
		if (character != NULL)
		{
			// update the current character team slot
///\todo: can be done outside the loop
			if ( newCharacter->getPhysScores()._PhysicalScores[ SCORES::hit_points ].Max != 0)
				hp = (uint8) ( ( float(TeamMembersStatusMaxValue) * ( newCharacter->getPhysScores()._PhysicalScores[ SCORES::hit_points ].Current ) ) / ( newCharacter->getPhysScores()._PhysicalScores[ SCORES::hit_points ].Max ) );
			else
				hp = 0;

			if ( newCharacter->getPhysScores()._PhysicalScores[ SCORES::sap ].Max != 0)
				sap = (uint8) ( ( float(TeamMembersStatusMaxValue) * ( newCharacter->getPhysScores()._PhysicalScores[ SCORES::sap ].Current ) ) / ( newCharacter->getPhysScores()._PhysicalScores[ SCORES::sap ].Max ) );
			else
				sap = 0;

			if ( newCharacter->getPhysScores()._PhysicalScores[ SCORES::stamina ].Max != 0)
				stamina = (uint8) ( ( float(TeamMembersStatusMaxValue) * ( newCharacter->getPhysScores()._PhysicalScores[ SCORES::stamina ].Current ) ) / ( newCharacter->getPhysScores()._PhysicalScores[ SCORES::stamina ].Max ) );
			else
				stamina = 0;

			CMirrorPropValueRO<uint32> nameIndexValue1( TheDataset, newCharacter->getId(), "NameIndex" );
			nameId = nameIndexValue1();

			CBankAccessor_PLR::TGROUP::TArray &arrayItem = CBankAccessor_PLR::getGROUP().getArray(position);
//			sprintf(buffer, "GROUP:%d:HP",position );
//			character->_PropertyDatabase.setProp( buffer, hp );
			arrayItem.setHP(character->_PropertyDatabase, hp);

//			sprintf(buffer, "GROUP:%d:SAP",position );
//			character->_PropertyDatabase.setProp( buffer, sap );
			arrayItem.setSAP(character->_PropertyDatabase, sap);

//			sprintf(buffer, "GROUP:%d:STA",position );
//			character->_PropertyDatabase.setProp( buffer, stamina );
			arrayItem.setSTA(character->_PropertyDatabase, stamina);

//			sprintf(buffer, "GROUP:%d:NAME",position );
//			character->_PropertyDatabase.setProp( buffer, nameId );
			arrayItem.setNAME(character->_PropertyDatabase, nameId);

//			sprintf(buffer, "GROUP:%d:UID",position );
//			character->_PropertyDatabase.setProp( buffer, newCharacter->getEntityRowId().getCompressedIndex() );
			arrayItem.setUID(character->_PropertyDatabase, newCharacter->getEntityRowId().getCompressedIndex());

//			sprintf(buffer, "GROUP:%d:PRESENT",position );
//			character->_PropertyDatabase.setProp( buffer, (uint8)1 );
			arrayItem.setPRESENT(character->_PropertyDatabase, true);

			// update the new character team slot corresponding to character
			if ( character->getPhysScores()._PhysicalScores[ SCORES::hit_points ].Max != 0)
				hp = (uint8)  ( ( float(TeamMembersStatusMaxValue) * ( character->getPhysScores()._PhysicalScores[ SCORES::hit_points ].Current ) ) / ( character->getPhysScores()._PhysicalScores[ SCORES::hit_points ].Max ) );
			else
				hp = 0;
				
			if ( character->getPhysScores()._PhysicalScores[ SCORES::sap ].Max != 0)
				sap = (uint8) ( ( float(TeamMembersStatusMaxValue) * ( character->getPhysScores()._PhysicalScores[ SCORES::sap ].Current ) ) / ( character->getPhysScores()._PhysicalScores[ SCORES::sap ].Max ) );
			else
				sap = 0;

			if ( character->getPhysScores()._PhysicalScores[ SCORES::stamina ].Max != 0)
				stamina = (uint8) ( ( float(TeamMembersStatusMaxValue) * ( character->getPhysScores()._PhysicalScores[ SCORES::stamina ].Current ) ) / ( character->getPhysScores()._PhysicalScores[ SCORES::stamina ].Max ) );
			else
				stamina = 0;

			CMirrorPropValueRO<uint32> nameIndexValue2( TheDataset, character->getId(), "NameIndex" );
			nameId = nameIndexValue2();

			CBankAccessor_PLR::TGROUP::TArray &newArrayItem = CBankAccessor_PLR::getGROUP().getArray(i);
//			sprintf(buffer, "GROUP:%d:HP",i );
//			newCharacter->_PropertyDatabase.setProp( buffer, hp );
			newArrayItem.setHP(newCharacter->_PropertyDatabase, hp);
				
//			sprintf(buffer, "GROUP:%d:SAP",i );
//			newCharacter->_PropertyDatabase.setProp( buffer, sap );
			newArrayItem.setSAP(newCharacter->_PropertyDatabase, sap);

//			sprintf(buffer, "GROUP:%d:STA",i );
//			newCharacter->_PropertyDatabase.setProp( buffer, stamina );
			newArrayItem.setSTA(newCharacter->_PropertyDatabase, stamina);

//			sprintf(buffer, "GROUP:%d:NAME",i );
//			newCharacter->_PropertyDatabase.setProp( buffer, nameId );
			newArrayItem.setNAME(newCharacter->_PropertyDatabase, nameId);

//			sprintf(buffer, "GROUP:%d:UID",i );
//			newCharacter->_PropertyDatabase.setProp( buffer, character->getEntityRowId().getCompressedIndex() );
			newArrayItem.setUID(newCharacter->_PropertyDatabase, character->getEntityRowId().getCompressedIndex());

//			sprintf(buffer, "GROUP:%d:PRESENT",i );
//			newCharacter->_PropertyDatabase.setProp( buffer, (uint8)1 );
			newArrayItem.setPRESENT(newCharacter->_PropertyDatabase, true);
		}
		else
			nlwarning("<CTeam::addCharacter> Unknown character %s", (*it).toString().c_str() );
		++i;
	}


	// insert new member
	_TeamMembers.push_back( newCharacter->getId() );
	++_NbMembers;
	
	// set the character team
	newCharacter->setTeamId(_TeamId);

	// Add character to chat group
	TGroupId idGroupe = CHAT_GROUPS_IDS::getTeamChatGroupId(_TeamId);
	CMessage msgout("ADD_TO_GROUP");
	msgout.serial( idGroupe );
	msgout.serial( const_cast<CEntityId&> (newCharacter->getId()) );
	sendMessageViaMirror( "IOS", msgout );
	
	// send messages to members
	SM_STATIC_PARAMS_1(params, STRING_MANAGER::player);

	// to new member
	//CCharacter::sendMessageToClient(newCharacter->getId(),"OPS_JOIN_TEAM_E",_LeaderId);
	params[0].setEId(  _LeaderId );
	PHRASE_UTILITIES::sendDynamicSystemMessage(newCharacter->getEntityRowId(), "TEAM_YOU_JOIN", params);
	
	params[0].setEIdAIAlias( newCharacter->getId(), CAIAliasTranslator::getInstance()->getAIAlias( newCharacter->getId()) );

	set<CEntityId> exclude;
	exclude.insert( newCharacter->getId() );
	this->sendDynamicMessageToMembers("TEAM_ACCEPT",params,exclude);

	// update the reward share if needed
	if ( _RewardSharing )
	{
		CMessage msgout ("IMPULSION_ID");
		msgout.serial ((CEntityId&)(newCharacter->getId()));
		CBitMemStream bms;
		if (!GenericMsgManager.pushNameToStream ("TEAM:SHARE_OPEN", bms))
			nlstopex (("Missing TEAM:SHARE_OPEN in msg.xml"));
		msgout.serialBufferWithSize ((uint8*)bms.buffer(), bms.length());
		sendMessageViaMirror ( NLNET::TServiceId(newCharacter->getId().getDynamicId()), msgout);
		_RewardSharing->resetCandidates(this);
	}

	// update positions
	updateMembersPositions(true);

	/*TGroupId groupId = TGroupId idGroupe = CHAT_GROUPS_IDS::getTeamChatGroupId(_TeamId);
	string msgName = "OPS_JOIN_TEAM_ACCEPT_E";
	CMessage msggroup("STATIC_STRING");
	msggroup.serial( groupId );
	
	msggroup.serialCont( exclude);
	msggroup.serial( msgName );
	msggroup.serial( const_cast<CEntityId&>(newCharacter->getId()) );
	sendMessageViaMirror( "IOS", msggroup );
*/

	// tell progression system this player has joigned this team
	PROGRESSIONPVE::CCharacterProgressionPVE::getInstance()->playerJoinsTeam(newCharacter->getId(), _TeamId);
	PROGRESSIONPVP::CCharacterProgressionPVP::getInstance()->playerJoinsTeam(newCharacter, _TeamId);

	newCharacter->updateTargetingChars();
}// CTeam addCharacter
Beispiel #18
0
//---------------------------------------------------
// CTeam removeCharacter
//---------------------------------------------------
void CTeam::removeCharacter( CCharacter * player )
{
	// check already done
	nlassert(player);

	const CEntityId & charId = player->getId();
	uint16 teamId = player->getTeamId();

	// check if the character is in the team and remove him
	uint formerPos = 0;
	bool found = false;
	for ( std::list<NLMISC::CEntityId>::iterator it = _TeamMembers.begin(); it != _TeamMembers.end(); ++it )
	{
		if ( charId  == *it )
		{
			clearPlayerTeamDB(charId);
			_TeamMembers.erase(it);
			--_NbMembers;
			found = true;
			break;
		}
		formerPos++;
	}
	if ( !found )
	{
		nlwarning("<CTeam removeCharacter> charId %s not found in the team", charId.toString().c_str() );
		return;
	}
	if ( _RewardSharing )
	{
		CMessage msgout ("IMPULSION_ID");
		msgout.serial ((CEntityId&)(player->getId()));
		CBitMemStream bms;
		if (!GenericMsgManager.pushNameToStream ("TEAM:SHARE_CLOSE", bms))
			nlstopex (("Missing TEAM:SHARE_CLOSE in msg.xml"));
		msgout.serialBufferWithSize ((uint8*)bms.buffer(), bms.length());
		sendMessageViaMirror (NLNET::TServiceId(player->getId().getDynamicId()), msgout);
		_RewardSharing->resetCandidates(this);
	}

	///\todo give him a player team Id
	player->setTeamId( CTEAM::InvalidTeamId );
	player->updateTargetingChars();

	// tell progression system this player has been removed from his team
	PROGRESSIONPVE::CCharacterProgressionPVE::getInstance()->playerLeavesTeam(charId, _TeamId);
	PROGRESSIONPVP::CCharacterProgressionPVP::getInstance()->playerLeavesTeam(player, _TeamId);

	if ( player->getPVPInterface().isValid() )
		player->getPVPInterface().leavePVP( IPVP::QuitTeam );

	// check if the team must be removed
	if ( _NbMembers == 1 )
	{
		const uint size = (uint)_Missions.size();
		uint count = 0;
		while ( !_Missions.empty() && count < size )
		{
			_Missions[0]->onFailure(true);
			count++;
		}
		
		// send a message to the last team member
		PHRASE_UTILITIES::sendDynamicSystemMessage(TheDataset.getDataSetRow(_TeamMembers.front()), "TEAM_DISOLVED");
		
		// clear the player DB
		clearPlayerTeamDB( *_TeamMembers.begin() );
		CCharacter * lastPlayer = PlayerManager.getOnlineChar( *_TeamMembers.begin() );
		if ( lastPlayer )
			lastPlayer->setTeamId( CTEAM::InvalidTeamId );
		else
		{
			nlwarning("<CTeam removeCharacter> charId %s not found in the team", (*_TeamMembers.begin()).toString().c_str() );
			return;
		}

		// remove the team chat group
		TGroupId idGroupe = CHAT_GROUPS_IDS::getTeamChatGroupId(_TeamId);
		CMessage msgRemoveGroup("REMOVE_GROUP");
		msgRemoveGroup.serial( idGroupe );
		sendMessageViaMirror( "IOS", msgRemoveGroup );
	
		// release the team
		release();
		//remove the team from the manager
		TeamManager.removeTeam(teamId);

		// let the last player continue his escort mission (with a fake team) if he has one
		CMissionManager::getInstance()->updateEscortTeam( lastPlayer->getId() );

		return;
	}

	// if that was the leader, get another one
	else if ( _LeaderId == charId )
	{
		_LeaderId = _SuccessorId;
		_SuccessorId = CEntityId::Unknown;
		for (list<CEntityId>::const_iterator it = _TeamMembers.begin(); it != _TeamMembers.end(); ++it)
		{
			if ( (*it) != _LeaderId )
			{
				_SuccessorId = (*it );
				break;
			}
		}


		// switch dyn chat speaker
		CMissionManager::getInstance()->switchDynChatSpeaker(player,_LeaderId);

		// inform the new leader
		SM_STATIC_PARAMS_1(params1, STRING_MANAGER::player);		
		params1[0].setEId( charId );
		PHRASE_UTILITIES::sendDynamicSystemMessage(TheDataset.getDataSetRow(_LeaderId), "TEAM_YOU_NEW_LEADER", params1);

		// inform the group 
		SM_STATIC_PARAMS_2(params, STRING_MANAGER::player, STRING_MANAGER::player);		
		params[0].setEId( charId );
		params[1].setEId( _LeaderId );

		set<CEntityId> exclude;
		exclude.insert( _LeaderId );
		exclude.insert( charId );
		sendDynamicMessageToMembers("TEAM_NEW_LEADER", params, exclude);

		// update leader DB
		CCharacter *leader = PlayerManager.getOnlineChar( _LeaderId );
		if (leader)
		{
//			leader->_PropertyDatabase.setProp( "GROUP:LEADER_INDEX", -1 );
			CBankAccessor_PLR::getGROUP().setLEADER_INDEX(leader->_PropertyDatabase, 0xf);
//			leader->_PropertyDatabase.setProp( "GROUP:SUCCESSOR_INDEX", 0 );
			CBankAccessor_PLR::getGROUP().setSUCCESSOR_INDEX(leader->_PropertyDatabase, 0);
		}
		else
			nlwarning("<CTeam removeCharacter> invalid new leader %s", _LeaderId.toString().c_str() );
	}
	// if that was the successor, inform the new one
/*	else if ( formerPos == 1 && _NbMembers > 2)
	{
		list<CEntityId>::iterator itTmp = _TeamMembers.begin();
		++itTmp;
		const CEntityId & successorId = *(itTmp);
		CCharacter *successor = PlayerManager.getOnlineChar( successorId );
		if (successor)
		{
			successor->_PropertyDatabase.setProp( "GROUP:SUCCESSOR_INDEX", -1 );
		}
		else
			nlwarning("<CTeam removeCharacter> invalid new successor %s", successorId.toString().c_str() );

	}
*/
	else if ( _SuccessorId == charId )
	{
		for (list<CEntityId>::const_iterator it = _TeamMembers.begin(); it != _TeamMembers.end(); ++it)
		{
			if ( (*it) != _LeaderId )
			{
				_SuccessorId = (*it );
				CCharacter *successor = PlayerManager.getOnlineChar( _SuccessorId );
				if (successor)
				{
//					successor->_PropertyDatabase.setProp( "GROUP:SUCCESSOR_INDEX", -1 );
					CBankAccessor_PLR::getGROUP().setSUCCESSOR_INDEX(successor->_PropertyDatabase, 0xf);
				}
				break;
			}
		}
	}

	for (std::list<NLMISC::CEntityId>::iterator it = _TeamMembers.begin() ; it != _TeamMembers.end() ; ++it)
	{
		uint8 hp, sap, stamina;
		uint32 nameId;
		uint pos = 0;
//		char buffer[256];

		CCharacter * ch1 = PlayerManager.getOnlineChar( (*it) );
		///\todo log if nothing
		if (ch1)
		{
			for (std::list<NLMISC::CEntityId>::iterator it2 = _TeamMembers.begin() ; it2 != _TeamMembers.end() ; ++it2)
			{
				if ( (*it) == (*it2) )
					continue;	

				CBankAccessor_PLR::TGROUP::TArray &groupItem = CBankAccessor_PLR::getGROUP().getArray(pos);

				CCharacter * ch2 = PlayerManager.getOnlineChar( (*it2) );	
				if (ch2 != NULL)
				{
					// update new char for old char
					if ( ch2->getPhysScores()._PhysicalScores[ SCORES::hit_points ].Max != 0)
						hp = (uint8) ( ( float(TeamMembersStatusMaxValue) * ( ch2->getPhysScores()._PhysicalScores[ SCORES::hit_points ].Current ) ) / ( ch2->getPhysScores()._PhysicalScores[ SCORES::hit_points ].Max ) );
					else
						hp = 0;
					if ( ch2->getPhysScores()._PhysicalScores[ SCORES::sap ].Max != 0)
						sap = (uint8) ( ( float(TeamMembersStatusMaxValue) * ( ch2->getPhysScores()._PhysicalScores[ SCORES::sap ].Current ) ) / ( ch2->getPhysScores()._PhysicalScores[ SCORES::sap ].Max ) );
					else
						sap = 0;
					if ( ch2->getPhysScores()._PhysicalScores[ SCORES::stamina ].Max != 0)
						stamina = (uint8) ( ( float(TeamMembersStatusMaxValue) * ( ch2->getPhysScores()._PhysicalScores[ SCORES::stamina ].Current ) ) / ( ch2->getPhysScores()._PhysicalScores[ SCORES::stamina ].Max ) );
					else
						stamina = 0;
					
					CMirrorPropValueRO<uint32> nameIndexValue( TheDataset, ch2->getId(), "NameIndex" );
					nameId = nameIndexValue();
									
//					sprintf(buffer, "GROUP:%d:HP",pos );
//					ch1->_PropertyDatabase.setProp( buffer, hp );
					groupItem.setHP(ch1->_PropertyDatabase, hp);
					
//					sprintf(buffer, "GROUP:%d:SAP",pos );
//					ch1->_PropertyDatabase.setProp( buffer, sap );
					groupItem.setSAP(ch1->_PropertyDatabase, sap);
					
//					sprintf(buffer, "GROUP:%d:STA",pos );
//					ch1->_PropertyDatabase.setProp( buffer, stamina );
					groupItem.setSTA(ch1->_PropertyDatabase, stamina);
					
//					sprintf(buffer, "GROUP:%d:NAME",pos );
//					ch1->_PropertyDatabase.setProp( buffer, nameId );
					groupItem.setNAME(ch1->_PropertyDatabase, nameId);

//					sprintf(buffer, "GROUP:%d:UID",pos );
//					ch1->_PropertyDatabase.setProp( buffer, ch2->getEntityRowId().getCompressedIndex() );
					groupItem.setUID(ch1->_PropertyDatabase, ch2->getEntityRowId().getCompressedIndex());
					
//					sprintf(buffer, "GROUP:%d:PRESENT",pos );
//					ch1->_PropertyDatabase.setProp( buffer, (uint8)1 );
					groupItem.setPRESENT(ch1->_PropertyDatabase, true);
				}
				pos++;
			}

			CBankAccessor_PLR::TGROUP::TArray &groupItem = CBankAccessor_PLR::getGROUP().getArray(pos);

//			sprintf(buffer, "GROUP:%d:PRESENT",pos );
//			ch1->_PropertyDatabase.setProp( buffer, (uint8)0 );
			groupItem.setHP(ch1->_PropertyDatabase, 0);
//			sprintf(buffer, "GROUP:%d:NAME",pos );
//			ch1->_PropertyDatabase.setProp( buffer, (uint32)0 );
			groupItem.setNAME(ch1->_PropertyDatabase, 0);
//			sprintf(buffer, "GROUP:%d:UID",pos );
//			ch1->_PropertyDatabase.setProp( buffer, (uint32)CLFECOMMON::INVALID_CLIENT_DATASET_INDEX );
			groupItem.setUID(ch1->_PropertyDatabase, CLFECOMMON::INVALID_CLIENT_DATASET_INDEX);
		}
	}

	if ( _RewardSharing )
		_RewardSharing->resetCandidates(this);

	// update positions
	updateMembersPositions();

	// remove character from chat group
	TGroupId idGroupe = CHAT_GROUPS_IDS::getTeamChatGroupId(_TeamId);
	CMessage msgRemoveGroup("REMOVE_FROM_GROUP");
	msgRemoveGroup.serial( idGroupe );
	msgRemoveGroup.serial( const_cast<CEntityId&> ( charId ) );
	sendMessageViaMirror( "IOS", msgRemoveGroup );

}// CTeam removeCharacter
Beispiel #19
0
// ****************************************************************************
void CHugeListObs::update(ICDBNode * /* node */)
{
	nlassert((uint) _Category < ListTypeCount); // must call setListType
	// if botchat is not active, dont care with update
	if ((_Category == Trading) || (_Category == ItemForMissions) || (_Category == Missions))
	{
		if (!CBotChatManager::getInstance()->getCurrPage())
			return;
	}

	if (!init())
	{
		nlwarning("Can't do init");
		return;
	}
	// check if good session
	if (_Session->getValue16() != _CurrentSessionNb)
	{
		// msg from a previous session, dont care
		return;
	}
	TItemVect *itemPages = &_ItemsPages;
	uint pageID = (uint) _PageID->getValue16();
	if (pageID >= TRADE_MAX_NUM_PAGES) return; // bad page index
	if (pageID >= itemPages->size())
	{
		// expand items list
		itemPages->resize(pageID + 1);
	}
	// if 'has_next' flag is set, then ask server for more pages (if it is not a page update)
	if (_HasNext->getValueBool())
	{
		static const char *msgItemForMoney = "BOTCHAT:NEXT_PAGE_ITEM";
		static const char *msgItemForMission = "TRADE:NEXT_PAGE_MISSION_ITEM";
		static const char *msgAscensor = "GUILD:NEXT_ASCENSOR_PAGE";
		static const char *msgMissions;
		if(_MType==MISSION_DESC::ZCCharge)
			msgMissions= "BOTCHAT:NEXT_PAGE_DUTY";
		else
			msgMissions= "BOTCHAT:NEXT_PAGE_MISSION";

		const char* msgName;
		switch(_Category)
		{
			case Trading: msgName = msgItemForMoney; break;
			case ItemForMissions: msgName = msgItemForMission; break;
			case Ascensor: msgName = msgAscensor; break;
			case Missions: msgName = msgMissions; break;
			default:
				nlassert(0); // You have to provide message for ping-pong behavior
			break;
		}

		CBitMemStream out;
		if(GenericMsgHeaderMngr.pushNameToStream(msgName, out))
		{
			out.serial(_CurrentSessionNb);
			NetMngr.push(out);
			//nlinfo("impulseCallBack : %s %d sent", msgName, _CurrentSessionNb);
		}
		else
		{
			nlwarning("<CHandlerAcceptExchange::execute> unknown message name '%s'", msgName);
		}
	}
	else
	{
		_DownloadComplete = true;
	}

	CItemPage &page = (*itemPages)[pageID];
	uint k;
	// copy items page into temporary stuff
	for (k = 0; k < TRADE_PAGE_NUM_ITEMS; ++k)
	{
		switch(_Category)
		{
			case Trading:
			{
				page.Items[k].SlotType = (TRADE_SLOT_TYPE::TTradeSlotType) _Items[k].SlotType->getValue32();
				page.Items[k].Quality = (uint16) _Items[k].Quality->getValue16();
				page.Items[k].SheetIDOrSkill = (uint32) _Items[k].SheetIDOrSkill->getValue32();
				page.Items[k].Price = (uint32) _Items[k].Price->getValue32();
				page.Items[k].Weight= (uint16) _Items[k].Weight->getValue16();
				page.Items[k].NameId= (uint32) _Items[k].NameId->getValue32();
				page.Items[k].UserColor = _Items[k].UserColor->getValue32();
				page.Items[k].Enchant = _Items[k].Enchant->getValue32();
				page.Items[k].RMClassType = _Items[k].RMClassType->getValue32();
				page.Items[k].RMFaberStatType = _Items[k].RMFaberStatType->getValue32();
				page.Items[k].PrerequisitValid = _Items[k].PrerequisitValid->getValue32();
				page.Items[k].InfoVersion= (uint16) _Items[k].InfoVersion->getValue16();
				page.Items[k].Quantity= (uint16) _Items[k].Quantity->getValue16();
				page.Items[k].PriceRetire= (uint32) _Items[k].PriceRetire->getValue32();
				page.Items[k].ResaleTimeLeft= (uint32) _Items[k].ResaleTimeLeft->getValue32();
				page.Items[k].VendorNameId= (uint32) _Items[k].VendorNameId->getValue32();
				page.Items[k].FactionType= (uint32) _Items[k].FactionType->getValue32();
				page.Items[k].FactionPointPrice= (uint32) _Items[k].FactionPointPrice->getValue32();
				page.Items[k].SellerType= (uint32) _Items[k].SellerType->getValue32();
				// is the sheet is a phrase sheet, discard it if already known
				/*
				CEntitySheet *sheet = SheetMngr.get(CSheetId(page.Items[k].SheetIDOrSkill));
				if (sheet && sheet->Type == CEntitySheet::SPHRASE)
				{
					CSPhraseSheet *ps = (CSPhraseSheet *) sheet;
					CSPhraseCom pc;
					pc.Bricks.swap(ps->Bricks); // substitute brick in the object (for the time of comparison)
					if (CSPhraseManager::getInstance()->isPhraseKnown(pc))
					{
						page.Items[k].SheetIDOrSkill = 0; // already known, do not show in list
					}
					pc.Bricks.swap(ps->Bricks); // restore list of sheet
				}
				*/
			}
			break;
			case ItemForMissions:
				page.Items[k].SlotType = (TRADE_SLOT_TYPE::TTradeSlotType) _Items[k].SlotType->getValue32();
				page.Items[k].Quality = (uint16) _Items[k].Quality->getValue16();
				page.Items[k].SheetIDOrSkill = (uint32) _Items[k].SheetIDOrSkill->getValue32();
				page.Items[k].LogicTextID = (uint32) _Items[k].LogicTextID->getValue32();
				page.Items[k].DescTextID = (uint32) _Items[k].DescTextID->getValue32();
				page.Items[k].Weight= (uint16) _Items[k].Weight->getValue16();
				page.Items[k].NameId= (uint32) _Items[k].NameId->getValue32();
				page.Items[k].UserColor = _Items[k].UserColor->getValue32();
				page.Items[k].Enchant = _Items[k].Enchant->getValue32();
				page.Items[k].RMClassType = _Items[k].RMClassType->getValue32();
				page.Items[k].RMFaberStatType = _Items[k].RMFaberStatType->getValue32();
				page.Items[k].InfoVersion= (uint16) _Items[k].InfoVersion->getValue16();
			break;
			case Ascensor:
				page.Items[k].GuildIcon	= (uint64) _Items[k].GuildIcon->getValue64();
				page.Items[k].GuildName = (uint32) _Items[k].GuildName->getValue32();
			break;
			case Missions:
				page.Items[k].MissionText = (uint32) _Items[k].MissionText->getValue64();
				page.Items[k].MissionDetailText = (uint32) _Items[k].MissionDetailText->getValue64();
				page.Items[k].MissionIcon = (uint32) _Items[k].MissionIcon->getValue32();
				page.Items[k].MissionPreReqState = (uint32) _Items[k].MissionPreReqState->getValue32();
				break;
			default:
				nlassert(0); // You have to provide code for element that you want to be copied
			break;
		}
	}
	page.PageLoaded = true;
	page.PageVisible = false; // force update, even if shown before
	uint numLoadedPages;
	// In the display we want a contiguous set of items. Not For Trading, because of Resale
	if(_Category==Trading)
	{
		numLoadedPages= (uint)itemPages->size();
	}
	else
	{
		for(numLoadedPages = 0; numLoadedPages < itemPages->size(); ++numLoadedPages)
		{
			if ((*itemPages)[numLoadedPages].PageLoaded == false && numLoadedPages != pageID) break;
		}
	}
	//
	for(k = 0; k < numLoadedPages; ++k)
	{
		// still must test if page really loaded
		if ( (*itemPages)[k].PageLoaded && (*itemPages)[k].PageVisible == false)
		{
			updateUIItemPage(k);
			(*itemPages)[k].PageVisible = true;
		}
	}

	// **** Special RoleMaster Trading
	_PhraseClientFillNumPhrase= 0;
	_PhraseClientFillFlags= 0;
	_PhraseClientFillRace= 0;
	_PhraseClientFill= false;
	// clientFill must at least be possible
	if(_Category==Trading && _PhrasePriceUpdateAndMaybeClientFill && _RoleMasterFlagDB && _RoleMasterRaceDB)
	{
		_PhraseClientFillFlags= _RoleMasterFlagDB->getValue32();
		_PhraseClientFillRace= _RoleMasterRaceDB->getValue32();
		_PhraseClientFill= _PhraseClientFillFlags!=0;
		if(_PhraseClientFill)
		{
			clientGenerateAllPhrases();
			recomputeAllPhrasePrices();
		}
	}

}
Beispiel #20
0
//---------------------------------------------------
// joinProposal :
//---------------------------------------------------
void CTeamManager::joinProposal( CCharacter * leader, const CEntityId &targetId)
{
	//check already done
	nlassert(leader);

	const NLMISC::CEntityId &leaderId = leader->getId();
	if (targetId == leaderId )
	{
		nlwarning("<CTeamManager joinProposal> Player %s invited himself in his team, cancel", leaderId.toString().c_str() );
		return;
	}

	// get targeted player
	CCharacter *invitedPlayer = PlayerManager.getOnlineChar( targetId );
	if ( invitedPlayer == NULL )
	{
		CCharacter::sendDynamicSystemMessage( leader->getId(),"INVALID_LEAGUE_TARGET" );
		return;
	}
	
	// god player are forbidden to team
	if (leader->godMode() || invitedPlayer->godMode())
	{
		nlwarning("<CTeamManager joinProposal> Player %s invited %s, but at least on of them is god, forbidden", 
			leaderId.toString().c_str(),
			targetId.toString().c_str());
		CCharacter::sendDynamicSystemMessage( leader->getId(),"TEAM_GOD_FORBIDDEN" );
		return;
	}

	TInviteRetCode code = isInvitableBy(invitedPlayer,leader);
	if ( code == AlreadyInvited )
	{
		CCharacter::sendDynamicSystemMessage( leader->getId(),"TEAM_ALREADY_INVITED" );
		return;
	}
	else if ( code == AlreadyInTeam )
	{
		CCharacter::sendDynamicSystemMessage( leader->getId(),"TEAM_TARGET_ALREADY_IN_TEAM" );
		return;
	}
	else if ( code == CantInviteEnemy )
	{
		CCharacter::sendDynamicSystemMessage( leader->getId(),"TEAM_CANT_INVITE_ENEMY" );
		return;
	}
	else if ( code == CantInvite )
	{
		CCharacter::sendDynamicSystemMessage( leader->getId(),"TEAM_CANT_INVITE" );
		return;
	}

	/// the invitor must not be in the ignore list of the target
	if(invitedPlayer->hasInIgnoreList(leaderId))
	{
		SM_STATIC_PARAMS_1( params1, STRING_MANAGER::player );
		params1[0].setEIdAIAlias( targetId, CAIAliasTranslator::getInstance()->getAIAlias( targetId) );
		// Use the standard "player declines your offer". Don't use specific message because
		// maybe not a good idea to inform a player that someone ignores him
		CCharacter::sendDynamicSystemMessage( leaderId, "TEAM_DECLINE", params1 );
		return;
	}

	//set the target's invitor
	invitedPlayer->setTeamInvitor(leaderId);


	//send the appropriate string to the client
	SM_STATIC_PARAMS_1(params, STRING_MANAGER::player);
	params[0].setEIdAIAlias( leaderId, CAIAliasTranslator::getInstance()->getAIAlias( leaderId ) );
	uint32 strId = STRING_MANAGER::sendStringToClient(TheDataset.getDataSetRow(targetId),"TEAM_PROPOSAL", params);

	//send the invitation msg to the target, with the id of the built string
	CMessage msgout( "IMPULSION_ID" );
	CBitMemStream bms;
	CEntityId targetIdToSerial = targetId;
	msgout.serial( targetIdToSerial );
	if ( ! GenericMsgManager.pushNameToStream( "TEAM:INVITATION", bms) )
	{
		nlwarning("<CTeamManager joinProposal> Msg name TEAM:INVITATION not found");
		return;
	}

	bms.serial(strId);
	msgout.serialBufferWithSize((uint8*)bms.buffer(), bms.length());
	sendMessageViaMirror( NLNET::TServiceId(targetId.getDynamicId()), msgout );

//	TVectorParamCheck params;
//	params.resize(1);

	// inform the team leader	
//	params[0].Type = STRING_MANAGER::player;	
	params[0].setEIdAIAlias( targetId, CAIAliasTranslator::getInstance()->getAIAlias( targetId ) );
	PHRASE_UTILITIES::sendDynamicSystemMessage(leader->getEntityRowId(), "TEAM_INVITE", params);
	
	leader->updateTarget();
} // joinProposal //