Beispiel #1
0
void CGraphics_Threaded::DrawVisualObject(int VisualObjectIDX, float *pColor, char** pOffsets, unsigned int *IndicedVertexDrawNum, size_t NumIndicesOffet)
{
	if(NumIndicesOffet == 0) return;
	
	//add the VertexArrays and draw
	CCommandBuffer::SCommand_RenderVertexArray Cmd;
	Cmd.m_State = m_State;
	Cmd.m_IndicesDrawNum = NumIndicesOffet;
	Cmd.m_VisualObjectIDX = m_VertexArrayIndices[VisualObjectIDX];
	mem_copy(&Cmd.m_Color, pColor, sizeof(Cmd.m_Color));
	float ScreenZoomRatio = ScreenWidth() / (m_State.m_ScreenBR.x - m_State.m_ScreenTL.x);
	//the number of pixels we would skip in the fragment shader -- basically the LOD
	float LODFactor = (64.f / (32.f * ScreenZoomRatio));
	//log2 gives us the amount of halving the texture for mipmapping
	int LOD = (int)log2f(LODFactor);
	//5 because log2(1024/(2^5)) is 5 -- 2^5 = 32 which would mean 2 pixels per tile index
	if(LOD > 5) LOD = 5;
	if(LOD < 0) LOD = 0;
	Cmd.m_LOD = LOD;

	void *Data = m_pCommandBuffer->AllocData((sizeof(char*) + sizeof(unsigned int))*NumIndicesOffet);
	if(Data == 0x0)
	{
		// kick command buffer and try again
		KickCommandBuffer();
	
		void *Data = m_pCommandBuffer->AllocData((sizeof(char*) + sizeof(unsigned int))*NumIndicesOffet);
		if(Data == 0x0)
		{
			dbg_msg("graphics", "failed to allocate data for vertices");
			return;
		}
	}
	Cmd.m_pIndicesOffsets = (char**)Data;
	Cmd.m_pDrawCount = (unsigned int*)(((char*)Data) + (sizeof(char*)*NumIndicesOffet));
	
	// check if we have enough free memory in the commandbuffer
	if(!m_pCommandBuffer->AddCommand(Cmd))
	{
		// kick command buffer and try again
		KickCommandBuffer();

		Data = m_pCommandBuffer->AllocData((sizeof(char*) + sizeof(unsigned int))*NumIndicesOffet);
		if(Data == 0x0)
		{
			dbg_msg("graphics", "failed to allocate data for vertices");
			return;
		}
		Cmd.m_pIndicesOffsets = (char**)Data;
		Cmd.m_pDrawCount = (unsigned int*)(((char*)Data) + (sizeof(char*)*NumIndicesOffet));

		if(!m_pCommandBuffer->AddCommand(Cmd))
		{
			dbg_msg("graphics", "failed to allocate memory for render command");
			return;
		}
	}

	
	mem_copy(Cmd.m_pIndicesOffsets, pOffsets, sizeof(char*)*NumIndicesOffet);
	mem_copy(Cmd.m_pDrawCount, IndicedVertexDrawNum, sizeof(unsigned int)*NumIndicesOffet);
	
	//todo max indices group check!!
}
Beispiel #2
0
void CGameClient::OnNewSnapshot()
{
	m_NewTick = true;
	
	// clear out the invalid pointers
	mem_zero(&g_GameClient.m_Snap, sizeof(g_GameClient.m_Snap));
	m_Snap.m_LocalClientID = -1;

	// secure snapshot
	{
		int Num = Client()->SnapNumItems(IClient::SNAP_CURRENT);
		for(int Index = 0; Index < Num; Index++)
		{
			IClient::CSnapItem Item;
			void *pData = Client()->SnapGetItem(IClient::SNAP_CURRENT, Index, &Item);
			if(m_NetObjHandler.ValidateObj(Item.m_Type, pData, Item.m_DataSize) != 0)
			{
				if(g_Config.m_Debug)
				{
					char aBuf[256];
					str_format(aBuf, sizeof(aBuf), "invalidated index=%d type=%d (%s) size=%d id=%d", Index, Item.m_Type, m_NetObjHandler.GetObjName(Item.m_Type), Item.m_DataSize, Item.m_ID);
					Console()->Print(IConsole::OUTPUT_LEVEL_DEBUG, "game", aBuf);
				}
				Client()->SnapInvalidateItem(IClient::SNAP_CURRENT, Index);
			}
		}
	}
		
	ProcessEvents();

	if(g_Config.m_DbgStress)
	{
		if((Client()->GameTick()%100) == 0)
		{
			char aMessage[64];
			int MsgLen = rand()%(sizeof(aMessage)-1);
			for(int i = 0; i < MsgLen; i++)
				aMessage[i] = 'a'+(rand()%('z'-'a'));
			aMessage[MsgLen] = 0;
				
			CNetMsg_Cl_Say Msg;
			Msg.m_Team = rand()&1;
			Msg.m_pMessage = aMessage;
			Client()->SendPackMsg(&Msg, MSGFLAG_VITAL);
		}
	}

	// go trough all the items in the snapshot and gather the info we want
	{
		m_Snap.m_aTeamSize[TEAM_RED] = m_Snap.m_aTeamSize[TEAM_BLUE] = 0;
		
		int Num = Client()->SnapNumItems(IClient::SNAP_CURRENT);
		for(int i = 0; i < Num; i++)
		{
			IClient::CSnapItem Item;
			const void *pData = Client()->SnapGetItem(IClient::SNAP_CURRENT, i, &Item);

			if(Item.m_Type == NETOBJTYPE_CLIENTINFO)
			{
				const CNetObj_ClientInfo *pInfo = (const CNetObj_ClientInfo *)pData;
				int ClientID = Item.m_ID;
				IntsToStr(&pInfo->m_Name0, 4, m_aClients[ClientID].m_aName);
				IntsToStr(&pInfo->m_Clan0, 3, m_aClients[ClientID].m_aClan);
				m_aClients[ClientID].m_Country = GetCountryIndex(pInfo->m_Country);
				IntsToStr(&pInfo->m_Skin0, 6, m_aClients[ClientID].m_aSkinName);
				
				m_aClients[ClientID].m_UseCustomColor = pInfo->m_UseCustomColor;
				m_aClients[ClientID].m_ColorBody = pInfo->m_ColorBody;
				m_aClients[ClientID].m_ColorFeet = pInfo->m_ColorFeet;
				
				// prepare the info
				if(m_aClients[ClientID].m_aSkinName[0] == 'x' || m_aClients[ClientID].m_aSkinName[1] == '_')
					str_copy(m_aClients[ClientID].m_aSkinName, "default", 64);
					
				m_aClients[ClientID].m_SkinInfo.m_ColorBody = m_pSkins->GetColorV4(m_aClients[ClientID].m_ColorBody);
				m_aClients[ClientID].m_SkinInfo.m_ColorFeet = m_pSkins->GetColorV4(m_aClients[ClientID].m_ColorFeet);
				m_aClients[ClientID].m_SkinInfo.m_Size = 64;
				
				// find new skin
				m_aClients[ClientID].m_SkinID = g_GameClient.m_pSkins->Find(m_aClients[ClientID].m_aSkinName);
				if(m_aClients[ClientID].m_SkinID < 0)
				{
					m_aClients[ClientID].m_SkinID = g_GameClient.m_pSkins->Find("default");
					if(m_aClients[ClientID].m_SkinID < 0)
						m_aClients[ClientID].m_SkinID = 0;
				}
				
				if(m_aClients[ClientID].m_UseCustomColor)
					m_aClients[ClientID].m_SkinInfo.m_Texture = g_GameClient.m_pSkins->Get(m_aClients[ClientID].m_SkinID)->m_ColorTexture;
				else
				{
					m_aClients[ClientID].m_SkinInfo.m_Texture = g_GameClient.m_pSkins->Get(m_aClients[ClientID].m_SkinID)->m_OrgTexture;
					m_aClients[ClientID].m_SkinInfo.m_ColorBody = vec4(1,1,1,1);
					m_aClients[ClientID].m_SkinInfo.m_ColorFeet = vec4(1,1,1,1);
				}

				m_aClients[ClientID].UpdateRenderInfo();
				
			}
			else if(Item.m_Type == NETOBJTYPE_PLAYERINFO)
			{
				const CNetObj_PlayerInfo *pInfo = (const CNetObj_PlayerInfo *)pData;
				
				m_aClients[pInfo->m_ClientID].m_Team = pInfo->m_Team;
				m_aClients[pInfo->m_ClientID].m_Active = true;
				m_Snap.m_paPlayerInfos[pInfo->m_ClientID] = pInfo;
				m_Snap.m_NumPlayers++;
				
				if(pInfo->m_Local)
				{
					m_Snap.m_LocalClientID = Item.m_ID;
					m_Snap.m_pLocalInfo = pInfo;
					
					if(pInfo->m_Team == TEAM_SPECTATORS)
					{
						m_Snap.m_SpecInfo.m_Active = true;
						m_Snap.m_SpecInfo.m_SpectatorID = SPEC_FREEVIEW;
					}
				}
				
				// calculate team-balance
				if(pInfo->m_Team != TEAM_SPECTATORS)
					m_Snap.m_aTeamSize[pInfo->m_Team]++;
				
			}
			else if(Item.m_Type == NETOBJTYPE_CHARACTER)
			{
				const void *pOld = Client()->SnapFindItem(IClient::SNAP_PREV, NETOBJTYPE_CHARACTER, Item.m_ID);
				m_Snap.m_aCharacters[Item.m_ID].m_Cur = *((const CNetObj_Character *)pData);
				if(pOld)
				{
					m_Snap.m_aCharacters[Item.m_ID].m_Active = true;
					m_Snap.m_aCharacters[Item.m_ID].m_Prev = *((const CNetObj_Character *)pOld);

					if(m_Snap.m_aCharacters[Item.m_ID].m_Prev.m_Tick)
						Evolve(&m_Snap.m_aCharacters[Item.m_ID].m_Prev, Client()->PrevGameTick());
					if(m_Snap.m_aCharacters[Item.m_ID].m_Cur.m_Tick)
						Evolve(&m_Snap.m_aCharacters[Item.m_ID].m_Cur, Client()->GameTick());
				}
			}
			else if(Item.m_Type == NETOBJTYPE_SPECTATORINFO)
			{
				m_Snap.m_pSpectatorInfo = (const CNetObj_SpectatorInfo *)pData;
				m_Snap.m_pPrevSpectatorInfo = (const CNetObj_SpectatorInfo *)Client()->SnapFindItem(IClient::SNAP_PREV, NETOBJTYPE_SPECTATORINFO, Item.m_ID);

				m_Snap.m_SpecInfo.m_SpectatorID = m_Snap.m_pSpectatorInfo->m_SpectatorID;
			}
			else if(Item.m_Type == NETOBJTYPE_GAMEINFO)
			{
				static bool s_GameOver = 0;
				m_Snap.m_pGameInfoObj = (const CNetObj_GameInfo *)pData;
				if(!s_GameOver && m_Snap.m_pGameInfoObj->m_GameStateFlags&GAMESTATEFLAG_GAMEOVER)
					OnGameOver();
				else if(s_GameOver && !(m_Snap.m_pGameInfoObj->m_GameStateFlags&GAMESTATEFLAG_GAMEOVER))
					OnStartGame();
				s_GameOver = m_Snap.m_pGameInfoObj->m_GameStateFlags&GAMESTATEFLAG_GAMEOVER;
			}
			else if(Item.m_Type == NETOBJTYPE_GAMEDATA)
			{
				m_Snap.m_pGameDataObj = (const CNetObj_GameData *)pData;
				m_Snap.m_GameDataSnapID = Item.m_ID;
			}
			else if(Item.m_Type == NETOBJTYPE_FLAG)
				m_Snap.m_paFlags[Item.m_ID%2] = (const CNetObj_Flag *)pData;
		}
	}
	
	// setup local pointers
	if(m_Snap.m_LocalClientID >= 0)
	{
		CSnapState::CCharacterInfo *c = &m_Snap.m_aCharacters[m_Snap.m_LocalClientID];
		if(c->m_Active)
		{
			m_Snap.m_pLocalCharacter = &c->m_Cur;
			m_Snap.m_pLocalPrevCharacter = &c->m_Prev;
			m_LocalCharacterPos = vec2(m_Snap.m_pLocalCharacter->m_X, m_Snap.m_pLocalCharacter->m_Y);
		}
		else if(Client()->SnapFindItem(IClient::SNAP_PREV, NETOBJTYPE_CHARACTER, m_Snap.m_LocalClientID))
		{
			// player died
			m_pControls->OnPlayerDeath();
		}
	}
	else
	{
		m_Snap.m_SpecInfo.m_Active = true;
		if(Client()->State() == IClient::STATE_DEMOPLAYBACK && DemoPlayer()->GetDemoType() == IDemoPlayer::DEMOTYPE_SERVER &&
			m_DemoSpecID != SPEC_FREEVIEW && m_Snap.m_aCharacters[m_DemoSpecID].m_Active)
			m_Snap.m_SpecInfo.m_SpectatorID = m_DemoSpecID;
		else
			m_Snap.m_SpecInfo.m_SpectatorID = SPEC_FREEVIEW;
	}

	// clear out unneeded client data
	for(int i = 0; i < MAX_CLIENTS; ++i)
	{
		if(!m_Snap.m_paPlayerInfos[i] && m_aClients[i].m_Active)
			m_aClients[i].Reset();
	}

	// update friend state
	for(int i = 0; i < MAX_CLIENTS; ++i)
	{
		if(i == m_Snap.m_LocalClientID || !m_Snap.m_paPlayerInfos[i] || !Friends()->IsFriend(m_aClients[i].m_aName, m_aClients[i].m_aClan))
			m_aClients[i].m_Friend = false;
		else
			m_aClients[i].m_Friend = true;
	}

	// sort player infos by score
	mem_copy(m_Snap.m_paInfoByScore, m_Snap.m_paPlayerInfos, sizeof(m_Snap.m_paInfoByScore));
	for(int k = 0; k < MAX_CLIENTS-1; k++) // ffs, bubblesort
	{
		for(int i = 0; i < MAX_CLIENTS-k-1; i++)
		{
			if(m_Snap.m_paInfoByScore[i+1] && (!m_Snap.m_paInfoByScore[i] || m_Snap.m_paInfoByScore[i]->m_Score < m_Snap.m_paInfoByScore[i+1]->m_Score))
			{
				const CNetObj_PlayerInfo *pTmp = m_Snap.m_paInfoByScore[i];
				m_Snap.m_paInfoByScore[i] = m_Snap.m_paInfoByScore[i+1];
				m_Snap.m_paInfoByScore[i+1] = pTmp;
			}
		}
	}
	
	CTuningParams StandardTuning;
	CServerInfo CurrentServerInfo;
	Client()->GetServerInfo(&CurrentServerInfo);
	if(CurrentServerInfo.m_aGameType[0] != '0')
	{
		if(str_comp(CurrentServerInfo.m_aGameType, "DM") != 0 && str_comp(CurrentServerInfo.m_aGameType, "TDM") != 0 && str_comp(CurrentServerInfo.m_aGameType, "CTF") != 0)
			m_ServerMode = SERVERMODE_MOD;
		else if(mem_comp(&StandardTuning, &m_Tuning, sizeof(CTuningParams)) == 0)
			m_ServerMode = SERVERMODE_PURE;
		else
			m_ServerMode = SERVERMODE_PUREMOD;
	}

}
Beispiel #3
0
void CGraphics_Threaded::FlushVertices()
{
	if(m_NumVertices == 0)
		return;

	int NumVerts = m_NumVertices;
	m_NumVertices = 0;

	CCommandBuffer::SCommand_Render Cmd;
	Cmd.m_State = m_State;

	if(m_Drawing == DRAWING_QUADS)
	{
		if(g_Config.m_GfxQuadAsTriangle)
		{
			Cmd.m_PrimType = CCommandBuffer::PRIMTYPE_TRIANGLES;
			Cmd.m_PrimCount = NumVerts/3;
		}
		else
		{
			Cmd.m_PrimType = CCommandBuffer::PRIMTYPE_QUADS;
			Cmd.m_PrimCount = NumVerts/4;
		}
	}
	else if(m_Drawing == DRAWING_LINES)
	{
		Cmd.m_PrimType = CCommandBuffer::PRIMTYPE_LINES;
		Cmd.m_PrimCount = NumVerts/2;
	}
	else
		return;

	Cmd.m_pVertices = (CCommandBuffer::SVertex *)m_pCommandBuffer->AllocData(sizeof(CCommandBuffer::SVertex)*NumVerts);
	if(Cmd.m_pVertices == 0x0)
	{
		// kick command buffer and try again
		KickCommandBuffer();

		Cmd.m_pVertices = (CCommandBuffer::SVertex *)m_pCommandBuffer->AllocData(sizeof(CCommandBuffer::SVertex)*NumVerts);
		if(Cmd.m_pVertices == 0x0)
		{
			dbg_msg("graphics", "failed to allocate data for vertices");
			return;
		}
	}

	// check if we have enough free memory in the commandbuffer
	if(!m_pCommandBuffer->AddCommand(Cmd))
	{
		// kick command buffer and try again
		KickCommandBuffer();

		Cmd.m_pVertices = (CCommandBuffer::SVertex *)m_pCommandBuffer->AllocData(sizeof(CCommandBuffer::SVertex)*NumVerts);
		if(Cmd.m_pVertices == 0x0)
		{
			dbg_msg("graphics", "failed to allocate data for vertices");
			return;
		}

		if(!m_pCommandBuffer->AddCommand(Cmd))
		{
			dbg_msg("graphics", "failed to allocate memory for render command");
			return;
		}
	}

	mem_copy(Cmd.m_pVertices, m_aVertices, sizeof(CCommandBuffer::SVertex)*NumVerts);
}
Beispiel #4
0
int CEditorMap::Load(class IStorage *pStorage, const char *pFileName, int StorageType)
{
    CDataFileReader DataFile;
    //DATAFILE *df = datafile_load(filename);
    if(!DataFile.Open(pStorage, pFileName, StorageType))
        return 0;

    Clean();

    // check version
    CMapItemVersion *pItem = (CMapItemVersion *)DataFile.FindItem(MAPITEMTYPE_VERSION, 0);
    if(!pItem)
    {
        // import old map
        /*MAP old_mapstuff;
        editor->reset();
        editor_load_old(df, this);
        */
        return 0;
    }
    else if(pItem->m_Version == 1)
    {
        //editor.reset(false);

        // load map info
        {
            CMapItemInfo *pItem = (CMapItemInfo *)DataFile.FindItem(MAPITEMTYPE_INFO, 0);
            if(pItem && pItem->m_Version == 1)
            {
                if(pItem->m_Author > -1)
                    str_copy(m_MapInfo.m_aAuthor, (char *)DataFile.GetData(pItem->m_Author), sizeof(m_MapInfo.m_aAuthor));
                if(pItem->m_MapVersion > -1)
                    str_copy(m_MapInfo.m_aVersion, (char *)DataFile.GetData(pItem->m_MapVersion), sizeof(m_MapInfo.m_aVersion));
                if(pItem->m_Credits > -1)
                    str_copy(m_MapInfo.m_aCredits, (char *)DataFile.GetData(pItem->m_Credits), sizeof(m_MapInfo.m_aCredits));
                if(pItem->m_License > -1)
                    str_copy(m_MapInfo.m_aLicense, (char *)DataFile.GetData(pItem->m_License), sizeof(m_MapInfo.m_aLicense));
            }
        }

        // load images
        {
            int Start, Num;
            DataFile.GetType( MAPITEMTYPE_IMAGE, &Start, &Num);
            for(int i = 0; i < Num; i++)
            {
                CMapItemImage *pItem = (CMapItemImage *)DataFile.GetItem(Start+i, 0, 0);
                char *pName = (char *)DataFile.GetData(pItem->m_ImageName);

                // copy base info
                CEditorImage *pImg = new CEditorImage(m_pEditor);
                pImg->m_External = pItem->m_External;

                if(pItem->m_External)
                {
                    char aBuf[256];
                    str_format(aBuf, sizeof(aBuf),"mapres/%s.png", pName);

                    // load external
                    CEditorImage ImgInfo(m_pEditor);
                    if(m_pEditor->Graphics()->LoadPNG(&ImgInfo, aBuf, IStorage::TYPE_ALL))
                    {
                        *pImg = ImgInfo;
                        pImg->m_TexID = m_pEditor->Graphics()->LoadTextureRaw(ImgInfo.m_Width, ImgInfo.m_Height, ImgInfo.m_Format, ImgInfo.m_pData, CImageInfo::FORMAT_AUTO, 0);
                        ImgInfo.m_pData = 0;
                        pImg->m_External = 1;
                    }
                }
                else
                {
                    pImg->m_Width = pItem->m_Width;
                    pImg->m_Height = pItem->m_Height;
                    pImg->m_Format = CImageInfo::FORMAT_RGBA;

                    // copy image data
                    void *pData = DataFile.GetData(pItem->m_ImageData);
                    pImg->m_pData = mem_alloc(pImg->m_Width*pImg->m_Height*4, 1);
                    mem_copy(pImg->m_pData, pData, pImg->m_Width*pImg->m_Height*4);
                    pImg->m_TexID = m_pEditor->Graphics()->LoadTextureRaw(pImg->m_Width, pImg->m_Height, pImg->m_Format, pImg->m_pData, CImageInfo::FORMAT_AUTO, 0);
                }

                // copy image name
                if(pName)
                    str_copy(pImg->m_aName, pName, 128);

                // load auto mapper file
                pImg->m_AutoMapper.Load(pImg->m_aName);

                m_lImages.add(pImg);

                // unload image
                DataFile.UnloadData(pItem->m_ImageData);
                DataFile.UnloadData(pItem->m_ImageName);
            }
        }

        // load groups
        {
            int LayersStart, LayersNum;
            DataFile.GetType(MAPITEMTYPE_LAYER, &LayersStart, &LayersNum);

            int Start, Num;
            DataFile.GetType(MAPITEMTYPE_GROUP, &Start, &Num);
            for(int g = 0; g < Num; g++)
            {
                CMapItemGroup *pGItem = (CMapItemGroup *)DataFile.GetItem(Start+g, 0, 0);

                if(pGItem->m_Version < 1 || pGItem->m_Version > CMapItemGroup::CURRENT_VERSION)
                    continue;

                CLayerGroup *pGroup = NewGroup();
                pGroup->m_ParallaxX = pGItem->m_ParallaxX;
                pGroup->m_ParallaxY = pGItem->m_ParallaxY;
                pGroup->m_OffsetX = pGItem->m_OffsetX;
                pGroup->m_OffsetY = pGItem->m_OffsetY;

                if(pGItem->m_Version >= 2)
                {
                    pGroup->m_UseClipping = pGItem->m_UseClipping;
                    pGroup->m_ClipX = pGItem->m_ClipX;
                    pGroup->m_ClipY = pGItem->m_ClipY;
                    pGroup->m_ClipW = pGItem->m_ClipW;
                    pGroup->m_ClipH = pGItem->m_ClipH;
                }

                // load group name
                if(pGItem->m_Version >= 3)
                    IntsToStr(pGItem->m_aName, sizeof(pGroup->m_aName)/sizeof(int), pGroup->m_aName);

                for(int l = 0; l < pGItem->m_NumLayers; l++)
                {
                    CLayer *pLayer = 0;
                    CMapItemLayer *pLayerItem = (CMapItemLayer *)DataFile.GetItem(LayersStart+pGItem->m_StartLayer+l, 0, 0);
                    if(!pLayerItem)
                        continue;

                    if(pLayerItem->m_Type == LAYERTYPE_TILES)
                    {
                        CMapItemLayerTilemap *pTilemapItem = (CMapItemLayerTilemap *)pLayerItem;
                        CLayerTiles *pTiles = 0;

                        if(pTilemapItem->m_Flags&TILESLAYERFLAG_PHYSICS)
                        {
                            pTiles = new CLayerPhysics(pTilemapItem->m_Width, pTilemapItem->m_Height);
                            MakePhysicsLayer(pTiles);
                            MakeGameGroup(pGroup);
                        }
                        else if(pTilemapItem->m_Flags&TILESLAYERFLAG_ZONE)
                        {
                            pTiles = new CLayerZone(pTilemapItem->m_Width, pTilemapItem->m_Height);
                            MakeZoneLayer(pTiles);
                            MakeGameGroup(pGroup);
                        }
                        else if(pTilemapItem->m_Flags&TILESLAYERFLAG_ENTITY)
                        {
                            pTiles = new CLayerEntity(pTilemapItem->m_Width, pTilemapItem->m_Height);
                            MakeEntityLayer(pTiles);
                            MakeGameGroup(pGroup);
                        }
                        else
                        {
                            pTiles = new CLayerTiles(pTilemapItem->m_Width, pTilemapItem->m_Height);
                            pTiles->m_pEditor = m_pEditor;
                            pTiles->m_Color = pTilemapItem->m_Color;
                            pTiles->m_ColorEnv = pTilemapItem->m_ColorEnv;
                            pTiles->m_ColorEnvOffset = pTilemapItem->m_ColorEnvOffset;
                        }

                        pLayer = pTiles;

                        pGroup->AddLayer(pTiles);
                        void *pData = DataFile.GetData(pTilemapItem->m_Data);
                        pTiles->m_Image = pTilemapItem->m_Image;
                        pTiles->m_GameFlags = pTilemapItem->m_Flags;

                        // load layer name
                        if(pTilemapItem->m_Version >= 3)
                        {
                            if(pTilemapItem->m_Flags&TILESLAYERFLAG_PHYSICS)
                                str_copy(pTiles->m_aName, "Physics", sizeof(pTiles->m_aName));
                            else if(pTilemapItem->m_Flags&TILESLAYERFLAG_ZONE)
                                str_copy(pTiles->m_aName, "Zones", sizeof(pTiles->m_aName));
                            else if(pTilemapItem->m_Flags&TILESLAYERFLAG_ENTITY)
                                str_copy(pTiles->m_aName, "Entities", sizeof(pTiles->m_aName));
                            else
                                IntsToStr(pTilemapItem->m_aName, sizeof(pTiles->m_aName)/sizeof(int), pTiles->m_aName);
                        }
                        mem_copy(pTiles->m_pTiles, pData, pTiles->m_Width*pTiles->m_Height*sizeof(CTile));

                        if((pTiles->m_GameFlags & TILESLAYERFLAG_PHYSICS) && pTilemapItem->m_Version == MakeVersion(1, *pTilemapItem))
                        {
                            for(int i = 0; i < pTiles->m_Width*pTiles->m_Height; i++)
                            {
                                if(pTiles->m_pTiles[i].m_Index)
                                    pTiles->m_pTiles[i].m_Index += ENTITY_OFFSET;
                            }
                        }

                        DataFile.UnloadData(pTilemapItem->m_Data);
                    }
                    else if(pLayerItem->m_Type == LAYERTYPE_QUADS)
                    {
                        CMapItemLayerQuads *pQuadsItem = (CMapItemLayerQuads *)pLayerItem;
                        CLayerQuads *pQuads = new CLayerQuads;
                        pQuads->m_pEditor = m_pEditor;
                        pLayer = pQuads;
                        pQuads->m_Image = pQuadsItem->m_Image;
                        if(pQuads->m_Image < -1 || pQuads->m_Image >= m_lImages.size())
                            pQuads->m_Image = -1;

                        // load layer name
                        if(pQuadsItem->m_Version >= 2)
                            IntsToStr(pQuadsItem->m_aName, sizeof(pQuads->m_aName)/sizeof(int), pQuads->m_aName);

                        void *pData = DataFile.GetDataSwapped(pQuadsItem->m_Data);
                        pGroup->AddLayer(pQuads);
                        pQuads->m_lQuads.set_size(pQuadsItem->m_NumQuads);
                        mem_copy(pQuads->m_lQuads.base_ptr(), pData, sizeof(CQuad)*pQuadsItem->m_NumQuads);
                        DataFile.UnloadData(pQuadsItem->m_Data);
                    }

                    if(pLayer)
                        pLayer->m_Flags = pLayerItem->m_Flags;
                }
            }
        }

        if(!m_pGameGroup)
        {
            MakeGameGroup(NewGroup());
        }
        if(!m_pPhysicsLayer)
        {
            MakePhysicsLayer(new CLayerPhysics(50, 50));
            m_pGameGroup->AddLayer(m_pPhysicsLayer);
        }
        if(!m_pEntityLayer)
        {
            MakeEntityLayer(new CLayerEntity(50, 50));
            m_pGameGroup->AddLayer(m_pEntityLayer);
        }
        if(!m_pZoneLayer)
        {
            MakeZoneLayer(new CLayerZone(50, 50));
            m_pGameGroup->AddLayer(m_pZoneLayer);
        }

        // load envelopes
        {
            CEnvPoint *pPoints = 0;

            {
                int Start, Num;
                DataFile.GetType(MAPITEMTYPE_ENVPOINTS, &Start, &Num);
                if(Num)
                    pPoints = (CEnvPoint *)DataFile.GetItem(Start, 0, 0);
            }

            int Start, Num;
            DataFile.GetType(MAPITEMTYPE_ENVELOPE, &Start, &Num);
            for(int e = 0; e < Num; e++)
            {
                CMapItemEnvelope *pItem = (CMapItemEnvelope *)DataFile.GetItem(Start+e, 0, 0);
                CEnvelope *pEnv = new CEnvelope(pItem->m_Channels);
                pEnv->m_lPoints.set_size(pItem->m_NumPoints);
                mem_copy(pEnv->m_lPoints.base_ptr(), &pPoints[pItem->m_StartPoint], sizeof(CEnvPoint)*pItem->m_NumPoints);
                if(pItem->m_aName[0] != -1)	// compatibility with old maps
                    IntsToStr(pItem->m_aName, sizeof(pItem->m_aName)/sizeof(int), pEnv->m_aName);
                m_lEnvelopes.add(pEnv);
                if(pItem->m_Version >= 2)
                    pEnv->m_Synchronized = pItem->m_Synchronized;
            }
        }
    }
    else
        return 0;

    return 1;
}
Beispiel #5
0
int CControls::SnapInput(int *pData)
{
	static int64 LastSendTime = 0;
	bool Send = false;

	// update player state
	if(m_pClient->m_pChat->IsActive())
		m_InputData.m_PlayerFlags = PLAYERFLAG_CHATTING;
	else
		m_InputData.m_PlayerFlags = 0;

	if(m_pClient->m_pScoreboard->Active())
		m_InputData.m_PlayerFlags |= PLAYERFLAG_SCOREBOARD;

	if(m_LastData.m_PlayerFlags != m_InputData.m_PlayerFlags)
		Send = true;

	m_LastData.m_PlayerFlags = m_InputData.m_PlayerFlags;

	// we freeze the input if chat or menu is activated
	if(m_pClient->m_pChat->IsActive() || m_pClient->m_pMenus->IsActive())
	{
		OnReset();

		mem_copy(pData, &m_InputData, sizeof(m_InputData));

		// send once a second just to be sure
		if(time_get() > LastSendTime + time_freq())
			Send = true;
	}
	else
	{

		m_InputData.m_TargetX = (int)m_MousePos.x;
		m_InputData.m_TargetY = (int)m_MousePos.y;
		if(!m_InputData.m_TargetX && !m_InputData.m_TargetY)
		{
			m_InputData.m_TargetX = 1;
			m_MousePos.x = 1;
		}

		// set direction
		m_InputData.m_Direction = 0;
		if(m_InputDirectionLeft && !m_InputDirectionRight)
			m_InputData.m_Direction = -1;
		if(!m_InputDirectionLeft && m_InputDirectionRight)
			m_InputData.m_Direction = 1;

		// stress testing
		if(g_Config.m_DbgStress)
		{
			float t = Client()->LocalTime();
			mem_zero(&m_InputData, sizeof(m_InputData));

			m_InputData.m_Direction = ((int)t/2)%3-1;
			m_InputData.m_Jump = ((int)t)&1;
			m_InputData.m_Fire = ((int)(t*10));
			m_InputData.m_Hook = ((int)(t*2))&1;
			m_InputData.m_WantedWeapon = ((int)t)%NUM_WEAPONS;
			m_InputData.m_TargetX = (int)(sinf(t*3)*100.0f);
			m_InputData.m_TargetY = (int)(cosf(t*3)*100.0f);
		}

		// check if we need to send input
		if(m_InputData.m_Direction != m_LastData.m_Direction) Send = true;
		else if(m_InputData.m_Jump != m_LastData.m_Jump) Send = true;
		else if(m_InputData.m_Fire != m_LastData.m_Fire) Send = true;
		else if(m_InputData.m_Hook != m_LastData.m_Hook) Send = true;
		else if(m_InputData.m_WantedWeapon != m_LastData.m_WantedWeapon) Send = true;
		else if(m_InputData.m_NextWeapon != m_LastData.m_NextWeapon) Send = true;
		else if(m_InputData.m_PrevWeapon != m_LastData.m_PrevWeapon) Send = true;

		// send at at least 10hz
		if(time_get() > LastSendTime + time_freq()/25)
			Send = true;
	}

	// copy and return size
	m_LastData = m_InputData;

	if(!Send)
		return 0;

	LastSendTime = time_get();
	mem_copy(pData, &m_InputData, sizeof(m_InputData));
	return sizeof(m_InputData);
}
Beispiel #6
0
static int glnvg__convertPaint(GLNVGcontext* gl, GLNVGfragUniforms* frag, NVGpaint* paint,
    NVGscissor* scissor, float width, float fringe, float strokeThr)
{
    PROFILER_CPU_TIMESLICE("NVG backend convertPaint");

    GLNVGtexture* tex = NULL;
    float invxform[6];

    mem_zero(frag);

    frag->innerCol = glnvg__premulColor(paint->innerColor);
    frag->outerCol = glnvg__premulColor(paint->outerColor);

    if (scissor->extent[0] < -0.5f || scissor->extent[1] < -0.5f) {
        mem_zero(frag->scissorMat);
        frag->scissorExt[0] = 1.0f;
        frag->scissorExt[1] = 1.0f;
        frag->scissorScale[0] = 1.0f;
        frag->scissorScale[1] = 1.0f;
    } else {
        nvgTransformInverse(invxform, scissor->xform);
        glnvg__xformToMat3x4(frag->scissorMat, invxform);
        frag->scissorExt[0] = scissor->extent[0];
        frag->scissorExt[1] = scissor->extent[1];
        frag->scissorScale[0] = ml::sqrt(scissor->xform[0] * scissor->xform[0] + scissor->xform[2] * scissor->xform[2]) / fringe;
        frag->scissorScale[1] = ml::sqrt(scissor->xform[1] * scissor->xform[1] + scissor->xform[3] * scissor->xform[3]) / fringe;
    }

    mem_copy(frag->extent, paint->extent, sizeof(frag->extent));
    frag->strokeMult = (width*0.5f + fringe*0.5f) / fringe;
    frag->strokeThr = strokeThr;

    if (paint->image != 0) {
        tex = glnvg__findTexture(gl, paint->image);
        if (tex == NULL) return 0;
        if ((tex->flags & NVGL_TEXTURE_FLIP_Y) != 0) {
            float flipped[6];
            nvgTransformScale(flipped, 1.0f, -1.0f);
            nvgTransformMultiply(flipped, paint->xform);
            nvgTransformInverse(invxform, flipped);
        } else {
            nvgTransformInverse(invxform, paint->xform);
        }
        frag->type = NSVG_SHADER_FILLIMG;

        if (tex->type == NVG_TEXTURE_RGBA)
            frag->texType = (tex->flags & NVGL_TEXTURE_PREMULTIPLIED) ? 0 : 1;
        else
            frag->texType = 2;
        //		printf("frag->texType = %d\n", frag->texType);
    } else {
        frag->type = NSVG_SHADER_FILLGRAD;
        frag->radius = paint->radius;
        frag->feather = paint->feather;
        nvgTransformInverse(invxform, paint->xform);
    }

    glnvg__xformToMat3x4(frag->paintMat, invxform);

    return 1;
}
Beispiel #7
0
static void glnvg__renderStroke(void* uptr, NVGpaint* paint, NVGscissor* scissor, float fringe,
    float strokeWidth, const NVGpath* paths, int npaths)
{
    PROFILER_CPU_TIMESLICE("NVG backend renderStroke");

    GLNVGcontext* gl = (GLNVGcontext*)uptr;
    GLNVGcall* call = glnvg__allocCall(gl);
    GLuint maxverts, offset;

    if (call == NULL) return;

    call->type = GLNVG_STROKE;
    call->pathOffset = glnvg__allocPaths(gl, npaths);
    if (call->pathOffset == -1) goto error;
    call->pathCount = npaths;
    call->image = paint->image;

    // Allocate vertices for all the paths.
    maxverts = glnvg__maxVertCount(paths, npaths);
    NVGvertex* vtx = gfx::frameAllocVertices<NVGvertex>(maxverts, &offset);
    if (!vtx) goto error;

    for (int i = 0; i < npaths; i++) {
        GLNVGpath* copy = &gl->paths[call->pathOffset + i];
        const NVGpath* path = &paths[i];
        mem_zero(copy);
        if (path->nstroke) {
            copy->strokeOffset = offset;
            copy->strokeCount  = path->nstroke;
            mem_copy(vtx, path->stroke, sizeof(NVGvertex) * path->nstroke);
            offset += path->nstroke;
            vtx    += path->nstroke;
        }
    }

    GLNVGfragUniforms* frag;

    gfx::dynbufAlignMem(gfx::caps.uboAlignment, &call->uniformOffset);

    if (gl->flags & NVG_STENCIL_STROKES) {
        // Fill shader
        frag = (GLNVGfragUniforms*)gfx::dynbufAlloc(gl->fragSize);
        if (!frag) goto error;
        glnvg__convertPaint(gl, frag, paint, scissor, strokeWidth, fringe, -1.0f);

        frag = (GLNVGfragUniforms*)gfx::dynbufAlloc(gl->fragSize);
        if (!frag) goto error;
        glnvg__convertPaint(gl, frag, paint, scissor, strokeWidth, fringe, 1.0f - 0.5f / 255.0f);

    } else {
        // Fill shader
        frag = (GLNVGfragUniforms*)gfx::dynbufAlloc(gl->fragSize);
        if (!frag) goto error;
        glnvg__convertPaint(gl, frag, paint, scissor, strokeWidth, fringe, -1.0f);
    }

    return;

error:
    // We get here if call alloc was ok, but something else is not.
    // Roll back the last call to prevent drawing it.
    if (gl->ncalls > 0) gl->ncalls--;
}
Beispiel #8
0
void CGameConsole::CInstance::OnInput(IInput::CEvent Event)
{
	bool Handled = false;

	if(Event.m_Flags&IInput::FLAG_PRESS)
	{
		if(Event.m_Key == KEY_RETURN || Event.m_Key == KEY_KP_ENTER)
		{
			if(m_Input.GetString()[0])
			{
				if(m_Type == CONSOLETYPE_LOCAL || m_pGameConsole->Client()->RconAuthed())
				{
					char *pEntry = m_History.Allocate(m_Input.GetLength()+1);
					mem_copy(pEntry, m_Input.GetString(), m_Input.GetLength()+1);
				}
				ExecuteLine(m_Input.GetString());
				m_Input.Clear();
				m_pHistoryEntry = 0x0;
			}

			Handled = true;
		}
		else if (Event.m_Key == KEY_UP)
		{
			if (m_pHistoryEntry)
			{
				char *pTest = m_History.Prev(m_pHistoryEntry);

				if (pTest)
					m_pHistoryEntry = pTest;
			}
			else
				m_pHistoryEntry = m_History.Last();

			if (m_pHistoryEntry)
				m_Input.Set(m_pHistoryEntry);
			Handled = true;
		}
		else if (Event.m_Key == KEY_DOWN)
		{
			if (m_pHistoryEntry)
				m_pHistoryEntry = m_History.Next(m_pHistoryEntry);

			if (m_pHistoryEntry)
				m_Input.Set(m_pHistoryEntry);
			else
				m_Input.Clear();
			Handled = true;
		}
		else if(Event.m_Key == KEY_TAB)
		{
			if(m_Type == CGameConsole::CONSOLETYPE_LOCAL || m_pGameConsole->Client()->RconAuthed())
			{
				m_CompletionChosen++;
				m_CompletionEnumerationCount = 0;
				m_pGameConsole->m_pConsole->PossibleCommands(m_aCompletionBuffer, m_CompletionFlagmask, m_Type != CGameConsole::CONSOLETYPE_LOCAL &&
					m_pGameConsole->Client()->RconAuthed() && m_pGameConsole->Client()->UseTempRconCommands(),	PossibleCommandsCompleteCallback, this);

				// handle wrapping
				if(m_CompletionEnumerationCount && m_CompletionChosen >= m_CompletionEnumerationCount)
				{
					m_CompletionChosen %= m_CompletionEnumerationCount;
					m_CompletionEnumerationCount = 0;
					m_pGameConsole->m_pConsole->PossibleCommands(m_aCompletionBuffer, m_CompletionFlagmask, m_Type != CGameConsole::CONSOLETYPE_LOCAL &&
						m_pGameConsole->Client()->RconAuthed() && m_pGameConsole->Client()->UseTempRconCommands(),	PossibleCommandsCompleteCallback, this);
				}
			}
		}
		else if(Event.m_Key == KEY_PAGEUP)
		{
			++m_BacklogActPage;
		}
		else if(Event.m_Key == KEY_PAGEDOWN)
		{
			--m_BacklogActPage;
			if(m_BacklogActPage < 0)
				m_BacklogActPage = 0;
		}
	}

	if(!Handled)
		m_Input.ProcessInput(Event);

	if(Event.m_Flags&IInput::FLAG_PRESS)
	{
		if(Event.m_Key != KEY_TAB)
		{
			m_CompletionChosen = -1;
			str_copy(m_aCompletionBuffer, m_Input.GetString(), sizeof(m_aCompletionBuffer));
		}

		// find the current command
		{
			char aBuf[64] = {0};
			const char *pSrc = GetString();
			int i = 0;
			for(; i < (int)sizeof(aBuf)-1 && *pSrc && *pSrc != ' '; i++, pSrc++)
				aBuf[i] = *pSrc;
			aBuf[i] = 0;

			const IConsole::CCommandInfo *pCommand = m_pGameConsole->m_pConsole->GetCommandInfo(aBuf, m_CompletionFlagmask,
				m_Type != CGameConsole::CONSOLETYPE_LOCAL && m_pGameConsole->Client()->RconAuthed() && m_pGameConsole->Client()->UseTempRconCommands());
			if(pCommand)
			{
				m_IsCommand = true;
				str_copy(m_aCommandName, pCommand->m_pName, IConsole::TEMPCMD_NAME_LENGTH);
				str_copy(m_aCommandHelp, pCommand->m_pHelp, IConsole::TEMPCMD_HELP_LENGTH);
				str_copy(m_aCommandParams, pCommand->m_pParams, IConsole::TEMPCMD_PARAMS_LENGTH);
			}
			else
				m_IsCommand = false;
		}
	}
}
Beispiel #9
0
/*===========================================================================*
 *				do_fork					     *
 *===========================================================================*/
PUBLIC int do_fork()
{
/* The process pointed to by 'mp' has forked.  Create a child process. */

  register struct mproc *rmp;	/* pointer to parent */
  register struct mproc *rmc;	/* pointer to child */
  int i, child_nr, t;
  char *sptr, *dptr;
  phys_clicks prog_clicks, child_base;
#if (CHIP == INTEL)
  long prog_bytes;
  long parent_abs, child_abs;
#endif

 /* If tables might fill up during FORK, don't even start since recovery half
  * way through is such a nuisance.
  */

  rmp = mp;
  if (procs_in_use == NR_PROCS) return(EAGAIN);
  if (procs_in_use >= NR_PROCS - LAST_FEW && rmp->mp_effuid != 0)return(EAGAIN);

  /* Determine how much memory to allocate. */
  prog_clicks = (phys_clicks) rmp->mp_seg[S].mem_len;
  prog_clicks += (rmp->mp_seg[S].mem_vir - rmp->mp_seg[D].mem_vir);
#if (CHIP == INTEL)
  if (rmp->mp_flags & SEPARATE) prog_clicks += rmp->mp_seg[T].mem_len;
  prog_bytes = (long) prog_clicks << CLICK_SHIFT;
#endif
  if ( (child_base = alloc_mem(prog_clicks)) == NO_MEM) return(EAGAIN);

#if (CHIP == INTEL)
  /* Create a copy of the parent's core image for the child. */
  child_abs = (long) child_base << CLICK_SHIFT;
  parent_abs = (long) rmp->mp_seg[T].mem_phys << CLICK_SHIFT;
  i = mem_copy(ABS, 0, parent_abs, ABS, 0, child_abs, prog_bytes);
  if ( i < 0) panic("do_fork can't copy", i);
#endif

  /* Find a slot in 'mproc' for the child process.  A slot must exist. */
  for (rmc = &mproc[0]; rmc < &mproc[NR_PROCS]; rmc++)
	if ( (rmc->mp_flags & IN_USE) == 0) break;

  /* Set up the child and its memory map; copy its 'mproc' slot from parent. */
  child_nr = (int)(rmc - mproc);	/* slot number of the child */
  procs_in_use++;
  sptr = (char *) rmp;		/* pointer to parent's 'mproc' slot */
  dptr = (char *) rmc;		/* pointer to child's 'mproc' slot */
  i = sizeof(struct mproc);	/* number of bytes in a proc slot. */
  while (i--) *dptr++ = *sptr++;/* copy from parent slot to child's */

  rmc->mp_parent = who;		/* record child's parent */
  rmc->mp_flags &= ~TRACED;	/* child does not inherit trace status */
#if (CHIP == INTEL)
  rmc->mp_seg[T].mem_phys = child_base;
  rmc->mp_seg[D].mem_phys = child_base + rmc->mp_seg[T].mem_len;
  rmc->mp_seg[S].mem_phys = rmc->mp_seg[D].mem_phys + 
			(rmp->mp_seg[S].mem_phys - rmp->mp_seg[D].mem_phys);
#endif
  rmc->mp_exitstatus = 0;
  rmc->mp_sigstatus = 0;

  /* Find a free pid for the child and put it in the table. */
  do {
	t = 0;			/* 't' = 0 means pid still free */
	next_pid = (next_pid < 30000 ? next_pid + 1 : INIT_PID + 1);
	for (rmp = &mproc[0]; rmp < &mproc[NR_PROCS]; rmp++)
		if (rmp->mp_pid == next_pid || rmp->mp_procgrp == next_pid) {
			t = 1;
			break;
		}
	rmc->mp_pid = next_pid;	/* assign pid to child */
  } while (t);

  /* Set process group. */
  if (who == INIT_PROC_NR) rmc->mp_procgrp = rmc->mp_pid;

  /* Tell kernel and file system about the (now successful) FORK. */
#if (CHIP == M68000)
  sys_fork(who, child_nr, rmc->mp_pid, child_base);
#else
  sys_fork(who, child_nr, rmc->mp_pid);
#endif

  tell_fs(FORK, who, child_nr, rmc->mp_pid);

#if (CHIP == INTEL)
  /* Report child's memory map to kernel. */
  sys_newmap(child_nr, rmc->mp_seg);
#endif

  /* Reply to child to wake it up. */
  reply(child_nr, 0, 0, NIL_PTR);
  return(next_pid);		 /* child's pid */
}
Beispiel #10
0
static void run_service(struct omap_sdma_thc_service_binding_t *sv)
{
    omap_sdma_service_msg_t msg;
    bool loop = true;

    // this is the bitmap of messages we are interested in receiving
    struct omap_sdma_service_selector selector = {
        .mem_copy = 1, .mem_copy_2d = 1,
        .mem_fill = 1, .mem_fill_2d = 1,
    };

    while (loop) {
        // receive any message
        sv->recv_any(sv, &msg, selector);

        errval_t reterr = SYS_ERR_OK;

        // dispatch it
        switch(msg.msg) {
        case omap_sdma_mem_copy:
            reterr = mem_copy(
                msg.args.mem_copy.in.dst,
                msg.args.mem_copy.in.src);
            sv->send.mem_copy(sv, reterr);
            break;
        case omap_sdma_mem_fill:
            reterr = mem_fill(
                msg.args.mem_fill.in.dst,
                msg.args.mem_fill.in.color);
            sv->send.mem_fill(sv, reterr);
            break;
        case omap_sdma_mem_copy_2d:
            reterr = mem_copy_2d(
                msg.args.mem_copy_2d.in.dst,
                msg.args.mem_copy_2d.in.src,
                msg.args.mem_copy_2d.in.count,
                msg.args.mem_copy_2d.in.transparent,
                msg.args.mem_copy_2d.in.color);
            sv->send.mem_copy_2d(sv, reterr);
            break;
        case omap_sdma_mem_fill_2d:
            reterr = mem_fill_2d(
                msg.args.mem_fill_2d.in.dst,
                msg.args.mem_fill_2d.in.count,
                msg.args.mem_fill_2d.in.color);
            sv->send.mem_fill_2d(sv, reterr);
            break;
        default:
            debug_printf("unexpected message: %d\n", msg.msg);
            loop = false;
            break;
        }
    }

    free(sv);
}

void start_service(void)
{
    errval_t err;

    struct omap_sdma_thc_export_info e_info;
    struct omap_sdma_thc_service_binding_t *sv;
    struct omap_sdma_binding *b;
    iref_t iref;

    err = omap_sdma_thc_export(&e_info, "sdma",
                             get_default_waitset(),
                             IDC_EXPORT_FLAGS_DEFAULT,
                             &iref);
    if (err_is_fail(err)) {
        USER_PANIC_ERR(err, "thc export failed");
    }

    DO_FINISH({
        while(true) {
            err = omap_sdma_thc_accept(&e_info, &b);
            if (err_is_fail(err)) {
                USER_PANIC_ERR(err, "thc accept failed");
            }

            sv = malloc(sizeof(struct omap_sdma_thc_service_binding_t));
            assert(sv != NULL);

            err = omap_sdma_thc_init_service(sv, b, b);
            if (err_is_fail(err)) {
                USER_PANIC_ERR(err, "thc init failed");
            }

            ASYNC({run_service(sv);});
        }
    });
Beispiel #11
0
void CServerBrowser::Refresh(int Type)
{
	// clear out everything
	m_ServerlistHeap.Reset();
	m_NumServers = 0;
	m_NumSortedServers = 0;
	mem_zero(m_aServerlistIp, sizeof(m_aServerlistIp));
	m_pFirstReqServer = 0;
	m_pLastReqServer = 0;
	m_NumRequests = 0;
	m_CurrentMaxRequests = g_Config.m_BrMaxRequests;
	// next token
	m_CurrentToken = (m_CurrentToken+1)&0xff;

	//
	m_ServerlistType = Type;

	if(Type == IServerBrowser::TYPE_LAN)
	{
		unsigned char Buffer[sizeof(SERVERBROWSE_GETINFO)+1];
		CNetChunk Packet;
		int i;

		mem_copy(Buffer, SERVERBROWSE_GETINFO, sizeof(SERVERBROWSE_GETINFO));
		Buffer[sizeof(SERVERBROWSE_GETINFO)] = m_CurrentToken;

		/* do the broadcast version */
		Packet.m_ClientID = -1;
		mem_zero(&Packet, sizeof(Packet));
		Packet.m_Address.type = m_pNetClient->NetType()|NETTYPE_LINK_BROADCAST;
		Packet.m_Flags = NETSENDFLAG_CONNLESS;
		Packet.m_DataSize = sizeof(Buffer);
		Packet.m_pData = Buffer;
		m_BroadcastTime = time_get();

		for(i = 8303; i <= 8310; i++)
		{
			Packet.m_Address.port = i;
			m_pNetClient->Send(&Packet);
		}

		if(g_Config.m_Debug)
			m_pConsole->Print(IConsole::OUTPUT_LEVEL_DEBUG, "client_srvbrowse", "broadcasting for servers");
	}
	else if(Type == IServerBrowser::TYPE_INTERNET)
		m_NeedRefresh = 1;
	else if(Type == IServerBrowser::TYPE_FAVORITES)
	{
		for(int i = 0; i < m_NumFavoriteServers; i++)
			Set(m_aFavoriteServers[i], IServerBrowser::SET_FAV_ADD, -1, 0);
	}
	else if(Type == IServerBrowser::TYPE_DDNET)
	{
		LoadDDNet();

		// remove unknown elements of exclude list
		DDNetCountryFilterClean();
		DDNetTypeFilterClean();

		for(int i = 0; i < m_NumDDNetCountries; i++)
		{
			CDDNetCountry *pCntr = &m_aDDNetCountries[i];

			// check for filter
			if(DDNetFiltered(g_Config.m_BrFilterExcludeCountries, pCntr->m_aName))
				continue;

			for(int g = 0; g < pCntr->m_NumServers; g++)
			{
				if(!DDNetFiltered(g_Config.m_BrFilterExcludeTypes, pCntr->m_aTypes[g]))
					Set(pCntr->m_aServers[g], IServerBrowser::SET_DDNET_ADD, -1, 0);
			}
		}
	}
}
Beispiel #12
0
int CInput::Update()
{
	// keep the counter between 1..0xFFFF, 0 means not pressed
	m_InputCounter = (m_InputCounter%0xFFFF)+1;

	{
		int i;
		const Uint8 *pState = SDL_GetKeyboardState(&i);
		if(i >= KEY_LAST)
			i = KEY_LAST-1;
		mem_copy(m_aInputState, pState, i);
	}

	// these states must always be updated manually because they are not in the GetKeyState from SDL
	int i = SDL_GetMouseState(NULL, NULL);
	if(i&SDL_BUTTON(1)) m_aInputState[KEY_MOUSE_1] = 1; // 1 is left
	if(i&SDL_BUTTON(3)) m_aInputState[KEY_MOUSE_2] = 1; // 3 is right
	if(i&SDL_BUTTON(2)) m_aInputState[KEY_MOUSE_3] = 1; // 2 is middle
	if(i&SDL_BUTTON(4)) m_aInputState[KEY_MOUSE_4] = 1;
	if(i&SDL_BUTTON(5)) m_aInputState[KEY_MOUSE_5] = 1;
	if(i&SDL_BUTTON(6)) m_aInputState[KEY_MOUSE_6] = 1;
	if(i&SDL_BUTTON(7)) m_aInputState[KEY_MOUSE_7] = 1;
	if(i&SDL_BUTTON(8)) m_aInputState[KEY_MOUSE_8] = 1;
	if(i&SDL_BUTTON(9)) m_aInputState[KEY_MOUSE_9] = 1;

	{
		SDL_Event Event;

		while(SDL_PollEvent(&Event))
		{
			int Key = -1;
			int Scancode = 0;
			int Action = IInput::FLAG_PRESS;
			switch (Event.type)
			{
				case SDL_TEXTINPUT:
					AddEvent(Event.text.text, 0, IInput::FLAG_TEXT);
					break;

				// handle keys
				case SDL_KEYDOWN:
					Key = KeycodeToKey(Event.key.keysym.sym);
					Scancode = Event.key.keysym.scancode;
					break;
				case SDL_KEYUP:
					Action = IInput::FLAG_RELEASE;
					Key = KeycodeToKey(Event.key.keysym.sym);
					Scancode = Event.key.keysym.scancode;
					break;

				// handle the joystick events
				case SDL_JOYBUTTONUP:
					Action = IInput::FLAG_RELEASE;

					// fall through
				case SDL_JOYBUTTONDOWN:
					Key = Event.jbutton.button + KEY_JOYSTICK_BUTTON_0;
					Scancode = Key;
					break;

				case SDL_JOYHATMOTION:
					switch (Event.jhat.value) {
					case SDL_HAT_LEFTUP:
						Key = KEY_JOY_HAT_LEFTUP;
						Scancode = Key;
						m_PreviousHat = Key;
						break;
					case SDL_HAT_UP:
						Key = KEY_JOY_HAT_UP;
						Scancode = Key;
						m_PreviousHat = Key;
						break;
					case SDL_HAT_RIGHTUP:
						Key = KEY_JOY_HAT_RIGHTUP;
						Scancode = Key;
						m_PreviousHat = Key;
						break;
					case SDL_HAT_LEFT:
						Key = KEY_JOY_HAT_LEFT;
						Scancode = Key;
						m_PreviousHat = Key;
						break;
					case SDL_HAT_CENTERED:
						Action = IInput::FLAG_RELEASE;
						Key = m_PreviousHat;
						Scancode = m_PreviousHat;
						m_PreviousHat = 0;
						break;
					case SDL_HAT_RIGHT:
						Key = KEY_JOY_HAT_RIGHT;
						Scancode = Key;
						m_PreviousHat = Key;
						break;
					case SDL_HAT_LEFTDOWN:
						Key = KEY_JOY_HAT_LEFTDOWN;
						Scancode = Key;
						m_PreviousHat = Key;
						break;
					case SDL_HAT_DOWN:
						Key = KEY_JOY_HAT_DOWN;
						Scancode = Key;
						m_PreviousHat = Key;
						break;
					case SDL_HAT_RIGHTDOWN:
						Key = KEY_JOY_HAT_RIGHTDOWN;
						Scancode = Key;
						m_PreviousHat = Key;
						break;
					}
					break;

				// handle mouse buttons
				case SDL_MOUSEBUTTONUP:
					Action = IInput::FLAG_RELEASE;

					// fall through
				case SDL_MOUSEBUTTONDOWN:
					if(Event.button.button == SDL_BUTTON_LEFT) Key = KEY_MOUSE_1; // ignore_convention
					if(Event.button.button == SDL_BUTTON_RIGHT) Key = KEY_MOUSE_2; // ignore_convention
					if(Event.button.button == SDL_BUTTON_MIDDLE) Key = KEY_MOUSE_3; // ignore_convention
					if(Event.button.button == 4) Key = KEY_MOUSE_4; // ignore_convention
					if(Event.button.button == 5) Key = KEY_MOUSE_5; // ignore_convention
					if(Event.button.button == 6) Key = KEY_MOUSE_6; // ignore_convention
					if(Event.button.button == 7) Key = KEY_MOUSE_7; // ignore_convention
					if(Event.button.button == 8) Key = KEY_MOUSE_8; // ignore_convention
					if(Event.button.button == 9) Key = KEY_MOUSE_9; // ignore_convention
					if(Event.button.button == SDL_BUTTON_LEFT)
					{
						if(Event.button.clicks%2 == 0)
							m_MouseDoubleClick = true;
						if(Event.button.clicks == 1)
							m_MouseDoubleClick = false;
					}
					Scancode = Key;
					break;

				case SDL_MOUSEWHEEL:
					if(Event.wheel.y > 0) Key = KEY_MOUSE_WHEEL_UP; // ignore_convention
					if(Event.wheel.y < 0) Key = KEY_MOUSE_WHEEL_DOWN; // ignore_convention
					Action |= IInput::FLAG_RELEASE;
					break;

#if defined(CONF_PLATFORM_MACOSX)	// Todo SDL: remove this when fixed (mouse state is faulty on start)
				case SDL_WINDOWEVENT:
					if(Event.window.event == SDL_WINDOWEVENT_MAXIMIZED)
					{
						MouseModeAbsolute();
						MouseModeRelative();
					}
					break;
#endif

				// other messages
				case SDL_QUIT:
					return 1;
			}

			//
			if(Key != -1)
			{
				if(Action&IInput::FLAG_PRESS)
				{
					m_aInputState[Scancode] = 1;
					m_aInputCount[Key] = m_InputCounter;
				}
				AddEvent(0, Key, Action);
			}

		}
	}

	return 0;
}
Beispiel #13
0
int CConsoleNetConnection::Recv(char *pLine, int MaxLength)
{
	if(State() == NET_CONNSTATE_ONLINE)
	{
		if(m_BufferOffset)
		{
			// find message start
			int StartOffset = 0;
			while(m_aBuffer[StartOffset] == '\r' || m_aBuffer[StartOffset] == '\n')
			{
				// detect clients line ending format
				if(!m_LineEndingDetected)
				{
					m_aLineEnding[0] = m_aBuffer[StartOffset];
					if(StartOffset+1 < m_BufferOffset && (m_aBuffer[StartOffset+1] == '\r' || m_aBuffer[StartOffset+1] == '\n') &&
						m_aBuffer[StartOffset] != m_aBuffer[StartOffset+1])
						m_aLineEnding[1] = m_aBuffer[StartOffset+1];
					m_LineEndingDetected = true;
				}

				if(++StartOffset >= m_BufferOffset)
				{
					m_BufferOffset = 0;
					return 0;
				}
			}

			// find message end
			int EndOffset = StartOffset;
			while(m_aBuffer[EndOffset] != '\r' && m_aBuffer[EndOffset] != '\n')
			{
				if(++EndOffset >= m_BufferOffset)
				{
					if(StartOffset > 0)
					{
						mem_move(m_aBuffer, m_aBuffer+StartOffset, m_BufferOffset-StartOffset);
						m_BufferOffset -= StartOffset;
					}
					return 0;
				}
			}

			// extract message and update buffer
			if(MaxLength-1 < EndOffset-StartOffset)
			{
				if(StartOffset > 0)
				{
					mem_move(m_aBuffer, m_aBuffer+StartOffset, m_BufferOffset-StartOffset);
					m_BufferOffset -= StartOffset;
				}
				return 0;
			}
			mem_copy(pLine, m_aBuffer+StartOffset, EndOffset-StartOffset);
			pLine[EndOffset-StartOffset] = 0;
			str_sanitize_cc(pLine);
			mem_move(m_aBuffer, m_aBuffer+EndOffset, m_BufferOffset-EndOffset);
			m_BufferOffset -= EndOffset;
			return 1;
		}
	}
	return 0;
}
Beispiel #14
0
void CServer::ProcessClientPacket(CNetChunk *pPacket)
{
	int ClientID = pPacket->m_ClientID;
	CUnpacker Unpacker;
	Unpacker.Reset(pPacket->m_pData, pPacket->m_DataSize);

	// unpack msgid and system flag
	int Msg = Unpacker.GetInt();
	int Sys = Msg&1;
	Msg >>= 1;

	if(Unpacker.Error())
		return;

	if(Sys)
	{
		// system message
		if(Msg == NETMSG_INFO)
		{
			if(m_aClients[ClientID].m_State == CClient::STATE_AUTH)
			{
				const char *pVersion = Unpacker.GetString(CUnpacker::SANITIZE_CC);
				if(str_comp(pVersion, GameServer()->NetVersion()) != 0)
				{
					// wrong version
					char aReason[256];
					str_format(aReason, sizeof(aReason), "Wrong version. Server is running '%s' and client '%s'", GameServer()->NetVersion(), pVersion);
					m_NetServer.Drop(ClientID, aReason);
					return;
				}

				const char *pPassword = Unpacker.GetString(CUnpacker::SANITIZE_CC);
				if(g_Config.m_Password[0] != 0 && str_comp(g_Config.m_Password, pPassword) != 0)
				{
					// wrong password
					m_NetServer.Drop(ClientID, "Wrong password");
					return;
				}

				m_aClients[ClientID].m_State = CClient::STATE_CONNECTING;
				SendMap(ClientID);
			}
		}
		else if(Msg == NETMSG_REQUEST_MAP_DATA)
		{
			if(m_aClients[ClientID].m_State < CClient::STATE_CONNECTING)
				return;

			int Chunk = Unpacker.GetInt();
			unsigned int ChunkSize = 1024-128;
			unsigned int Offset = Chunk * ChunkSize;
			int Last = 0;

			// drop faulty map data requests
			if(Chunk < 0 || Offset > m_CurrentMapSize)
				return;

			if(Offset+ChunkSize >= m_CurrentMapSize)
			{
				ChunkSize = m_CurrentMapSize-Offset;
				if(ChunkSize < 0)
					ChunkSize = 0;
				Last = 1;
			}

			CMsgPacker Msg(NETMSG_MAP_DATA);
			Msg.AddInt(Last);
			Msg.AddInt(m_CurrentMapCrc);
			Msg.AddInt(Chunk);
			Msg.AddInt(ChunkSize);
			Msg.AddRaw(&m_pCurrentMapData[Offset], ChunkSize);
			SendMsgEx(&Msg, MSGFLAG_VITAL|MSGFLAG_FLUSH, ClientID, true);

			if(g_Config.m_Debug)
			{
				char aBuf[256];
				str_format(aBuf, sizeof(aBuf), "sending chunk %d with size %d", Chunk, ChunkSize);
				Console()->Print(IConsole::OUTPUT_LEVEL_DEBUG, "server", aBuf);
			}
		}
		else if(Msg == NETMSG_READY)
		{
			if(m_aClients[ClientID].m_State == CClient::STATE_CONNECTING)
			{
				char aAddrStr[NETADDR_MAXSTRSIZE];
				net_addr_str(m_NetServer.ClientAddr(ClientID), aAddrStr, sizeof(aAddrStr), true);

				char aBuf[256];
				str_format(aBuf, sizeof(aBuf), "player is ready. ClientID=%x addr=%s", ClientID, aAddrStr);
				Console()->Print(IConsole::OUTPUT_LEVEL_ADDINFO, "server", aBuf);
				m_aClients[ClientID].m_State = CClient::STATE_READY;
				GameServer()->OnClientConnected(ClientID);
				SendConnectionReady(ClientID);
			}
		}
		else if(Msg == NETMSG_ENTERGAME)
		{
			if(m_aClients[ClientID].m_State == CClient::STATE_READY && GameServer()->IsClientReady(ClientID))
			{
				char aAddrStr[NETADDR_MAXSTRSIZE];
				net_addr_str(m_NetServer.ClientAddr(ClientID), aAddrStr, sizeof(aAddrStr), true);

				char aBuf[256];
				str_format(aBuf, sizeof(aBuf), "player has entered the game. ClientID=%x addr=%s", ClientID, aAddrStr);
				Console()->Print(IConsole::OUTPUT_LEVEL_STANDARD, "server", aBuf);
				m_aClients[ClientID].m_State = CClient::STATE_INGAME;
				GameServer()->OnClientEnter(ClientID);
			}
		}
		else if(Msg == NETMSG_INPUT)
		{
			CClient::CInput *pInput;
			int64 TagTime;

			m_aClients[ClientID].m_LastAckedSnapshot = Unpacker.GetInt();
			int IntendedTick = Unpacker.GetInt();
			int Size = Unpacker.GetInt();

			// check for errors
			if(Unpacker.Error() || Size/4 > MAX_INPUT_SIZE)
				return;

			if(m_aClients[ClientID].m_LastAckedSnapshot > 0)
				m_aClients[ClientID].m_SnapRate = CClient::SNAPRATE_FULL;

			if(m_aClients[ClientID].m_Snapshots.Get(m_aClients[ClientID].m_LastAckedSnapshot, &TagTime, 0, 0) >= 0)
				m_aClients[ClientID].m_Latency = (int)(((time_get()-TagTime)*1000)/time_freq());

			// add message to report the input timing
			// skip packets that are old
			if(IntendedTick > m_aClients[ClientID].m_LastInputTick)
			{
				int TimeLeft = ((TickStartTime(IntendedTick)-time_get())*1000) / time_freq();

				CMsgPacker Msg(NETMSG_INPUTTIMING);
				Msg.AddInt(IntendedTick);
				Msg.AddInt(TimeLeft);
				SendMsgEx(&Msg, 0, ClientID, true);
			}

			m_aClients[ClientID].m_LastInputTick = IntendedTick;

			pInput = &m_aClients[ClientID].m_aInputs[m_aClients[ClientID].m_CurrentInput];

			if(IntendedTick <= Tick())
				IntendedTick = Tick()+1;

			pInput->m_GameTick = IntendedTick;

			for(int i = 0; i < Size/4; i++)
				pInput->m_aData[i] = Unpacker.GetInt();

			mem_copy(m_aClients[ClientID].m_LatestInput.m_aData, pInput->m_aData, MAX_INPUT_SIZE*sizeof(int));

			m_aClients[ClientID].m_CurrentInput++;
			m_aClients[ClientID].m_CurrentInput %= 200;

			// call the mod with the fresh input data
			if(m_aClients[ClientID].m_State == CClient::STATE_INGAME)
				GameServer()->OnClientDirectInput(ClientID, m_aClients[ClientID].m_LatestInput.m_aData);
		}
		else if(Msg == NETMSG_RCON_CMD)
		{
			const char *pCmd = Unpacker.GetString();

			if(Unpacker.Error() == 0 && m_aClients[ClientID].m_Authed)
			{
				char aBuf[256];
				str_format(aBuf, sizeof(aBuf), "ClientID=%d rcon='%s'", ClientID, pCmd);
				Console()->Print(IConsole::OUTPUT_LEVEL_ADDINFO, "server", aBuf);
				m_RconClientID = ClientID;
				m_RconAuthLevel = m_aClients[ClientID].m_Authed;
				Console()->SetAccessLevel(m_aClients[ClientID].m_Authed == AUTHED_ADMIN ? IConsole::ACCESS_LEVEL_ADMIN : IConsole::ACCESS_LEVEL_MOD);
				Console()->ExecuteLineFlag(pCmd, CFGFLAG_SERVER);
				Console()->SetAccessLevel(IConsole::ACCESS_LEVEL_ADMIN);
				m_RconClientID = IServer::RCON_CID_SERV;
				m_RconAuthLevel = AUTHED_ADMIN;
			}
		}
		else if(Msg == NETMSG_RCON_AUTH)
		{
			const char *pPw;
			Unpacker.GetString(); // login name, not used
			pPw = Unpacker.GetString(CUnpacker::SANITIZE_CC);

			if(Unpacker.Error() == 0)
			{
				if(g_Config.m_SvRconPassword[0] == 0 && g_Config.m_SvRconModPassword[0] == 0)
				{
					SendRconLine(ClientID, "No rcon password set on server. Set sv_rcon_password and/or sv_rcon_mod_password to enable the remote console.");
				}
				else if(g_Config.m_SvRconPassword[0] && str_comp(pPw, g_Config.m_SvRconPassword) == 0)
				{
					CMsgPacker Msg(NETMSG_RCON_AUTH_STATUS);
					Msg.AddInt(1);	//authed
					Msg.AddInt(1);	//cmdlist
					SendMsgEx(&Msg, MSGFLAG_VITAL, ClientID, true);

					m_aClients[ClientID].m_Authed = AUTHED_ADMIN;
					int SendRconCmds = Unpacker.GetInt();
					if(Unpacker.Error() == 0 && SendRconCmds)
						m_aClients[ClientID].m_pRconCmdToSend = Console()->FirstCommandInfo(IConsole::ACCESS_LEVEL_ADMIN, CFGFLAG_SERVER);
					SendRconLine(ClientID, "Admin authentication successful. Full remote console access granted.");
					char aBuf[256];
					str_format(aBuf, sizeof(aBuf), "ClientID=%d authed (admin)", ClientID);
					Console()->Print(IConsole::OUTPUT_LEVEL_STANDARD, "server", aBuf);
				}
				else if(g_Config.m_SvRconModPassword[0] && str_comp(pPw, g_Config.m_SvRconModPassword) == 0)
				{
					CMsgPacker Msg(NETMSG_RCON_AUTH_STATUS);
					Msg.AddInt(1);	//authed
					Msg.AddInt(1);	//cmdlist
					SendMsgEx(&Msg, MSGFLAG_VITAL, ClientID, true);

					m_aClients[ClientID].m_Authed = AUTHED_MOD;
					int SendRconCmds = Unpacker.GetInt();
					if(Unpacker.Error() == 0 && SendRconCmds)
						m_aClients[ClientID].m_pRconCmdToSend = Console()->FirstCommandInfo(IConsole::ACCESS_LEVEL_MOD, CFGFLAG_SERVER);
					SendRconLine(ClientID, "Moderator authentication successful. Limited remote console access granted.");
					char aBuf[256];
					str_format(aBuf, sizeof(aBuf), "ClientID=%d authed (moderator)", ClientID);
					Console()->Print(IConsole::OUTPUT_LEVEL_STANDARD, "server", aBuf);
				}
				else if(g_Config.m_SvRconMaxTries)
				{
					m_aClients[ClientID].m_AuthTries++;
					char aBuf[128];
					str_format(aBuf, sizeof(aBuf), "Wrong password %d/%d.", m_aClients[ClientID].m_AuthTries, g_Config.m_SvRconMaxTries);
					SendRconLine(ClientID, aBuf);
					if(m_aClients[ClientID].m_AuthTries >= g_Config.m_SvRconMaxTries)
					{
						if(!g_Config.m_SvRconBantime)
							m_NetServer.Drop(ClientID, "Too many remote console authentication tries");
						else
							m_ServerBan.BanAddr(m_NetServer.ClientAddr(ClientID), g_Config.m_SvRconBantime*60, "Too many remote console authentication tries");
					}
				}
				else
				{
					SendRconLine(ClientID, "Wrong password.");
				}
			}
		}
		else if(Msg == NETMSG_PING)
		{
			CMsgPacker Msg(NETMSG_PING_REPLY);
			SendMsgEx(&Msg, 0, ClientID, true);
		}
		else
		{
			if(g_Config.m_Debug)
			{
				char aHex[] = "0123456789ABCDEF";
				char aBuf[512];

				for(int b = 0; b < pPacket->m_DataSize && b < 32; b++)
				{
					aBuf[b*3] = aHex[((const unsigned char *)pPacket->m_pData)[b]>>4];
					aBuf[b*3+1] = aHex[((const unsigned char *)pPacket->m_pData)[b]&0xf];
					aBuf[b*3+2] = ' ';
					aBuf[b*3+3] = 0;
				}

				char aBufMsg[256];
				str_format(aBufMsg, sizeof(aBufMsg), "strange message ClientID=%d msg=%d data_size=%d", ClientID, Msg, pPacket->m_DataSize);
				Console()->Print(IConsole::OUTPUT_LEVEL_DEBUG, "server", aBufMsg);
				Console()->Print(IConsole::OUTPUT_LEVEL_DEBUG, "server", aBuf);
			}
		}
	}
Beispiel #15
0
void CEventVariable::Set(const char *pStr)
{
    m_Type = EVENT_TYPE_STRING;
    Allocate(str_length(pStr) + 1);
    mem_copy(m_pData, pStr, str_length(pStr) + 1);
}
Beispiel #16
0
void CNamePlates::RenderNameplate(
	const CNetObj_Character *pPrevChar,
	const CNetObj_Character *pPlayerChar,
	const CNetObj_PlayerInfo *pPlayerInfo
	)
{
	float IntraTick = Client()->IntraGameTick();
	int ClientID = pPlayerInfo->m_ClientID;

	vec2 Position;
	if((!m_pClient->AntiPingPlayers() && !pPlayerInfo->m_Local) || m_pClient->m_Snap.m_SpecInfo.m_Active)
	{
		Position = mix(vec2(pPrevChar->m_X, pPrevChar->m_Y), vec2(pPlayerChar->m_X, pPlayerChar->m_Y), IntraTick);
	}
	else if(!m_pClient->AntiPingPlayers() && pPlayerInfo->m_Local)
	{
		Position = vec2(m_pClient->m_LocalCharacterPos.x, m_pClient->m_LocalCharacterPos.y);
	}
	else
	{
		Position = m_pPlayers->m_CurPredictedPos[ClientID];
	}

	bool OtherTeam;

	if(m_pClient->m_aClients[m_pClient->m_Snap.m_LocalClientID].m_Team == TEAM_SPECTATORS && m_pClient->m_Snap.m_SpecInfo.m_SpectatorID == SPEC_FREEVIEW)
		OtherTeam = false;
	else if(m_pClient->m_Snap.m_SpecInfo.m_Active && m_pClient->m_Snap.m_SpecInfo.m_SpectatorID != SPEC_FREEVIEW)
		OtherTeam = m_pClient->m_Teams.Team(pPlayerInfo->m_ClientID) != m_pClient->m_Teams.Team(m_pClient->m_Snap.m_SpecInfo.m_SpectatorID);
	else
		OtherTeam = m_pClient->m_Teams.Team(pPlayerInfo->m_ClientID) != m_pClient->m_Teams.Team(m_pClient->m_Snap.m_LocalClientID);

	float FontSize = 18.0f + 20.0f * g_Config.m_ClNameplatesSize / 100.0f;
	float FontSizeClan = 18.0f + 20.0f * g_Config.m_ClNameplatesClanSize / 100.0f;
	// render name plate
	if(!pPlayerInfo->m_Local || g_Config.m_ClNameplatesOwn)
	{
		float a = 1;
		if(g_Config.m_ClNameplatesAlways == 0)
			a = clamp(1-powf(distance(m_pClient->m_pControls->m_TargetPos[g_Config.m_ClDummy], Position)/200.0f,16.0f), 0.0f, 1.0f);

		const char *pName = m_pClient->m_aClients[pPlayerInfo->m_ClientID].m_aName;
		if(str_comp(pName, m_aNamePlates[ClientID].m_aName) != 0 || FontSize != m_aNamePlates[ClientID].m_NameTextFontSize)
		{
			mem_copy(m_aNamePlates[ClientID].m_aName, pName, sizeof(m_aNamePlates[ClientID].m_aName));
			m_aNamePlates[ClientID].m_NameTextFontSize = FontSize;

			m_aNamePlates[ClientID].m_NameTextWidth = TextRender()->TextWidth(0, FontSize, pName, -1);

			if(m_aNamePlates[ClientID].m_NameTextContainerIndex != -1)
				TextRender()->DeleteTextContainer(m_aNamePlates[ClientID].m_NameTextContainerIndex);

			CTextCursor Cursor;
			TextRender()->SetCursor(&Cursor, 0, 0, FontSize, TEXTFLAG_RENDER);
			Cursor.m_LineWidth = -1;

			// create nameplates at standard zoom
			float ScreenX0, ScreenY0, ScreenX1, ScreenY1;
			Graphics()->GetScreen(&ScreenX0, &ScreenY0, &ScreenX1, &ScreenY1);
			MapscreenToGroup(m_pClient->m_pCamera->m_Center.x, m_pClient->m_pCamera->m_Center.y, Layers()->GameGroup());
			m_aNamePlates[ClientID].m_NameTextContainerIndex = TextRender()->CreateTextContainer(&Cursor, pName);
			Graphics()->MapScreen(ScreenX0, ScreenY0, ScreenX1, ScreenY1);
		}

		if(g_Config.m_ClNameplatesClan)
		{
			const char *pClan = m_pClient->m_aClients[ClientID].m_aClan;
			if(str_comp(pClan, m_aNamePlates[ClientID].m_aClanName) != 0 || FontSizeClan != m_aNamePlates[ClientID].m_ClanNameTextFontSize)
			{
				mem_copy(m_aNamePlates[ClientID].m_aClanName, pClan, sizeof(m_aNamePlates[ClientID].m_aClanName));
				m_aNamePlates[ClientID].m_ClanNameTextFontSize = FontSizeClan;

				m_aNamePlates[ClientID].m_ClanNameTextWidth = TextRender()->TextWidth(0, FontSizeClan, pClan, -1);

				if(m_aNamePlates[ClientID].m_ClanNameTextContainerIndex != -1)
					TextRender()->DeleteTextContainer(m_aNamePlates[ClientID].m_ClanNameTextContainerIndex);

				CTextCursor Cursor;
				TextRender()->SetCursor(&Cursor, 0, 0, FontSizeClan, TEXTFLAG_RENDER);
				Cursor.m_LineWidth = -1;

				// create nameplates at standard zoom
				float ScreenX0, ScreenY0, ScreenX1, ScreenY1;
				Graphics()->GetScreen(&ScreenX0, &ScreenY0, &ScreenX1, &ScreenY1);
				MapscreenToGroup(m_pClient->m_pCamera->m_Center.x, m_pClient->m_pCamera->m_Center.y, Layers()->GameGroup());
				m_aNamePlates[ClientID].m_ClanNameTextContainerIndex = TextRender()->CreateTextContainer(&Cursor, pClan);
				Graphics()->MapScreen(ScreenX0, ScreenY0, ScreenX1, ScreenY1);
			}
		}

		float tw = m_aNamePlates[ClientID].m_NameTextWidth;
		vec3 rgb = vec3(1.0f, 1.0f, 1.0f);
		if(g_Config.m_ClNameplatesTeamcolors && m_pClient->m_Teams.Team(ClientID))
			rgb = HslToRgb(vec3(m_pClient->m_Teams.Team(ClientID) / 64.0f, 1.0f, 0.75f));

		STextRenderColor TColor;
		STextRenderColor TOutlineColor;

		if(OtherTeam)
		{
			TOutlineColor.Set(0.0f, 0.0f, 0.0f, 0.2f);
			TColor.Set(rgb.r, rgb.g, rgb.b, g_Config.m_ClShowOthersAlpha / 100.0f);
		}
		else
		{
			TOutlineColor.Set(0.0f, 0.0f, 0.0f, 0.5f*a);
			TColor.Set(rgb.r, rgb.g, rgb.b, a);
		}
		if(g_Config.m_ClNameplatesTeamcolors && m_pClient->m_Snap.m_pGameInfoObj && m_pClient->m_Snap.m_pGameInfoObj->m_GameFlags&GAMEFLAG_TEAMS)
		{
			if(m_pClient->m_aClients[ClientID].m_Team == TEAM_RED)
				TColor.Set(1.0f, 0.5f, 0.5f, a);
			else if(m_pClient->m_aClients[ClientID].m_Team == TEAM_BLUE)
				TColor.Set(0.7f, 0.7f, 1.0f, a);
		}

		if(m_aNamePlates[ClientID].m_NameTextContainerIndex != -1)
			TextRender()->RenderTextContainer(m_aNamePlates[ClientID].m_NameTextContainerIndex, &TColor, &TOutlineColor, Position.x - tw / 2.0f, Position.y - FontSize - 38.0f);

		if(g_Config.m_ClNameplatesClan)
		{
			if(m_aNamePlates[ClientID].m_ClanNameTextContainerIndex != -1)
				TextRender()->RenderTextContainer(m_aNamePlates[ClientID].m_ClanNameTextContainerIndex, &TColor, &TOutlineColor, Position.x - m_aNamePlates[ClientID].m_ClanNameTextWidth / 2.0f, Position.y - FontSize - FontSizeClan - 38.0f);
		}

		if(g_Config.m_Debug) // render client id when in debug as well
		{
			char aBuf[128];
			str_format(aBuf, sizeof(aBuf),"%d", pPlayerInfo->m_ClientID);
			float Offset = g_Config.m_ClNameplatesClan ? (FontSize * 2 + FontSizeClan) : (FontSize * 2);
			float tw_id = TextRender()->TextWidth(0, FontSize, aBuf, -1);
			TextRender()->Text(0, Position.x-tw_id/2.0f, Position.y-Offset-38.0f, 28.0f, aBuf, -1);
		}

		TextRender()->TextColor(1,1,1,1);
		TextRender()->TextOutlineColor(0.0f, 0.0f, 0.0f, 0.3f);
	}
}
Beispiel #17
0
void CEventVariable::Set(const char *pData, int Size)
{
    m_Type = EVENT_TYPE_DATA;
    Allocate(Size);
    mem_copy(m_pData, pData, Size);
}
Beispiel #18
0
int CControls::SnapInput(int *pData)
{
	static int64 LastSendTime = 0;
	bool Send = false;

	// update player state
	if(m_pClient->m_pChat->IsActive())
		m_InputData[g_Config.m_ClDummy].m_PlayerFlags = PLAYERFLAG_CHATTING;
	else if(m_pClient->m_pMenus->IsActive())
		m_InputData[g_Config.m_ClDummy].m_PlayerFlags = PLAYERFLAG_IN_MENU;
	else
		m_InputData[g_Config.m_ClDummy].m_PlayerFlags = PLAYERFLAG_PLAYING;

	if(m_pClient->m_pScoreboard->Active())
		m_InputData[g_Config.m_ClDummy].m_PlayerFlags |= PLAYERFLAG_SCOREBOARD;

	if(m_InputData[g_Config.m_ClDummy].m_PlayerFlags != PLAYERFLAG_PLAYING)
		m_JoystickTapTime = 0; // Do not launch hook on first tap

	if (m_pClient->m_pControls->m_ShowHookColl[g_Config.m_ClDummy])
		m_InputData[g_Config.m_ClDummy].m_PlayerFlags |= PLAYERFLAG_AIM;

	if(m_LastData[g_Config.m_ClDummy].m_PlayerFlags != m_InputData[g_Config.m_ClDummy].m_PlayerFlags)
		Send = true;

	m_LastData[g_Config.m_ClDummy].m_PlayerFlags = m_InputData[g_Config.m_ClDummy].m_PlayerFlags;

	// we freeze the input if chat or menu is activated
	if(!(m_InputData[g_Config.m_ClDummy].m_PlayerFlags&PLAYERFLAG_PLAYING))
	{
		ResetInput(g_Config.m_ClDummy);

		mem_copy(pData, &m_InputData[g_Config.m_ClDummy], sizeof(m_InputData[0]));

		// send once a second just to be sure
		if(time_get() > LastSendTime + time_freq())
			Send = true;
	}
	else
	{
		m_InputData[g_Config.m_ClDummy].m_TargetX = (int)m_MousePos[g_Config.m_ClDummy].x;
		m_InputData[g_Config.m_ClDummy].m_TargetY = (int)m_MousePos[g_Config.m_ClDummy].y;
		if(!m_InputData[g_Config.m_ClDummy].m_TargetX && !m_InputData[g_Config.m_ClDummy].m_TargetY)
		{
			m_InputData[g_Config.m_ClDummy].m_TargetX = 1;
			m_MousePos[g_Config.m_ClDummy].x = 1;
		}

		// set direction
		m_InputData[g_Config.m_ClDummy].m_Direction = 0;
		if(m_InputDirectionLeft[g_Config.m_ClDummy] && !m_InputDirectionRight[g_Config.m_ClDummy])
			m_InputData[g_Config.m_ClDummy].m_Direction = -1;
		if(!m_InputDirectionLeft[g_Config.m_ClDummy] && m_InputDirectionRight[g_Config.m_ClDummy])
			m_InputData[g_Config.m_ClDummy].m_Direction = 1;

		// dummy copy moves
		if(g_Config.m_ClDummyCopyMoves)
		{
			CNetObj_PlayerInput *DummyInput = &Client()->DummyInput;
			DummyInput->m_Direction = m_InputData[g_Config.m_ClDummy].m_Direction;
			DummyInput->m_Hook = m_InputData[g_Config.m_ClDummy].m_Hook;
			DummyInput->m_Jump = m_InputData[g_Config.m_ClDummy].m_Jump;
			DummyInput->m_PlayerFlags = m_InputData[g_Config.m_ClDummy].m_PlayerFlags;
			DummyInput->m_TargetX = m_InputData[g_Config.m_ClDummy].m_TargetX;
			DummyInput->m_TargetY = m_InputData[g_Config.m_ClDummy].m_TargetY;
			DummyInput->m_WantedWeapon = m_InputData[g_Config.m_ClDummy].m_WantedWeapon;



			DummyInput->m_Fire += m_InputData[g_Config.m_ClDummy].m_Fire - m_LastData[g_Config.m_ClDummy].m_Fire;
			DummyInput->m_NextWeapon += m_InputData[g_Config.m_ClDummy].m_NextWeapon - m_LastData[g_Config.m_ClDummy].m_NextWeapon;
			DummyInput->m_PrevWeapon += m_InputData[g_Config.m_ClDummy].m_PrevWeapon - m_LastData[g_Config.m_ClDummy].m_PrevWeapon;

			m_InputData[!g_Config.m_ClDummy] = *DummyInput;
		}

		// stress testing
		if(g_Config.m_DbgStress)
		{
			float t = Client()->LocalTime();
			mem_zero(&m_InputData[g_Config.m_ClDummy], sizeof(m_InputData[0]));

			m_InputData[g_Config.m_ClDummy].m_Direction = ((int)t/2)&1;
			m_InputData[g_Config.m_ClDummy].m_Jump = ((int)t);
			m_InputData[g_Config.m_ClDummy].m_Fire = ((int)(t*10));
			m_InputData[g_Config.m_ClDummy].m_Hook = ((int)(t*2))&1;
			m_InputData[g_Config.m_ClDummy].m_WantedWeapon = ((int)t)%NUM_WEAPONS;
			m_InputData[g_Config.m_ClDummy].m_TargetX = (int)(sinf(t*3)*100.0f);
			m_InputData[g_Config.m_ClDummy].m_TargetY = (int)(cosf(t*3)*100.0f);
		}

		// check if we need to send input
		if(m_InputData[g_Config.m_ClDummy].m_Direction != m_LastData[g_Config.m_ClDummy].m_Direction) Send = true;
		else if(m_InputData[g_Config.m_ClDummy].m_Jump != m_LastData[g_Config.m_ClDummy].m_Jump) Send = true;
		else if(m_InputData[g_Config.m_ClDummy].m_Fire != m_LastData[g_Config.m_ClDummy].m_Fire) Send = true;
		else if(m_InputData[g_Config.m_ClDummy].m_Hook != m_LastData[g_Config.m_ClDummy].m_Hook) Send = true;
		else if(m_InputData[g_Config.m_ClDummy].m_WantedWeapon != m_LastData[g_Config.m_ClDummy].m_WantedWeapon) Send = true;
		else if(m_InputData[g_Config.m_ClDummy].m_NextWeapon != m_LastData[g_Config.m_ClDummy].m_NextWeapon) Send = true;
		else if(m_InputData[g_Config.m_ClDummy].m_PrevWeapon != m_LastData[g_Config.m_ClDummy].m_PrevWeapon) Send = true;

		// send at at least 10hz
		if(time_get() > LastSendTime + time_freq()/25)
			Send = true;

		if(m_pClient->m_Snap.m_pLocalCharacter && m_pClient->m_Snap.m_pLocalCharacter->m_Weapon == WEAPON_NINJA
			&& (m_InputData[g_Config.m_ClDummy].m_Direction || m_InputData[g_Config.m_ClDummy].m_Jump || m_InputData[g_Config.m_ClDummy].m_Hook))
			Send = true;
	}

	// copy and return size
	m_LastData[g_Config.m_ClDummy] = m_InputData[g_Config.m_ClDummy];

	if(!Send)
		return 0;

	LastSendTime = time_get();
	mem_copy(pData, &m_InputData[g_Config.m_ClDummy], sizeof(m_InputData[0]));
	return sizeof(m_InputData[0]);
}
Beispiel #19
0
static void glnvg__renderFill(void* uptr, NVGpaint* paint, NVGscissor* scissor, float fringe,
    const float* bounds, const NVGpath* paths, int npaths)
{
    PROFILER_CPU_TIMESLICE("NVG backend renderFill");

    GLNVGcontext* gl = (GLNVGcontext*)uptr;
    GLNVGcall* call = glnvg__allocCall(gl);
    GLNVGfragUniforms* frag;
    GLuint maxverts, offset;

    if (call == NULL) return;

    call->type = GLNVG_FILL;
    call->pathOffset = glnvg__allocPaths(gl, npaths);
    if (call->pathOffset == -1) goto error;
    call->pathCount = npaths;
    call->image = paint->image;

    if (npaths == 1 && paths[0].convex)
        call->type = GLNVG_CONVEXFILL;

    // Allocate vertices for all the paths.
    maxverts = glnvg__maxVertCount(paths, npaths) + 6;
    NVGvertex* vtx = gfx::frameAllocVertices<NVGvertex>(maxverts, &offset);
    if (!vtx) goto error;

    for (int i = 0; i < npaths; i++) {
        GLNVGpath* copy = &gl->paths[call->pathOffset + i];
        const NVGpath* path = &paths[i];
        mem_zero(copy);
        if (path->nfill > 0) {
            copy->fillOffset = offset;
            copy->fillCount = path->nfill;
            mem_copy(vtx, path->fill, sizeof(NVGvertex) * path->nfill);
            offset += path->nfill;
            vtx    += path->nfill;
        }
        if (path->nstroke > 0) {
            copy->strokeOffset = offset;
            copy->strokeCount = path->nstroke;
            mem_copy(vtx, path->stroke, sizeof(NVGvertex) * path->nstroke);
            offset += path->nstroke;
            vtx    += path->nstroke;
        }
    }

    // Quad
    call->triangleOffset = offset;
    call->triangleCount = 6;
    *vtx++ = {bounds[0], bounds[3], 0.5f, 1.0f};
    *vtx++ = {bounds[2], bounds[3], 0.5f, 1.0f};
    *vtx++ = {bounds[2], bounds[1], 0.5f, 1.0f};

    *vtx++ = {bounds[0], bounds[3], 0.5f, 1.0f};
    *vtx++ = {bounds[2], bounds[1], 0.5f, 1.0f};
    *vtx++ = {bounds[0], bounds[1], 0.5f, 1.0f};

    gfx::dynbufAlignMem(gfx::caps.uboAlignment, &call->uniformOffset);

    // Setup uniforms for draw calls
    if (call->type == GLNVG_FILL) {
        // Simple shader for stencil
        frag = (GLNVGfragUniforms*)gfx::dynbufAlloc(gl->fragSize);
        if (!frag) goto error;
        mem_zero(frag);
        frag->strokeThr = -1.0f;
        frag->type = NSVG_SHADER_SIMPLE;

        // Fill shader
        frag = (GLNVGfragUniforms*)gfx::dynbufAlloc(gl->fragSize);
        if (!frag) goto error;
        glnvg__convertPaint(gl, frag, paint, scissor, fringe, fringe, -1.0f);
    } else {
        // Fill shader
        frag = (GLNVGfragUniforms*)gfx::dynbufAlloc(gl->fragSize);
        if (!frag) goto error;
        glnvg__convertPaint(gl, frag, paint, scissor, fringe, fringe, -1.0f);
    }

    return;

error:
    // We get here if call alloc was ok, but something else is not.
    // Roll back the last call to prevent drawing it.
    if (gl->ncalls > 0) gl->ncalls--;
}
Beispiel #20
0
pvartype  STDCALL load_var( pubyte* input, pubyte* output, uint count, 
                            puint size, uint align )
{
   pvartype   psub;
   povmtype   newtype;
   pubyte     out = *output;
   pubyte     ptr = *input;
   pvartype   ret;
   uint       i, off = 0, flag, len, k;
   
   ret = psub = ( pvartype )out;
         
   out += count * sizeof( vartype );
//   print("Count=%i ---------\n", count );
   for ( i = 0; i < count; i++ )
   {
      mem_zero( psub, sizeof( vartype ));
      psub->type = load_convert( &ptr );   
      psub->off = align ? ( off >> 2 ) : off;
      flag = *ptr++;
      psub->flag = ( ubyte )flag;
      if ( flag & VAR_NAME )
      {
         len = mem_copyuntilzero( out, ptr ); 
         psub->name = out;
         ptr += len;
//         print("    Field %i %s\n", i, psub->name );
         out += len;
      }
      newtype = ( povmtype )PCMD( psub->type );
      off += flag & VAR_PARAM ? ( newtype->stsize << 2 ) : newtype->size;

      if ( flag & VAR_OFTYPE )
         psub->oftype = load_convert( &ptr );

      psub->ptr = ( puint )out;

      if ( flag & VAR_DIM )
      {
         len = 1;
         psub->dim = *ptr++;
         
         for ( k = 0; k < psub->dim; k++ )      
         {
            *( puint )out = load_bwd( &ptr );
            len *= *( puint )out;
            out += sizeof( uint );
         }
         // Если reserved < 4 удаляем лишнее
         if ( psub->type == TReserved )
            off += len - 4;
      }
      if ( flag & VAR_DATA )
      {
         psub->data = 1;
//         print("Data=%s\n", psub->name );
         if ( newtype->vmo.flag & GHTY_STACK )
            len = newtype->size;
         else
         {
            if ( psub->type == TStr )
            {
               len = mem_len( ptr ) + 1;
//               print("Val=%s\n", ptr );
            }
            else
            {
               *( puint )out = load_bwd( &ptr );
               len = *( puint )out;
//               print("Load %i %x\n", len, *( puint )ptr );
               out += sizeof( uint );
            }
         }
         mem_copy( out, ptr, len );
         ptr += len;
         out += len;
      }
      // Alignment
      if ( align && ( off & 3 ))
         off += 4 - ( off & 0x3 );
//      print("off = %i \n", off );

      psub++;         
   }
   *size = off;

   *output = out;
   *input = ptr;
   return ret;
}
Beispiel #21
0
int CEditorMap::Save(class IStorage *pStorage, const char *pFileName)
{
    char aBuf[256];
    str_format(aBuf, sizeof(aBuf), "saving to '%s'...", pFileName);
    m_pEditor->Console()->Print(IConsole::OUTPUT_LEVEL_STANDARD, "editor", aBuf);
    CDataFileWriter df;
    if(!df.Open(pStorage, pFileName))
    {
        str_format(aBuf, sizeof(aBuf), "failed to open file '%s'...", pFileName);
        m_pEditor->Console()->Print(IConsole::OUTPUT_LEVEL_STANDARD, "editor", aBuf);
        return 0;
    }

    // save version
    {
        CMapItemVersion Item;
        Item.m_Version = 1;
        df.AddItem(MAPITEMTYPE_VERSION, 0, sizeof(Item), &Item);
    }

    // save map info
    {
        CMapItemInfo Item;
        Item.m_Version = 1;

        if(m_MapInfo.m_aAuthor[0])
            Item.m_Author = df.AddData(str_length(m_MapInfo.m_aAuthor)+1, m_MapInfo.m_aAuthor);
        else
            Item.m_Author = -1;
        if(m_MapInfo.m_aVersion[0])
            Item.m_MapVersion = df.AddData(str_length(m_MapInfo.m_aVersion)+1, m_MapInfo.m_aVersion);
        else
            Item.m_MapVersion = -1;
        if(m_MapInfo.m_aCredits[0])
            Item.m_Credits = df.AddData(str_length(m_MapInfo.m_aCredits)+1, m_MapInfo.m_aCredits);
        else
            Item.m_Credits = -1;
        if(m_MapInfo.m_aLicense[0])
            Item.m_License = df.AddData(str_length(m_MapInfo.m_aLicense)+1, m_MapInfo.m_aLicense);
        else
            Item.m_License = -1;

        df.AddItem(MAPITEMTYPE_INFO, 0, sizeof(Item), &Item);
    }

    // save images
    for(int i = 0; i < m_lImages.size(); i++)
    {
        CEditorImage *pImg = m_lImages[i];

        // analyse the image for when saving (should be done when we load the image)
        // TODO!
        pImg->AnalyseTileFlags();

        CMapItemImage Item;
        Item.m_Version = 1;

        Item.m_Width = pImg->m_Width;
        Item.m_Height = pImg->m_Height;
        Item.m_External = pImg->m_External;
        Item.m_ImageName = df.AddData(str_length(pImg->m_aName)+1, pImg->m_aName);
        if(pImg->m_External)
            Item.m_ImageData = -1;
        else
            Item.m_ImageData = df.AddData(Item.m_Width*Item.m_Height*4, pImg->m_pData);
        df.AddItem(MAPITEMTYPE_IMAGE, i, sizeof(Item), &Item);
    }

    // save layers
    int LayerCount = 0, GroupCount = 0;
    for(int g = 0; g < m_lGroups.size(); g++)
    {
        CLayerGroup *pGroup = m_lGroups[g];
        if(!pGroup->m_SaveToMap)
            continue;

        CMapItemGroup GItem;
        GItem.m_Version = CMapItemGroup::CURRENT_VERSION;

        GItem.m_ParallaxX = pGroup->m_ParallaxX;
        GItem.m_ParallaxY = pGroup->m_ParallaxY;
        GItem.m_OffsetX = pGroup->m_OffsetX;
        GItem.m_OffsetY = pGroup->m_OffsetY;
        GItem.m_UseClipping = pGroup->m_UseClipping;
        GItem.m_ClipX = pGroup->m_ClipX;
        GItem.m_ClipY = pGroup->m_ClipY;
        GItem.m_ClipW = pGroup->m_ClipW;
        GItem.m_ClipH = pGroup->m_ClipH;
        GItem.m_StartLayer = LayerCount;
        GItem.m_NumLayers = 0;

        // save group name
        StrToInts(GItem.m_aName, sizeof(GItem.m_aName)/sizeof(int), pGroup->m_aName);

        for(int l = 0; l < pGroup->m_lLayers.size(); l++)
        {
            if(!pGroup->m_lLayers[l]->m_SaveToMap)
                continue;

            if(pGroup->m_lLayers[l]->m_Type == LAYERTYPE_TILES)
            {
                m_pEditor->Console()->Print(IConsole::OUTPUT_LEVEL_ADDINFO, "editor", "saving tiles layer");
                CLayerTiles *pLayer = (CLayerTiles *)pGroup->m_lLayers[l];
                pLayer->PrepareForSave();

                CMapItemLayerTilemap Item;
                Item.m_Version = 3;

                Item.m_Layer.m_Flags = pLayer->m_Flags;
                Item.m_Layer.m_Type = pLayer->m_Type;

                Item.m_Color = pLayer->m_Color;
                Item.m_ColorEnv = pLayer->m_ColorEnv;
                Item.m_ColorEnvOffset = pLayer->m_ColorEnvOffset;

                Item.m_Width = pLayer->m_Width;
                Item.m_Height = pLayer->m_Height;
                Item.m_Flags = pLayer->m_GameFlags;
                Item.m_Image = pLayer->m_Image;
                Item.m_Data = df.AddData(pLayer->m_Width*pLayer->m_Height*sizeof(CTile), pLayer->m_pTiles);

                // save layer name
                StrToInts(Item.m_aName, sizeof(Item.m_aName)/sizeof(int), pLayer->m_aName);

                df.AddItem(MAPITEMTYPE_LAYER, LayerCount, sizeof(Item), &Item);

                GItem.m_NumLayers++;
                LayerCount++;
            }
            else if(pGroup->m_lLayers[l]->m_Type == LAYERTYPE_QUADS)
            {
                m_pEditor->Console()->Print(IConsole::OUTPUT_LEVEL_ADDINFO, "editor", "saving quads layer");
                CLayerQuads *pLayer = (CLayerQuads *)pGroup->m_lLayers[l];
                if(pLayer->m_lQuads.size())
                {
                    CMapItemLayerQuads Item;
                    Item.m_Version = 2;
                    Item.m_Layer.m_Flags = pLayer->m_Flags;
                    Item.m_Layer.m_Type = pLayer->m_Type;
                    Item.m_Image = pLayer->m_Image;

                    // add the data
                    Item.m_NumQuads = pLayer->m_lQuads.size();
                    Item.m_Data = df.AddDataSwapped(pLayer->m_lQuads.size()*sizeof(CQuad), pLayer->m_lQuads.base_ptr());

                    // save layer name
                    StrToInts(Item.m_aName, sizeof(Item.m_aName)/sizeof(int), pLayer->m_aName);

                    df.AddItem(MAPITEMTYPE_LAYER, LayerCount, sizeof(Item), &Item);

                    // clean up
                    //mem_free(quads);

                    GItem.m_NumLayers++;
                    LayerCount++;
                }
            }
        }

        df.AddItem(MAPITEMTYPE_GROUP, GroupCount++, sizeof(GItem), &GItem);
    }

    // save envelopes
    int PointCount = 0;
    for(int e = 0; e < m_lEnvelopes.size(); e++)
    {
        CMapItemEnvelope Item;
        Item.m_Version = CMapItemEnvelope::CURRENT_VERSION;
        Item.m_Channels = m_lEnvelopes[e]->m_Channels;
        Item.m_StartPoint = PointCount;
        Item.m_NumPoints = m_lEnvelopes[e]->m_lPoints.size();
        Item.m_Synchronized = m_lEnvelopes[e]->m_Synchronized;
        StrToInts(Item.m_aName, sizeof(Item.m_aName)/sizeof(int), m_lEnvelopes[e]->m_aName);

        df.AddItem(MAPITEMTYPE_ENVELOPE, e, sizeof(Item), &Item);
        PointCount += Item.m_NumPoints;
    }

    // save points
    int TotalSize = sizeof(CEnvPoint) * PointCount;
    CEnvPoint *pPoints = (CEnvPoint *)mem_alloc(TotalSize, 1);
    PointCount = 0;

    for(int e = 0; e < m_lEnvelopes.size(); e++)
    {
        int Count = m_lEnvelopes[e]->m_lPoints.size();
        mem_copy(&pPoints[PointCount], m_lEnvelopes[e]->m_lPoints.base_ptr(), sizeof(CEnvPoint)*Count);
        PointCount += Count;
    }

    df.AddItem(MAPITEMTYPE_ENVPOINTS, 0, TotalSize, pPoints);
    mem_free(pPoints);

    // finish the data file
    df.Finish();
    m_pEditor->Console()->Print(IConsole::OUTPUT_LEVEL_ADDINFO, "editor", "saving done");

    return 1;
}
Beispiel #22
0
void CEventVariable::Set(long int Value)
{
    m_Type = EVENT_TYPE_INTEGER;
    Allocate(16);
    mem_copy(m_pData, &Value, sizeof(Value));
}
Beispiel #23
0
static void server_process_client_packet(NETCHUNK *packet)
{
	int cid = packet->client_id;
	NETADDR addr;
	
	int sys;
	int msg = msg_unpack_start(packet->data, packet->data_size, &sys);
	
	if(clients[cid].state == SRVCLIENT_STATE_AUTH)
	{
		if(sys && msg == NETMSG_INFO)
		{
			char version[64];
			const char *password;
			str_copy(version, msg_unpack_string(), 64);
			if(strcmp(version, mods_net_version()) != 0)
			{
				/* OH F**K! wrong version, drop him */
				char reason[256];
				str_format(reason, sizeof(reason), "wrong version. server is running '%s' and client '%s'.", mods_net_version(), version);
				netserver_drop(net, cid, reason);
				return;
			}
			
			str_copy(clients[cid].name, msg_unpack_string(), MAX_NAME_LENGTH);
			str_copy(clients[cid].clan, msg_unpack_string(), MAX_CLANNAME_LENGTH);
			password = msg_unpack_string();
			
			if(config.password[0] != 0 && strcmp(config.password, password) != 0)
			{
				/* wrong password */
				netserver_drop(net, cid, "wrong password");
				return;
			}
			
			clients[cid].state = SRVCLIENT_STATE_CONNECTING;
			server_send_map(cid);
		}
	}
	else
	{
		if(sys)
		{
			/* system message */
			if(msg == NETMSG_REQUEST_MAP_DATA)
			{
				int chunk = msg_unpack_int();
				int chunk_size = 1024-128;
				int offset = chunk * chunk_size;
				int last = 0;
				
				/* drop faulty map data requests */
				if(chunk < 0 || offset > current_map_size)
					return;
				
				if(offset+chunk_size >= current_map_size)
				{
					chunk_size = current_map_size-offset;
					if(chunk_size < 0)
						chunk_size = 0;
					last = 1;
				}
				
				msg_pack_start_system(NETMSG_MAP_DATA, MSGFLAG_VITAL|MSGFLAG_FLUSH);
				msg_pack_int(last);
				msg_pack_int(current_map_size);
				msg_pack_int(chunk_size);
				msg_pack_raw(&current_map_data[offset], chunk_size);
				msg_pack_end();
				server_send_msg(cid);
				
				if(config.debug)
					dbg_msg("server", "sending chunk %d with size %d", chunk, chunk_size);
			}
			else if(msg == NETMSG_READY)
			{
				if(clients[cid].state == SRVCLIENT_STATE_CONNECTING)
				{
					netserver_client_addr(net, cid, &addr);
					
					dbg_msg("server", "player is ready. cid=%x ip=%d.%d.%d.%d",
						cid,
						addr.ip[0], addr.ip[1], addr.ip[2], addr.ip[3]
						);
					clients[cid].state = SRVCLIENT_STATE_READY;
					mods_connected(cid);
				}
			}
			else if(msg == NETMSG_ENTERGAME)
			{
				if(clients[cid].state == SRVCLIENT_STATE_READY)
				{
					netserver_client_addr(net, cid, &addr);
					
					dbg_msg("server", "player has entered the game. cid=%x ip=%d.%d.%d.%d",
						cid,
						addr.ip[0], addr.ip[1], addr.ip[2], addr.ip[3]
						);
					clients[cid].state = SRVCLIENT_STATE_INGAME;
					mods_client_enter(cid);
				}
			}
			else if(msg == NETMSG_INPUT)
			{
				int tick, size, i;
				CLIENT_INPUT *input;
				int64 tagtime;
				
				clients[cid].last_acked_snapshot = msg_unpack_int();
				tick = msg_unpack_int();
				size = msg_unpack_int();
				
				/* check for errors */
				if(msg_unpack_error() || size/4 > MAX_INPUT_SIZE)
					return;

				if(clients[cid].last_acked_snapshot > 0)
					clients[cid].snap_rate = SRVCLIENT_SNAPRATE_FULL;
					
				if(snapstorage_get(&clients[cid].snapshots, clients[cid].last_acked_snapshot, &tagtime, 0, 0) >= 0)
					clients[cid].latency = (int)(((time_get()-tagtime)*1000)/time_freq());

				/* add message to report the input timing */
				/* skip packets that are old */
				if(tick > clients[cid].last_input_tick)
				{
					int time_left = ((server_tick_start_time(tick)-time_get())*1000) / time_freq();
					msg_pack_start_system(NETMSG_INPUTTIMING, 0);
					msg_pack_int(tick);
					msg_pack_int(time_left);
					msg_pack_end();
					server_send_msg(cid);
				}

				clients[cid].last_input_tick = tick;

				input = &clients[cid].inputs[clients[cid].current_input];
				
				if(tick <= server_tick())
					tick = server_tick()+1;

				input->game_tick = tick;
				
				for(i = 0; i < size/4; i++)
					input->data[i] = msg_unpack_int();
				
				mem_copy(clients[cid].latestinput.data, input->data, MAX_INPUT_SIZE*sizeof(int));
				
				clients[cid].current_input++;
				clients[cid].current_input %= 200;
			
				/* call the mod with the fresh input data */
				if(clients[cid].state == SRVCLIENT_STATE_INGAME)
					mods_client_direct_input(cid, clients[cid].latestinput.data);
			}
			else if(msg == NETMSG_RCON_CMD)
			{
				const char *cmd = msg_unpack_string();
				
				if(msg_unpack_error() == 0 && clients[cid].authed)
				{
					dbg_msg("server", "cid=%d rcon='%s'", cid, cmd);
					console_execute_line(cmd);
				}
			}
			else if(msg == NETMSG_RCON_AUTH)
			{
				const char *pw;
				msg_unpack_string(); /* login name, not used */
				pw = msg_unpack_string();
				
				if(msg_unpack_error() == 0)
				{
					if(config.sv_rcon_password[0] == 0)
					{
						server_send_rcon_line(cid, "No rcon password set on server. Set sv_rcon_password to enable the remote console.");
					}
					else if(strcmp(pw, config.sv_rcon_password) == 0)
					{
						msg_pack_start_system(NETMSG_RCON_AUTH_STATUS, MSGFLAG_VITAL);
						msg_pack_int(1);
						msg_pack_end();
						server_send_msg(cid);
						
						clients[cid].authed = 1;
						server_send_rcon_line(cid, "Authentication successful. Remote console access granted.");
						dbg_msg("server", "cid=%d authed", cid);
					}
					else
					{
						server_send_rcon_line(cid, "Wrong password.");
					}
				}
			}
			else if(msg == NETMSG_PING)
			{
				msg_pack_start_system(NETMSG_PING_REPLY, 0);
				msg_pack_end();
				server_send_msg(cid);
			}
			else
			{
				char hex[] = "0123456789ABCDEF";
				char buf[512];
				int b;

				for(b = 0; b < packet->data_size && b < 32; b++)
				{
					buf[b*3] = hex[((const unsigned char *)packet->data)[b]>>4];
					buf[b*3+1] = hex[((const unsigned char *)packet->data)[b]&0xf];
					buf[b*3+2] = ' ';
					buf[b*3+3] = 0;
				}

				dbg_msg("server", "strange message cid=%d msg=%d data_size=%d", cid, msg, packet->data_size);
				dbg_msg("server", "%s", buf);
				
			}
		}
		else
		{
			/* game message */
			if(clients[cid].state >= SRVCLIENT_STATE_READY)
				mods_message(msg, cid);
		}
	}
Beispiel #24
0
void CEventVariable::Set(float Value)
{
    m_Type = EVENT_TYPE_FLOAT;
    Allocate(16);
    mem_copy(m_pData, &Value, sizeof(Value));
}
void CMenus::RenderSettingsPlayer(CUIRect MainView)
{
	CUIRect Button;
	CUIRect LeftView, RightView;

	MainView.VSplitLeft(MainView.w/2, &LeftView, &RightView);
    LeftView.HSplitTop(20.0f, &Button, &LeftView);

	// render settings
	{
		char aBuf[128];

		LeftView.HSplitTop(20.0f, &Button, &LeftView);
		str_format(aBuf, sizeof(aBuf), "%s:", Localize("Name"));
		UI()->DoLabel(&Button, aBuf, 14.0, -1);
		Button.VSplitLeft(80.0f, 0, &Button);
		Button.VSplitLeft(180.0f, &Button, 0);
		static float Offset = 0.0f;
		if(DoEditBox(g_Config.m_PlayerName, &Button, g_Config.m_PlayerName, sizeof(g_Config.m_PlayerName), 14.0f, &Offset))
			m_NeedSendinfo = true;

		// extra spacing
		LeftView.HSplitTop(10.0f, 0, &LeftView);

		static int s_DynamicCameraButton = 0;
		LeftView.HSplitTop(20.0f, &Button, &LeftView);
		if(DoButton_CheckBox(&s_DynamicCameraButton, Localize("Dynamic Camera"), g_Config.m_ClMouseDeadzone != 0, &Button))
		{

			if(g_Config.m_ClMouseDeadzone)
			{
				g_Config.m_ClMouseFollowfactor = 0;
				g_Config.m_ClMouseMaxDistance = 400;
				g_Config.m_ClMouseDeadzone = 0;
			}
			else
			{
				g_Config.m_ClMouseFollowfactor = 60;
				g_Config.m_ClMouseMaxDistance = 1000;
				g_Config.m_ClMouseDeadzone = 300;
			}
		}

		LeftView.HSplitTop(20.0f, &Button, &LeftView);
		if(DoButton_CheckBox(&g_Config.m_ClAutoswitchWeapons, Localize("Switch weapon on pickup"), g_Config.m_ClAutoswitchWeapons, &Button))
			g_Config.m_ClAutoswitchWeapons ^= 1;

		LeftView.HSplitTop(20.0f, &Button, &LeftView);
		if(DoButton_CheckBox(&g_Config.m_ClNameplates, Localize("Show name plates"), g_Config.m_ClNameplates, &Button))
			g_Config.m_ClNameplates ^= 1;

		//if(config.cl_nameplates)
		{
			LeftView.HSplitTop(20.0f, &Button, &LeftView);
			Button.VSplitLeft(15.0f, 0, &Button);
			if(DoButton_CheckBox(&g_Config.m_ClNameplatesAlways, Localize("Always show name plates"), g_Config.m_ClNameplatesAlways, &Button))
				g_Config.m_ClNameplatesAlways ^= 1;
		}

        {
            const CSkins::CSkin *pOwnSkin = m_pClient->m_pSkins->Get(max(0, m_pClient->m_pSkins->Find(g_Config.m_PlayerSkin)));

            CTeeRenderInfo OwnSkinInfo;
            OwnSkinInfo.m_Texture = pOwnSkin->m_OrgTexture;
            OwnSkinInfo.m_ColorBody = vec4(1, 1, 1, 1);
            OwnSkinInfo.m_ColorFeet = vec4(1, 1, 1, 1);

            if(g_Config.m_PlayerUseCustomColor)
            {
                OwnSkinInfo.m_ColorBody = m_pClient->m_pSkins->GetColorV4(g_Config.m_PlayerColorBody);
                OwnSkinInfo.m_ColorFeet = m_pClient->m_pSkins->GetColorV4(g_Config.m_PlayerColorFeet);
                OwnSkinInfo.m_Texture = pOwnSkin->m_ColorTexture;
            }

            OwnSkinInfo.m_Size = UI()->Scale()*50.0f;

            LeftView.HSplitTop(20.0f, &Button, &LeftView);
            LeftView.HSplitTop(20.0f, &Button, &LeftView);

            str_format(aBuf, sizeof(aBuf), "%s:", Localize("Your skin"));
            UI()->DoLabel(&Button, aBuf, 14.0, -1);

            CUIRect SkinRect;
            LeftView.VSplitLeft(LeftView.w/1.2f, &SkinRect, 0);
            SkinRect.HSplitTop(50.0f, &SkinRect, 0);
            RenderTools()->DrawUIRect(&SkinRect, vec4(1, 1, 1, 0.25f), CUI::CORNER_ALL, 10.0f);

            Button.VSplitLeft(30.0f, 0, &Button);
            Button.HSplitTop(50.0f, 0, &Button);
            RenderTools()->RenderTee(CAnimState::GetIdle(), &OwnSkinInfo, 0, vec2(1, 0), vec2(Button.x, Button.y));

            LeftView.HSplitTop(20.0f, &Button, &LeftView);
            Button.HSplitTop(15.0f, 0, &Button);
            Button.VSplitLeft(100.0f, 0, &Button);

            str_format(aBuf, sizeof(aBuf), "%s", g_Config.m_PlayerSkin);
			CTextCursor Cursor;
			TextRender()->SetCursor(&Cursor, Button.x, Button.y, 14.0f, TEXTFLAG_RENDER|TEXTFLAG_STOP_AT_END);
			Cursor.m_LineWidth = SkinRect.w-(Button.x-SkinRect.x)-5.0f;
			TextRender()->TextEx(&Cursor, aBuf, -1);
        }

		RightView.HSplitTop(20.0f, &Button, &RightView);
		RightView.HSplitTop(20.0f, &Button, &RightView);

		if(DoButton_CheckBox(&g_Config.m_PlayerColorBody, Localize("Custom colors"), g_Config.m_PlayerUseCustomColor, &Button))
		{
			g_Config.m_PlayerUseCustomColor = g_Config.m_PlayerUseCustomColor?0:1;
			m_NeedSendinfo = true;
		}

		if(g_Config.m_PlayerUseCustomColor)
		{
			int *paColors[2];
			paColors[0] = &g_Config.m_PlayerColorBody;
			paColors[1] = &g_Config.m_PlayerColorFeet;

			const char *paParts[] = {
				Localize("Body"),
				Localize("Feet")};
			const char *paLabels[] = {
				Localize("Hue"),
				Localize("Sat."),
				Localize("Lht.")};
			static int s_aColorSlider[2][3] = {{0}};
			//static float v[2][3] = {{0, 0.5f, 0.25f}, {0, 0.5f, 0.25f}};

			for(int i = 0; i < 2; i++)
			{
				CUIRect Text;
				RightView.HSplitTop(20.0f, &Text, &RightView);
				Text.VSplitLeft(15.0f, 0, &Text);
				UI()->DoLabel(&Text, paParts[i], 14.0f, -1);

				int PrevColor = *paColors[i];
				int Color = 0;
				for(int s = 0; s < 3; s++)
				{
					CUIRect Text;
					RightView.HSplitTop(19.0f, &Button, &RightView);
					Button.VSplitLeft(30.0f, 0, &Button);
					Button.VSplitLeft(70.0f, &Text, &Button);
					Button.VSplitRight(5.0f, &Button, 0);
					Button.HSplitTop(4.0f, 0, &Button);

					float k = ((PrevColor>>((2-s)*8))&0xff)  / 255.0f;
					k = DoScrollbarH(&s_aColorSlider[i][s], &Button, k);
					Color <<= 8;
					Color += clamp((int)(k*255), 0, 255);
					UI()->DoLabel(&Text, paLabels[s], 15.0f, -1);

				}

				if(*paColors[i] != Color)
					m_NeedSendinfo = true;

				*paColors[i] = Color;
				RightView.HSplitTop(5.0f, 0, &RightView);
			}
		}

        MainView.HSplitTop(MainView.h/2, 0, &MainView);

		// render skinselector
		static bool s_InitSkinlist = true;
		static sorted_array<const CSkins::CSkin *> s_paSkinList;
		static float s_ScrollValue = 0;
		if(s_InitSkinlist)
		{
			s_paSkinList.clear();
			for(int i = 0; i < m_pClient->m_pSkins->Num(); ++i)
			{
				const CSkins::CSkin *s = m_pClient->m_pSkins->Get(i);
				// no special skins
				if(s->m_aName[0] == 'x' && s->m_aName[1] == '_')
					continue;
				s_paSkinList.add(s);
			}
			s_InitSkinlist = false;
		}

		int OldSelected = -1;
		UiDoListboxStart(&s_InitSkinlist, &MainView, 50.0f, Localize("Skins"), "", s_paSkinList.size(), 4, OldSelected, s_ScrollValue);

		for(int i = 0; i < s_paSkinList.size(); ++i)
		{
			const CSkins::CSkin *s = s_paSkinList[i];
			if(s == 0)
				continue;

			if(str_comp(s->m_aName, g_Config.m_PlayerSkin) == 0)
				OldSelected = i;

			CListboxItem Item = UiDoListboxNextItem(&s_paSkinList[i], OldSelected == i);
			if(Item.m_Visible)
			{
				CTeeRenderInfo Info;
				Info.m_Texture = s->m_OrgTexture;
				Info.m_ColorBody = vec4(1, 1, 1, 1);
				Info.m_ColorFeet = vec4(1, 1, 1, 1);

				if(g_Config.m_PlayerUseCustomColor)
				{
					Info.m_ColorBody = m_pClient->m_pSkins->GetColorV4(g_Config.m_PlayerColorBody);
					Info.m_ColorFeet = m_pClient->m_pSkins->GetColorV4(g_Config.m_PlayerColorFeet);
					Info.m_Texture = s->m_ColorTexture;
				}

				Info.m_Size = UI()->Scale()*50.0f;
				Item.m_Rect.HSplitTop(5.0f, 0, &Item.m_Rect); // some margin from the top
				RenderTools()->RenderTee(CAnimState::GetIdle(), &Info, 0, vec2(1, 0), vec2(Item.m_Rect.x+Item.m_Rect.w/2, Item.m_Rect.y+Item.m_Rect.h/2));

				if(g_Config.m_Debug)
				{
					vec3 BloodColor = g_Config.m_PlayerUseCustomColor ? m_pClient->m_pSkins->GetColorV3(g_Config.m_PlayerColorBody) : s->m_BloodColor;
					Graphics()->TextureSet(-1);
					Graphics()->QuadsBegin();
					Graphics()->SetColor(BloodColor.r, BloodColor.g, BloodColor.b, 1.0f);
					IGraphics::CQuadItem QuadItem(Item.m_Rect.x, Item.m_Rect.y, 12, 12);
					Graphics()->QuadsDrawTL(&QuadItem, 1);
					Graphics()->QuadsEnd();
				}
			}
		}

		const int NewSelected = UiDoListboxEnd(&s_ScrollValue, 0);
		if(OldSelected != NewSelected)
		{
			mem_copy(g_Config.m_PlayerSkin, s_paSkinList[NewSelected]->m_aName, sizeof(g_Config.m_PlayerSkin));
			m_NeedSendinfo = true;
		}
	}
Beispiel #26
0
void CEventVariable::Set(bool Value)
{
    m_Type = EVENT_TYPE_BOOL;
    Allocate(16);
    mem_copy(m_pData, &Value, sizeof(Value));
}
Beispiel #27
0
int main(void)
{
    dbg_logger_stdout();
    char aUserdir[1024] = {0};
    char aPixelFile[1024] = {0};
    int PngCounter = 0;

    fs_storage_path("Teeworlds", aUserdir, sizeof(aUserdir));
    str_format(aPixelFile, sizeof(aPixelFile), "%s/tmp/pixelstream/video.stream", aUserdir);
    IOHANDLE PixelStream = io_open(aPixelFile, IOFLAG_READ);

    long long t = 0;
    long long tOld = 0;
    long long tOldAdj = 0;
    unsigned char *pData = 0;
    unsigned char *pDataOld = 0;
    unsigned char *pDataMixed = 0;
    unsigned char *pTempRow = 0;

    CThreadData *pThreadData = new CThreadData();
    mem_zero(pThreadData, sizeof(CThreadData));

    int64 StartTime = time_get();
    int64 SpeedTime = time_get();
    while(PixelStream)
    {
        int Size = 0;
        int W = 0;
        int H = 0;
        int len = io_read(PixelStream, &t, sizeof(t));
        io_read(PixelStream, &Size, sizeof(Size));
        io_read(PixelStream, &W, sizeof(W));
        io_read(PixelStream, &H, sizeof(H));

        if (len == 0)
            break;

        if (!pData)
            pData = new unsigned char[Size];
        if (!pDataOld)
            pDataOld = new unsigned char[Size];
        if (!pDataMixed)
            pDataMixed = new unsigned char[Size];
        if (!pTempRow)
            pTempRow = new unsigned char[W * 3];

        io_read(PixelStream, pData, Size);

        if (pThreadData->m_Size == 0)
        {
            pThreadData->m_Size = Size;
            pThreadData->m_H = H;
            pThreadData->m_W = W;
            thread_detach(thread_create(RotThread, pThreadData));
        }

        int i = 0;
        while(1)
        {
            if (pThreadData->m_pDataIn[i] == 0)
            {
                pThreadData->m_CounterIn++;
                pThreadData->m_aIndexIn[i] = pThreadData->m_CounterIn;
                unsigned char *p = new unsigned char[Size];
                mem_copy(p, pData, Size);
                pThreadData->m_pDataIn[i] = p;
            }
            i++;
            if (i == 10)
                break;
            if (THREADWAITDELAY)
                thread_sleep(THREADWAITDELAY);
        }
        while(1)
        {
            int MinIndex = 0;
            int MinI= 0;
            for (int i = 0; i < 10; i++)
            {
                if (pThreadData->m_pDataOut[i] != 0 && (MinIndex == 0 || MinIndex > pThreadData->m_aIndexOut[i]))
                {
                    MinIndex = pThreadData->m_aIndexOut[i];
                    MinI = i;
                }
            }
            if (MinIndex != 0)
            {
                mem_copy(pData, pThreadData->m_pDataOut[MinI], Size);
                delete []pThreadData->m_pDataOut[MinI];
                pThreadData->m_pDataOut[MinI] = 0;
                break;
            }
            if (THREADWAITDELAY)
                thread_sleep(THREADWAITDELAY);
        }

        float tAdj = 0.0f;
        if (tOld && tOld + tAdj + FRAMETIME < t)
        {
            while(tOld && tOld + tAdj + FRAMETIME < t)
            {
                PngCounter++;
                char aBuf[1024];
                if (PngCounter < 10)
                    str_format(aBuf, sizeof(aBuf), "%s/tmp/pixelstream/png0000%i.png", aUserdir, PngCounter);
                if (PngCounter < 100)
                    str_format(aBuf, sizeof(aBuf), "%s/tmp/pixelstream/png000%i.png", aUserdir, PngCounter);
                if (PngCounter < 1000)
                    str_format(aBuf, sizeof(aBuf), "%s/tmp/pixelstream/png00%i.png", aUserdir, PngCounter);
                if (PngCounter < 10000)
                    str_format(aBuf, sizeof(aBuf), "%s/tmp/pixelstream/png0%i.png", aUserdir, PngCounter);
                if (PngCounter < 100000)
                    str_format(aBuf, sizeof(aBuf), "%s/tmp/pixelstream/png%i.png", aUserdir, PngCounter);

                #if THREADCOUNT > 0
                CBlendThreadData *apBlendData[THREADCOUNT];
                for (int i = 0; i < THREADCOUNT; i++)
                {
                    apBlendData[i] = new CBlendThreadData();
                    mem_zero(apBlendData[i], sizeof(CBlendThreadData));
                    apBlendData[i]->m_pIn1 = pData;
                    apBlendData[i]->m_pIn2 = pDataOld;
                    apBlendData[i]->m_pOut = pDataMixed;
                    apBlendData[i]->m_Size = Size;
                    apBlendData[i]->m_Steps = THREADCOUNT;
                    apBlendData[i]->m_Start = i;
                    apBlendData[i]->m_Mix = 1.0f - (tAdj + FRAMETIMEHALF) / ((float)(t - tOld));
                    thread_detach(thread_create(BlendThread, apBlendData[i]));
                }
                while (1)
                {
                    bool Done = true;
                    for (int i = 0; i < THREADCOUNT; i++)
                    {
                        if (apBlendData[i]->m_Finished == false)
                        {
                            Done = false;
                            break;
                        }
                    }
                    if (THREADWAITDELAY)
                        thread_sleep(THREADWAITDELAY);
                    if (Done)
                        break;
                }
                #else
                for (int i = 0; i < Size; i++)
                {
                    pDataMixed[i] = mix(pData[i], pDataOld[i], 1.0f - (tAdj + FRAMETIMEHALF) / ((float)(t - tOld)));
                }
                #endif

                png_t Png;
                png_init(0,0);
                png_open_file_write(&Png, aBuf); // ignore_convention
                png_set_data(&Png, W, H, 8, PNG_TRUECOLOR, (unsigned char *)pDataMixed); // ignore_convention
                png_close_file(&Png); // ignore_convention

                if (time_get() - SpeedTime > time_freq())
                {
                    dbg_msg("Frame", "%i (Avg: %.2f s)", PngCounter, ((float)(time_get() - StartTime) / (float)time_freq()) / (float)PngCounter);
                    dbg_msg("FPS", "%.f", (float)PngCounter / ((float)(time_get() - StartTime) / (float)time_freq()));
                    SpeedTime = time_get();
                }

                tAdj = tAdj + FRAMETIME;
            }
        }
        else
        {
            PngCounter++;
            char aBuf[1024];
            if (PngCounter < 10)
                str_format(aBuf, sizeof(aBuf), "%s/tmp/pixelstream/png0000%i.png", aUserdir, PngCounter);
            if (PngCounter < 100)
                str_format(aBuf, sizeof(aBuf), "%s/tmp/pixelstream/png000%i.png", aUserdir, PngCounter);
            if (PngCounter < 1000)
                str_format(aBuf, sizeof(aBuf), "%s/tmp/pixelstream/png00%i.png", aUserdir, PngCounter);
            if (PngCounter < 10000)
                str_format(aBuf, sizeof(aBuf), "%s/tmp/pixelstream/png0%i.png", aUserdir, PngCounter);
            if (PngCounter < 100000)
                str_format(aBuf, sizeof(aBuf), "%s/tmp/pixelstream/png%i.png", aUserdir, PngCounter);

            png_t Png;
            png_init(0,0);
            png_open_file_write(&Png, aBuf); // ignore_convention
            png_set_data(&Png, W, H, 8, PNG_TRUECOLOR, (unsigned char *)pData); // ignore_convention
            png_close_file(&Png); // ignore_convention

            if (time_get() - SpeedTime > time_freq())
            {
                dbg_msg("Frame", "%i (Avg: %.2f s)", PngCounter, ((float)(time_get() - StartTime) / (float)time_freq()) / (float)PngCounter);
                dbg_msg("FPS", "%.f", (float)PngCounter / ((float)(time_get() - StartTime) / (float)time_freq()));
                SpeedTime = time_get();
            }

        }

        mem_copy(pDataOld, pData, Size);
        tOld = t;
    }
    delete[] pData;
    delete[] pDataOld;
    delete[] pDataMixed;
    return 0;
}
Beispiel #28
0
void CEventVariable::Set(char Value)
{
    m_Type = EVENT_TYPE_CHAR;
    Allocate(16);
    mem_copy(m_pData, &Value, sizeof(Value));
}
Beispiel #29
0
bool CChat::OnInput(IInput::CEvent Event)
{
	if(m_Mode == MODE_NONE)
		return false;

	if(Event.m_Flags&IInput::FLAG_PRESS && Event.m_Key == KEY_ESCAPE)
	{
		m_Mode = MODE_NONE;
		m_pClient->OnRelease();
	}
	else if(Event.m_Flags&IInput::FLAG_PRESS && (Event.m_Key == KEY_RETURN || Event.m_Key == KEY_KP_ENTER))
	{
		if(m_Input.GetString()[0])
		{
			bool AddEntry = false;

			if(m_LastChatSend+time_freq() < time_get())
			{
				Say(m_Mode == MODE_ALL ? 0 : 1, m_Input.GetString());
				AddEntry = true;
			}
			else if(m_PendingChatCounter < 3)
			{
				++m_PendingChatCounter;
				AddEntry = true;
			}

			if(AddEntry)
			{
				CHistoryEntry *pEntry = m_History.Allocate(sizeof(CHistoryEntry)+m_Input.GetLength());
				pEntry->m_Team = m_Mode == MODE_ALL ? 0 : 1;
				mem_copy(pEntry->m_aText, m_Input.GetString(), m_Input.GetLength()+1);
			}
		}
		m_pHistoryEntry = 0x0;
		m_Mode = MODE_NONE;
		m_pClient->OnRelease();
	}
	if(Event.m_Flags&IInput::FLAG_PRESS && Event.m_Key == KEY_TAB)
	{
		// fill the completion buffer
		if(m_CompletionChosen < 0)
		{
			const char *pCursor = m_Input.GetString()+m_Input.GetCursorOffset();
			for(int Count = 0; Count < m_Input.GetCursorOffset() && *(pCursor-1) != ' '; --pCursor, ++Count);
			m_PlaceholderOffset = pCursor-m_Input.GetString();

			for(m_PlaceholderLength = 0; *pCursor && *pCursor != ' '; ++pCursor)
				++m_PlaceholderLength;

			str_copy(m_aCompletionBuffer, m_Input.GetString()+m_PlaceholderOffset, min(static_cast<int>(sizeof(m_aCompletionBuffer)), m_PlaceholderLength+1));
		}

		// find next possible name
		const char *pCompletionString = 0;
		if(m_CompletionChosen < 0 && m_CompletionFav >= 0)
			m_CompletionChosen = m_CompletionFav;
		else
		{
			if (m_ReverseCompletion)
				m_CompletionChosen = (m_CompletionChosen - 1 + 2 * MAX_CLIENTS) % (2 * MAX_CLIENTS);
			else
				m_CompletionChosen = (m_CompletionChosen + 1) % (2 * MAX_CLIENTS);
		}

		for(int i = 0; i < 2*MAX_CLIENTS; ++i)
		{
			int SearchType;
			int Index;

			if(m_ReverseCompletion)
			{
				SearchType = ((m_CompletionChosen-i +2*MAX_CLIENTS)%(2*MAX_CLIENTS))/MAX_CLIENTS;
				Index = (m_CompletionChosen-i + MAX_CLIENTS )%MAX_CLIENTS;
			}
			else
			{
				SearchType = ((m_CompletionChosen+i)%(2*MAX_CLIENTS))/MAX_CLIENTS;
				Index = (m_CompletionChosen+i)%MAX_CLIENTS;
			}

			if(!m_pClient->m_aClients[Index].m_Active)
				continue;

			bool Found = false;
			if(SearchType == 1)
			{
				if(str_comp_nocase_num(m_pClient->m_aClients[Index].m_aName, m_aCompletionBuffer, str_length(m_aCompletionBuffer)) &&
					str_find_nocase(m_pClient->m_aClients[Index].m_aName, m_aCompletionBuffer))
					Found = true;
			}
			else if(!str_comp_nocase_num(m_pClient->m_aClients[Index].m_aName, m_aCompletionBuffer, str_length(m_aCompletionBuffer)))
				Found = true;

			if(Found)
			{
				pCompletionString = m_pClient->m_aClients[Index].m_aName;
				m_CompletionChosen = Index+SearchType*MAX_CLIENTS;
				m_CompletionFav = m_CompletionChosen;
				break;
			}
		}

		// insert the name
		if(pCompletionString)
		{
			char aBuf[256];
			// add part before the name
			str_copy(aBuf, m_Input.GetString(), min(static_cast<int>(sizeof(aBuf)), m_PlaceholderOffset+1));

			// add the name
			str_append(aBuf, pCompletionString, sizeof(aBuf));

			// add seperator
			const char *pSeparator = "";
			if(*(m_Input.GetString()+m_PlaceholderOffset+m_PlaceholderLength) != ' ')
				pSeparator = m_PlaceholderOffset == 0 ? ": " : " ";
			else if(m_PlaceholderOffset == 0)
				pSeparator = ":";
			if(*pSeparator)
				str_append(aBuf, pSeparator, sizeof(aBuf));

			// add part after the name
			str_append(aBuf, m_Input.GetString()+m_PlaceholderOffset+m_PlaceholderLength, sizeof(aBuf));

			m_PlaceholderLength = str_length(pSeparator)+str_length(pCompletionString);
			m_OldChatStringLength = m_Input.GetLength();
			m_Input.Set(aBuf);
			m_Input.SetCursorOffset(m_PlaceholderOffset+m_PlaceholderLength);
			m_InputUpdate = true;
		}
	}
	else
	{
		m_OldChatStringLength = m_Input.GetLength();
		if(m_Input.ProcessInput(Event))
		{
			m_InputUpdate = true;
			
			// reset name completion process
			m_CompletionChosen = -1;
		}
	}

	if(Event.m_Flags&IInput::FLAG_PRESS && Event.m_Key == KEY_LCTRL)
		m_ReverseCompletion = true;
	else if(Event.m_Flags&IInput::FLAG_RELEASE && Event.m_Key == KEY_LCTRL)
		m_ReverseCompletion = false;

	if(Event.m_Flags&IInput::FLAG_PRESS && Event.m_Key == KEY_UP)
	{
		if(m_pHistoryEntry)
		{
			CHistoryEntry *pTest = m_History.Prev(m_pHistoryEntry);

			if(pTest)
				m_pHistoryEntry = pTest;
		}
		else
			m_pHistoryEntry = m_History.Last();

		if(m_pHistoryEntry)
			m_Input.Set(m_pHistoryEntry->m_aText);
	}
	else if (Event.m_Flags&IInput::FLAG_PRESS && Event.m_Key == KEY_DOWN)
	{
		if(m_pHistoryEntry)
			m_pHistoryEntry = m_History.Next(m_pHistoryEntry);

		if (m_pHistoryEntry)
			m_Input.Set(m_pHistoryEntry->m_aText);
		else
			m_Input.Clear();
	}

	return true;
}
Beispiel #30
0
/*
	TODO: chopp up this function into smaller working parts
*/
int CNetServer::Recv(CNetChunk *pChunk)
{
    unsigned Now = time_timestamp();

    while(1)
    {
        NETADDR Addr;

        // check for a chunk
        if(m_RecvUnpacker.FetchChunk(pChunk))
            return 1;

        // TODO: empty the recvinfo
        int Bytes = net_udp_recv(m_Socket, &Addr, m_RecvUnpacker.m_aBuffer, NET_MAX_PACKETSIZE);

        // no more packets for now
        if(Bytes <= 0)
            break;

        if(CNetBase::UnpackPacket(m_RecvUnpacker.m_aBuffer, Bytes, &m_RecvUnpacker.m_Data) == 0)
        {
            CBan *pBan = 0;
            NETADDR BanAddr = Addr;
            int IpHash = (BanAddr.ip[0]+BanAddr.ip[1]+BanAddr.ip[2]+BanAddr.ip[3]+BanAddr.ip[4]+BanAddr.ip[5]+BanAddr.ip[6]+BanAddr.ip[7]+
                          BanAddr.ip[8]+BanAddr.ip[9]+BanAddr.ip[10]+BanAddr.ip[11]+BanAddr.ip[12]+BanAddr.ip[13]+BanAddr.ip[14]+BanAddr.ip[15])&0xff;
            int Found = 0;
            BanAddr.port = 0;

            // search a ban
            for(pBan = m_aBans[IpHash]; pBan; pBan = pBan->m_pHashNext)
            {
                if(net_addr_comp(&pBan->m_Info.m_Addr, &BanAddr) == 0)
                    break;
            }

            // check if we just should drop the packet
            if(pBan)
            {
                // banned, reply with a message
                char BanStr[128];
                if(pBan->m_Info.m_Expires && pBan->m_Info.m_Expires != -1)
                {
                    int Mins = ((pBan->m_Info.m_Expires - Now)+59)/60;
                    if(Mins == 1)
                        str_format(BanStr, sizeof(BanStr), "Banned for 1 minute (%s)", pBan->m_Info.m_Reason);
                    else
                        str_format(BanStr, sizeof(BanStr), "Banned for %d minutes (%s)", Mins, pBan->m_Info.m_Reason);
                }
                else
                    str_format(BanStr, sizeof(BanStr), "Banned for life (%s)", pBan->m_Info.m_Reason);
                CNetBase::SendControlMsg(m_Socket, &Addr, 0, NET_CTRLMSG_CLOSE, BanStr, str_length(BanStr)+1);
                continue;
            }

            if(m_RecvUnpacker.m_Data.m_Flags&NET_PACKETFLAG_CONNLESS)
            {
                pChunk->m_Flags = NETSENDFLAG_CONNLESS;
                pChunk->m_ClientID = -1;
                pChunk->m_Address = Addr;
                pChunk->m_DataSize = m_RecvUnpacker.m_Data.m_DataSize;
                pChunk->m_pData = m_RecvUnpacker.m_Data.m_aChunkData;
                return 1;
            }
            else
            {
                // TODO: check size here
                if(m_RecvUnpacker.m_Data.m_Flags&NET_PACKETFLAG_CONTROL && m_RecvUnpacker.m_Data.m_aChunkData[0] == NET_CTRLMSG_CONNECT)
                {
                    Found = 0;

                    // check if we already got this client
                    for(int i = 0; i < MaxClients(); i++)
                    {
                        NETADDR PeerAddr = m_aSlots[i].m_Connection.PeerAddress();
                        if(m_aSlots[i].m_Connection.State() != NET_CONNSTATE_OFFLINE &&
                                net_addr_comp(&PeerAddr, &Addr) == 0)
                        {
                            Found = 1; // silent ignore.. we got this client already
                            break;
                        }
                    }

                    // client that wants to connect
                    if(!Found)
                    {
                        CNetChunk Packet;
                        char aBuffer[sizeof(BANMASTER_IPCHECK) + NETADDR_MAXSTRSIZE];
                        mem_copy(aBuffer, BANMASTER_IPCHECK, sizeof(BANMASTER_IPCHECK));
                        net_addr_str(&Addr, aBuffer + sizeof(BANMASTER_IPCHECK), sizeof(aBuffer) - sizeof(BANMASTER_IPCHECK));

                        Packet.m_ClientID = -1;
                        Packet.m_Flags = NETSENDFLAG_CONNLESS;
                        Packet.m_DataSize = str_length(aBuffer) + 1;
                        Packet.m_pData = aBuffer;

                        for(int i = 0; i < m_NumBanmasters; i++)
                        {
                            Packet.m_Address = m_aBanmasters[i];
                            Send(&Packet);
                        }

                        // only allow a specific number of players with the same ip
                        NETADDR ThisAddr = Addr, OtherAddr;
                        int FoundAddr = 1;
                        ThisAddr.port = 0;
                        for(int i = 0; i < MaxClients(); ++i)
                        {
                            if(m_aSlots[i].m_Connection.State() == NET_CONNSTATE_OFFLINE)
                                continue;

                            OtherAddr = m_aSlots[i].m_Connection.PeerAddress();
                            OtherAddr.port = 0;
                            if(!net_addr_comp(&ThisAddr, &OtherAddr))
                            {
                                if(FoundAddr++ >= m_MaxClientsPerIP)
                                {
                                    char aBuf[128];
                                    str_format(aBuf, sizeof(aBuf), "Only %d players with the same IP are allowed", m_MaxClientsPerIP);
                                    CNetBase::SendControlMsg(m_Socket, &Addr, 0, NET_CTRLMSG_CLOSE, aBuf, sizeof(aBuf));
                                    return 0;
                                }
                            }
                        }

                        for(int i = 0; i < MaxClients(); i++)
                        {
                            if(m_aSlots[i].m_Connection.State() == NET_CONNSTATE_OFFLINE)
                            {
                                Found = 1;
                                m_aSlots[i].m_Connection.Feed(&m_RecvUnpacker.m_Data, &Addr);
                                if(m_pfnNewClient)
                                    m_pfnNewClient(i, m_UserPtr);

                                break;
                            }
                        }

                        if(!Found)
                        {
                            const char FullMsg[] = "This server is full";
                            CNetBase::SendControlMsg(m_Socket, &Addr, 0, NET_CTRLMSG_CLOSE, FullMsg, sizeof(FullMsg));
                        }
                    }
                }
                else
                {
                    // normal packet, find matching slot
                    for(int i = 0; i < MaxClients(); i++)
                    {
                        NETADDR PeerAddr = m_aSlots[i].m_Connection.PeerAddress();
                        if(net_addr_comp(&PeerAddr, &Addr) == 0)
                        {
                            if(m_aSlots[i].m_Connection.Feed(&m_RecvUnpacker.m_Data, &Addr))
                            {
                                if(m_RecvUnpacker.m_Data.m_DataSize)
                                    m_RecvUnpacker.Start(&Addr, &m_aSlots[i].m_Connection, i);
                            }
                        }
                    }
                }
            }
        }
    }
    return 0;
}