Switched to a proper new recorder instead of using the auto one

This commit is contained in:
Corantin H 2019-05-21 12:49:19 +02:00
parent 817bdaf9cd
commit ac4d7085c5
12 changed files with 9074 additions and 51 deletions

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,424 @@
/* (c) Magnus Auvinen. See licence.txt in the root of the distribution for more information. */
/* If you are missing that file, acquire a complete release at teeworlds.com. */
#ifndef GAME_CLIENT_COMPONENTS_MENUS_H
#define GAME_CLIENT_COMPONENTS_MENUS_H
#include <base/vmath.h>
#include <base/tl/sorted_array.h>
#include <engine/demo.h>
#include <engine/friends.h>
#include <game/voting.h>
#include <game/client/component.h>
#include <game/client/ui.h>
// compnent to fetch keypresses, override all other input
class CMenusKeyBinder : public CComponent
{
public:
bool m_TakeKey;
bool m_GotKey;
IInput::CEvent m_Key;
int m_Modifier;
CMenusKeyBinder();
virtual bool OnInput(IInput::CEvent Event);
};
class CMenus : public CComponent
{
static ColorRGBA ms_GuiColor;
static ColorRGBA ms_ColorTabbarInactiveOutgame;
static ColorRGBA ms_ColorTabbarActiveOutgame;
static ColorRGBA ms_ColorTabbarInactiveIngame;
static ColorRGBA ms_ColorTabbarActiveIngame;
static ColorRGBA ms_ColorTabbarInactive;
static ColorRGBA ms_ColorTabbarActive;
float ButtonColorMul(const void *pID);
int DoButton_DemoPlayer(const void *pID, const char *pText, int Checked, const CUIRect *pRect);
int DoButton_Sprite(const void *pID, int ImageID, int SpriteID, int Checked, const CUIRect *pRect, int Corners);
int DoButton_Toggle(const void *pID, int Checked, const CUIRect *pRect, bool Active);
int DoButton_Menu(const void *pID, const char *pText, int Checked, const CUIRect *pRect);
int DoButton_MenuTab(const void *pID, const char *pText, int Checked, const CUIRect *pRect, int Corners);
int DoButton_CheckBox_Common(const void *pID, const char *pText, const char *pBoxText, const CUIRect *pRect);
int DoButton_CheckBox(const void *pID, const char *pText, int Checked, const CUIRect *pRect);
int DoButton_CheckBox_Number(const void *pID, const char *pText, int Checked, const CUIRect *pRect);
/*static void ui_draw_menu_button(const void *id, const char *text, int checked, const CUIRect *r, const void *extra);
static void ui_draw_keyselect_button(const void *id, const char *text, int checked, const CUIRect *r, const void *extra);
static void ui_draw_menu_tab_button(const void *id, const char *text, int checked, const CUIRect *r, const void *extra);
static void ui_draw_settings_tab_button(const void *id, const char *text, int checked, const CUIRect *r, const void *extra);
*/
int DoButton_Icon(int ImageId, int SpriteId, const CUIRect *pRect);
int DoButton_GridHeader(const void *pID, const char *pText, int Checked, const CUIRect *pRect);
//static void ui_draw_browse_icon(int what, const CUIRect *r);
//static void ui_draw_grid_header(const void *id, const char *text, int checked, const CUIRect *r, const void *extra);
/*static void ui_draw_checkbox_common(const void *id, const char *text, const char *boxtext, const CUIRect *r, const void *extra);
static void ui_draw_checkbox(const void *id, const char *text, int checked, const CUIRect *r, const void *extra);
static void ui_draw_checkbox_number(const void *id, const char *text, int checked, const CUIRect *r, const void *extra);
*/
int DoEditBox(void *pID, const CUIRect *pRect, char *pStr, unsigned StrSize, float FontSize, float *Offset, bool Hidden=false, int Corners=CUI::CORNER_ALL, const char *pEmptyText = "");
int DoClearableEditBox(void *pID, void *pClearID, const CUIRect *pRect, char *pStr, unsigned StrSize, float FontSize, float *Offset, bool Hidden=false, int Corners=CUI::CORNER_ALL, const char *pEmptyText = "");
//static int ui_do_edit_box(void *id, const CUIRect *rect, char *str, unsigned str_size, float font_size, bool hidden=false);
float DoScrollbarV(const void *pID, const CUIRect *pRect, float Current);
float DoScrollbarH(const void *pID, const CUIRect *pRect, float Current);
void DoButton_KeySelect(const void *pID, const char *pText, int Checked, const CUIRect *pRect);
int DoKeyReader(void *pID, const CUIRect *pRect, int Key, int Modifier, int *NewModifier);
//static int ui_do_key_reader(void *id, const CUIRect *rect, int key);
void UiDoGetButtons(int Start, int Stop, CUIRect View, CUIRect ScopeView);
struct CListboxItem
{
int m_Visible;
int m_Selected;
CUIRect m_Rect;
CUIRect m_HitRect;
};
void UiDoListboxStart(const void *pID, const CUIRect *pRect, float RowHeight, const char *pTitle, const char *pBottomText, int NumItems,
int ItemsPerRow, int SelectedIndex, float ScrollValue);
CListboxItem UiDoListboxNextItem(const void *pID, bool Selected = false, bool KeyEvents = true);
CListboxItem UiDoListboxNextRow();
int UiDoListboxEnd(float *pScrollValue, bool *pItemActivated, bool *pListBoxActive = 0);
//static void demolist_listdir_callback(const char *name, int is_dir, void *user);
//static void demolist_list_callback(const CUIRect *rect, int index, void *user);
int m_GamePage;
int m_Popup;
int m_ActivePage;
bool m_MenuActive;
bool m_UseMouseButtons;
vec2 m_MousePos;
bool m_MouseSlow;
int64 m_LastInput;
// loading
int m_LoadCurrent;
int m_LoadTotal;
//
char m_aMessageTopic[512];
char m_aMessageBody[512];
char m_aMessageButton[512];
void PopupMessage(const char *pTopic, const char *pBody, const char *pButton);
// TODO: this is a bit ugly but.. well.. yeah
enum { MAX_INPUTEVENTS = 32 };
static IInput::CEvent m_aInputEvents[MAX_INPUTEVENTS];
static int m_NumInputEvents;
// some settings
static float ms_ButtonHeight;
static float ms_ListheaderHeight;
static float ms_ListitemAdditionalHeight;
static float ms_FontmodHeight;
// for settings
bool m_NeedRestartSkins;
bool m_NeedRestartGraphics;
bool m_NeedRestartSound;
bool m_NeedRestartUpdate;
bool m_NeedRestartDDNet;
bool m_NeedSendinfo;
bool m_NeedSendDummyinfo;
int m_SettingPlayerPage;
//
bool m_EscapePressed;
bool m_EnterPressed;
bool m_DeletePressed;
// for map download popup
int64 m_DownloadLastCheckTime;
int m_DownloadLastCheckSize;
float m_DownloadSpeed;
// for call vote
int m_CallvoteSelectedOption;
int m_CallvoteSelectedPlayer;
char m_aCallvoteReason[VOTE_REASON_LENGTH];
char m_aFilterString[25];
// demo
enum
{
SORT_DEMONAME=0,
SORT_MARKERS,
SORT_LENGTH,
SORT_DATE,
};
struct CDemoItem
{
char m_aFilename[128];
char m_aName[128];
bool m_IsDir;
int m_StorageType;
time_t m_Date;
bool m_InfosLoaded;
bool m_Valid;
CDemoHeader m_Info;
CTimelineMarkers m_TimelineMarkers;
int NumMarkers() const
{
return ((m_TimelineMarkers.m_aNumTimelineMarkers[0]<<24)&0xFF000000) | ((m_TimelineMarkers.m_aNumTimelineMarkers[1]<<16)&0xFF0000) |
((m_TimelineMarkers.m_aNumTimelineMarkers[2]<<8)&0xFF00) | (m_TimelineMarkers.m_aNumTimelineMarkers[3]&0xFF);
}
int Length() const
{
return ((m_Info.m_aLength[0]<<24)&0xFF000000) | ((m_Info.m_aLength[1]<<16)&0xFF0000) |
((m_Info.m_aLength[2]<<8)&0xFF00) | (m_Info.m_aLength[3]&0xFF);
}
bool operator<(const CDemoItem &Other) const
{
if(!str_comp(m_aFilename, ".."))
return true;
if(!str_comp(Other.m_aFilename, ".."))
return false;
if(m_IsDir && !Other.m_IsDir)
return true;
if(!m_IsDir && Other.m_IsDir)
return false;
const CDemoItem &Left = g_Config.m_BrDemoSortOrder ? Other : *this;
const CDemoItem &Right = g_Config.m_BrDemoSortOrder ? *this : Other;
if(g_Config.m_BrDemoSort == SORT_DEMONAME)
return str_comp_nocase(Left.m_aFilename, Right.m_aFilename) < 0;
if(g_Config.m_BrDemoSort == SORT_DATE)
return Left.m_Date < Right.m_Date;
if(!Other.m_InfosLoaded)
return m_InfosLoaded;
if(!m_InfosLoaded)
return !Other.m_InfosLoaded;
if(g_Config.m_BrDemoSort == SORT_MARKERS)
return Left.NumMarkers() < Right.NumMarkers();
if(g_Config.m_BrDemoSort == SORT_LENGTH)
return Left.Length() < Right.Length();
// Unknown sort
return true;
}
};
//sorted_array<CDemoItem> m_lDemos;
char m_aCurrentDemoFolder[256];
char m_aCurrentDemoFile[64];
int m_DemolistSelectedIndex;
bool m_DemolistSelectedIsDir;
int m_DemolistStorageType;
void DemolistOnUpdate(bool Reset);
//void DemolistPopulate();
static int DemolistFetchCallback(const char *pName, time_t Date, int IsDir, int StorageType, void *pUser);
// friends
struct CFriendItem
{
const CFriendInfo *m_pFriendInfo;
int m_NumFound;
bool operator<(const CFriendItem &Other)
{
if(m_NumFound && !Other.m_NumFound)
return true;
else if(!m_NumFound && Other.m_NumFound)
return false;
else
{
int Result = str_comp(m_pFriendInfo->m_aName, Other.m_pFriendInfo->m_aName);
if(Result)
return Result < 0;
else
return str_comp(m_pFriendInfo->m_aClan, Other.m_pFriendInfo->m_aClan) < 0;
}
}
};
sorted_array<CFriendItem> m_lFriends;
int m_FriendlistSelectedIndex;
void FriendlistOnUpdate();
// found in menus.cpp
int Render();
//void render_background();
//void render_loading(float percent);
int RenderMenubar(CUIRect r);
void RenderNews(CUIRect MainView);
// found in menus_demo.cpp
static bool DemoFilterChat(const void *pData, int Size, void *pUser);
bool FetchHeader(CDemoItem &Item);
void FetchAllHeaders();
void RenderDemoPlayer(CUIRect MainView);
void RenderDemoList(CUIRect MainView);
// found in menus_ingame.cpp
void RenderGame(CUIRect MainView);
void RenderPlayers(CUIRect MainView);
void RenderServerInfo(CUIRect MainView);
void RenderServerControl(CUIRect MainView);
bool RenderServerControlKick(CUIRect MainView, bool FilterSpectators);
bool RenderServerControlServer(CUIRect MainView);
// found in menus_browser.cpp
int m_SelectedIndex;
int m_DoubleClickIndex;
int m_ScrollOffset;
void RenderServerbrowserServerList(CUIRect View);
void RenderServerbrowserServerDetail(CUIRect View);
void RenderServerbrowserFilters(CUIRect View);
void RenderServerbrowserFriends(CUIRect View);
void RenderServerbrowser(CUIRect MainView);
static void ConchainFriendlistUpdate(IConsole::IResult *pResult, void *pUserData, IConsole::FCommandCallback pfnCallback, void *pCallbackUserData);
static void ConchainServerbrowserUpdate(IConsole::IResult *pResult, void *pUserData, IConsole::FCommandCallback pfnCallback, void *pCallbackUserData);
// found in menus_settings.cpp
void RenderLanguageSelection(CUIRect MainView);
void RenderSettingsGeneral(CUIRect MainView);
void RenderSettingsPlayer(CUIRect MainView);
void RenderSettingsDummyPlayer(CUIRect MainView);
void RenderSettingsTee(CUIRect MainView);
void RenderSettingsControls(CUIRect MainView);
void RenderSettingsGraphics(CUIRect MainView);
void RenderSettingsSound(CUIRect MainView);
void RenderSettings(CUIRect MainView);
void SetActive(bool Active);
public:
void RenderBackground();
void UseMouseButtons(bool Use) { m_UseMouseButtons = Use; }
static CMenusKeyBinder m_Binder;
CMenus();
void RenderLoading();
void RenderUpdating(const char *pCaption, int current=0, int total=0);
bool IsActive() const { return m_MenuActive; }
virtual void OnInit();
virtual void OnStateChange(int NewState, int OldState);
virtual void OnReset();
virtual void OnRender();
virtual bool OnInput(IInput::CEvent Event);
virtual bool OnMouseMove(float x, float y);
enum
{
PAGE_NEWS=1,
PAGE_GAME,
PAGE_PLAYERS,
PAGE_SERVER_INFO,
PAGE_CALLVOTE,
PAGE_INTERNET,
PAGE_LAN,
PAGE_FAVORITES,
PAGE_DDNET,
PAGE_KOG,
PAGE_DEMOS,
PAGE_SETTINGS,
PAGE_SYSTEM,
PAGE_NETWORK,
PAGE_GHOST
};
// DDRace
int DoButton_CheckBox_DontCare(const void *pID, const char *pText, int Checked, const CUIRect *pRect);
sorted_array<CDemoItem> m_lDemos;
void DemolistPopulate();
bool m_Dummy;
const char *GetCurrentDemoFolder() const { return m_aCurrentDemoFolder; }
// Ghost
struct CGhostItem
{
char m_aFilename[256];
char m_aPlayer[MAX_NAME_LENGTH];
int m_Time;
int m_Slot;
bool m_Own;
CGhostItem() : m_Slot(-1), m_Own(false) { m_aFilename[0] = 0; }
bool operator<(const CGhostItem &Other) { return m_Time < Other.m_Time; }
bool Active() const { return m_Slot != -1; }
bool HasFile() const { return m_aFilename[0]; }
};
sorted_array<CGhostItem> m_lGhosts;
void GhostlistPopulate();
CGhostItem *GetOwnGhost();
void UpdateOwnGhost(CGhostItem Item);
void DeleteGhostItem(int Index);
void setPopup(int Popup) { m_Popup = Popup; }
int m_DemoPlayerState;
char m_aDemoPlayerPopupHint[256];
enum
{
POPUP_NONE=0,
POPUP_FIRST_LAUNCH,
POPUP_CONNECTING,
POPUP_MESSAGE,
POPUP_DISCONNECTED,
POPUP_PURE,
POPUP_LANGUAGE,
POPUP_COUNTRY,
POPUP_DELETE_DEMO,
POPUP_RENAME_DEMO,
POPUP_REMOVE_FRIEND,
POPUP_SOUNDERROR,
POPUP_PASSWORD,
POPUP_QUIT,
POPUP_DISCONNECT,
POPUP_DISCONNECT_DUMMY,
POPUP_REPLAY_ENABLING_ERROR,
// demo player states
DEMOPLAYER_NONE=0,
DEMOPLAYER_SLICE_SAVE,
};
private:
static int GhostlistFetchCallback(const char *pName, int IsDir, int StorageType, void *pUser);
// found in menus_ingame.cpp
void RenderInGameNetwork(CUIRect MainView);
void RenderGhost(CUIRect MainView);
// found in menus_settings.cpp
void RenderSettingsDDNet(CUIRect MainView);
void RenderSettingsHUD(CUIRect MainView);
};
#endif

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,425 @@
/* (c) Magnus Auvinen. See licence.txt in the root of the distribution for more information. */
/* If you are missing that file, acquire a complete release at teeworlds.com. */
#ifndef ENGINE_CLIENT_CLIENT_H
#define ENGINE_CLIENT_CLIENT_H
#include <memory>
#include <base/hash.h>
#include <engine/client/http.h>
#define CONNECTLINK "ddnet:"
class CGraph
{
public:
enum
{
// restrictions: Must be power of two
MAX_VALUES=128,
};
float m_Min, m_Max;
float m_aValues[MAX_VALUES];
float m_aColors[MAX_VALUES][3];
int m_Index;
void Init(float Min, float Max);
void ScaleMax();
void ScaleMin();
void Add(float v, float r, float g, float b);
void Render(IGraphics *pGraphics, int Font, float x, float y, float w, float h, const char *pDescription);
};
class CSmoothTime
{
int64 m_Snap;
int64 m_Current;
int64 m_Target;
CGraph m_Graph;
int m_SpikeCounter;
float m_aAdjustSpeed[2]; // 0 = down, 1 = up
public:
void Init(int64 Target);
void SetAdjustSpeed(int Direction, float Value);
int64 Get(int64 Now);
void UpdateInt(int64 Target);
void Update(CGraph *pGraph, int64 Target, int TimeLeft, int AdjustDirection);
};
class CClient : public IClient, public CDemoPlayer::IListener
{
// needed interfaces
IEngine *m_pEngine;
IEditor *m_pEditor;
IEngineInput *m_pInput;
IEngineGraphics *m_pGraphics;
IEngineSound *m_pSound;
IGameClient *m_pGameClient;
IEngineMap *m_pMap;
IConsole *m_pConsole;
IStorage *m_pStorage;
IUpdater *m_pUpdater;
IEngineMasterServer *m_pMasterServer;
enum
{
NUM_SNAPSHOT_TYPES=2,
PREDICTION_MARGIN=1000/50/2, // magic network prediction value
};
class CNetClient m_NetClient[3];
class CDemoPlayer m_DemoPlayer;
class CDemoRecorder m_DemoRecorder[RECORDER_MAX];
class CDemoEditor m_DemoEditor;
class CGhostRecorder m_GhostRecorder;
class CGhostLoader m_GhostLoader;
class CServerBrowser m_ServerBrowser;
class CUpdater m_Updater;
class CFriends m_Friends;
class CFriends m_Foes;
char m_aServerAddressStr[256];
unsigned m_SnapshotParts[2];
int64 m_LocalStartTime;
int m_DebugFont;
int replayCounter = 0;
int64 m_LastRenderTime;
float m_RenderFrameTimeLow;
float m_RenderFrameTimeHigh;
int m_RenderFrames;
NETADDR m_ServerAddress;
int m_SnapCrcErrors;
bool m_AutoScreenshotRecycle;
bool m_AutoStatScreenshotRecycle;
bool m_AutoCSVRecycle;
bool m_EditorActive;
bool m_SoundInitFailed;
bool m_ResortServerBrowser;
int m_AckGameTick[2];
int m_CurrentRecvTick[2];
int m_RconAuthed[2];
char m_RconPassword[32];
int m_UseTempRconCommands;
char m_Password[32];
bool m_SendPassword;
// version-checking
char m_aVersionStr[10];
// pinging
int64 m_PingStartTime;
char m_aCurrentMap[MAX_PATH_LENGTH];
char m_aCurrentMapPath[MAX_PATH_LENGTH];
char m_aTimeoutCodes[2][32];
bool m_aTimeoutCodeSent[2];
bool m_GenerateTimeoutSeed;
//
char m_aCmdConnect[256];
char m_aCmdPlayDemo[MAX_PATH_LENGTH];
// map download
std::shared_ptr<CGetFile> m_pMapdownloadTask;
char m_aMapdownloadFilename[256];
char m_aMapdownloadName[256];
IOHANDLE m_MapdownloadFile;
int m_MapdownloadChunk;
int m_MapdownloadCrc;
int m_MapdownloadAmount;
int m_MapdownloadTotalsize;
bool m_MapdownloadSha256Present;
SHA256_DIGEST m_MapdownloadSha256;
bool m_MapDetailsPresent;
char m_aMapDetailsName[256];
int m_MapDetailsCrc;
SHA256_DIGEST m_MapDetailsSha256;
std::shared_ptr<CGetFile> m_pDDNetInfoTask;
// time
CSmoothTime m_GameTime[2];
CSmoothTime m_PredictedTime;
// input
struct // TODO: handle input better
{
int m_aData[MAX_INPUT_SIZE]; // the input data
int m_Tick; // the tick that the input is for
int64 m_PredictedTime; // prediction latency when we sent this input
int64 m_Time;
} m_aInputs[2][200];
int m_CurrentInput[2];
bool m_LastDummy;
bool m_LastDummy2;
bool m_DummySendConnInfo;
// graphs
CGraph m_InputtimeMarginGraph;
CGraph m_GametimeMarginGraph;
CGraph m_FpsGraph;
// the game snapshots are modifiable by the game
class CSnapshotStorage m_SnapshotStorage[2];
CSnapshotStorage::CHolder *m_aSnapshots[2][NUM_SNAPSHOT_TYPES];
int m_ReceivedSnapshots[2];
char m_aSnapshotIncomingData[CSnapshot::MAX_SIZE];
class CSnapshotStorage::CHolder m_aDemorecSnapshotHolders[NUM_SNAPSHOT_TYPES];
char *m_aDemorecSnapshotData[NUM_SNAPSHOT_TYPES][2][CSnapshot::MAX_SIZE];
class CSnapshotDelta m_SnapshotDelta;
//
class CServerInfo m_CurrentServerInfo;
int64 m_CurrentServerInfoRequestTime; // >= 0 should request, == -1 got info
// version info
struct CVersionInfo
{
enum
{
STATE_INIT=0,
STATE_START,
STATE_READY,
};
int m_State;
class CHostLookup m_VersionServeraddr;
} m_VersionInfo;
volatile int m_GfxState;
static void GraphicsThreadProxy(void *pThis) { ((CClient*)pThis)->GraphicsThread(); }
void GraphicsThread();
#if defined(CONF_FAMILY_UNIX)
CFifo m_Fifo;
#endif
public:
IEngine *Engine() { return m_pEngine; }
IEngineGraphics *Graphics() { return m_pGraphics; }
IEngineInput *Input() { return m_pInput; }
IEngineSound *Sound() { return m_pSound; }
IGameClient *GameClient() { return m_pGameClient; }
IEngineMasterServer *MasterServer() { return m_pMasterServer; }
IStorage *Storage() { return m_pStorage; }
IUpdater *Updater() { return m_pUpdater; }
CClient();
// ----- send functions -----
virtual int SendMsg(CMsgPacker *pMsg, int Flags);
virtual int SendMsgExY(CMsgPacker *pMsg, int Flags, bool System=true, int NetClient=1);
int SendMsgEx(CMsgPacker *pMsg, int Flags, bool System=true);
void SendInfo();
void SendEnterGame();
void SendReady();
void SendMapRequest();
virtual bool RconAuthed() { return m_RconAuthed[g_Config.m_ClDummy] != 0; }
virtual bool UseTempRconCommands() { return m_UseTempRconCommands != 0; }
void RconAuth(const char *pName, const char *pPassword);
virtual void Rcon(const char *pCmd);
virtual bool ConnectionProblems();
virtual bool SoundInitFailed() { return m_SoundInitFailed; }
virtual int GetDebugFont() { return m_DebugFont; }
void DirectInput(int *pInput, int Size);
void SendInput();
// TODO: OPT: do this a lot smarter!
virtual int *GetInput(int Tick);
virtual int *GetDirectInput(int Tick);
const char *LatestVersion();
// ------ state handling -----
void SetState(int s);
// called when the map is loaded and we should init for a new round
void OnEnterGame();
virtual void EnterGame();
virtual void Connect(const char *pAddress, const char *pPassword = NULL);
void DisconnectWithReason(const char *pReason);
virtual void Disconnect();
virtual void DummyDisconnect(const char *pReason);
virtual void DummyConnect();
virtual bool DummyConnected();
virtual bool DummyConnecting();
int m_DummyConnected;
int m_LastDummyConnectTime;
virtual void GetServerInfo(CServerInfo *pServerInfo);
void ServerInfoRequest();
int LoadData();
// ---
int GetPredictionTime();
void *SnapGetItem(int SnapID, int Index, CSnapItem *pItem);
void SnapInvalidateItem(int SnapID, int Index);
void *SnapFindItem(int SnapID, int Type, int ID);
int SnapNumItems(int SnapID);
void SnapSetStaticsize(int ItemType, int Size);
void Render();
void DebugRender();
virtual void Restart();
virtual void Quit();
virtual const char *ErrorString();
const char *LoadMap(const char *pName, const char *pFilename, SHA256_DIGEST *pWantedSha256, unsigned WantedCrc);
const char *LoadMapSearch(const char *pMapName, SHA256_DIGEST *pWantedSha256, int WantedCrc);
static int PlayerScoreNameComp(const void *a, const void *b);
void ProcessConnlessPacket(CNetChunk *pPacket);
void ProcessServerInfo(int Type, NETADDR *pFrom, const void *pData, int DataSize);
void ProcessServerPacket(CNetChunk *pPacket);
void ProcessServerPacketDummy(CNetChunk *pPacket);
void ResetMapDownload();
void FinishMapDownload();
void RequestDDNetInfo();
void ResetDDNetInfo();
void FinishDDNetInfo();
void LoadDDNetInfo();
virtual const char *MapDownloadName() { return m_aMapdownloadName; }
virtual int MapDownloadAmount() { return !m_pMapdownloadTask ? m_MapdownloadAmount : (int)m_pMapdownloadTask->Current(); }
virtual int MapDownloadTotalsize() { return !m_pMapdownloadTask ? m_MapdownloadTotalsize : (int)m_pMapdownloadTask->Size(); }
void PumpNetwork();
virtual void OnDemoPlayerSnapshot(void *pData, int Size);
virtual void OnDemoPlayerMessage(void *pData, int Size);
void Update();
void RegisterInterfaces();
void InitInterfaces();
void Run();
bool CtrlShiftKey(int Key, bool &Last);
static void Con_Connect(IConsole::IResult *pResult, void *pUserData);
static void Con_Disconnect(IConsole::IResult *pResult, void *pUserData);
static void Con_DummyConnect(IConsole::IResult *pResult, void *pUserData);
static void Con_DummyDisconnect(IConsole::IResult *pResult, void *pUserData);
static void Con_Quit(IConsole::IResult *pResult, void *pUserData);
static void Con_DemoPlay(IConsole::IResult *pResult, void *pUserData);
static void Con_DemoSpeed(IConsole::IResult *pResult, void *pUserData);
static void Con_Minimize(IConsole::IResult *pResult, void *pUserData);
static void Con_Ping(IConsole::IResult *pResult, void *pUserData);
static void Con_Screenshot(IConsole::IResult *pResult, void *pUserData);
static void Con_Rcon(IConsole::IResult *pResult, void *pUserData);
static void Con_RconAuth(IConsole::IResult *pResult, void *pUserData);
static void Con_RconLogin(IConsole::IResult *pResult, void *pUserData);
static void Con_AddFavorite(IConsole::IResult *pResult, void *pUserData);
static void Con_RemoveFavorite(IConsole::IResult *pResult, void *pUserData);
static void Con_Play(IConsole::IResult *pResult, void *pUserData);
static void Con_Record(IConsole::IResult *pResult, void *pUserData);
static void Con_StopRecord(IConsole::IResult *pResult, void *pUserData);
static void Con_AddDemoMarker(IConsole::IResult *pResult, void *pUserData);
static void ConchainServerBrowserUpdate(IConsole::IResult *pResult, void *pUserData, IConsole::FCommandCallback pfnCallback, void *pCallbackUserData);
static void ConchainFullscreen(IConsole::IResult *pResult, void *pUserData, IConsole::FCommandCallback pfnCallback, void *pCallbackUserData);
static void ConchainWindowBordered(IConsole::IResult *pResult, void *pUserData, IConsole::FCommandCallback pfnCallback, void *pCallbackUserData);
static void ConchainWindowScreen(IConsole::IResult *pResult, void *pUserData, IConsole::FCommandCallback pfnCallback, void *pCallbackUserData);
static void ConchainWindowVSync(IConsole::IResult *pResult, void *pUserData, IConsole::FCommandCallback pfnCallback, void *pCallbackUserData);
static void ConchainTimeoutSeed(IConsole::IResult *pResult, void *pUserData, IConsole::FCommandCallback pfnCallback, void *pCallbackUserData);
static void ConchainPassword(IConsole::IResult *pResult, void *pUserData, IConsole::FCommandCallback pfnCallback, void *pCallbackUserData);
static void Con_DemoSlice(IConsole::IResult *pResult, void *pUserData);
static void Con_DemoSliceBegin(IConsole::IResult *pResult, void *pUserData);
static void Con_DemoSliceEnd(IConsole::IResult *pResult, void *pUserData);
static void Con_SaveReplay(IConsole::IResult *pResult, void *pUserData);
void RegisterCommands();
const char *DemoPlayer_Play(const char *pFilename, int StorageType);
void DemoRecorder_Start(const char *pFilename, bool WithTimestamp, int Recorder);
void DemoRecorder_HandleAutoStart();
void DemoRecorder_Stop(int Recorder);
void DemoRecorder_AddDemoMarker(int Recorder);
class IDemoRecorder *DemoRecorder(int Recorder);
void AutoScreenshot_Start();
void AutoStatScreenshot_Start();
void AutoScreenshot_Cleanup();
void AutoStatScreenshot_Cleanup();
void AutoCSV_Start();
void AutoCSV_Cleanup();
void ServerBrowserUpdate();
void HandleConnectLink(const char *pLink);
void HandleDemoPath(const char *pPath);
// gfx
void SwitchWindowScreen(int Index);
void ToggleFullscreen();
void ToggleWindowBordered();
void ToggleWindowVSync();
void LoadFont();
// DDRace
void GenerateTimeoutSeed();
void GenerateTimeoutCodes();
virtual int GetCurrentRaceTime();
const char *GetCurrentMap();
const char *GetCurrentMapPath();
unsigned GetMapCrc();
void RaceRecord_Start(const char *pFilename);
void RaceRecord_Stop();
bool RaceRecord_IsRecording();
virtual void DemoSliceBegin();
virtual void DemoSliceEnd();
virtual void DemoSlice(const char *pDstPath, CLIENTFUNC_FILTER pfnFilter, void *pUser);
virtual void SaveReplay();
bool EditorHasUnsavedData() { return m_pEditor->HasUnsavedData(); }
virtual IFriends* Foes() {return &m_Foes; }
void GetSmoothTick(int *pSmoothTick, float *pSmoothIntraTick, float MixAmount);
};
#endif

View file

@ -13,7 +13,8 @@ enum
RECORDER_MANUAL=0,
RECORDER_AUTO=1,
RECORDER_RACE=2,
RECORDER_MAX=3,
RECORDER_REPLAYS=3,
RECORDER_MAX=4,
};
typedef bool (*CLIENTFUNC_FILTER)(const void *pData, int DataSize, void *pUser);

View file

@ -263,9 +263,9 @@ void CSmoothTime::Update(CGraph *pGraph, int64 Target, int TimeLeft, int AdjustD
CClient::CClient() : m_DemoPlayer(&m_SnapshotDelta)
{
m_DemoRecorder[0] = CDemoRecorder(&m_SnapshotDelta);
m_DemoRecorder[1] = CDemoRecorder(&m_SnapshotDelta);
m_DemoRecorder[2] = CDemoRecorder(&m_SnapshotDelta);
for (int i = 0; i < RECORDER_MAX; i++) {
m_DemoRecorder[i] = CDemoRecorder(&m_SnapshotDelta);
}
m_pEditor = 0;
m_pInput = 0;
@ -681,8 +681,6 @@ void CClient::Connect(const char *pAddress, const char *pPassword)
char aBuf[512];
int Port = 8303;
replayCounter = 0;
Disconnect();
str_copy(m_aServerAddressStr, pAddress, sizeof(m_aServerAddressStr));
@ -784,7 +782,7 @@ void CClient::Disconnect()
// make sure to remove replay tmp demo
if(g_Config.m_ClRaceReplays)
{
Storage()->RemoveFile((&m_DemoRecorder[RECORDER_AUTO])->GetCurrentFilename(), IStorage::TYPE_SAVE);
Storage()->RemoveFile((&m_DemoRecorder[RECORDER_REPLAYS])->GetCurrentFilename(), IStorage::TYPE_SAVE);
}
}
@ -3295,35 +3293,26 @@ void CClient::SaveReplay()
{
m_pConsole->Print(IConsole::OUTPUT_LEVEL_STANDARD, "replay", "Feature is disabled. Please enabled it via the configuration");
} else {
if(!DemoRecorder(RECORDER_AUTO)->IsRecording())
if(!DemoRecorder(RECORDER_REPLAYS)->IsRecording())
{
m_pConsole->Print(IConsole::OUTPUT_LEVEL_STANDARD, "replay", "Error: demorecorder isn't recording. Try to rejoin to fix that.");
}
else
{
//DemoRecorder_HandleAutoStart();
DemoRecorder_Stop(RECORDER_AUTO);
replayCounter++;
char aFilename[256];
char aDate[64];
str_timestamp(aDate, sizeof(aDate));
str_format(aFilename, sizeof(aFilename), "demos/replays/%s_%s (replay).demo", m_aCurrentMap, aDate);
char *pSrc = (&m_DemoRecorder[RECORDER_AUTO])->GetCurrentFilename();
char *pSrc = (&m_DemoRecorder[RECORDER_REPLAYS])->GetCurrentFilename();
// Slice the demo to get only the last 30 seconds
// Slice the demo to get only the last cl_replay_length seconds
m_DemoEditor.Slice(pSrc, aFilename, GameTick() - g_Config.m_ClReplayLength * GameTickSpeed(), GameTick(), NULL, 0);
Storage()->RemoveFile(pSrc, IStorage::TYPE_SAVE);
char aBuf[256];
str_format(aBuf, sizeof(aBuf), "Successfully saved the replay to %s !", aFilename);
m_pConsole->Print(IConsole::OUTPUT_LEVEL_STANDARD, "replay", aBuf);
DemoRecorder_HandleAutoStart();
}
}
}
@ -3451,12 +3440,12 @@ void CClient::DemoRecorder_HandleAutoStart()
AutoDemos.Init(Storage(), "demos/auto", "" /* empty for wild card */, ".demo", g_Config.m_ClAutoDemoMax);
}
}
else if(g_Config.m_ClRaceReplays)
if(g_Config.m_ClRaceReplays)
{
DemoRecorder_Stop(RECORDER_AUTO);
DemoRecorder_Stop(RECORDER_REPLAYS);
char aBuf[512];
str_format(aBuf, sizeof(aBuf), "replays/replay-%s", m_aCurrentMap);
DemoRecorder_Start(aBuf, true, RECORDER_AUTO);
DemoRecorder_Start(aBuf, true, RECORDER_REPLAYS);
}
//TODO
@ -3498,6 +3487,7 @@ void CClient::Con_AddDemoMarker(IConsole::IResult *pResult, void *pUserData)
pSelf->DemoRecorder_AddDemoMarker(RECORDER_MANUAL);
pSelf->DemoRecorder_AddDemoMarker(RECORDER_RACE);
pSelf->DemoRecorder_AddDemoMarker(RECORDER_AUTO);
pSelf->DemoRecorder_AddDemoMarker(RECORDER_REPLAYS);
}
void CClient::ServerBrowserUpdate()

View file

@ -94,7 +94,6 @@ class CClient : public IClient, public CDemoPlayer::IListener
int64 m_LocalStartTime;
int m_DebugFont;
int replayCounter = 0;
int64 m_LastRenderTime;
float m_RenderFrameTimeLow;

View file

@ -1159,12 +1159,6 @@ int CMenus::Render()
pButtonText = Localize("Ok");
ExtraAlign = -1;
}
else if(m_Popup == POPUP_REPLAY_ENABLING_ERROR)
{
pTitle = Localize("Error enabling replays");
pExtraText = Localize("As the replay system uses the demo recorder system, no other record options should be used along with replays. Please disable any other option if you want to enable replays.");
ExtraAlign = -1;
}
CUIRect Box, Part;
Box = Screen;
@ -1267,18 +1261,6 @@ int CMenus::Render()
m_Popup = POPUP_NONE;
}
}
else if (m_Popup == POPUP_REPLAY_ENABLING_ERROR)
{
CUIRect Ok;
Box.HSplitBottom(20.f, &Box, &Part);
Box.HSplitBottom(24.f, &Box, &Part);
Part.VMargin(40.0f, &Ok);
static int s_ButtonOk = 0;
if (DoButton_Menu(&s_ButtonOk, Localize("Got it"), 0, &Ok) || m_EscapePressed)
m_Popup = POPUP_NONE;
}
else if(m_Popup == POPUP_PASSWORD)
{
CUIRect Label, TextBox, TryAgain, Abort;

View file

@ -402,7 +402,6 @@ public:
POPUP_QUIT,
POPUP_DISCONNECT,
POPUP_DISCONNECT_DUMMY,
POPUP_REPLAY_ENABLING_ERROR,
// demo player states
DEMOPLAYER_NONE=0,

View file

@ -2000,14 +2000,7 @@ void CMenus::RenderSettingsDDNet(CUIRect MainView)
Left.HSplitTop(20.0f, &Button, &Left);
if(DoButton_CheckBox(&g_Config.m_ClRaceReplays, Localize("Enable replays"), g_Config.m_ClRaceReplays, &Button))
{
if(g_Config.m_ClAutoDemoRecord && !g_Config.m_ClRaceReplays)
{
m_Popup = POPUP_REPLAY_ENABLING_ERROR;
}
else
{
g_Config.m_ClRaceReplays ^= 1;
}
g_Config.m_ClRaceReplays ^= 1;
}

View file

@ -525,7 +525,8 @@ void CScoreboard::RenderRecordingNotification(float x)
{
if(!m_pClient->DemoRecorder(RECORDER_MANUAL)->IsRecording() &&
!m_pClient->DemoRecorder(RECORDER_AUTO)->IsRecording() &&
!m_pClient->DemoRecorder(RECORDER_RACE)->IsRecording())
!m_pClient->DemoRecorder(RECORDER_RACE)->IsRecording() &&
!m_pClient->DemoRecorder(RECORDER_REPLAYS)->IsRecording())
{
return;
}
@ -553,6 +554,12 @@ void CScoreboard::RenderRecordingNotification(float x)
str_format(aBuf2, sizeof(aBuf2), Localize("Auto %3d:%02d "), Seconds/60, Seconds%60);
str_append(aBuf, aBuf2, sizeof(aBuf));
}
if (m_pClient->DemoRecorder(RECORDER_REPLAYS)->IsRecording())
{
Seconds = m_pClient->DemoRecorder(RECORDER_REPLAYS)->Length();
str_format(aBuf2, sizeof(aBuf2), Localize("Replay %3d:%02d "), Seconds / 60, Seconds % 60);
str_append(aBuf, aBuf2, sizeof(aBuf));
}
float w = TextRender()->TextWidth(0, 20.0f, aBuf, -1);