Diff of /trunk/src/osm-gps-map-osd-classic.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 86 by harbaum, Sun Aug 30 19:05:44 2009 UTC revision 87 by harbaum, Mon Aug 31 12:01:28 2009 UTC
# Line 19  Line 19 
19    
20  #include "config.h"  #include "config.h"
21  #include <stdlib.h>  // abs  #include <stdlib.h>  // abs
22  #include <math.h>    // M_PI  #include <math.h>    // M_PI/cos()
   
 #define OSD_SOURCE_SEL  
   
 #define OSD_Y  (-10)  
23    
24  /* parameters that can be overwritten from the config file: */  /* parameters that can be overwritten from the config file: */
25  /* OSD_DIAMETER */  /* OSD_DIAMETER */
# Line 43  typedef struct { Line 39  typedef struct {
39      /* the offscreen representation of the OSD */      /* the offscreen representation of the OSD */
40      cairo_surface_t *overlay;      cairo_surface_t *overlay;
41    
42        /* values to handle the "source" menu */
43      cairo_surface_t *map_source;      cairo_surface_t *map_source;
44      gboolean expanded;      gboolean expanded;
45      gint shift, dir, count;      gint shift, dir, count;
46      gint handler_id;      gint handler_id;
47        gint width, height;
48    
49  } osd_priv_t;  } osd_priv_t;
50    
51  /* position and extent of bounding box */  /* position and extent of bounding box */
# Line 128  osd_labels(cairo_t *cr, gint width, gboo Line 127  osd_labels(cairo_t *cr, gint width, gboo
127      if(enabled)  gdk_cairo_set_source_color(cr, fg);      if(enabled)  gdk_cairo_set_source_color(cr, fg);
128      else         gdk_cairo_set_source_color(cr, disabled);      else         gdk_cairo_set_source_color(cr, disabled);
129      cairo_set_line_width (cr, width);      cairo_set_line_width (cr, width);
     cairo_stroke (cr);  
130  }  }
131  #else  #else
132  static void  static void
# Line 136  osd_labels(cairo_t *cr, gint width, gboo Line 134  osd_labels(cairo_t *cr, gint width, gboo
134      if(enabled)  cairo_set_source_rgb (cr, OSD_COLOR);      if(enabled)  cairo_set_source_rgb (cr, OSD_COLOR);
135      else         cairo_set_source_rgb (cr, OSD_COLOR_DISABLED);      else         cairo_set_source_rgb (cr, OSD_COLOR_DISABLED);
136      cairo_set_line_width (cr, width);      cairo_set_line_width (cr, width);
     cairo_stroke (cr);  
137  }  }
138  #endif  #endif
139    
# Line 145  static void Line 142  static void
142  osd_labels_shadow(cairo_t *cr, gint width, gboolean enabled) {  osd_labels_shadow(cairo_t *cr, gint width, gboolean enabled) {
143      cairo_set_source_rgba (cr, 0, 0, 0, enabled?0.3:0.15);      cairo_set_source_rgba (cr, 0, 0, 0, enabled?0.3:0.15);
144      cairo_set_line_width (cr, width);      cairo_set_line_width (cr, width);
     cairo_stroke (cr);  
145  }  }
146  #endif  #endif
147    
# Line 271  osd_check_zoom(gint x, gint y) { Line 267  osd_check_zoom(gint x, gint y) {
267  #define OSD_S_PH  (2 * Z_RAD)  #define OSD_S_PH  (2 * Z_RAD)
268  #define OSD_S_H   (OSD_S_PH + OSD_SHADOW)  #define OSD_S_H   (OSD_S_PH + OSD_SHADOW)
269    
270  /* size of usable area when exapnded */  /* size of usable area when expanded */
271  #define OSD_S_AREA_W (200)  #define OSD_S_AREA_W (priv->width)
272  #define OSD_S_AREA_H (200)  #define OSD_S_AREA_H (priv->height)
273  #define OSD_S_EXP_W  (OSD_S_PW + OSD_S_AREA_W + OSD_SHADOW)  #define OSD_S_EXP_W  (OSD_S_PW + OSD_S_AREA_W + OSD_SHADOW)
274  #define OSD_S_EXP_H  (OSD_S_AREA_H + OSD_SHADOW)  #define OSD_S_EXP_H  (OSD_S_AREA_H + OSD_SHADOW)
275    
276  /* internal value to draw the arrow on the "puller" */  /* internal value to draw the arrow on the "puller" */
277  #define OSD_S_D0  (OSD_S_RAD/2)  #define OSD_S_D0  (OSD_S_RAD/2)
278    #ifndef OSD_FONT_SIZE
279    #define OSD_FONT_SIZE 16.0
280    #endif
281    #define OSD_TEXT_BORDER   (OSD_FONT_SIZE/2)
282    #define OSD_TEXT_SKIP     (OSD_FONT_SIZE/8)
283    
284  static void  static void
285  osd_source_shape(osd_priv_t *priv, cairo_t *cr, gint x, gint y) {  osd_source_shape(osd_priv_t *priv, cairo_t *cr, gint x, gint y) {
# Line 305  osd_source_shape(osd_priv_t *priv, cairo Line 306  osd_source_shape(osd_priv_t *priv, cairo
306  }  }
307    
308  static void  static void
309  osd_source_content(osd_priv_t *priv, cairo_t *cr, gint x, gint y) {  osd_source_content(osm_gps_map_osd_t *osd, cairo_t *cr, gint offset) {
310      y += OSD_S_RAD - OSD_S_D0;      osd_priv_t *priv = (osd_priv_t*)osd->priv;
311    
312        int py = offset + OSD_S_RAD - OSD_S_D0;
313    
314      if(!priv->expanded) {      if(!priv->expanded) {
315          /* draw the "puller" open (<) arrow */          /* draw the "puller" open (<) arrow */
316          cairo_move_to (cr, x + OSD_S_RAD + OSD_S_D0/2, y);          cairo_move_to (cr, offset + OSD_S_RAD + OSD_S_D0/2, py);
317          cairo_rel_line_to (cr, -OSD_S_D0, +OSD_S_D0);          cairo_rel_line_to (cr, -OSD_S_D0, +OSD_S_D0);
318          cairo_rel_line_to (cr, +OSD_S_D0, +OSD_S_D0);          cairo_rel_line_to (cr, +OSD_S_D0, +OSD_S_D0);
319      } else {      } else {
320          if(OSD_S_Y < 0)          if(OSD_S_Y < 0)
321              y += OSD_S_AREA_H - OSD_S_PH;              py += OSD_S_AREA_H - OSD_S_PH;
322    
323          /* draw the "puller" close (>) arrow */          /* draw the "puller" close (>) arrow */
324          cairo_move_to (cr, x + OSD_S_RAD - OSD_S_D0/2, y);          cairo_move_to (cr, offset + OSD_S_RAD - OSD_S_D0/2, py);
325          cairo_rel_line_to (cr, +OSD_S_D0, +OSD_S_D0);          cairo_rel_line_to (cr, +OSD_S_D0, +OSD_S_D0);
326          cairo_rel_line_to (cr, -OSD_S_D0, +OSD_S_D0);          cairo_rel_line_to (cr, -OSD_S_D0, +OSD_S_D0);
327            cairo_stroke(cr);
328    
329            /* don't draw a shadow for the text content */
330            if(offset == 1) {
331                gint source;
332                g_object_get(osd->widget, "map-source", &source, NULL);
333    
334                cairo_select_font_face (cr, "Sans",
335                                        CAIRO_FONT_SLANT_NORMAL,
336                                        CAIRO_FONT_WEIGHT_BOLD);
337                cairo_set_font_size (cr, OSD_FONT_SIZE);
338    
339                int i, step = (priv->height - 2*OSD_TEXT_BORDER)
340                    / OSM_GPS_MAP_SOURCE_LAST;
341                for(i=OSM_GPS_MAP_SOURCE_NULL+1;i<=OSM_GPS_MAP_SOURCE_LAST;i++) {
342                    cairo_text_extents_t extents;
343                    const char *src = osm_gps_map_source_get_friendly_name(i);
344                    cairo_text_extents (cr, src, &extents);
345    
346                    int x = offset + OSD_S_PW + OSD_TEXT_BORDER;
347                    int y = offset + step * (i-1) + OSD_TEXT_BORDER;
348    
349                    /* draw filled rectangle if selected */
350                    if(source == i) {
351                        cairo_rectangle(cr, x - OSD_TEXT_BORDER/2,
352                                        y - OSD_TEXT_SKIP,
353                                        priv->width - OSD_TEXT_BORDER,
354                                        step + OSD_TEXT_SKIP);
355                        cairo_fill(cr);
356    
357                        /* temprarily draw with background color */
358    #ifndef OSD_COLOR
359                        GdkColor bg = osd->widget->style->bg[GTK_STATE_NORMAL];
360                        gdk_cairo_set_source_color(cr, &bg);
361    #else
362                        cairo_set_source_rgb (cr, OSD_COLOR_BG);
363    #endif
364                    }
365    
366                    cairo_move_to (cr, x, y + OSD_TEXT_SKIP - extents.y_bearing);
367                    cairo_show_text (cr, src);
368    
369                    /* restore color */
370                    if(source == i) {
371    #ifndef OSD_COLOR
372                        GdkColor fg = osd->widget->style->fg[GTK_STATE_NORMAL];
373                        gdk_cairo_set_source_color(cr, &fg);
374    #else
375                        cairo_set_source_rgb (cr, OSD_COLOR);
376    #endif
377                    }
378                }
379            }
380      }      }
381  }  }
382    
# Line 354  osd_render_source_sel(osm_gps_map_osd_t Line 410  osd_render_source_sel(osm_gps_map_osd_t
410  #endif  #endif
411    
412  #ifdef OSD_SHADOW_ENABLE  #ifdef OSD_SHADOW_ENABLE
     osd_source_content(priv, cr, 1+OSD_LBL_SHADOW, 1+OSD_LBL_SHADOW);  
413      osd_labels_shadow(cr, Z_RAD/3, TRUE);      osd_labels_shadow(cr, Z_RAD/3, TRUE);
414        osd_source_content(osd, cr, 1+OSD_LBL_SHADOW);
415        cairo_stroke (cr);
416  #endif  #endif
     osd_source_content(priv, cr, 1, 1);  
417  #ifndef OSD_COLOR  #ifndef OSD_COLOR
418      osd_labels(cr, Z_RAD/3, TRUE, &fg, &da);      osd_labels(cr, Z_RAD/3, TRUE, &fg, &da);
419  #else  #else
420      osd_labels(cr, Z_RAD/3, TRUE);      osd_labels(cr, Z_RAD/3, TRUE);
421  #endif  #endif
422        osd_source_content(osd, cr, 1);
423        cairo_stroke (cr);
424    
425      cairo_destroy(cr);      cairo_destroy(cr);
426  }  }
# Line 373  osd_source_reallocate(osm_gps_map_osd_t Line 431  osd_source_reallocate(osm_gps_map_osd_t
431    
432      /* re-allocate offscreen bitmap */      /* re-allocate offscreen bitmap */
433      g_assert (priv->map_source);      g_assert (priv->map_source);
     cairo_surface_destroy(priv->map_source);  
434    
435      int w = OSD_S_W, h = OSD_S_H;      int w = OSD_S_W, h = OSD_S_H;
436      if(priv->expanded) {      if(priv->expanded) {
437            /* ... and right of it the waypoint id */
438            cairo_text_extents_t extents;
439    
440            /* determine content size */
441            cairo_t *cr = cairo_create(priv->map_source);
442            cairo_select_font_face (cr, "Sans",
443                                    CAIRO_FONT_SLANT_NORMAL,
444                                    CAIRO_FONT_WEIGHT_BOLD);
445            cairo_set_font_size (cr, OSD_FONT_SIZE);
446    
447            /* calculate menu size */
448            int i, max_h = 0, max_w = 0;
449            for(i=OSM_GPS_MAP_SOURCE_NULL+1;i<=OSM_GPS_MAP_SOURCE_LAST;i++) {
450                const char *src = osm_gps_map_source_get_friendly_name(i);
451                cairo_text_extents (cr, src, &extents);
452    
453                //            printf("Source %d: %s = %f %f\n", i, src,
454                //                   extents.width, extents.height);
455    
456                if(extents.width > max_w) max_w = extents.width;
457                if(extents.height > max_h) max_h = extents.height;
458            }
459            cairo_destroy(cr);
460    
461            priv->width  = max_w + 2*OSD_TEXT_BORDER;
462            priv->height = OSM_GPS_MAP_SOURCE_LAST *
463                (max_h + 2*OSD_TEXT_SKIP) + 2*OSD_TEXT_BORDER;
464    
465          w = OSD_S_EXP_W;          w = OSD_S_EXP_W;
466          h = OSD_S_EXP_H;          h = OSD_S_EXP_H;
467      }      }
468    
469        cairo_surface_destroy(priv->map_source);
470      priv->map_source =      priv->map_source =
471          cairo_image_surface_create(CAIRO_FORMAT_ARGB32, w+2, h+2);          cairo_image_surface_create(CAIRO_FORMAT_ARGB32, w+2, h+2);
472    
# Line 389  osd_source_reallocate(osm_gps_map_osd_t Line 475  osd_source_reallocate(osm_gps_map_osd_t
475  }  }
476    
477  #define OSD_HZ      15  #define OSD_HZ      15
478  #define OSD_TIME    1000  #define OSD_TIME    500
479    
480  static gboolean osd_source_animate(gpointer data) {  static gboolean osd_source_animate(gpointer data) {
481      osm_gps_map_osd_t *osd = (osm_gps_map_osd_t*)data;      osm_gps_map_osd_t *osd = (osm_gps_map_osd_t*)data;
# Line 641  osd_render(osm_gps_map_osd_t *osd) { Line 727  osd_render(osm_gps_map_osd_t *osd) {
727      /* --------- draw zoom and dpad labels --------- */      /* --------- draw zoom and dpad labels --------- */
728    
729  #ifdef OSD_SHADOW_ENABLE  #ifdef OSD_SHADOW_ENABLE
730        osd_labels_shadow(cr, Z_RAD/3, TRUE);
731      osd_zoom_labels(cr, 1+OSD_LBL_SHADOW, 1+OSD_LBL_SHADOW);      osd_zoom_labels(cr, 1+OSD_LBL_SHADOW, 1+OSD_LBL_SHADOW);
732  #ifndef OSD_NO_DPAD  #ifndef OSD_NO_DPAD
733      osd_dpad_labels(cr, 1+OSD_LBL_SHADOW, 1+OSD_LBL_SHADOW);      osd_dpad_labels(cr, 1+OSD_LBL_SHADOW, 1+OSD_LBL_SHADOW);
734  #endif  #endif
735      osd_labels_shadow(cr, Z_RAD/3, TRUE);      cairo_stroke(cr);
736  #ifdef OSD_GPS_BUTTON  #ifdef OSD_GPS_BUTTON
     osd_dpad_gps(cr, 1+OSD_LBL_SHADOW, 1+OSD_LBL_SHADOW);  
737      osd_labels_shadow(cr, Z_RAD/6, osd->cb != NULL);      osd_labels_shadow(cr, Z_RAD/6, osd->cb != NULL);
738        osd_dpad_gps(cr, 1+OSD_LBL_SHADOW, 1+OSD_LBL_SHADOW);
739        cairo_stroke(cr);
740  #endif  #endif
741  #endif  #endif
742    
     osd_zoom_labels(cr, 1, 1);  
 #ifndef OSD_NO_DPAD  
     osd_dpad_labels(cr, 1, 1);  
 #endif  
743  #ifndef OSD_COLOR  #ifndef OSD_COLOR
744      osd_labels(cr, Z_RAD/3, TRUE, &fg, &da);      osd_labels(cr, Z_RAD/3, TRUE, &fg, &da);
745  #else  #else
746      osd_labels(cr, Z_RAD/3, TRUE);      osd_labels(cr, Z_RAD/3, TRUE);
747  #endif  #endif
748  #ifdef OSD_GPS_BUTTON      osd_zoom_labels(cr, 1, 1);
749      osd_dpad_gps(cr, 1, 1);  #ifndef OSD_NO_DPAD
750        osd_dpad_labels(cr, 1, 1);
751    #endif
752        cairo_stroke(cr);
753    
754  #ifndef OSD_COLOR  #ifndef OSD_COLOR
755      osd_labels(cr, Z_RAD/6, osd->cb != NULL, &fg, &da);      osd_labels(cr, Z_RAD/6, osd->cb != NULL, &fg, &da);
756  #else  #else
757      osd_labels(cr, Z_RAD/6, osd->cb != NULL);      osd_labels(cr, Z_RAD/6, osd->cb != NULL);
758  #endif  #endif
759    #ifdef OSD_GPS_BUTTON
760        osd_dpad_gps(cr, 1, 1);
761  #endif  #endif
762        cairo_stroke(cr);
763    
764      cairo_destroy(cr);      cairo_destroy(cr);
765    
# Line 751  osd_free(osm_gps_map_osd_t *osd) Line 842  osd_free(osm_gps_map_osd_t *osd)
842      g_free(priv);      g_free(priv);
843  }  }
844    
845    /* this is the only function that's externally visible */
846    static gboolean
847    osd_busy(osm_gps_map_osd_t *osd)
848    {
849        osd_priv_t *priv = (osd_priv_t *)(osd->priv);
850        return (priv->handler_id != 0);
851    }
852    
853  static osm_gps_map_osd_t osd_classic = {  static osm_gps_map_osd_t osd_classic = {
854      .draw       = osd_draw,      .draw       = osd_draw,
855      .check      = osd_check,      .check      = osd_check,
856      .render     = osd_render,      .render     = osd_render,
857      .free       = osd_free,      .free       = osd_free,
858        .busy       = osd_busy,
859    
860      .cb         = NULL,      .cb         = NULL,
861      .data       = NULL,      .data       = NULL,

Legend:
Removed from v.86  
changed lines
  Added in v.87