69b7efa5f644de700ac1dd5f9cd70d5c74f0dca3
[vrfileman] / src / main.cc
1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <SDL2/SDL.h>
4 #include "app.h"
5
6 static void process_event(SDL_Event *ev);
7
8 static SDL_Window *win;
9 static SDL_GLContext ctx;
10 static bool redraw_pending = true;
11 static bool quit;
12
13 static SDL_Window *create_window(int width, int height)
14 {
15         SDL_Window *win;
16         int x = SDL_WINDOWPOS_UNDEFINED;
17         int y = SDL_WINDOWPOS_UNDEFINED;
18         unsigned int flags = SDL_WINDOW_OPENGL | SDL_WINDOW_RESIZABLE | SDL_WINDOW_ALLOW_HIGHDPI;
19         if(!(win = SDL_CreateWindow("vrfileman", x, y, width, height, flags))) {
20                 return 0;
21         }
22         return win;
23 }
24
25 int main(int argc, char **argv)
26 {
27         if(SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER) == -1) {
28                 fprintf(stderr, "failed to initialize SDL\n");
29                 return 1;
30         }
31
32         SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, 1);
33         SDL_GL_SetAttribute(SDL_GL_MULTISAMPLESAMPLES, 8);
34         SDL_GL_SetAttribute(SDL_GL_FRAMEBUFFER_SRGB_CAPABLE, 1);
35
36         if(!(win = create_window(def_opt.width, def_opt.height))) {
37                 // try again without the SRGB capability
38                 SDL_GL_SetAttribute(SDL_GL_FRAMEBUFFER_SRGB_CAPABLE, 0);
39                 if(!(win = create_window(win_width, win_height))) {
40                         fprintf(stderr, "failed to create window\n");
41                         return 1;
42                 }
43                 fprintf(stderr, "failed to create sRGB-capable window, defaulting to non-linear color space\n");
44                 def_opt.srgb = false;
45         }
46
47         if(!(ctx = SDL_GL_CreateContext(win))) {
48                 fprintf(stderr, "failed to create OpenGL context\n");
49                 return 1;
50         }
51         SDL_GL_GetDrawableSize(win, &win_width, &win_height);
52         win_aspect = (float)win_width / (float)win_height;
53
54         if(!app_init(argc, argv)) {
55                 SDL_Quit();
56                 return 1;
57         }
58         app_reshape(win_width, win_height);
59
60         while(!quit) {
61                 SDL_Event ev;
62
63                 if(!redraw_pending) {
64                         if(!SDL_WaitEvent(0)) {
65                                 fprintf(stderr, "error while waiting for events\n");
66                                 break;
67                         }
68                 }
69
70                 time_msec = app_get_msec();
71                 time_sec = (double)time_msec / 1000.0;
72                 while(SDL_PollEvent(&ev)) {
73                         process_event(&ev);
74                         if(quit) goto break_evloop;
75                 }
76
77                 if(redraw_pending) {
78                         redraw_pending = false;
79                         app_draw();
80                 }
81         }
82 break_evloop:
83
84         app_cleanup();
85         SDL_Quit();
86         return 0;
87 }
88
89 void app_resize(int x, int y)
90 {
91         SDL_SetWindowSize(win, x, y);
92 }
93
94 void app_fullscreen(bool fs)
95 {
96         SDL_SetWindowFullscreen(win, fs ? SDL_WINDOW_FULLSCREEN_DESKTOP : 0);
97 }
98
99 void app_quit()
100 {
101         quit = true;
102 }
103
104 void app_redraw()
105 {
106         redraw_pending = true;
107 }
108
109 void app_swap_buffers()
110 {
111         SDL_GL_SwapWindow(win);
112 }
113
114 long app_get_msec()
115 {
116         return SDL_GetTicks();
117 }
118
119 static void process_event(SDL_Event *ev)
120 {
121         switch(ev->type) {
122         case SDL_QUIT:
123                 quit = true;
124                 break;
125
126         case SDL_KEYDOWN:
127         case SDL_KEYUP:
128                 app_keyboard(ev->key.keysym.sym, ev->key.state == SDL_PRESSED);
129                 break;
130
131         case SDL_MOUSEBUTTONDOWN:
132         case SDL_MOUSEBUTTONUP:
133                 app_mouse_button(ev->button.button - SDL_BUTTON_LEFT, ev->button.state == SDL_PRESSED,
134                                 ev->button.x, ev->button.y);
135                 break;
136
137         case SDL_MOUSEMOTION:
138                 app_mouse_motion(ev->motion.x, ev->motion.y);
139                 break;
140
141         case SDL_WINDOWEVENT:
142                 if(ev->window.event == SDL_WINDOWEVENT_RESIZED) {
143                         win_width = ev->window.data1;
144                         win_height = ev->window.data2;
145                         win_aspect = (float)win_width / (float)win_height;
146                         app_reshape(win_width, win_height);
147                 }
148                 break;
149         }
150 }