Teeworlds 0.6

List of snap items

Note there is also documentation about snapshots in libtw2.

The network messages NETMSG_SNAP, NETMSG_SNAPEMPTY, NETMSG_SNAPSINGLE and NETMSG_SNAPSMALL contain snapshots which represent the current game state. The snapshot data is containing snap items which represent things like tees, projectiles and similar. All of those items are encoded as packed integers. The snapshot is build by the server and sent to the client.

Item order

For some snap items the order they appear in the snap matters. For example obj_game_info is usually the first item in the snap. And obj_client_info should not be added in the snap before it. Because the client code loops over all snap items in the order they were added. And when inserting the clients it looks at the obj_game_info->m_GameFlags and if the teams flag is set the clients tee is colored in team colors. If the obj_game_info would be after the obj_client_info the client would not know yet about it and assume no teams are set.

Known size table

type_id size name parameters description
1 10 obj_player_input int m_Direction;
int m_TargetX;
int m_TargetY;
int m_Jump;
int m_Fire;
int m_Hook;
int m_PlayerFlags;
int m_WantedWeapon;
int m_NextWeapon;
int m_PrevWeapon;
This is a special snap item that is not actually included in the snap. But instead sent by the client in the system message NETMSG_INPUT

The m_PlayerFlags field has the following flags:
  • PLAYERFLAG_PLAYING (1)
  • PLAYERFLAG_IN_MENU (2)
  • PLAYERFLAG_CHATTING (4)
  • PLAYERFLAG_SCOREBOARD (8)
  • PLAYERFLAG_AIM (16)
2 6 obj_projectile int m_X;
int m_Y;
int m_VelX;
int m_VelY;
int m_Type;
int m_StartTick;
desc
3 5 obj_laser int m_X;
int m_Y;
int m_FromX;
int m_FromY;
int m_StartTick;
desc
4 4 obj_pickup int m_X;
int m_Y;
int m_Type;
int m_Subtype;
m_Type can be on of those:
  • 0 - POWERUP_HEALTH
  • 1 - POWERUP_ARMOR
  • 2 - POWERUP_WEAPON
  • 3 - POWERUP_NINJA
m_Subtype is only used if the type is POWERUP_WEAPON
And its value can be one of those:
  • 0 - WEAPON_HAMMER
  • 1 - WEAPON_GUN
  • 2 - WEAPON_SHOTGUN
  • 3 - WEAPON_GRENADE
  • 4 - WEAPON_LASER
  • 5 - WEAPON_NINJA
5 3 obj_flag int m_X;
int m_Y;
int m_Team;
desc
6 8 obj_game_info int m_GameFlags;
int m_GameStateFlags;
int m_RoundStartTick;
int m_WarmupTimer;
int m_ScoreLimit;
int m_TimeLimit;
int m_RoundNum;
int m_RoundCurrent;
Possible m_GameFlags are:
  • GAMEFLAG_TEAMS (1)
  • GAMEFLAG_FLAGS (2)
Possible m_GameStateFlags are:
  • GAMESTATEFLAG_GAMEOVER (1)
  • GAMESTATEFLAG_SUDDENDEATH (2)
  • GAMESTATEFLAG_PAUSED (4)
Note these are flags and can be combined using bitwise operations. And are not mutually exclusive states.
7 4 obj_game_data int m_TeamscoreRed;
int m_TeamscoreBlue;
int m_FlagCarrierRed;
int m_FlagCarrierBlue;
desc
8 15 obj_character_core int m_Tick;
int m_X;
int m_Y;
int m_VelX;
int m_VelY;
int m_Angle;
int m_Direction;
int m_Jumped;
int m_HookedPlayer;
int m_HookState;
int m_HookTick;
int m_HookX;
int m_HookY;
int m_HookDx;
int m_HookDy;
This item is not being sent in the snap directly. It is only ever sent as part of obj_character. So the snap item type id 8 is unused.

<Zwelf> m_HookTick has the type NetTick in protocol.py, but is used as HookDuration. Starting with zero and incrementing one each tick until the roughly 60 ticks = 1.2s are passed.
9 22 obj_character /* core */
int m_Tick;
int m_X;
int m_Y;
int m_VelX;
int m_VelY;
int m_Angle;
int m_Direction;
int m_Jumped;
int m_HookedPlayer;
int m_HookState;
int m_HookTick;
int m_HookX;
int m_HookY;
int m_HookDx;
int m_HookDy;

/* character extension */
int m_PlayerFlags;
int m_Health;
int m_Armor;
int m_AmmoCount;
int m_Weapon;
int m_Emote;
int m_AttackTick;
desc
10 5 obj_player_info int m_Local;
int m_ClientID;
int m_Team;
int m_Score;
int m_Latency;
Unpacked by the client in gameclient.cpp
                        
    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]++;

    }
                        
                    
11 17 obj_client_info int m_Name0;
int m_Name1;
int m_Name2;
int m_Name3;
int m_Clan0;
int m_Clan1;
int m_Clan2;
int m_Country;
int m_Skin0;
int m_Skin1;
int m_Skin2;
int m_Skin3;
int m_Skin4;
int m_Skin5;
int m_UseCustomColor;
int m_ColorBody;
int m_ColorFeet;
This snap items ID field matches the corresponding Client ID. As you can see in this gameclient.cpp snippet.
                        
    if(Item.m_Type == NETOBJTYPE_CLIENTINFO)
    {
        const CNetObj_ClientInfo *pInfo = (const CNetObj_ClientInfo *)pData;
        int ClientID = Item.m_ID;
        if(ClientID < MAX_CLIENTS)
        {
            CClientData *pClient = &m_aClients[ClientID];
                        
                    
12 3 obj_spectator_info int m_SpectatorID;
int m_X;
int m_Y;
desc
13 2 event_common int m_X;
int m_Y;
This item is not being sent in the snap directly. It is only ever sent as part of other events. So the snap item type id 13 is unused.
14 2 event_explosion int m_X;
int m_Y;
desc
15 2 event_spawn int m_X;
int m_Y;
desc
16 2 event_hammerhit int m_X;
int m_Y;
desc
17 3 event_death /* common */
int m_X;
int m_Y;

/* death */
int m_ClientID;
desc
18 3 event_sound_global /* common */
int m_X;
int m_Y;

/* sound_global */
int m_SoundID;
desc
19 3 event_sound_world /* common */
int m_X;
int m_Y;

/* sound_world */
int m_SoundID;
desc
20 3 event_damage_indicator /* common */
int m_X;
int m_Y;

/* damage_indicator */
int m_Angle;
desc