Mercurial > geeqie
view src/pan-calendar.c @ 111:3a69a7a3f461
Wed Nov 15 02:05:27 2006 John Ellis <johne@verizon.net>
* view_file_icon.c: Fix odd crash when removing files, it seems the
high priority idle sync is no longer called before the treeview tries
to redraw itself, so fix the cleanup of removed pointers so that they
are always valid or NULL (I wonder if the priorities used by
GtkTreeView have changed in newer versions of GTK?).
* view_file_list.c: Fix progress bar warning when files are removed
before thumbnail generation is finished.
author | gqview |
---|---|
date | Wed, 15 Nov 2006 07:19:16 +0000 |
parents | de64a683d5d0 |
children | 71e1ebee420e |
line wrap: on
line source
/* * GQview * (C) 2006 John Ellis * * Author: John Ellis * * This software is released under the GNU General Public License (GNU GPL). * Please read the included file COPYING for more information. * This software comes with no warranty of any kind, use at your own risk! */ #include "gqview.h" #include "pan-types.h" #include <math.h> #define PAN_CAL_POPUP_COLOR 220, 220, 220 #define PAN_CAL_POPUP_ALPHA 255 #define PAN_CAL_POPUP_BORDER 1 #define PAN_CAL_POPUP_BORDER_COLOR 0, 0, 0 #define PAN_CAL_POPUP_TEXT_COLOR 0, 0, 0 #define PAN_CAL_DAY_WIDTH 100 #define PAN_CAL_DAY_HEIGHT 80 #define PAN_CAL_DAY_COLOR 255, 255, 255 #define PAN_CAL_DAY_ALPHA 220 #define PAN_CAL_DAY_BORDER 2 #define PAN_CAL_DAY_BORDER_COLOR 0, 0, 0 #define PAN_CAL_DAY_TEXT_COLOR 0, 0, 0 #define PAN_CAL_MONTH_COLOR 255, 255, 255 #define PAN_CAL_MONTH_ALPHA 200 #define PAN_CAL_MONTH_BORDER 4 #define PAN_CAL_MONTH_BORDER_COLOR 0, 0, 0 #define PAN_CAL_MONTH_TEXT_COLOR 0, 0, 0 #define PAN_CAL_DOT_SIZE 3 #define PAN_CAL_DOT_GAP 2 #define PAN_CAL_DOT_COLOR 128, 128, 128 #define PAN_CAL_DOT_ALPHA 128 /* *----------------------------------------------------------------------------- * calendar *----------------------------------------------------------------------------- */ void pan_calendar_update(PanWindow *pw, PanItem *pi_day) { PanItem *pbox; PanItem *pi; GList *list; GList *work; gint x1, y1, x2, y2, x3, y3; gint x, y, w, h; gint grid; gint column; while ((pi = pan_item_find_by_key(pw, PAN_ITEM_NONE, "day_bubble"))) pan_item_remove(pw, pi); if (!pi_day || pi_day->type != PAN_ITEM_BOX || !pi_day->key || strcmp(pi_day->key, "day") != 0) return; list = pan_layout_intersect(pw, pi_day->x, pi_day->y, pi_day->width, pi_day->height); work = list; while (work) { PanItem *dot; GList *node; dot = work->data; node = work; work = work->next; if (dot->type != PAN_ITEM_BOX || !dot->fd || !dot->key || strcmp(dot->key, "dot") != 0) { list = g_list_delete_link(list, node); } } #if 0 if (!list) return; #endif grid = (gint)(sqrt(g_list_length(list)) + 0.5); x = pi_day->x + pi_day->width + 4; y = pi_day->y; #if 0 if (y + grid * (PAN_THUMB_SIZE + PAN_THUMB_GAP) + PAN_BOX_BORDER * 4 > pw->pr->image_height) { y = pw->pr->image_height - (grid * (PAN_THUMB_SIZE + PAN_THUMB_GAP) + PAN_BOX_BORDER * 4); } #endif pbox = pan_item_box_new(pw, NULL, x, y, PAN_BOX_BORDER, PAN_BOX_BORDER, PAN_CAL_POPUP_BORDER, PAN_CAL_POPUP_COLOR, PAN_CAL_POPUP_ALPHA, PAN_CAL_POPUP_BORDER_COLOR, PAN_CAL_POPUP_ALPHA); pan_item_set_key(pbox, "day_bubble"); if (pi_day->fd) { PanItem *plabel; gchar *buf; buf = pan_date_value_string(pi_day->fd->date, PAN_DATE_LENGTH_WEEK); plabel = pan_item_text_new(pw, x, y, buf, PAN_TEXT_ATTR_BOLD | PAN_TEXT_ATTR_HEADING, PAN_TEXT_BORDER_SIZE, PAN_CAL_POPUP_TEXT_COLOR, 255); pan_item_set_key(plabel, "day_bubble"); g_free(buf); pan_item_size_by_item(pbox, plabel, 0); y += plabel->height; } if (list) { column = 0; x += PAN_BOX_BORDER; y += PAN_BOX_BORDER; work = list; while (work) { PanItem *dot; dot = work->data; work = work->next; if (dot->fd) { PanItem *pimg; pimg = pan_item_thumb_new(pw, file_data_new_simple(dot->fd->path), x, y); pan_item_set_key(pimg, "day_bubble"); pan_item_size_by_item(pbox, pimg, PAN_BOX_BORDER); column++; if (column < grid) { x += PAN_THUMB_SIZE + PAN_THUMB_GAP; } else { column = 0; x = pbox->x + PAN_BOX_BORDER; y += PAN_THUMB_SIZE + PAN_THUMB_GAP; } } } } x1 = pi_day->x + pi_day->width - 8; y1 = pi_day->y + 8; x2 = pbox->x + 1; y2 = pbox->y + MIN(42, pbox->height); x3 = pbox->x + 1; y3 = MAX(pbox->y, y2 - 30); util_clip_triangle(x1, y1, x2, y2, x3, y3, &x, &y, &w, &h); pi = pan_item_tri_new(pw, NULL, x, y, w, h, x1, y1, x2, y2, x3, y3, PAN_CAL_POPUP_COLOR, PAN_CAL_POPUP_ALPHA); pan_item_tri_border(pi, PAN_BORDER_1 | PAN_BORDER_3, PAN_CAL_POPUP_BORDER_COLOR, PAN_CAL_POPUP_ALPHA); pan_item_set_key(pi, "day_bubble"); pan_item_added(pw, pi); pan_item_box_shadow(pbox, PAN_SHADOW_OFFSET * 2, PAN_SHADOW_FADE * 2); pan_item_added(pw, pbox); pan_layout_resize(pw); } void pan_calendar_compute(PanWindow *pw, const gchar *path, gint *width, gint *height) { GList *list; GList *work; gint x, y; time_t tc; gint count; gint day_max; gint day_width; gint day_height; gint grid; gint year = 0; gint month = 0; gint end_year = 0; gint end_month = 0; list = pan_list_tree(path, SORT_NONE, TRUE, pw->ignore_symlinks); if (pw->cache_list && pw->exif_date_enable) { pw->cache_list = filelist_sort(pw->cache_list, SORT_NAME, TRUE); list = filelist_sort(list, SORT_NAME, TRUE); pan_cache_sync_date(pw, list); } pw->cache_list = filelist_sort(pw->cache_list, SORT_TIME, TRUE); list = filelist_sort(list, SORT_TIME, TRUE); day_max = 0; count = 0; tc = 0; work = list; while (work) { FileData *fd; fd = work->data; work = work->next; if (!pan_date_compare(fd->date, tc, PAN_DATE_LENGTH_DAY)) { count = 0; tc = fd->date; } else { count++; if (day_max < count) day_max = count; } } if (debug) printf("biggest day contains %d images\n", day_max); grid = (gint)(sqrt((double)day_max) + 0.5) * (PAN_THUMB_SIZE + PAN_SHADOW_OFFSET * 2 + PAN_THUMB_GAP); day_width = MAX(PAN_CAL_DAY_WIDTH, grid); day_height = MAX(PAN_CAL_DAY_HEIGHT, grid); if (list) { FileData *fd = list->data; year = pan_date_value(fd->date, PAN_DATE_LENGTH_YEAR); month = pan_date_value(fd->date, PAN_DATE_LENGTH_MONTH); } work = g_list_last(list); if (work) { FileData *fd = work->data; end_year = pan_date_value(fd->date, PAN_DATE_LENGTH_YEAR); end_month = pan_date_value(fd->date, PAN_DATE_LENGTH_MONTH); } *width = PAN_BOX_BORDER * 2; *height = PAN_BOX_BORDER * 2; x = PAN_BOX_BORDER; y = PAN_BOX_BORDER; work = list; while (work && (year < end_year || (year == end_year && month <= end_month))) { PanItem *pi_month; PanItem *pi_text; gint day; gint days; gint col; gint row; time_t dt; gchar *buf; /* figure last second of this month */ dt = pan_date_to_time((month == 12) ? year + 1 : year, (month == 12) ? 1 : month + 1, 1); dt -= 60 * 60 * 24; /* anything to show this month? */ if (!pan_date_compare(((FileData *)(work->data))->date, dt, PAN_DATE_LENGTH_MONTH)) { month ++; if (month > 12) { year++; month = 1; } continue; } days = pan_date_value(dt, PAN_DATE_LENGTH_DAY); dt = pan_date_to_time(year, month, 1); col = pan_date_value(dt, PAN_DATE_LENGTH_WEEK); row = 1; x = PAN_BOX_BORDER; pi_month = pan_item_box_new(pw, NULL, x, y, PAN_CAL_DAY_WIDTH * 7, PAN_CAL_DAY_HEIGHT / 4, PAN_CAL_MONTH_BORDER, PAN_CAL_MONTH_COLOR, PAN_CAL_MONTH_ALPHA, PAN_CAL_MONTH_BORDER_COLOR, PAN_CAL_MONTH_ALPHA); buf = pan_date_value_string(dt, PAN_DATE_LENGTH_MONTH); pi_text = pan_item_text_new(pw, x, y, buf, PAN_TEXT_ATTR_BOLD | PAN_TEXT_ATTR_HEADING, PAN_TEXT_BORDER_SIZE, PAN_CAL_MONTH_TEXT_COLOR, 255); g_free(buf); pi_text->x = pi_month->x + (pi_month->width - pi_text->width) / 2; pi_month->height = pi_text->y + pi_text->height - pi_month->y; x = PAN_BOX_BORDER + col * PAN_CAL_DAY_WIDTH; y = pi_month->y + pi_month->height + PAN_BOX_BORDER; for (day = 1; day <= days; day++) { FileData *fd; PanItem *pi_day; gint dx, dy; gint n = 0; dt = pan_date_to_time(year, month, day); fd = g_new0(FileData, 1); /* path and name must be non NULL, so make them an invalid filename */ fd->path = g_strdup("//"); fd->name = path; fd->date = dt; pi_day = pan_item_box_new(pw, fd, x, y, PAN_CAL_DAY_WIDTH, PAN_CAL_DAY_HEIGHT, PAN_CAL_DAY_BORDER, PAN_CAL_DAY_COLOR, PAN_CAL_DAY_ALPHA, PAN_CAL_DAY_BORDER_COLOR, PAN_CAL_DAY_ALPHA); pan_item_set_key(pi_day, "day"); dx = x + PAN_CAL_DOT_GAP * 2; dy = y + PAN_CAL_DOT_GAP * 2; fd = (work) ? work->data : NULL; while (fd && pan_date_compare(fd->date, dt, PAN_DATE_LENGTH_DAY)) { PanItem *pi; pi = pan_item_box_new(pw, fd, dx, dy, PAN_CAL_DOT_SIZE, PAN_CAL_DOT_SIZE, 0, PAN_CAL_DOT_COLOR, PAN_CAL_DOT_ALPHA, 0, 0, 0, 0); pan_item_set_key(pi, "dot"); dx += PAN_CAL_DOT_SIZE + PAN_CAL_DOT_GAP; if (dx + PAN_CAL_DOT_SIZE > pi_day->x + pi_day->width - PAN_CAL_DOT_GAP * 2) { dx = x + PAN_CAL_DOT_GAP * 2; dy += PAN_CAL_DOT_SIZE + PAN_CAL_DOT_GAP; } if (dy + PAN_CAL_DOT_SIZE > pi_day->y + pi_day->height - PAN_CAL_DOT_GAP * 2) { /* must keep all dots within respective day even if it gets ugly */ dy = y + PAN_CAL_DOT_GAP * 2; } n++; work = work->next; fd = (work) ? work->data : NULL; } if (n > 0) { PanItem *pi; pi_day->color_r = MAX(pi_day->color_r - 61 - n * 3, 80); pi_day->color_g = pi_day->color_r; buf = g_strdup_printf("( %d )", n); pi = pan_item_text_new(pw, x, y, buf, PAN_TEXT_ATTR_NONE, PAN_TEXT_BORDER_SIZE, PAN_CAL_DAY_TEXT_COLOR, 255); g_free(buf); pi->x = pi_day->x + (pi_day->width - pi->width) / 2; pi->y = pi_day->y + (pi_day->height - pi->height) / 2; } buf = g_strdup_printf("%d", day); pan_item_text_new(pw, x + 4, y + 4, buf, PAN_TEXT_ATTR_BOLD | PAN_TEXT_ATTR_HEADING, PAN_TEXT_BORDER_SIZE, PAN_CAL_DAY_TEXT_COLOR, 255); g_free(buf); pan_item_size_coordinates(pi_day, PAN_BOX_BORDER, width, height); col++; if (col > 6) { col = 0; row++; x = PAN_BOX_BORDER; y += PAN_CAL_DAY_HEIGHT; } else { x += PAN_CAL_DAY_WIDTH; } } if (col > 0) y += PAN_CAL_DAY_HEIGHT; y += PAN_BOX_BORDER * 2; month ++; if (month > 12) { year++; month = 1; } } *width += grid; *height = MAX(*height, grid + PAN_BOX_BORDER * 2 * 2); g_list_free(list); }