12
12
#include <SDL2/SDL_ttf.h>
13
13
#include <SDL2/SDL_video.h>
14
14
15
+ #include <stdarg.h>
15
16
#include <stdio.h>
16
17
#include <string.h>
17
18
#include <stdlib.h>
18
19
#include <stdbool.h>
19
20
#define SHEEP_DYNARRAY_IMPLEMENTATION
20
21
#include "dynarray.h"
22
+ #ifndef NO_JSON_CONFIG
21
23
#define SHEEP_SJSON_IMPLEMENTATION
22
24
#include "sjson.h"
25
+ #endif
23
26
#define SHEEP_XMALLOC_IMPLEMENTATION
24
27
#include "xmalloc.h"
25
28
#include "config.h"
26
29
#include "tinyfiledialogs.h"
27
30
28
- #ifdef USE_UNIFONT
31
+ #ifndef NO_UNIFONT
29
32
#include "unifont.h"
30
33
#else
31
34
#include "font.h"
43
46
#define PATH_MAX 4096
44
47
#endif
45
48
49
+ #define die (...) _die(__LINE__, __VA_ARGS__)
50
+
51
+ static void _die (int line_number , const char * format , ...)
52
+ {
53
+ va_list vargs ;
54
+ va_start (vargs , format );
55
+ fprintf (stderr , "%d: " , line_number );
56
+ vfprintf (stderr , format , vargs );
57
+ fprintf (stderr , ".\n" );
58
+ va_end (vargs );
59
+ exit (1 );
60
+ }
61
+
62
+
46
63
enum FrameType {
47
64
FRAMETEXT ,
48
65
FRAMEIMAGE ,
@@ -71,16 +88,18 @@ static SDL_Renderer *rend;
71
88
static TTF_Font * fonts [FONT_NSCALES + 1 ];
72
89
static int fontsheight [FONT_NSCALES + 1 ];
73
90
static const int linespacing = 3 ;
74
- static const SDL_Color bg = { 255 , 255 , 255 , 255 };
75
- static const SDL_Color fg = { 0 , 0 , 0 , 255 };
76
91
static Slide slide ;
77
92
static char * fontpath = NULL ;
78
93
/* work directory, if reading from file
79
94
* this is directory which that file is in
80
95
* else if reading from stdin it's NULL */
81
96
static char * slidewd = NULL ;
97
+ static bool progressbar = true;
98
+ static bool invert = false;
82
99
100
+ #ifndef NO_JSON_CONFIG
83
101
void readconfig ();
102
+ #endif
84
103
void loadfonts ();
85
104
Slide parse_slide_from_file (FILE * in );
86
105
int getfontsize (Frame frame , int * width , int * height );
@@ -94,7 +113,7 @@ void loadfonts() {
94
113
if (fontpath == NULL ) {
95
114
fontrw = SDL_RWFromMem (font_ttf , font_ttf_len );
96
115
if (fontrw == NULL ) {
97
- fprintf ( stderr , "FontRwop: %s\n " , SDL_GetError ());
116
+ die ( "FontRwop: %s" , SDL_GetError ());
98
117
}
99
118
}
100
119
for (int i = 1 ; i <= FONT_NSCALES ; i ++ ) {
@@ -105,7 +124,7 @@ void loadfonts() {
105
124
fonts [i ] = TTF_OpenFont (fontpath , i * FONT_STEP );
106
125
}
107
126
if (fonts [i ] == NULL ) {
108
- fprintf (stderr , "Open Font fail %d : %s\n" , i , SDL_GetError ());
127
+ fprintf (stderr , "Open Font fail (size: %d) : %s\n" , i , SDL_GetError ());
109
128
}
110
129
fontsheight [i ] = TTF_FontHeight (fonts [i ]);
111
130
}
@@ -151,8 +170,7 @@ void init() {
151
170
SDL_Init (SDL_INIT_VIDEO );
152
171
TTF_Init ();
153
172
if (IMG_Init (IMG_INIT_AVIF | IMG_INIT_JPG | IMG_INIT_PNG | IMG_INIT_WEBP ) < 1 ) {
154
- fprintf (stderr , "IMG_Init Failed: %s" , IMG_GetError ());
155
- exit (1 );
173
+ die ("Img_INIT: %s" , IMG_GetError ());
156
174
}
157
175
win = SDL_CreateWindow ("Slide" , SDL_WINDOWPOS_CENTERED , SDL_WINDOWPOS_CENTERED , w , h , SDL_WINDOW_RESIZABLE );
158
176
rend = SDL_CreateRenderer (win , -1 , 0 );
@@ -195,7 +213,7 @@ void drawframe(Frame frame) {
195
213
196
214
for (size_t i = 0 ; i < arrlen (frame .lines ); i ++ ) {
197
215
SDL_Surface * textsurface = TTF_RenderUTF8_Blended (fonts [fontsize ],
198
- frame .lines [i ], fg );
216
+ frame .lines [i ], invert ? bg : fg );
199
217
SDL_Texture * texttexture = SDL_CreateTextureFromSurface (rend , textsurface );
200
218
int linew , lineh ;
201
219
SDL_QueryTexture (texttexture , NULL , NULL , & linew , & lineh );
@@ -233,20 +251,31 @@ void drawframe(Frame frame) {
233
251
}
234
252
235
253
void drawpage (Page page ) {
236
- SDL_SetRenderDrawColor (rend , bg .r , bg .g , bg .b , bg .a );
254
+ SDL_Color realbg = invert ? fg : bg ;
255
+ SDL_SetRenderDrawColor (rend , realbg .r , realbg .g , realbg .b , realbg .a );
237
256
SDL_RenderClear (rend );
238
257
for (size_t i = 0 ; i < arrlen (page ); i ++ ) {
239
258
drawframe (page [i ]);
240
259
}
241
- SDL_RenderPresent (rend );
260
+ }
261
+
262
+ void drawprogressbar (float progress /* value between 0 and 1 */ ) {
263
+ SDL_Rect bar = {
264
+ .x = 0 ,
265
+ .y = h - PROGRESSBAR_HEIGHT ,
266
+ .w = progress * w ,
267
+ .h = PROGRESSBAR_HEIGHT ,
268
+ };
269
+ SDL_Color realfg = invert ? bg : fg ;
270
+ SDL_SetRenderDrawColor (rend , realfg .r , realfg .g , realfg .b , realfg .a );
271
+ SDL_RenderFillRect (rend , & bar );
242
272
}
243
273
244
274
void run () {
245
275
size_t pagei = 0 ;
246
276
SDL_Event event ;
247
- drawpage (slide [pagei ]);
248
277
249
- while (1 ) {
278
+ while (true ) {
250
279
bool redraw = false;
251
280
/* event loop */
252
281
while (SDL_PollEvent (& event )) {
@@ -279,6 +308,14 @@ void run() {
279
308
pagei = arrlen (slide ) - 1 ;
280
309
redraw = true;
281
310
break ;
311
+ case SDLK_i :
312
+ invert ^= true;
313
+ redraw = true;
314
+ break ;
315
+ case SDLK_p :
316
+ progressbar ^= true;
317
+ redraw = true;
318
+ break ;
282
319
default :
283
320
break ;
284
321
}
@@ -306,6 +343,10 @@ void run() {
306
343
307
344
if (redraw ) {
308
345
drawpage (slide [pagei ]);
346
+ if (progressbar ) {
347
+ drawprogressbar ((float )(pagei + 1 )/arrlen (slide ));
348
+ }
349
+ SDL_RenderPresent (rend );
309
350
}
310
351
SDL_Delay (15 );
311
352
}
@@ -327,8 +368,7 @@ int main(int argc, char **argv) {
327
368
if (srcfile != NULL /* not reading from stdin */ ) {
328
369
fin = fopen (srcfile , "r" );
329
370
if (fin == NULL ) {
330
- fprintf (stderr , "Failed opening file\n" );
331
- exit (1 );
371
+ die ("Failed opening file %s" , srcfile );
332
372
}
333
373
/* basename() is not portable */
334
374
char * sep = srcfile + strlen (srcfile );
@@ -347,7 +387,9 @@ int main(int argc, char **argv) {
347
387
}
348
388
}
349
389
390
+ #ifndef NO_JSON_CONFIG
350
391
readconfig ();
392
+ #endif
351
393
init ();
352
394
loadfonts ();
353
395
slide = parse_slide_from_file (fin );
@@ -374,8 +416,7 @@ Slide parse_slide_from_file(FILE *in) {
374
416
375
417
if (ret == NULL /* EOF */ ) {
376
418
if (arrlen (slide ) == 0 ) {
377
- fprintf (stderr , "Error parsing: Slide has no page, make sure every page is terminated" );
378
- exit (1 );
419
+ die ("Slide has no page, make sure every page is terminated" );
379
420
}
380
421
/* didn't add page to slide, must free now to prevent memory leak */
381
422
arrfree (page );
@@ -387,29 +428,25 @@ Slide parse_slide_from_file(FILE *in) {
387
428
break ;
388
429
}
389
430
if (buf [0 ] != ';' ) {
390
- fprintf (stderr , "Wrong slide format: no geometry before frame" );
391
- exit (1 );
431
+ die ("No geometry before frame" );
392
432
}
393
433
if (buf [1 ] == 'f' ) {
394
434
frame .x = frame .y = 0 ;
395
435
frame .w = frame .h = 100 ;
396
436
} else if (sscanf (buf , ";%d;%d;%d;%d" , & frame .x , & frame .y , & frame .w , & frame .h ) != 4 ) {
397
- fprintf (stderr , "Wrong slide format: Geometry need to be in ;x;y;w;h" );
398
- exit (1 );
437
+ die ("Geometry need to be in ;x;y;w;h" );
399
438
}
400
439
401
440
while (fgets (buf , sizeof buf , in ) != NULL /* EOF */ ) {
402
441
if (buf [0 ] == '%' ) {
403
442
if (frame .type == FRAMEIMAGE ) {
404
- fprintf (stderr , "Only one image per frame is allowed!" );
405
- exit (1 );
443
+ die ("Only one image per frame is allowed" );
406
444
}
407
445
char * newline = strchr (buf , '\n' );
408
446
if (newline != NULL ) {
409
447
* newline = '\x0' ;
410
448
} else {
411
- fprintf (stderr , "Error parsing" );
412
- exit (1 );
449
+ die ("Error parsing" );
413
450
}
414
451
char filename [PATH_MAX ] = { 0 };
415
452
if (in == stdin
@@ -432,7 +469,6 @@ Slide parse_slide_from_file(FILE *in) {
432
469
frame .image .texture = IMG_LoadTexture (rend , filename );
433
470
if (frame .image .texture == NULL ) {
434
471
fprintf (stderr , "Failed loading image %s: %s" , filename , SDL_GetError ());
435
- exit (1 );
436
472
}
437
473
int imgw , imgh ;
438
474
SDL_QueryTexture (frame .image .texture , NULL , NULL , & imgw , & imgh );
@@ -446,8 +482,7 @@ Slide parse_slide_from_file(FILE *in) {
446
482
continue ;
447
483
}
448
484
if (frame .type == FRAMEIMAGE ) {
449
- fprintf (stderr , "Text and image in same frame is not allowed!" );
450
- exit (1 );
485
+ die ("Text and image is same frame is not allowed" );
451
486
}
452
487
frame .type = FRAMETEXT ;
453
488
int blen = strlen (buf );
@@ -466,11 +501,11 @@ Slide parse_slide_from_file(FILE *in) {
466
501
return slide ;
467
502
}
468
503
504
+ #ifndef NO_JSON_CONFIG
469
505
void readconfig () {
470
506
char configpath [PATH_MAX ] = { 0 };
471
507
strcpy (configpath , gethomedir ());
472
508
strcat (configpath , "/.sslide.json" );
473
- puts (configpath );
474
509
FILE * configfile = fopen (configpath , "ab+" );
475
510
fseek (configfile , 0L , SEEK_END );
476
511
size_t fsize = ftell (configfile );
@@ -489,11 +524,10 @@ void readconfig() {
489
524
}
490
525
sjson_free (json );
491
526
free (content );
492
- return ;
493
527
bad :
494
- fprintf (stderr , "No/Bad config file, Skipping\n" );
495
528
return ;
496
529
}
530
+ #endif
497
531
498
532
char * gethomedir () {
499
533
char * ret = NULL ;
0 commit comments