X-Git-Url: https://git.cworth.org/git?a=blobdiff_plain;f=loa.c;h=5716a3627ef1e90e8f91822afd65c60c4c5f6e32;hb=9ec0c1c2741a39d38692ffeb0dfcbc88e874dbdf;hp=48b5b045c3fdf76e4418a03e773eb4157581fd3e;hpb=4ce79f50d09eb624783e864194669eb0862d6f7c;p=loa diff --git a/loa.c b/loa.c index 48b5b04..5716a36 100644 --- a/loa.c +++ b/loa.c @@ -20,6 +20,8 @@ #include #include +#include "loa-board.h" + #define BOARD_SIZE 8 typedef struct { @@ -30,6 +32,14 @@ typedef struct { int cell_size; } layout_t; +typedef struct { + layout_t layout; + loa_board_t board; + loa_bool_t has_selected; + int selected_x; + int selected_y; +} loa_game_t; + static gboolean on_delete_event_quit (GtkWidget *widget, GdkEvent *event, @@ -42,13 +52,69 @@ on_delete_event_quit (GtkWidget *widget, return FALSE; } +/* Something like buff */ +#define LIGHT_SQUARE_COLOR 0.89, 0.70, 0.40 +/* Something like mahogany */ +#define DARK_SQUARE_COLOR 0.26, 0.02, 0.01 + +static gboolean +on_button_press_event (GtkWidget *widget, + GdkEventButton *event, + gpointer user_data) +{ + loa_game_t *game = user_data; + layout_t *layout = &game->layout; + int x, y; + char *error; + + x = (event->x - layout->x_offset) / layout->cell_size; + y = (event->y - layout->y_offset) / layout->cell_size; + + if (! game->has_selected) { + if (game->board.cells[x][y] == game->board.player) { + game->has_selected = TRUE; + game->selected_x = x; + game->selected_y = y; + gtk_widget_queue_draw (widget); + } + return TRUE; + } + + if (x == game->selected_x && + y == game->selected_y) + { + game->has_selected = FALSE; + gtk_widget_queue_draw (widget); + return TRUE; + } + + if (loa_board_move (&game->board, + game->selected_x, game->selected_y, + x, y, &error)) + { + game->has_selected = FALSE; + gtk_widget_queue_draw (widget); + return TRUE; + } else { + printf ("Illegal move %c%d%c%d: %s\n", + 'a' + game->selected_x, + LOA_BOARD_SIZE - game->selected_y, + 'a' + x, + LOA_BOARD_SIZE - y, + error); + } + + return TRUE; +} + static gboolean on_expose_event_draw (GtkWidget *widget, GdkEventExpose *event, gpointer user_data) { + loa_game_t *game = user_data; + layout_t *layout = &game->layout; cairo_t *cr; - layout_t *layout = user_data; int x, y; if (layout->width != widget->allocation.width || @@ -74,14 +140,45 @@ on_expose_event_draw (GtkWidget *widget, for (y = 0; y < BOARD_SIZE; y++) { for (x = 0; x < BOARD_SIZE; x++) { + loa_cell_t cell; + cairo_save (cr); + cairo_translate(cr, x * layout->cell_size, y * layout->cell_size); if ((x + y) % 2 == 0) - cairo_set_source_rgb (cr, 0.89, 0.70, 0.40); + cairo_set_source_rgb (cr, LIGHT_SQUARE_COLOR); else - cairo_set_source_rgb (cr, 0.26, 0.02, 0.01); - cairo_rectangle (cr, - x * layout->cell_size, y * layout->cell_size, - layout->cell_size, layout->cell_size); + cairo_set_source_rgb (cr, DARK_SQUARE_COLOR); + cairo_rectangle (cr, 0, 0, layout->cell_size, layout->cell_size); cairo_fill (cr); + cell = game->board.cells[x][y]; + if (cell != LOA_CELL_EMPTY) { + cairo_arc (cr, + layout->cell_size / 2.0, layout->cell_size / 2.0, + layout->cell_size / 2.5, + 0, 2 * M_PI); + if (cell == LOA_CELL_BLACK) + cairo_set_source_rgb (cr, 0, 0, 0); /* black */ + else + cairo_set_source_rgb (cr, 1, 1, 1); /* white */ + cairo_fill_preserve (cr); + cairo_set_line_width (cr, 2.0); + if (cell == LOA_CELL_BLACK) + cairo_set_source_rgb (cr, LIGHT_SQUARE_COLOR); + else + cairo_set_source_rgb (cr, DARK_SQUARE_COLOR); + cairo_stroke (cr); + } + if (game->has_selected && + x == game->selected_x && + y == game->selected_y) + { + cairo_arc (cr, + layout->cell_size / 2.0, layout->cell_size / 2.0, + layout->cell_size / 2.5, + 0, 2 * M_PI); + cairo_set_source_rgba (cr, 0.2, 0.2, 1.0, 0.4); + cairo_fill (cr); + } + cairo_restore (cr); } } @@ -90,21 +187,31 @@ on_expose_event_draw (GtkWidget *widget, return TRUE; } +static void +loa_game_init (loa_game_t *game) +{ + game->layout.width = 0; + game->layout.height = 0; + + game->has_selected = FALSE; + + loa_board_init (&game->board); +} + int main (int argc, char *argv[]) { GtkWidget *window; GtkWidget *drawing_area; - layout_t layout; + loa_game_t game; - layout.width = 0; - layout.height = 0; + loa_game_init (&game); gtk_init (&argc, &argv); window = gtk_window_new (GTK_WINDOW_TOPLEVEL); - gtk_window_set_default_size (GTK_WINDOW (window), 100, 100); + gtk_window_set_default_size (GTK_WINDOW (window), 256, 256); g_signal_connect (window, "delete-event", G_CALLBACK (on_delete_event_quit), NULL); @@ -114,7 +221,11 @@ main (int argc, char *argv[]) gtk_container_add (GTK_CONTAINER (window), drawing_area); g_signal_connect (drawing_area, "expose-event", - G_CALLBACK (on_expose_event_draw), &layout); + G_CALLBACK (on_expose_event_draw), &game); + + gtk_widget_add_events (drawing_area, GDK_BUTTON_PRESS_MASK); + g_signal_connect (drawing_area, "button-press-event", + G_CALLBACK (on_button_press_event), &game); gtk_widget_show_all (window);