From: Hugo Villeneuve Date: Fri, 10 Sep 2010 06:49:44 +0000 (+0000) Subject: Fixed display problems when in non-dockapp mode for calendar X-Git-Tag: hvclock-1.0.1~3 X-Git-Url: http://gitweb.hugovil.com/?a=commitdiff_plain;h=a662ade87bc559e6ca79247cd8e139274c9b0fef;p=dockapps%2Fhvclock.git Fixed display problems when in non-dockapp mode for calendar Changed calendar fixed font sizes to relative font sizes Merged common hand drawing functions --- diff --git a/src/clock.c b/src/clock.c index 23f8dc3..0f808f3 100644 --- a/src/clock.c +++ b/src/clock.c @@ -58,7 +58,7 @@ #define HAND_HOURS_LENGTH_RATIO 0.55 #define HAND_MINUTES_LENGTH_RATIO 0.80 #define HAND_SECONDS_LENGTH1_RATIO 0.80 /* Main hand */ -#define HAND_SECONDS_LENGTH2_RATIO 0.30 /* Small hand on opposite side */ +#define HAND_SECONDS_LENGTH2_RATIO 0.25 /* Small extension on opposite side */ #define HAND_HOURS_WIDTH_RATIO 0.100 #define HAND_MINUTES_WIDTH_RATIO 0.070 @@ -69,11 +69,9 @@ #define CLOCK_DIGITS_FONTS_SIZE_RATIO 0.30 -#define CALENDAR_FONTS_SIZE 8.0 - /* Manual tweak for '11' oclock position */ -#define ELEVENTH_OCLOCK_FIRST_DIGIT_XOFFSET 1.99 -#define TENTH_OCLOCK_FIRST_DIGIT_XOFFSET 1.75 +#define ELEVENTH_OCLOCK_FIRST_DIGIT_XOFFSET_RATIO 0.04 +#define TENTH_OCLOCK_FIRST_DIGIT_XOFFSET_RATIO 0.04 /* Offset between digits of '10', '11' and '12' oclock positions */ #define SECOND_DIGIT_XOFFSET 1.0 @@ -84,6 +82,13 @@ /* Radius of small dots near each digit */ #define DIGITS_DOTS_RADIUS_RATIO 0.04 +#define CALENDAR_TEXT_FONTS_SIZE_RATIO 0.15 +#define CALENDAR_DIGITS_FONTS_SIZE_RATIO (3.5 * CALENDAR_TEXT_FONTS_SIZE_RATIO) + +#define CALENDAR_WEEKDAY_Y_POSITION_RATIO 0.20 +#define CALENDAR_MONTH_Y_POSITION_RATIO 0.40 +#define CALENDAR_DAYOFMONTH_Y_POSITION_RATIO 0.92 + struct hvclock_gtk_t { GtkDrawingArea parent; }; @@ -103,6 +108,25 @@ G_DEFINE_TYPE(HvClock, hvclock, GTK_TYPE_DRAWING_AREA); /* Starting mode is clock mode */ static int hvclock_mode = CLOCK_MODE; +static double +get_clock_face_radius(GtkWidget *clock) +{ + /* Compute clock face radius */ + return (MIN(clock->allocation.width, clock->allocation.height) / 2) - 1; +} + +static struct tm * +clock_get_time(void) +{ + time_t now; /* Current system time */ + + /* Get the current time */ + now = time(NULL); + + /* Format and print the time, "ddd yyyy-mm-dd hh:mm:ss zzz" */ + return localtime(&now); +} + static void draw_clock_background(GtkWidget *clock, cairo_t *cr) { @@ -114,9 +138,7 @@ draw_clock_background(GtkWidget *clock, cairo_t *cr) center_x = clock->allocation.width / 2; center_y = clock->allocation.height / 2; - /* Clock face radius */ - radius = MIN(clock->allocation.width / 2, clock->allocation.height / 2) - - 1; + radius = get_clock_face_radius(clock); /* Position of digits as a radius ratio */ radius_numbers = radius * DIGITS_POSITION_RATIO; @@ -134,9 +156,9 @@ draw_clock_background(GtkWidget *clock, cairo_t *cr) /* Draw clock background and outer rim */ cairo_set_line_width(cr, 1.5); cairo_arc(cr, center_x, center_y, radius, 0, 2 * M_PI); - cairo_set_source_rgb(cr, 1, 1, 1); + cairo_set_source_rgb(cr, 1.0, 1.0, 1.0); cairo_fill_preserve(cr); /* White background */ - cairo_set_source_rgb(cr, 0, 0, 0); + cairo_set_source_rgb(cr, 0.0, 0.0, 0.0); cairo_stroke(cr); /* Black rim */ /* Draw clock tick marks on outer circle */ @@ -162,18 +184,17 @@ draw_clock_background(GtkWidget *clock, cairo_t *cr) /* Manual tweak for '10' and '11' oclock position */ if (digit == 11) first_digit_xoffset = - ELEVENTH_OCLOCK_FIRST_DIGIT_XOFFSET; + ELEVENTH_OCLOCK_FIRST_DIGIT_XOFFSET_RATIO; else if (digit == 10) first_digit_xoffset = - TENTH_OCLOCK_FIRST_DIGIT_XOFFSET; - + TENTH_OCLOCK_FIRST_DIGIT_XOFFSET_RATIO; } xx = extents.width / divisor + extents.x_bearing; yy = extents.height / 2 + extents.y_bearing; text_start_x = center_x + radius_numbers * cos(angle) - xx + - first_digit_xoffset; + (first_digit_xoffset * radius); text_start_y = center_y - radius_numbers * sin(angle) - yy; cairo_move_to(cr, text_start_x, text_start_y); @@ -205,16 +226,36 @@ draw_clock_background(GtkWidget *clock, cairo_t *cr) cairo_restore(cr); } -static struct tm * -clock_get_time(void) +static void +draw_clock_hand_common(GtkWidget *clock, cairo_t *cr, double angle, + double len_main_ratio, double len_ext_ratio, double width_ratio) { - time_t now; /* Current system time */ + gint center_x, center_y; + double sin_x, cos_y; + double radius, length; - /* Get the current time */ - now = time(NULL); + radius = get_clock_face_radius(clock); - /* Format and print the time, "ddd yyyy-mm-dd hh:mm:ss zzz" */ - return localtime(&now); + center_x = clock->allocation.width / 2; + center_y = clock->allocation.height / 2; + + sin_x = sin(angle); + cos_y = cos(angle); + + cairo_set_line_width(cr, radius * width_ratio); + + length = radius * len_ext_ratio; + /* + * If optional extension len is non null, starting position is at the + * outer end of extension. Otherwise, starting position is at center. + */ + cairo_move_to(cr, center_x - length * sin_x, + center_y - length * -cos_y); + length = radius * len_main_ratio; + cairo_line_to(cr, center_x + length * sin_x, + center_y + length * -cos_y); + + cairo_stroke(cr); } static void @@ -222,9 +263,8 @@ draw_clock_hands(GtkWidget *clock, cairo_t *cr) { gint center_x, center_y; double angle = M_PI / 3; /* Starting angle at '12' oclock position */ - double radius, length; + double radius; int hours, minutes, seconds; - double sin_x, cos_y; struct tm *ts; ts = clock_get_time(); @@ -232,14 +272,13 @@ draw_clock_hands(GtkWidget *clock, cairo_t *cr) center_x = clock->allocation.width / 2; center_y = clock->allocation.height / 2; - /* Clock face radius */ - radius = MIN(clock->allocation.width / 2, clock->allocation.height / 2) - - 1; + radius = get_clock_face_radius(clock); cairo_save(cr); hours = ts->tm_hour; minutes = ts->tm_min; + seconds = ts->tm_sec; cairo_set_source_rgb(cr, 0.15, 0.15, 0.15); cairo_set_line_cap(cr, CAIRO_LINE_CAP_ROUND); @@ -249,40 +288,27 @@ draw_clock_hands(GtkWidget *clock, cairo_t *cr) * 1/2 a degree (pi/360 r) per minute */ angle = M_PI / 6 * hours + M_PI / 360 * minutes; - cairo_set_line_width(cr, radius * HAND_HOURS_WIDTH_RATIO); - cairo_move_to(cr, center_x, center_y); - length = radius * HAND_HOURS_LENGTH_RATIO; - cairo_line_to(cr, center_x + length * sin(angle), - center_y + length * -cos(angle)); - cairo_stroke(cr); + draw_clock_hand_common(clock, cr, angle, + HAND_HOURS_LENGTH_RATIO, 0, /* No extension */ + HAND_HOURS_WIDTH_RATIO); /* minute hand: * the minute hand is rotated 6 degrees (pi/30 r) per minute */ angle = M_PI / 30 * minutes; - cairo_move_to(cr, center_x, center_y); - cairo_set_line_width(cr, radius * HAND_MINUTES_WIDTH_RATIO); - length = radius * HAND_MINUTES_LENGTH_RATIO; - cairo_line_to(cr, center_x + length * sin(angle), - center_y + length * -cos(angle)); - cairo_stroke(cr); + draw_clock_hand_common(clock, cr, angle, + HAND_MINUTES_LENGTH_RATIO, 0, /* No extension */ + HAND_MINUTES_WIDTH_RATIO); /* seconds hand: * operates identically to the minute hand */ if (hvclock_infos.show_seconds) { - seconds = ts->tm_sec; angle = M_PI / 30 * seconds; - cairo_set_line_width(cr, radius * HAND_SECONDS_WIDTH_RATIO); - sin_x = sin(angle); - cos_y = cos(angle); - length = radius * HAND_SECONDS_LENGTH2_RATIO; - cairo_move_to(cr, center_x - length * sin_x, - center_y - length * -cos_y); - length = radius * HAND_SECONDS_LENGTH1_RATIO; - cairo_line_to(cr, center_x + length * sin_x, - center_y + length * -cos_y); - cairo_stroke(cr); + draw_clock_hand_common(clock, cr, angle, + HAND_SECONDS_LENGTH1_RATIO, + HAND_SECONDS_LENGTH2_RATIO, /* Draw small extension */ + HAND_SECONDS_WIDTH_RATIO); } /* Draw clock center circle */ @@ -302,61 +328,59 @@ draw_clock_hands(GtkWidget *clock, cairo_t *cr) } static void -draw_calendar(GtkWidget *clock, cairo_t *cr) +calendar_display_test(GtkWidget *clock, struct tm *ts, cairo_t *cr, + char *format, double y_ratio, double font_ratio) { - gint center_x, center_y; - char str[32]; - double x, y; cairo_text_extents_t extents; - struct tm *ts; + double x; + gint center_x, start_y; + double diameter; + char str[32]; + diameter = 2 * get_clock_face_radius(clock); center_x = clock->allocation.width / 2; - center_y = clock->allocation.height / 2; + start_y = (clock->allocation.height / 2) - (diameter / 2); - cairo_save(cr); + cairo_set_font_size(cr, diameter * font_ratio); - cairo_select_font_face(cr, "sans-serif", CAIRO_FONT_SLANT_NORMAL, - CAIRO_FONT_WEIGHT_BOLD); - cairo_set_font_size(cr, CALENDAR_FONTS_SIZE); - cairo_set_source_rgb(cr, 0, 0, 0); - - ts = clock_get_time(); + /* Obtain ASCII reprentation of time format specified. */ + strftime(str, 256, format, ts); - /* Weekday */ - strftime(str, 256, "%A", ts); /* Get text dimensions */ cairo_text_extents(cr, str, &extents); x = center_x - extents.width / 2; - cairo_move_to(cr, x, 11); + cairo_move_to(cr, x, start_y + (diameter * y_ratio)); cairo_show_text(cr, str); +} - strftime(str, 256, "%B", ts); - /* Get text dimensions */ - cairo_text_extents(cr, str, &extents); - x = center_x - extents.width / 2; - cairo_move_to(cr, x, 25); - cairo_show_text(cr, str); +static void +draw_calendar(GtkWidget *clock, cairo_t *cr) +{ + struct tm *ts; - /* Day of month */ - cairo_set_font_size(cr, 30); - strftime(str, 256, "%d", ts); + cairo_save(cr); - fprintf(stderr, "TIME=[%s]\n", str); + cairo_select_font_face(cr, "sans-serif", CAIRO_FONT_SLANT_NORMAL, + CAIRO_FONT_WEIGHT_BOLD); + cairo_set_source_rgb(cr, 0.0, 0.0, 0.0); /* Black */ - if (str[0] == '0') { - /* Remove leading zero */ - str[0] = str[1]; - str[1] = '\0'; - } + ts = clock_get_time(); - fprintf(stderr, "TIME=[%s]\n", str); + /* Weekday */ + calendar_display_test(clock, ts, cr, "%A", + CALENDAR_WEEKDAY_Y_POSITION_RATIO, + CALENDAR_TEXT_FONTS_SIZE_RATIO); - /* Get text dimensions */ - cairo_text_extents(cr, str, &extents); - x = center_x - extents.width / 2; - y = clock->allocation.height - 7; - cairo_move_to(cr, x, y); - cairo_show_text(cr, str); + /* Month */ + calendar_display_test(clock, ts, cr, "%B", + CALENDAR_MONTH_Y_POSITION_RATIO, + CALENDAR_TEXT_FONTS_SIZE_RATIO); + + /* Day of month */ + /* Minus sign in format -> No leading zero */ + calendar_display_test(clock, ts, cr, "%-d", + CALENDAR_DAYOFMONTH_Y_POSITION_RATIO, + CALENDAR_DIGITS_FONTS_SIZE_RATIO); cairo_restore(cr); } @@ -375,8 +399,7 @@ hvclock_expose(GtkWidget *clock, GdkEventExpose *event) cairo_paint(cr); } - cairo_rectangle(cr, - event->area.x, event->area.y, + cairo_rectangle(cr, event->area.x, event->area.y, event->area.width, event->area.height); cairo_clip(cr);