From 0ce85f6072f5d13db3b4cdf4f0bb59ec5b1a48a5 Mon Sep 17 00:00:00 2001 From: fosero Date: Tue, 8 Mar 2016 18:11:08 +0100 Subject: [PATCH] month-view: cleanup multi-row selection drawing The selection mode was drawing a number of boxes on multi-row selections, resulting in unwanted outlines within the selection area. This patch adds a multirow mode that just draws the outline of a selection. Make cell_{width,height} integers so divison lines always get drawn on exact grid coordinates, otherwise line calculations could result in fuzzy lines. https://bugzilla.gnome.org/show_bug.cgi?id=763217 --- src/gcal-month-view.c | 49 ++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 46 insertions(+), 3 deletions(-) diff --git a/src/gcal-month-view.c b/src/gcal-month-view.c index 7fbe2c1c..407b53ed 100644 --- a/src/gcal-month-view.c +++ b/src/gcal-month-view.c @@ -1381,7 +1381,8 @@ gcal_month_view_draw (GtkWidget *widget, gint font_width, font_height, pos_x, pos_y, shown_rows; gint i, j, sw, lower_mark = 43, upper_mark = -2; - gdouble start_grid_y, cell_width, cell_height, first_row_gap = 0.0; + gint cell_width, cell_height; + gdouble start_grid_y, first_row_gap = 0.0; gdouble days; priv = gcal_month_view_get_instance_private (GCAL_MONTH_VIEW (widget)); @@ -1672,9 +1673,9 @@ gcal_month_view_draw (GtkWidget *widget, gdk_cairo_set_source_rgba (cr, &color); cairo_set_line_width (cr, LINE_WIDTH); - /* horizontals */ if ((first_mark / 7) == (last_mark / 7)) { + /* selection in 1 row with 1 rectangular outline */ gint row = first_mark / 7; gint first_column = first_mark % 7; gint last_column = last_mark % 7; @@ -1686,8 +1687,9 @@ gcal_month_view_draw (GtkWidget *widget, cairo_rectangle (cr, pos_x + (LINE_WIDTH / 2), pos_y + (LINE_WIDTH / 2), pos_x2 - pos_x + (LINE_WIDTH / 2), pos_y2 - pos_y + (LINE_WIDTH / 2)); } - else + else if ((first_mark / 7) == ((last_mark / 7) - 1) && (first_mark % 7) > ((last_mark % 7) + 1)) { + /* selection in 2 rows with 2 seperate rectangular outlines */ gint first_row = first_mark / 7; gint last_row = last_mark / 7; gint first_column = first_mark % 7; @@ -1718,6 +1720,47 @@ gcal_month_view_draw (GtkWidget *widget, (gint)end + (LINE_WIDTH / 2), pos_y2 - pos_y + (LINE_WIDTH / 2)); } } + else + { + /* multi-row selection with a single outline */ + gint first_row = first_mark / 7; + gint last_row = last_mark / 7; + gint first_column = first_mark % 7; + gint last_column = last_mark % 7; + gdouble start_x = (cell_width * first_column) + (LINE_WIDTH / 2); + gdouble start_y = (cell_height * (first_row + first_row_gap)) + start_grid_y + (LINE_WIDTH / 2); + gdouble end_x = (cell_width * (last_column + 1.0)) + (LINE_WIDTH / 2); + gdouble end_y = (cell_height * (last_row + first_row_gap + 1.0)) + start_grid_y + (LINE_WIDTH / 2); + gdouble max_x = alloc.width - (LINE_WIDTH / 2); + + /* Draw the irregular shaped selection box starting from the + * top-left corner of the start date (start_{x,y}) clock-wise + * to the right-bottom corner of the end date (end_{x,y}) and + * on finishing at the start date again. + */ + cairo_move_to (cr, start_x, start_y); + cairo_line_to (cr, max_x, start_y); + + /* Skip intermediate drawing steps if end_{x,y} are at the + * last column in the row, this makes sure we always draw the + * outline within the visible drawing area. + */ + if (last_column == 6) + { + cairo_line_to (cr, max_x, end_y); + } + else + { + cairo_line_to (cr, max_x, end_y - cell_height); + cairo_line_to (cr, end_x, end_y - cell_height); + cairo_line_to (cr, end_x, end_y); + } + + cairo_line_to (cr, (LINE_WIDTH / 2), end_y); + cairo_line_to (cr, (LINE_WIDTH / 2), start_y + cell_height); + cairo_line_to (cr, start_x, start_y + cell_height); + cairo_line_to (cr, start_x, start_y); + } cairo_stroke (cr); }