From 1f3e70aafcdeaf13eeb906fba97825b5d64ccde9 Mon Sep 17 00:00:00 2001 From: Franklin Wei Date: Sun, 29 Oct 2017 17:39:29 -0400 Subject: puzzles: sync with upstream This includes the fix for Map's incorrect cursor positioning when zoomed in. Change-Id: I7d7d1f3031bbe1390e89340039996f99efaa8ef5 --- apps/plugins/puzzles/src/gtk.c | 6 ++-- apps/plugins/puzzles/src/map.c | 67 +++++++++++++++++++++++++++-------------- apps/plugins/puzzles/src/solo.c | 30 ++++++++++++++---- 3 files changed, 73 insertions(+), 30 deletions(-) diff --git a/apps/plugins/puzzles/src/gtk.c b/apps/plugins/puzzles/src/gtk.c index 37ba8078e2..3078e517ba 100644 --- a/apps/plugins/puzzles/src/gtk.c +++ b/apps/plugins/puzzles/src/gtk.c @@ -1397,7 +1397,9 @@ static gint configure_area(GtkWidget *widget, { frontend *fe = (frontend *)data; resize_puzzle_to_area(fe, event->width, event->height); +#if GTK_CHECK_VERSION(3,0,0) fe->awaiting_resize_ack = FALSE; +#endif return TRUE; } @@ -1522,8 +1524,8 @@ static void msgbox_button_clicked(GtkButton *button, gpointer data) gtk_widget_destroy(GTK_WIDGET(data)); } -int message_box(GtkWidget *parent, char *title, char *msg, int centre, - int type) +int message_box(GtkWidget *parent, const char *title, const char *msg, + int centre, int type) { GtkWidget *window, *hbox, *text, *button; char *titles; diff --git a/apps/plugins/puzzles/src/map.c b/apps/plugins/puzzles/src/map.c index cdcd5861a8..3a1633590c 100644 --- a/apps/plugins/puzzles/src/map.c +++ b/apps/plugins/puzzles/src/map.c @@ -2340,18 +2340,21 @@ struct game_drawstate { ((button) == CURSOR_UP) ? -1 : 0) -static int region_from_coords(const game_state *state, - const game_drawstate *ds, int x, int y) +/* + * Return the map region containing a point in tile (tx,ty), offset by + * (x_eps,y_eps) from the centre of the tile. + */ +static int region_from_logical_coords(const game_state *state, int tx, int ty, + int x_eps, int y_eps) { int w = state->p.w, h = state->p.h, wh = w*h /*, n = state->p.n */; - int tx = FROMCOORD(x), ty = FROMCOORD(y); - int dx = x - COORD(tx), dy = y - COORD(ty); + int quadrant; if (tx < 0 || tx >= w || ty < 0 || ty >= h) return -1; /* border */ - quadrant = 2 * (dx > dy) + (TILESIZE - dx > dy); + quadrant = 2 * (x_eps > y_eps) + (-x_eps > y_eps); quadrant = (quadrant == 0 ? BE : quadrant == 1 ? LE : quadrant == 2 ? RE : TE); @@ -2359,12 +2362,28 @@ static int region_from_coords(const game_state *state, return state->map->map[quadrant * wh + ty*w+tx]; } +static int region_from_coords(const game_state *state, + const game_drawstate *ds, int x, int y) +{ + int tx = FROMCOORD(x), ty = FROMCOORD(y); + return region_from_logical_coords( + state, tx, ty, x - COORD(tx) - TILESIZE/2, y - COORD(ty) - TILESIZE/2); +} + +static int region_from_ui_cursor(const game_state *state, const game_ui *ui) +{ + assert(ui->cur_visible); + return region_from_logical_coords(state, ui->cur_x, ui->cur_y, + EPSILON_X(ui->cur_lastmove), + EPSILON_Y(ui->cur_lastmove)); +} + static char *interpret_move(const game_state *state, game_ui *ui, const game_drawstate *ds, int x, int y, int button) { char *bufp, buf[256]; - int alt_button; + int alt_button, drop_region; /* * Enable or disable numeric labels on regions. @@ -2379,19 +2398,15 @@ static char *interpret_move(const game_state *state, game_ui *ui, ui->cur_visible = 1; ui->cur_moved = 1; ui->cur_lastmove = button; - ui->dragx = COORD(ui->cur_x) + TILESIZE/2 + EPSILON_X(button); - ui->dragy = COORD(ui->cur_y) + TILESIZE/2 + EPSILON_Y(button); return UI_UPDATE; } if (IS_CURSOR_SELECT(button)) { if (!ui->cur_visible) { - ui->dragx = COORD(ui->cur_x) + TILESIZE/2 + EPSILON_X(ui->cur_lastmove); - ui->dragy = COORD(ui->cur_y) + TILESIZE/2 + EPSILON_Y(ui->cur_lastmove); ui->cur_visible = 1; return UI_UPDATE; } if (ui->drag_colour == -2) { /* not currently cursor-dragging, start. */ - int r = region_from_coords(state, ds, ui->dragx, ui->dragy); + int r = region_from_ui_cursor(state, ui); if (r >= 0) { ui->drag_colour = state->colouring[r]; ui->drag_pencil = (ui->drag_colour >= 0) ? 0 : state->pencil[r]; @@ -2402,11 +2417,10 @@ static char *interpret_move(const game_state *state, game_ui *ui, ui->cur_moved = 0; return UI_UPDATE; } else { /* currently cursor-dragging; drop the colour in the new region. */ - x = COORD(ui->cur_x) + TILESIZE/2 + EPSILON_X(ui->cur_lastmove); - y = COORD(ui->cur_y) + TILESIZE/2 + EPSILON_Y(ui->cur_lastmove); alt_button = (button == CURSOR_SELECT2) ? 1 : 0; /* Double-select removes current colour. */ if (!ui->cur_moved) ui->drag_colour = -1; + drop_region = region_from_ui_cursor(state, ui); goto drag_dropped; } } @@ -2439,6 +2453,7 @@ static char *interpret_move(const game_state *state, game_ui *ui, if ((button == LEFT_RELEASE || button == RIGHT_RELEASE) && ui->drag_colour > -2) { alt_button = (button == RIGHT_RELEASE) ? 1 : 0; + drop_region = region_from_coords(state, ds, x, y); goto drag_dropped; } @@ -2446,7 +2461,7 @@ static char *interpret_move(const game_state *state, game_ui *ui, drag_dropped: { - int r = region_from_coords(state, ds, x, y); + int r = drop_region; int c = ui->drag_colour; int p = ui->drag_pencil; int oldp; @@ -2972,29 +2987,37 @@ static void game_redraw(drawing *dr, game_drawstate *ds, * Draw the dragged colour blob if any. */ if ((ui->drag_colour > -2) || ui->cur_visible) { - int bg, iscur = 0; + int bg, iscur = 0, cursor_x, cursor_y; if (ui->drag_colour >= 0) bg = COL_0 + ui->drag_colour; else if (ui->drag_colour == -1) { bg = COL_BACKGROUND; } else { - int r = region_from_coords(state, ds, ui->dragx, ui->dragy); + int r = region_from_ui_cursor(state, ui); int c = (r < 0) ? -1 : state->colouring[r]; - assert(ui->cur_visible); /*bg = COL_GRID;*/ bg = (c < 0) ? COL_BACKGROUND : COL_0 + c; iscur = 1; } - ds->dragx = ui->dragx - TILESIZE/2 - 2; - ds->dragy = ui->dragy - TILESIZE/2 - 2; + if (ui->cur_visible) { + cursor_x = COORD(ui->cur_x) + TILESIZE/2 + + EPSILON_X(ui->cur_lastmove); + cursor_y = COORD(ui->cur_y) + TILESIZE/2 + + EPSILON_Y(ui->cur_lastmove); + } else { + cursor_x = ui->dragx; + cursor_y = ui->dragy; + } + ds->dragx = cursor_x - TILESIZE/2 - 2; + ds->dragy = cursor_y - TILESIZE/2 - 2; blitter_save(dr, ds->bl, ds->dragx, ds->dragy); - draw_circle(dr, ui->dragx, ui->dragy, + draw_circle(dr, cursor_x, cursor_y, iscur ? TILESIZE/4 : TILESIZE/2, bg, COL_GRID); for (i = 0; i < FOUR; i++) if (ui->drag_pencil & (1 << i)) - draw_circle(dr, ui->dragx + ((i*4+2)%10-3) * TILESIZE/10, - ui->dragy + (i*2-3) * TILESIZE/10, + draw_circle(dr, cursor_x + ((i*4+2)%10-3) * TILESIZE/10, + cursor_y + (i*2-3) * TILESIZE/10, TILESIZE/8, COL_0 + i, COL_0 + i); draw_update(dr, ds->dragx, ds->dragy, TILESIZE + 3, TILESIZE + 3); ds->drag_visible = TRUE; diff --git a/apps/plugins/puzzles/src/solo.c b/apps/plugins/puzzles/src/solo.c index ef2852f1d9..dd04cdf281 100644 --- a/apps/plugins/puzzles/src/solo.c +++ b/apps/plugins/puzzles/src/solo.c @@ -1013,12 +1013,23 @@ static int solver_set(struct solver_usage *usage, /* * If count == 0, then there's a row with no 1s at all and - * the puzzle is internally inconsistent. However, we ought - * to have caught this already during the simpler reasoning - * methods, so we can safely fail an assertion if we reach - * this point here. + * the puzzle is internally inconsistent. */ - assert(count > 0); + if (count == 0) { +#ifdef STANDALONE_SOLVER + if (solver_show_working) { + va_list ap; + printf("%*s", solver_recurse_depth*4, + ""); + va_start(ap, fmt); + vprintf(fmt, ap); + va_end(ap); + printf(":\n%*s solver_set: impossible on entry\n", + solver_recurse_depth*4, ""); + } +#endif + return -1; + } if (count == 1) rowidx[i] = colidx[first] = FALSE; } @@ -1465,7 +1476,14 @@ static int solver_killer_sums(struct solver_usage *usage, int b, assert(nsquares == 0); return 0; } - assert(nsquares > 0); + if (nsquares == 0) { +#ifdef STANDALONE_SOLVER + if (solver_show_working) + printf("%*skiller: cage has no usable squares left\n", + solver_recurse_depth*4, ""); +#endif + return -1; + } if (nsquares < 2 || nsquares > 4) return 0; -- cgit v1.2.3