Line data Source code
1 : /* Copyright (C) 2022 Wildfire Games.
2 : * This file is part of 0 A.D.
3 : *
4 : * 0 A.D. is free software: you can redistribute it and/or modify
5 : * it under the terms of the GNU General Public License as published by
6 : * the Free Software Foundation, either version 2 of the License, or
7 : * (at your option) any later version.
8 : *
9 : * 0 A.D. is distributed in the hope that it will be useful,
10 : * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 : * GNU General Public License for more details.
13 : *
14 : * You should have received a copy of the GNU General Public License
15 : * along with 0 A.D. If not, see <http://www.gnu.org/licenses/>.
16 : */
17 :
18 : /*
19 : * Viewing profiling information (timing and other statistics)
20 : */
21 :
22 : #ifndef INCLUDED_PROFILE_VIEWER
23 : #define INCLUDED_PROFILE_VIEWER
24 :
25 : #include "lib/input.h"
26 : #include "ps/CStr.h"
27 : #include "ps/Singleton.h"
28 :
29 : #include <vector>
30 :
31 : class CCanvas2D;
32 :
33 : /**
34 : * Struct ProfileColumn: Describes one column of an AbstractProfileTable.
35 : */
36 77 : struct ProfileColumn
37 : {
38 : /// Title of the column
39 : CStr title;
40 :
41 : /// Recommended width of the column, in pixels.
42 : size_t width;
43 :
44 17 : ProfileColumn(const CStr& t, size_t w) : title(t), width(w) { }
45 : };
46 :
47 :
48 : /**
49 : * Class AbstractProfileTable: Profile table data model.
50 : *
51 : * Clients that wish to display debug information in the profile viewer
52 : * have to implement this class and hook it into CProfileViewer.
53 : *
54 : * Note that the profiling system is robust against deletion of
55 : * object instances in the sense that it will automatically remove
56 : * an AbstractProfileTable instance from its internal records when
57 : * you delete it.
58 : * Conversely, deleting an AbstractProfileTable instance is the responsibility
59 : * of its creator.
60 : */
61 6 : class AbstractProfileTable
62 : {
63 : public:
64 : virtual ~AbstractProfileTable();
65 :
66 : /**
67 : * GetName: Short descriptive name of this table (should be static).
68 : *
69 : * @return Descriptive name of this table.
70 : */
71 : virtual CStr GetName() = 0;
72 :
73 : /**
74 : * GetTitle: Longer, explanatory text (can be dynamic).
75 : *
76 : * @return Title for the table.
77 : */
78 : virtual CStr GetTitle() = 0;
79 :
80 :
81 : /**
82 : * GetNumberRows
83 : *
84 : * @return Number of rows in this table.
85 : */
86 : virtual size_t GetNumberRows() = 0;
87 :
88 : /**
89 : * GetColumnDescriptions
90 : *
91 : * @return A vector describing all columns of the table.
92 : */
93 : virtual const std::vector<ProfileColumn>& GetColumns() = 0;
94 :
95 : /**
96 : * GetCellText
97 : *
98 : * @param row Row index (the first row has index 0).
99 : * @param col Column index (the first column has index 0).
100 : *
101 : * @return Text to be displayed in the given cell.
102 : */
103 : virtual CStr GetCellText(size_t row, size_t col) = 0;
104 :
105 : /**
106 : * GetChild: Return a row's child table if the child is expandable.
107 : *
108 : * @param row Row index (the first row has index 0).
109 : *
110 : * @return Pointer to the child table if the given row has one.
111 : * Otherwise, return 0.
112 : */
113 : virtual AbstractProfileTable* GetChild(size_t row) = 0;
114 :
115 : /**
116 : * IsHighlightRow
117 : *
118 : * @param row Row index (the first row has index 0).
119 : *
120 : * @return true if the row should be highlighted in a special color.
121 : */
122 0 : virtual bool IsHighlightRow(size_t row) { UNUSED2(row); return false; }
123 : };
124 :
125 :
126 : struct CProfileViewerInternals;
127 :
128 : /**
129 : * Class CProfileViewer: Manage and display profiling tables.
130 : */
131 : class CProfileViewer : public Singleton<CProfileViewer>
132 : {
133 : friend class AbstractProfileTable;
134 :
135 : public:
136 : CProfileViewer();
137 : ~CProfileViewer();
138 :
139 : /**
140 : * RenderProfile: Render the profile display using OpenGL if the user
141 : * has enabled it.
142 : */
143 : void RenderProfile(CCanvas2D& canvas);
144 :
145 : /**
146 : * Input: Filter and handle any input events that the profile display
147 : * is interested in.
148 : *
149 : * In particular, this function handles enable/disable of the profile
150 : * display as well as navigating the information tree.
151 : *
152 : * @param ev The incoming event.
153 : *
154 : * @return IN_PASS or IN_HANDLED depending on whether the event relates
155 : * to the profiling display.
156 : */
157 : InReaction Input(const SDL_Event_* ev);
158 :
159 : /**
160 : * AddRootTable: Add a new profile table as a root table (i.e. the
161 : * tables that you cycle through via the profile hotkey).
162 : *
163 : * @note Tables added via this function are automatically removed from
164 : * the list of root tables when they are deleted.
165 : *
166 : * @param table This table is added as a root table.
167 : * @param front If true then the table will be the new first in the list,
168 : * else it will be the last.
169 : */
170 : void AddRootTable(AbstractProfileTable* table, bool front = false);
171 :
172 : /**
173 : * InputThunk: Delegate to the singleton's Input() member function
174 : * if the singleton has been initialized.
175 : *
176 : * This allows our input handler to be installed via in_add_handler
177 : * like a normal, global function input handler.
178 : */
179 : static InReaction InputThunk(const SDL_Event_* ev);
180 :
181 : /**
182 : * SaveToFile: Save the current profiler data (for all profile tables)
183 : * to a file in the 'logs' directory.
184 : */
185 : void SaveToFile();
186 :
187 : /**
188 : * ShowTable: Set the named profile table to be the displayed one. If it
189 : * is not found, no profile is displayed.
190 : *
191 : * @param table The table name (matching AbstractProfileTable::GetName),
192 : * or the empty string to display no table.
193 : */
194 : void ShowTable(const CStr& table);
195 :
196 : private:
197 : CProfileViewerInternals* m;
198 : };
199 :
200 : #define g_ProfileViewer CProfileViewer::GetSingleton()
201 :
202 : #endif
|