src/window.c

changeset 7
9dd76cbd6c90
parent 6
302971e8599b
child 9
6ad1a4213954
equal deleted inserted replaced
6:302971e8599b 7:9dd76cbd6c90
24 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 24 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
25 * POSSIBILITY OF SUCH DAMAGE. 25 * POSSIBILITY OF SUCH DAMAGE.
26 */ 26 */
27 27
28 #include "ascension/window.h" 28 #include "ascension/window.h"
29 #include "ascension/context.h"
30 #include "ascension/error.h"
29 31
30 #include <cx/linked_list.h> 32 #include <cx/linked_list.h>
31 #include <cx/printf.h> 33 #include <cx/printf.h>
32 34
33 #include <GL/glew.h> 35 #include <GL/glew.h>
48 cx_strfree(&buf); 50 cx_strfree(&buf);
49 } 51 }
50 52
51 53
52 static void asc_event_window_resized(Uint32 id, Sint32 width, Sint32 height) { 54 static void asc_event_window_resized(Uint32 id, Sint32 width, Sint32 height) {
53 CxIterator iter = cxListIterator(asc_context.windows); 55 for (unsigned int i = 0 ; i < ASC_MAX_WINDOWS ; i++) {
54 cx_foreach(AscWindow*, w, iter) { 56 if (asc_context.windows[i].id == id) {
55 if (w->id == id) { 57 asc_context.windows[i].dimensions.width = width;
56 w->dimensions.width = width; 58 asc_context.windows[i].dimensions.height = height;
57 w->dimensions.height = height;
58 return; 59 return;
59 } 60 }
60 } 61 }
61 } 62 }
62 63
85 break; 86 break;
86 } 87 }
87 } 88 }
88 89
89 // sync the windows 90 // sync the windows
90 CxMutIterator windows = cxListMutIterator(asc_context.windows); 91 for (unsigned int i = 0 ; i < ASC_MAX_WINDOWS ; i++) {
91 cx_foreach(AscWindow*, w, windows) { 92 if (asc_context.windows[i].id > 0) {
92 asc_window_sync(w); 93 asc_window_sync(&asc_context.windows[i]);
94 }
93 } 95 }
94 return true; 96 return true;
95 } 97 }
96 98
97 void asc_window_settings_init_defaults(AscWindowSettings* settings) { 99 void asc_window_settings_init_defaults(AscWindowSettings* settings) {
103 settings->gl_major_version = 3; 105 settings->gl_major_version = 3;
104 settings->gl_minor_version = 3; 106 settings->gl_minor_version = 3;
105 settings->title = "Ascended Window"; 107 settings->title = "Ascended Window";
106 } 108 }
107 109
108 void asc_window_initialize(AscWindow* window, AscWindowSettings const* settings) { 110 AscWindow *asc_window_initialize(unsigned int index, AscWindowSettings const *settings) {
111 if (index >= ASC_MAX_WINDOWS) {
112 asc_error("Maximum number of windows exceeded.");
113 return NULL;
114 }
115 AscWindow *window = &asc_context.windows[index];
116 if (window->id > 0) {
117 asc_error("Cannot create window - slot already occupied.");
118 asc_dprintf("Tried to create window with index %u", index);
119 return NULL;
120 }
121
109 Uint32 flags = SDL_WINDOW_OPENGL | SDL_WINDOW_SHOWN; 122 Uint32 flags = SDL_WINDOW_OPENGL | SDL_WINDOW_SHOWN;
110 flags |= settings->fullscreen ? SDL_WINDOW_FULLSCREEN_DESKTOP : SDL_WINDOW_RESIZABLE; 123 flags |= settings->fullscreen ? SDL_WINDOW_FULLSCREEN_DESKTOP : SDL_WINDOW_RESIZABLE;
111 124
112 window->window = SDL_CreateWindow( 125 window->window = SDL_CreateWindow(
113 settings->title, 126 settings->title,
117 settings->dimensions.height, 130 settings->dimensions.height,
118 flags 131 flags
119 ); 132 );
120 if (window->window == NULL) { 133 if (window->window == NULL) {
121 asc_error(SDL_GetError()); 134 asc_error(SDL_GetError());
122 return; 135 return NULL;
123 } 136 }
124 137
125 window->id = SDL_GetWindowID(window->window); 138 window->id = SDL_GetWindowID(window->window);
126 SDL_GetWindowSize(window->window, 139 SDL_GetWindowSize(window->window,
127 &window->dimensions.width, 140 &window->dimensions.width,
145 glEnable(GL_BLEND); 158 glEnable(GL_BLEND);
146 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); 159 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
147 glEnable(GL_DEBUG_OUTPUT); 160 glEnable(GL_DEBUG_OUTPUT);
148 glDebugMessageCallback(asc_gl_debug_callback, NULL); 161 glDebugMessageCallback(asc_gl_debug_callback, NULL);
149 asc_dprintf("Window %u initialized", window->id); 162 asc_dprintf("Window %u initialized", window->id);
150 cxListAdd(asc_context.windows, window); 163 return window;
151 return;
152 } else { 164 } else {
153 asc_error(glewGetErrorString(err)); 165 asc_error(glewGetErrorString(err));
154 } 166 }
155 } 167 }
156 168
162 SDL_DestroyWindow(window->window); 174 SDL_DestroyWindow(window->window);
163 window->window = NULL; 175 window->window = NULL;
164 window->id = 0; 176 window->id = 0;
165 } 177 }
166 178
167 void asc_window_destroy_impl(AscWindow* window) { 179 void asc_window_destroy(AscWindow* window) {
168 // destory the GL context and the window 180 // safeguard
181 if (window->id == 0) return;
182
183 // destroy the GL context and the window
169 if (window->glctx != NULL) { 184 if (window->glctx != NULL) {
170 SDL_GL_DeleteContext(window->glctx); 185 SDL_GL_DeleteContext(window->glctx);
171 } 186 }
172 if (window->window != NULL) { 187 if (window->window != NULL) {
173 SDL_DestroyWindow(window->window); 188 SDL_DestroyWindow(window->window);
174 } 189 }
175 190
176 // clean the data 191 // clean the data
177 asc_dprintf("Window %u and its OpenGL context destroyed.", window->id); 192 asc_dprintf("Window %u and its OpenGL context destroyed.", window->id);
178 memset(window, 0, sizeof(AscWindow)); 193 memset(window, 0, sizeof(AscWindow));
179 }
180
181 void asc_window_destroy(AscWindow* window) {
182 // find the window in the context and remove it
183 bool found = false;
184 CxMutIterator iter = cxListMutIterator(asc_context.windows);
185 cx_foreach(AscWindow*, w, iter) {
186 if (w == window) {
187 found = true;
188 cxIteratorFlagRemoval(iter);
189 }
190 }
191 if (!found) asc_window_destroy_impl(window);
192 } 194 }
193 195
194 void asc_window_sync(AscWindow const* window) { 196 void asc_window_sync(AscWindow const* window) {
195 SDL_GL_MakeCurrent(window->window, window->glctx); 197 SDL_GL_MakeCurrent(window->window, window->glctx);
196 SDL_GL_SwapWindow(window->window); 198 SDL_GL_SwapWindow(window->window);

mercurial