1 // Base services interface declaration
2 // for the Build Engine
3 // by Jonathon Fowler (jf@jonof.id.au)
4
5 #pragma once
6
7 #ifndef baselayer_h_
8 #define baselayer_h_
9
10 #include "compat.h"
11 #include "osd.h"
12 #include "timer.h"
13
14 #ifdef __cplusplus
15 extern "C" {
16 #endif
17
18 extern int app_main(int argc, char const * const * argv);
19 extern const char* AppProperName;
20 extern const char* AppTechnicalName;
21
22 #ifdef DEBUGGINGAIDS
23 # define DEBUG_MASK_DRAWING
24 extern int32_t g_maskDrawMode;
25 #endif
26
27 extern char quitevent, appactive;
28 extern char modechange;
29 extern char nogl;
30
31 extern int32_t vsync;
32 extern int32_t r_finishbeforeswap;
33 extern int32_t r_glfinish;
34 extern int32_t r_borderless;
35 extern int32_t r_displayindex;
36
37 extern void app_crashhandler(void);
38
39 // NOTE: these are implemented in game-land so they may be overridden in game specific ways
40 extern int32_t startwin_open(void);
41 extern int32_t startwin_close(void);
42 extern int32_t startwin_puts(const char *);
43 extern int32_t startwin_settitle(const char *);
44 extern int32_t startwin_idle(void *);
45 extern int32_t startwin_run(void);
46
47 // video
48 extern int32_t r_usenewaspect, newaspect_enable;
49 extern int32_t r_fpgrouscan;
50 extern int32_t setaspect_new_use_dimen;
51 extern uint32_t r_screenxy;
52 extern int32_t xres, yres, bpp, fullscreen, bytesperline;
53 extern double refreshfreq;
54 extern intptr_t frameplace;
55 extern char offscreenrendering;
56 extern int32_t nofog;
57
58 extern int32_t r_maxfps;
59 extern int32_t r_maxfpsoffset;
60
61 void calc_ylookup(int32_t bpl, int32_t lastyidx);
62
63 int32_t videoCheckMode(int32_t *x, int32_t *y, int32_t c, int32_t fs, int32_t forced);
64 int32_t videoSetMode(int32_t x, int32_t y, int32_t c, int32_t fs);
65 void videoGetModes(void);
66 void videoResetMode(void);
67 void videoEndDrawing(void);
68 void videoShowFrame(int32_t);
69 int32_t videoUpdatePalette(int32_t start, int32_t num);
70 int32_t videoSetGamma(void);
71 int32_t videoSetVsync(int32_t newSync);
72
73 //#define DEBUG_FRAME_LOCKING
74 #if !defined DEBUG_FRAME_LOCKING
75 void videoBeginDrawing(void);
76 #else
77 void begindrawing_real(void);
78 # define BEGINDRAWING_SIZE 256
79 extern uint32_t begindrawing_line[BEGINDRAWING_SIZE];
80 extern const char *begindrawing_file[BEGINDRAWING_SIZE];
81 extern int32_t lockcount;
82 # define videoBeginDrawing() do { \
83 if (lockcount < BEGINDRAWING_SIZE) { \
84 begindrawing_line[lockcount] = __LINE__; \
85 begindrawing_file[lockcount] = __FILE__; \
86 } \
87 begindrawing_real(); \
88 } while(0)
89 #endif
90
91 extern float g_videoGamma, g_videoContrast, g_videoBrightness;
92
93 #define DEFAULT_GAMMA 1.0f
94 #define DEFAULT_CONTRAST 1.0f
95 #define DEFAULT_BRIGHTNESS 0.0f
96
97 #define GAMMA_CALC ((int32_t)(min(max((float)((g_videoGamma - 1.0f) * 10.0f), 0.f), 15.f)))
98
99 #ifdef USE_OPENGL
100 extern int32_t (*baselayer_osdcmd_vidmode_func)(osdcmdptr_t parm);
101 extern int osdcmd_glinfo(osdcmdptr_t parm);
102
103 struct glinfo_t {
104 const char *vendor;
105 const char *renderer;
106 const char *version;
107 const char *extensions;
108
109 float maxanisotropy;
110
111 int filled;
112
113 union {
114 uint32_t features;
115 struct
116 {
117 int bgra : 1;
118 int bufferstorage : 1;
119 int clamptoedge : 1;
120 int debugoutput : 1;
121 int depthclamp : 1;
122 int depthtex : 1;
123 int fbos : 1;
124 int glsl : 1;
125 int multitex : 1;
126 int occlusionqueries : 1;
127 int rect : 1;
128 int shadow : 1;
129 int sync : 1;
130 int texcompr : 1;
131 int texnpot : 1;
132 int vbos : 1;
133 int vsync : 1;
134 };
135 };
136 };
137
138 extern struct glinfo_t glinfo;
139
140 extern void fill_glinfo(void);
141 #endif
142
143 vec2_t CONSTEXPR const g_defaultVideoModes []
144 = { { 2560, 1440 }, { 2560, 1200 }, { 2560, 1080 }, { 1920, 1440 }, { 1920, 1200 }, { 1920, 1080 }, { 1680, 1050 },
145 { 1600, 1200 }, { 1600, 900 }, { 1366, 768 }, { 1280, 1024 }, { 1280, 960 }, { 1280, 720 }, { 1152, 864 },
146 { 1024, 768 }, { 1024, 600 }, { 800, 600 }, { 640, 480 }, { 640, 400 }, { 512, 384 }, { 480, 360 },
147 { 400, 300 }, { 320, 240 }, { 320, 200 }, { 0, 0 } };
148
149 extern char inputdevices;
150
151 // keys
152 #define NUMKEYS 256
153 #define KEYFIFOSIZ 64
154
155 char CONSTEXPR const g_keyAsciiTable[128] = {
156 0 , 0, '1', '2', '3', '4', '5', '6', '7', '8', '9', '0', '-', '=', 0, 0, 'q', 'w', 'e', 'r', 't', 'y', 'u', 'i', 'o', 'p',
157 '[', ']', 0, 0, 'a', 's', 'd', 'f', 'g', 'h', 'j', 'k', 'l', ';', 39, '`', 0, 92, 'z', 'x', 'c', 'v', 'b', 'n', 'm', ',',
158 '.', '/', 0, '*', 0, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, '7', '8', '9', '-', '4', '5', '6',
159 '+', '1', '2', '3', '0', '.', 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
160 0 , 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
161 };
162
163 char CONSTEXPR const g_keyAsciiTableShift[128] = {
164 0 , 0, '!', '@', '#', '$', '%', '^', '&', '*', '(', ')', '_', '+', 0, 0, 'Q', 'W', 'E', 'R', 'T', 'Y', 'U', 'I', 'O', 'P',
165 '{', '}', 0, 0, 'A', 'S', 'D', 'F', 'G', 'H', 'J', 'K', 'L', ':', '"', '~', 0, '|', 'Z', 'X', 'C', 'V', 'B', 'N', 'M', '<',
166 '>', '?', 0, '*', 0, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, '7', '8', '9', '-', '4', '5', '6',
167 '+', '1', '2', '3', '0', '.', 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
168 0 , 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
169 };
170
171 extern char keystatus[NUMKEYS];
172 extern char g_keyFIFO[KEYFIFOSIZ];
173 extern char g_keyAsciiFIFO[KEYFIFOSIZ];
174 extern uint8_t g_keyAsciiPos;
175 extern uint8_t g_keyAsciiEnd;
176 extern uint8_t g_keyFIFOend;
177 extern char g_keyRemapTable[NUMKEYS];
178 extern char g_keyNameTable[NUMKEYS][24];
179
180 extern int32_t keyGetState(int32_t key);
181 extern void keySetState(int32_t key, int32_t state);
182
183 // mouse
184 extern vec2_t g_mousePos;
185 extern vec2_t g_mouseAbs;
186 extern int32_t g_mouseBits;
187 extern uint8_t g_mouseClickState;
188 extern bool g_mouseGrabbed;
189 extern bool g_mouseEnabled;
190 extern bool g_mouseInsideWindow;
191 extern bool g_mouseLockedToWindow;
192
193 enum
194 {
195 MOUSE_IDLE = 0,
196 MOUSE_PRESSED,
197 MOUSE_HELD,
198 MOUSE_RELEASED,
199 };
200 extern int32_t mouseAdvanceClickState(void);
201
202 // joystick
203
204 typedef struct
205 {
206 int32_t *pAxis;
207 int32_t *pHat;
208 void (*pCallback)(int32_t, int32_t);
209 int32_t bits;
210 int32_t numAxes;
211 int32_t numBalls;
212 int32_t numButtons;
213 int32_t numHats;
214 int32_t isGameController;
215 } controllerinput_t;
216
217 extern controllerinput_t joystick;
218
219 extern int32_t qsetmode;
220
221 #define in3dmode() (qsetmode==200)
222
223 int32_t initsystem(void);
224 void uninitsystem(void);
225 void system_getcvars(void);
226
227 extern int32_t g_logFlushWindow;
228 void initputs(const char *);
229 #define buildputs initputs
230 int initprintf(const char *, ...) ATTRIBUTE((format(printf,1,2)));
231 #define buildprintf initprintf
232 int debugprintf(const char *,...) ATTRIBUTE((format(printf,1,2)));
233
234 int32_t handleevents(void);
235 int32_t handleevents_peekkeys(void);
236
237 extern void (*keypresscallback)(int32_t,int32_t);
238 extern void (*g_mouseCallback)(int32_t,int32_t);
239
240 int32_t initinput(void);
241 void uninitinput(void);
242 void keySetCallback(void (*callback)(int32_t,int32_t));
243 void mouseSetCallback(void (*callback)(int32_t,int32_t));
244 void joySetCallback(void (*callback)(int32_t,int32_t));
245 const char *keyGetName(int32_t num);
246 const char *joyGetName(int32_t what, int32_t num); // what: 0=axis, 1=button, 2=hat
247 void joyScanDevices(void);
248
249 char keyGetScan(void);
250 char keyGetChar(void);
251 #define keyBufferWaiting() (g_keyAsciiPos != g_keyAsciiEnd)
252
keyBufferFull(void)253 static FORCE_INLINE int keyBufferFull(void)
254 {
255 return ((g_keyAsciiEnd+1)&(KEYFIFOSIZ-1)) == g_keyAsciiPos;
256 }
257
keyBufferInsert(char code)258 static FORCE_INLINE void keyBufferInsert(char code)
259 {
260 g_keyAsciiFIFO[g_keyAsciiEnd] = code;
261 g_keyAsciiEnd = ((g_keyAsciiEnd+1)&(KEYFIFOSIZ-1));
262 }
263
264 void keyFlushScans(void);
265 void keyFlushChars(void);
266
267 void mouseInit(void);
268 void mouseUninit(void);
269 int32_t mouseReadAbs(vec2_t *pResult, vec2_t const *pInput);
270 void mouseGrabInput(bool grab);
271 void mouseLockToWindow(char a);
272 void mouseMoveToCenter(void);
273 int32_t mouseReadButtons(void);
274 void mouseReadPos(int32_t *x, int32_t *y);
275
276 void joyReadButtons(int32_t *pResult);
277 void joySetDeadZone(int32_t axis, uint16_t dead, uint16_t satur);
278 void joyGetDeadZone(int32_t axis, uint16_t *dead, uint16_t *satur);
279 extern int32_t inputchecked;
280
281 int32_t wm_msgbox(const char *name, const char *fmt, ...) ATTRIBUTE((format(printf,2,3)));
282 int32_t wm_ynbox(const char *name, const char *fmt, ...) ATTRIBUTE((format(printf,2,3)));
283 void wm_setapptitle(const char *name);
284
285 // baselayer.c
286 int32_t baselayer_init();
287
288 void makeasmwriteable(void);
289 void maybe_redirect_outputs(void);
290
291 extern uint64_t g_frameDelay;
calcFrameDelay(int const maxFPS,int const offset)292 static inline uint64_t calcFrameDelay(int const maxFPS, int const offset)
293 {
294 uint64_t const perfFreq = timerGetPerformanceFrequency();
295
296 if (maxFPS == -1)
297 return perfFreq / refreshfreq;
298
299 return maxFPS ? perfFreq / (maxFPS + offset) : 0;
300 }
301 extern int engineFPSLimit(void);
302 #ifdef __cplusplus
303 }
304 #endif
305
306 #include "print.h"
307
308 #endif // baselayer_h_
309
310