comparison src/image-overlay.c @ 118:ac0f7f942c4d

Wed Nov 29 22:53:03 2006 John Ellis <johne@verizon.net> * image-overlay.[ch]: Prepare for icon notification display, and fix info overlay image index when on last image of slideshow. * img-view.c: Fix image index when on last image of slideshow.
author gqview
date Thu, 30 Nov 2006 03:56:25 +0000
parents 0c2e1f0a001b
children e2a8b7f2165b
comparison
equal deleted inserted replaced
117:0c2e1f0a001b 118:ac0f7f942c4d
34 34
35 gint show_info; 35 gint show_info;
36 gint show_status; 36 gint show_status;
37 37
38 gint ovl_info; 38 gint ovl_info;
39 gint ovl_color; 39
40 gint ovl_rotate; 40 gint icon_time[IMAGE_OSD_COUNT];
41 gint ovl_end; 41 gint icon_id[IMAGE_OSD_COUNT];
42 42
43 gint idle_id; 43 gint idle_id;
44 gint timer_id; 44 gint timer_id;
45 gulong destroy_id; 45 gulong destroy_id;
46 }; 46 };
47 47
48
49 typedef struct _OSDIcon OSDIcon;
50 struct _OSDIcon {
51 gint x;
52 gint y;
53 gchar *key;
54 };
55
56 static OSDIcon osd_icons[] = {
57 { 0, -10, PIXBUF_INLINE_ICON },
58 { -10, -10, "IMAGE_OSD_ROTATE_USER" },
59 { -10, -10, "IMAGE_OSD_ROTATE_AUTO" },
60 { -40, -10, "IMAGE_OSD_COLOR" },
61 { -70, -10, "IMAGE_OSD_FIRST" },
62 { -70, -10, "IMAGE_OSD_LAST" },
63 { 0, 0, NULL }
64 };
65
48 #define OSD_DATA "overlay-data" 66 #define OSD_DATA "overlay-data"
49 67
50 #define OSD_INFO_X 10 68 #define OSD_INFO_X 10
51 #define OSD_INFO_Y -10 69 #define OSD_INFO_Y -10
70
71 #define IMAGE_OSD_DEFAULT_DURATION 30
72
73
74 static void image_osd_timer_schedule(OverlayStateData *osd);
52 75
53 76
54 static GdkPixbuf *image_osd_info_render(ImageWindow *imd) 77 static GdkPixbuf *image_osd_info_render(ImageWindow *imd)
55 { 78 {
56 GdkPixbuf *pixbuf; 79 GdkPixbuf *pixbuf;
95 { 118 {
96 if (lw->slideshow) 119 if (lw->slideshow)
97 { 120 {
98 n = g_list_length(lw->slideshow->list_done); 121 n = g_list_length(lw->slideshow->list_done);
99 t = n + g_list_length(lw->slideshow->list); 122 t = n + g_list_length(lw->slideshow->list);
123 if (n == 0) n = t;
100 } 124 }
101 else 125 else
102 { 126 {
103 t = layout_list_count(lw, NULL); 127 t = layout_list_count(lw, NULL);
104 n = layout_list_get_index(lw, image_get_path(lw->image)) + 1; 128 n = layout_list_get_index(lw, image_get_path(lw->image)) + 1;
180 g_object_unref(G_OBJECT(layout)); 204 g_object_unref(G_OBJECT(layout));
181 205
182 return pixbuf; 206 return pixbuf;
183 } 207 }
184 208
185 static void image_osd_ovl_reset(OverlayStateData *osd, gint *id) 209 static GdkPixbuf *image_osd_icon_pixbuf(ImageOSDFlag flag)
186 { 210 {
187 if (*id) 211 static GdkPixbuf **icons = NULL;
188 { 212 GdkPixbuf *icon = NULL;
189 image_overlay_remove(osd->imd, *id); 213
190 *id = 0; 214 if (!icons) icons = g_new0(GdkPixbuf *, IMAGE_OSD_COUNT);
215 if (icons[flag]) return icons[flag];
216
217 icon = gdk_pixbuf_new(GDK_COLORSPACE_RGB, TRUE, 8, 24, 24);
218 pixbuf_set_rect_fill(icon, 1, 1, 22, 22, 255, 255, 255, 200);
219 pixbuf_set_rect(icon, 0, 0, 24, 24, 0, 0, 0, 128, 1, 1, 1, 1);
220 switch (flag)
221 {
222 case IMAGE_OSD_COLOR:
223 pixbuf_set_rect_fill(icon, 3, 3, 18, 6, 200, 0, 0, 255);
224 pixbuf_set_rect_fill(icon, 3, 9, 18, 6, 0, 200, 0, 255);
225 pixbuf_set_rect_fill(icon, 3, 15, 18, 6, 0, 0, 200, 255);
226 break;
227 case IMAGE_OSD_FIRST:
228 pixbuf_set_rect(icon, 3, 3, 18, 18, 0, 0, 0, 200, 3, 3, 3, 0);
229 pixbuf_draw_triangle(icon, 6, 5, 12, 6,
230 12, 5, 18, 11, 6, 11,
231 0, 0, 0, 255);
232 break;
233 case IMAGE_OSD_LAST:
234 pixbuf_set_rect(icon, 3, 3, 18, 18, 0, 0, 0, 200, 3, 3, 0, 3);
235 pixbuf_draw_triangle(icon, 6, 12, 12, 6,
236 12, 18, 6, 12, 18, 12,
237 0, 0, 0, 255);
238 break;
239 default:
240 break;
241 }
242
243 icons[flag] = icon;
244
245 return icon;
246 }
247
248 static void image_osd_icon_show(OverlayStateData *osd, ImageOSDFlag flag)
249 {
250 GdkPixbuf *pixbuf;
251
252 if (osd->icon_id[flag]) return;
253
254 pixbuf = image_osd_icon_pixbuf(flag);
255 if (!pixbuf) return;
256
257 osd->icon_id[flag] = image_overlay_add(osd->imd, pixbuf,
258 osd_icons[flag].x, osd_icons[flag].y,
259 TRUE, FALSE);
260 }
261
262 static void image_osd_icon_hide(OverlayStateData *osd, ImageOSDFlag flag)
263 {
264 if (osd->icon_id[flag])
265 {
266 image_overlay_remove(osd->imd, osd->icon_id[flag]);
267 osd->icon_id[flag] = 0;
191 } 268 }
192 } 269 }
193 270
194 static gint image_osd_update_cb(gpointer data) 271 static gint image_osd_update_cb(gpointer data)
195 { 272 {
214 g_object_unref(pixbuf); 291 g_object_unref(pixbuf);
215 } 292 }
216 } 293 }
217 else 294 else
218 { 295 {
219 image_osd_ovl_reset(osd, & osd->ovl_info); 296 if (osd->ovl_info)
297 {
298 image_overlay_remove(osd->imd, osd->ovl_info);
299 osd->ovl_info = 0;
300 }
220 } 301 }
221 302
222 if (osd->show_status) 303 if (osd->show_status)
223 { 304 {
305 gint i;
306
307 if (osd->changed_states & IMAGE_STATE_IMAGE)
308 {
309 for (i = 0; i < IMAGE_OSD_COUNT; i++) osd->icon_time[i] = 0;
310 }
311
312 if (osd->changed_states & IMAGE_STATE_COLOR_ADJ)
313 {
314 osd->icon_time[IMAGE_OSD_COLOR] = IMAGE_OSD_DEFAULT_DURATION + 1;
315 image_osd_timer_schedule(osd);
316 }
317
318 for (i = 0; i < IMAGE_OSD_COUNT; i++)
319 {
320 if (osd->icon_time[i] > 0)
321 {
322 image_osd_icon_show(osd, i);
323 }
324 else
325 {
326 image_osd_icon_hide(osd, i);
327 }
328 }
224 } 329 }
225 else 330 else
226 { 331 {
227 image_osd_ovl_reset(osd, & osd->ovl_color); 332 gint i;
228 image_osd_ovl_reset(osd, & osd->ovl_rotate); 333
229 image_osd_ovl_reset(osd, & osd->ovl_end); 334 for (i = 0; i < IMAGE_OSD_COUNT; i++)
230 } 335 {
231 336 image_osd_icon_hide(osd, i);
337 }
338 }
339
340 osd->changed_states = IMAGE_STATE_NONE;
232 osd->idle_id = -1; 341 osd->idle_id = -1;
233 return FALSE; 342 return FALSE;
234 } 343 }
235 344
236 static void image_osd_update_schedule(OverlayStateData *osd, gint force) 345 static void image_osd_update_schedule(OverlayStateData *osd, gint force)
253 if (!osd) return; 362 if (!osd) return;
254 363
255 image_osd_update_schedule(osd, TRUE); 364 image_osd_update_schedule(osd, TRUE);
256 } 365 }
257 366
367 static gint image_osd_timer_cb(gpointer data)
368 {
369 OverlayStateData *osd = data;
370 gint done = TRUE;
371 gint changed = FALSE;
372 gint i;
373
374 for (i = 0; i < IMAGE_OSD_COUNT; i++)
375 {
376 if (osd->icon_time[i] > 1)
377 {
378 osd->icon_time[i]--;
379 if (osd->icon_time[i] < 2)
380 {
381 osd->icon_time[i] = 0;
382 changed = TRUE;
383 }
384 else
385 {
386 done = FALSE;
387 }
388 }
389 }
390
391 if (changed) image_osd_update_schedule(osd, FALSE);
392
393 if (done)
394 {
395 osd->timer_id = -1;
396 return FALSE;
397 }
398
399 return TRUE;
400 }
401
402 static void image_osd_timer_schedule(OverlayStateData *osd)
403 {
404 if (osd->timer_id == -1)
405 {
406 osd->timer_id = g_timeout_add(100, image_osd_timer_cb, osd);
407 }
408 }
409
258 static void image_osd_state_cb(ImageWindow *imd, ImageState state, gpointer data) 410 static void image_osd_state_cb(ImageWindow *imd, ImageState state, gpointer data)
259 { 411 {
260 OverlayStateData *osd = data; 412 OverlayStateData *osd = data;
261 413
262 osd->changed_states |= state; 414 osd->changed_states |= state;
266 static void image_osd_free(OverlayStateData *osd) 418 static void image_osd_free(OverlayStateData *osd)
267 { 419 {
268 if (!osd) return; 420 if (!osd) return;
269 421
270 if (osd->idle_id != -1) g_source_remove(osd->idle_id); 422 if (osd->idle_id != -1) g_source_remove(osd->idle_id);
423 if (osd->timer_id != -1) g_source_remove(osd->timer_id);
271 424
272 if (osd->imd) 425 if (osd->imd)
273 { 426 {
427 gint i;
428
274 g_object_set_data(G_OBJECT(osd->imd->pr), "IMAGE_OVERLAY_DATA", NULL); 429 g_object_set_data(G_OBJECT(osd->imd->pr), "IMAGE_OVERLAY_DATA", NULL);
275 g_signal_handler_disconnect(osd->imd->pr, osd->destroy_id); 430 g_signal_handler_disconnect(osd->imd->pr, osd->destroy_id);
276 431
277 image_set_state_func(osd->imd, NULL, NULL); 432 image_set_state_func(osd->imd, NULL, NULL);
278 image_overlay_remove(osd->imd, osd->ovl_info); 433 image_overlay_remove(osd->imd, osd->ovl_info);
434
435 for (i = 0; i < IMAGE_OSD_COUNT; i++)
436 {
437 image_osd_icon_hide(osd, i);
438 }
279 } 439 }
280 440
281 g_free(osd); 441 g_free(osd);
282 } 442 }
283 443
352 if (status) *status = osd->show_status; 512 if (status) *status = osd->show_status;
353 513
354 return TRUE; 514 return TRUE;
355 } 515 }
356 516
517 /* duration:
518 0 = hide
519 1 = show
520 2+ = show for duration tenths of a second
521 -1 = use default duration
522 */
523 void image_osd_icon(ImageWindow *imd, ImageOSDFlag flag, gint duration)
524 {
525 OverlayStateData *osd;
526
527 if (!imd) return;
528
529 osd = g_object_get_data(G_OBJECT(imd->pr), "IMAGE_OVERLAY_DATA");
530 if (!osd) return;
531
532 if (flag < IMAGE_OSD_NONE || flag >= IMAGE_OSD_COUNT) return;
533 if (duration < 0) duration = IMAGE_OSD_DEFAULT_DURATION;
534 if (duration > 1) duration += 1;
535
536 osd->icon_time[flag] = duration;
537
538 image_osd_update_schedule(osd, FALSE);
539 image_osd_timer_schedule(osd);
540 }
541