diff --git a/cudoku.c b/cudoku.c index 60ea1ec..07ee19a 100644 --- a/cudoku.c +++ b/cudoku.c @@ -91,6 +91,8 @@ void draw_bg_grid_shader(Shader shader, unsigned int vao, float* transform, floa glBindVertexArray(vao); glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_INT, 0); + + glBindVertexArray(0); } void draw_bg_grid_texture(Shader shader, unsigned int vao, unsigned int texture, float* transform) { @@ -116,10 +118,43 @@ void draw_numbers(Shader shader, unsigned int vao, unsigned int vbo, float *tran glBindVertexArray(0); } -void draw_win_overlay(Shader shader, unsigned int vao, unsigned int vbo, float *transform) { +unsigned int prepare_win_overlay() { + unsigned int vbo, vao, ebo; + glGenVertexArrays(1, &vao); + glGenBuffers(1, &vbo); + glGenBuffers(1, &ebo); + + glBindVertexArray(vao); + + glBindBuffer(GL_ARRAY_BUFFER, vbo); + glBufferData(GL_ARRAY_BUFFER, sizeof(quad_vertices), quad_vertices, GL_STATIC_DRAW); + + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, ebo); + glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(quad_indices), quad_indices, GL_STATIC_DRAW); + + glEnableVertexAttribArray(0); + glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 5 * sizeof(float), (void *)0); + + glBindVertexArray(0); + + return vao; +} + +void draw_win_overlay(Shader win_shader, Shader font_shader, unsigned int vao, unsigned int font_vao, unsigned int font_vbo, float *transform) { + use_shader(win_shader); + + set_mat4f(win_shader, "transform", transform); + set_vec4f(win_shader, "aColor", 0.0, 0.0, 0.0, 0.8); + + glBindVertexArray(vao); + + glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_INT, 0); + + glBindVertexArray(0); + const char *text = "You won!"; Size text_size = calculate_text_size(text, 1.0f); - draw_text(shader, text, text_size, 1.5f, vao, vbo, transform); + draw_text(font_shader, text, text_size, 1.5f, font_vao, font_vbo, transform); } void prepare_selection_box(unsigned int *vao, unsigned int *vbo) { @@ -142,6 +177,7 @@ void draw_selection_box(Shader shader, unsigned int vao, unsigned int vbo, int x use_shader(shader); set_mat4f(shader, "transform", transform); + set_vec4f(shader, "aColor", 0.4, 0.4, 1.0, 0.5); glBindVertexArray(vao); @@ -196,13 +232,13 @@ void do_selection(Cudoku *game, int x, int y, int width, int height, float x_sca } void set_selected_number(Cudoku *game, int number) { - if (game->should_draw_selection) { + if (game->should_draw_selection && !game->has_won) { game->board[game->selection.x][game->selection.y] = number; } } void move_selection(Cudoku *game, int x, int y) { - if (game->should_draw_selection) { + if (game->should_draw_selection && !game->has_won) { game->selection.x += y; game->selection.y += x; @@ -221,5 +257,6 @@ void move_selection(Cudoku *game, int x, int y) { } void toggle_selection(Cudoku *game) { - game->should_draw_selection = !game->should_draw_selection; + if (!game->has_won) + game->should_draw_selection = !game->should_draw_selection; } diff --git a/cudoku.h b/cudoku.h index 07c9891..5a85d57 100644 --- a/cudoku.h +++ b/cudoku.h @@ -21,7 +21,8 @@ unsigned int prepare_bg(bool use_texture, unsigned int *texture); void draw_bg_grid_shader(Shader shader, unsigned int vao, float* transform, float resolution); void draw_bg_grid_texture(Shader shader, unsigned int vao, unsigned int texture, float* transform); void draw_numbers(Shader shader, unsigned int vao, unsigned int vbo, float *transform, int board[9][9]); -void draw_win_overlay(Shader shader, unsigned int vao, unsigned int vbo, float *transform); +unsigned int prepare_win_overlay(); +void draw_win_overlay(Shader win_shader, Shader font_shader, unsigned int vao, unsigned int font_vao, unsigned int font_vbo, float *transform); void prepare_selection_box(unsigned int *vao, unsigned int *vbo); void draw_selection_box(Shader shader, unsigned int vao, unsigned int vbo, int x, int y, float *transform); void do_selection(Cudoku *game, int x, int y, int width, int height, float x_scale, float y_scale); diff --git a/font.c b/font.c index 783a5a1..727b7df 100644 --- a/font.c +++ b/font.c @@ -175,7 +175,7 @@ void draw_number(Shader shader, int text, int row, int column, float scale, unsi void draw_text(Shader shader, const char *text, Size text_size, float scale, unsigned int vao, unsigned int vbo, float *transform) { use_shader(shader); - set_vec3f(shader, "textColor", 55.f / 255.f, 55.f / 255.f, 55.f / 255.f); + set_vec3f(shader, "textColor", 200.f / 255.f, 200.f / 255.f, 200.f / 255.f); set_mat4f(shader, "transform", transform); glActiveTexture(GL_TEXTURE0); glBindVertexArray(vao); diff --git a/main.c b/main.c index 7820b32..da28cd1 100644 --- a/main.c +++ b/main.c @@ -25,17 +25,32 @@ void handle_keypress(XEvent xev, Cudoku *game) { /* reset_board(&game); */ } else if (XLookupKeysym(&xev.xkey, 0) >= XK_0 && XLookupKeysym(&xev.xkey, 0) <= XK_9) { set_selected_number(game, XLookupKeysym(&xev.xkey, 0) - XK_0); - } else if (XLookupKeysym(&xev.xkey, 0) == XK_BackSpace || XLookupKeysym(&xev.xkey, 0) == XK_Delete) { + } else if (XLookupKeysym(&xev.xkey, 0) == XK_BackSpace || + XLookupKeysym(&xev.xkey, 0) == XK_Delete) { set_selected_number(game, 0); - } else if (XLookupKeysym(&xev.xkey, 0) == XK_Left || XLookupKeysym(&xev.xkey, 0) == XK_a || XLookupKeysym(&xev.xkey, 0) == XK_h) { + } else if ( + XLookupKeysym(&xev.xkey, 0) == XK_Left || + XLookupKeysym(&xev.xkey, 0) == XK_a || + XLookupKeysym(&xev.xkey, 0) == XK_h) { move_selection(game, -1, 0); - } else if (XLookupKeysym(&xev.xkey, 0) == XK_Right || XLookupKeysym(&xev.xkey, 0) == XK_d || XLookupKeysym(&xev.xkey, 0) == XK_l) { + } else if ( + XLookupKeysym(&xev.xkey, 0) == XK_Right || + XLookupKeysym(&xev.xkey, 0) == XK_d || + XLookupKeysym(&xev.xkey, 0) == XK_l) { move_selection(game, 1, 0); - } else if (XLookupKeysym(&xev.xkey, 0) == XK_Up || XLookupKeysym(&xev.xkey, 0) == XK_w || XLookupKeysym(&xev.xkey, 0) == XK_k) { + } else if ( + XLookupKeysym(&xev.xkey, 0) == XK_Up || + XLookupKeysym(&xev.xkey, 0) == XK_w || + XLookupKeysym(&xev.xkey, 0) == XK_k) { move_selection(game, 0, -1); - } else if (XLookupKeysym(&xev.xkey, 0) == XK_Down || XLookupKeysym(&xev.xkey, 0) == XK_s || XLookupKeysym(&xev.xkey, 0) == XK_j) { + } else if ( + XLookupKeysym(&xev.xkey, 0) == XK_Down || + XLookupKeysym(&xev.xkey, 0) == XK_s || + XLookupKeysym(&xev.xkey, 0) == XK_j) { move_selection(game, 0, 1); - } else if (XLookupKeysym(&xev.xkey, 0) == XK_Return || XLookupKeysym(&xev.xkey, 0) == XK_space) { + } else if ( + XLookupKeysym(&xev.xkey, 0) == XK_Return || + XLookupKeysym(&xev.xkey, 0) == XK_space) { toggle_selection(game); /* } else if (XLookupKeysym(&xev.xkey, 0) == XK_n) { */ /* new_board(&game); */ @@ -121,6 +136,9 @@ int main(int argc, char *argv[]) { unsigned int selection_vao, selection_vbo; prepare_selection_box(&selection_vao, &selection_vbo); + Shader win_shader = create_shader("shaders/board_v.vert", "shaders/quad.frag"); + unsigned int win_vao = prepare_win_overlay(); + srand(time(NULL)); for (int i = 0; i < 9; i++) { @@ -148,7 +166,8 @@ int main(int argc, char *argv[]) { } } else if (xev.type == KeyPress) { - if (XLookupKeysym(&xev.xkey, 0) == XK_Escape || XLookupKeysym(&xev.xkey, 0) == XK_q) { + if (XLookupKeysym(&xev.xkey, 0) == XK_Escape || + (XLookupKeysym(&xev.xkey, 0) == XK_q && xev.xkey.state & ControlMask)) { quit = true; break; } else { @@ -179,12 +198,18 @@ int main(int argc, char *argv[]) { draw_bg_grid_texture(grid_shader, board_vao, grid_texture, (float *)transform); if (game.should_draw_selection) - draw_selection_box(selection_shader, selection_vao, selection_vbo, game.selection.x, game.selection.y, (float *)transform); + draw_selection_box( + selection_shader, + selection_vao, + selection_vbo, + game.selection.x, + game.selection.y, + (float *)transform); draw_numbers(font_shader, font_vao, font_vbo, (float *)transform, game.board); if (game.has_won) { - draw_win_overlay(font_shader, font_vao, font_vbo, (float *)transform); + draw_win_overlay(win_shader, font_shader, win_vao, font_vao, font_vbo, (float *)transform); } glXSwapBuffers(display, window); diff --git a/shader.c b/shader.c index 12e0c8d..418e7f9 100644 --- a/shader.c +++ b/shader.c @@ -91,3 +91,8 @@ void set_vec3f(Shader shader, const char *name, float val1, float val2, float va int loc = glGetUniformLocation(shader.program, name); glUniform3f(loc, val1, val2, val3); } + +void set_vec4f(Shader shader, const char *name, float val1, float val2, float val3, float val4) { + int loc = glGetUniformLocation(shader.program, name); + glUniform4f(loc, val1, val2, val3, val4); +} diff --git a/shader.h b/shader.h index e46bc26..e17db7f 100644 --- a/shader.h +++ b/shader.h @@ -10,3 +10,4 @@ void use_shader(Shader shader); void set_mat4f(Shader shader, const char *name, float *mat); void set_float(Shader shader, const char *name, float val); void set_vec3f(Shader shader, const char *name, float val1, float val2, float val3); +void set_vec4f(Shader shader, const char *name, float val1, float val2, float val3, float val4); diff --git a/shaders/quad.frag b/shaders/quad.frag index e774429..e57a174 100644 --- a/shaders/quad.frag +++ b/shaders/quad.frag @@ -1,7 +1,8 @@ #version 330 core out vec4 FragColor; +uniform vec4 aColor; void main() { - FragColor = vec4(0.4, 0.4, 1.0, 0.5); + FragColor = vec4(aColor); }