--- src/map.c 2008/12/09 20:06:06 1 +++ trunk/src/map.c 2009/03/03 15:27:55 105 @@ -56,6 +56,15 @@ str = g_strdup_printf("%s #%ld", item_str, id); /* add some tags ... */ + /* + * XXX Should we just try to present only the name or the ref (or the + * alt_name, old_name, whatever) here? Hurling a load of tags in the + * user's face in some unpredictable, uninformative order isn't very + * friendly. + * + * Actually, a tag_short_desc() function would be useful in dialogs + * nd user messages too. + */ while(tag) { if(!collision && info_tag_key_collision(tags, tag)) collision = TRUE; @@ -146,7 +155,8 @@ float radius = map->style->highlight.width + map->style->node.radius; if(!node->ways) radius += map->style->node.border_radius; - if(node->icon_buf && map->style->icon.enable) { + if(node->icon_buf && map->style->icon.enable && + !appdata->settings->no_icons) { gint w = gdk_pixbuf_get_width(map_item->node->icon_buf); gint h = gdk_pixbuf_get_height(map_item->node->icon_buf); /* icons are technically square, so a radius slightly bigger */ @@ -156,7 +166,7 @@ map_hl_circle_new(map, CANVAS_GROUP_NODES_HL, new_map_item, x, y, radius, map->style->highlight.color); - + if(!map_item->item) { /* and draw a fake node */ new_map_item = g_new0(map_item_t, 1); @@ -208,6 +218,8 @@ diff.x = node_chain->node->lpos.x - last->lpos.x; diff.y = node_chain->node->lpos.y - last->lpos.y; + /* only draw arrow if there's sufficient space */ + /* TODO: what if there's not enough space anywhere? */ float len = sqrt(pow(diff.x, 2)+pow(diff.y, 2)); if(len > map->style->highlight.arrow_limit*arrow_width) { len /= arrow_width; @@ -222,7 +234,7 @@ points->coords[2*2+0] = center.x - diff.y - diff.x; points->coords[2*2+1] = center.y + diff.x - diff.y; - map_hl_polygon_new(map, CANVAS_GROUP_NODES_HL, new_map_item, + map_hl_polygon_new(map, CANVAS_GROUP_WAYS_DIR, new_map_item, points, map->style->highlight.arrow_color); canvas_points_free(points); @@ -366,11 +378,12 @@ map_item->type = MAP_TYPE_NODE; map_item->node = node; - if(!node->icon_buf || !map->style->icon.enable) - map_item->item = canvas_circle_new(map, CANVAS_GROUP_NODES, + if(!node->icon_buf || !map->style->icon.enable || + map->appdata->settings->no_icons) + map_item->item = canvas_circle_new(map->canvas, CANVAS_GROUP_NODES, node->lpos.x, node->lpos.y, radius, width, fill, border); else - map_item->item = canvas_image_new(map, CANVAS_GROUP_NODES, + map_item->item = canvas_image_new(map->canvas, CANVAS_GROUP_NODES, node->icon_buf, node->lpos.x - map->style->icon.scale/2 * gdk_pixbuf_get_width(node->icon_buf), @@ -402,7 +415,7 @@ map_item_t *map_item = g_new0(map_item_t, 1); map_item->type = MAP_TYPE_WAY; map_item->way = way; - map_item->item = canvas_circle_new(map, CANVAS_GROUP_WAYS, + map_item->item = canvas_circle_new(map->canvas, CANVAS_GROUP_WAYS, way->node_chain->node->lpos.x, way->node_chain->node->lpos.y, radius, width, fill, border); @@ -430,18 +443,22 @@ map_item->way = way; if(way->draw.flags & OSM_DRAW_FLAG_AREA) { - if(map->style->area.opaque) - map_item->item = canvas_polygon_new(map, group, points, + if(map->style->area.color & 0xff) + map_item->item = canvas_polygon_new(map->canvas, group, points, width, color, fill_color); else - map_item->item = canvas_polyline_new(map, group, points, + map_item->item = canvas_polyline_new(map->canvas, group, points, width, color); } else { - map_item->item = canvas_polyline_new(map, group, points, width, color); + map_item->item = canvas_polyline_new(map->canvas, group, points, width, color); } canvas_item_set_zoom_max(map_item->item, way->draw.zoom_max); + if (group != CANVAS_GROUP_WAYS_OL) + if (way->draw.dashed) + canvas_item_set_dashed(map_item->item, width, way->draw.dash_length); + /* attach map_item to ways map_item_chain */ map_item_chain_t **chain = &way->map_item_chain; while(*chain) chain = &(*chain)->next; @@ -458,7 +475,7 @@ void map_show_node(map_t *map, node_t *node) { map_node_new(map, node, map->style->node.radius, 0, - RGB2CANVAS(map->style->node.color), 0); + map->style->node.color, 0); } void map_way_draw(map_t *map, way_t *way) { @@ -473,7 +490,7 @@ if(nodes == 1) { /* draw a single dot where this single node is */ map_way_single_new(map, way, map->style->node.radius, 0, - RGB2CANVAS(map->style->node.color), 0); + map->style->node.color, 0); } else { canvas_points_t *points = canvas_points_new(nodes); @@ -509,14 +526,13 @@ map_node_new(map, node, map->style->node.radius, map->style->node.border_radius, - RGBA2CANVAS(map->style->node.fill_color, - map->style->node.has_fill_color?0xff:0x00), - RGB2CANVAS(map->style->node.color)); + map->style->node.fill_color, + map->style->node.color); else if(map->style->node.show_untagged || osm_node_has_tag(node)) map_node_new(map, node, map->style->node.radius, 0, - RGB2CANVAS(map->style->node.color), 0); + map->style->node.color, 0); } static void map_item_draw(map_t *map, map_item_t *map_item) { @@ -598,31 +614,34 @@ canvas_points_t *points = canvas_points_new(5); /* don't draw frisket at all if it's completely transparent */ - if(map->style->frisket.opaque) { - elemstyle_color_t color = - (map->style->background.color<<8) | map->style->frisket.opaque; + if(map->style->frisket.color & 0xff) { + elemstyle_color_t color = map->style->frisket.color; float mult = map->style->frisket.mult; /* top rectangle */ map_frisket_rectangle(points, mult*bounds->min.x, mult*bounds->max.x, mult*bounds->min.y, bounds->min.y); - canvas_polygon_new(map, CANVAS_GROUP_NODES, points, 1, NO_COLOR, color); + canvas_polygon_new(map->canvas, CANVAS_GROUP_FRISKET, points, + 1, NO_COLOR, color); /* bottom rectangle */ map_frisket_rectangle(points, mult*bounds->min.x, mult*bounds->max.x, bounds->max.y, mult*bounds->max.y); - canvas_polygon_new(map, CANVAS_GROUP_NODES, points, 1, NO_COLOR, color); + canvas_polygon_new(map->canvas, CANVAS_GROUP_FRISKET, points, + 1, NO_COLOR, color); /* left rectangle */ map_frisket_rectangle(points, mult*bounds->min.x, bounds->min.x, mult*bounds->min.y, mult*bounds->max.y); - canvas_polygon_new(map, CANVAS_GROUP_NODES, points, 1, NO_COLOR, color); + canvas_polygon_new(map->canvas, CANVAS_GROUP_FRISKET, points, + 1, NO_COLOR, color); /* right rectangle */ map_frisket_rectangle(points, bounds->max.x, mult*bounds->max.x, mult*bounds->min.y, mult*bounds->max.y); - canvas_polygon_new(map, CANVAS_GROUP_NODES, points, 1, NO_COLOR, color); + canvas_polygon_new(map->canvas, CANVAS_GROUP_FRISKET, points, + 1, NO_COLOR, color); } @@ -633,7 +652,7 @@ bounds->min.x-ew2, bounds->max.x+ew2, bounds->min.y-ew2, bounds->max.y+ew2); - canvas_polyline_new(map, CANVAS_GROUP_NODES, points, + canvas_polyline_new(map->canvas, CANVAS_GROUP_FRISKET, points, map->style->frisket.border.width, map->style->frisket.border.color); @@ -765,7 +784,7 @@ return NULL; } - if(map_item->highlight) + if(map_item->highlight) printf(" item is highlight\n"); switch(map_item->type) { @@ -784,7 +803,7 @@ } /* get the real item (no highlight) at x, y */ -static map_item_t *map_real_item_at(map_t *map, gint x, gint y) { +map_item_t *map_real_item_at(map_t *map, gint x, gint y) { map_item_t *map_item = map_item_at(map, x, y); /* no item or already a real one */ @@ -824,39 +843,39 @@ return map_item; } - - -#ifdef USE_GOOCANVAS - /* Limitations on the amount by which we can scroll. Keeps part of the * map visible at all times */ -static void map_limit_scroll(map_t *map, gint *sx, gint *sy) { - gdouble zoom = goo_canvas_get_scale(GOO_CANVAS(map->canvas)); - - gint sx_cu = *sx / zoom; - gint sy_cu = *sy / zoom; - - // Canvas viewport dimensions - GtkAllocation *a = >K_WIDGET(map->canvas)->allocation; - gint aw_cu = a->width / zoom; - gint ah_cu = a->height / zoom; - - // Data rect minimum and maximum - gint min_x, min_y, max_x, max_y; - min_x = map->appdata->osm->bounds->min.x; - min_y = map->appdata->osm->bounds->min.y; - max_x = map->appdata->osm->bounds->max.x; - max_y = map->appdata->osm->bounds->max.y; +static void map_limit_scroll(map_t *map, canvas_unit_t unit, + gint *sx, gint *sy) { - // limit stops - prevent scrolling beyond these - gint min_sy_cu = 0.95*(min_y - ah_cu); - gint min_sx_cu = 0.95*(min_x - aw_cu); - gint max_sy_cu = 0.95*(max_y); - gint max_sx_cu = 0.95*(max_x); - if (sy_cu < min_sy_cu) { *sy = min_sy_cu*zoom; } - if (sx_cu < min_sx_cu) { *sx = min_sx_cu*zoom; } - if (sy_cu > max_sy_cu) { *sy = max_sy_cu*zoom; } - if (sx_cu > max_sx_cu) { *sx = max_sx_cu*zoom; } + /* get scale factor for pixel->meter conversion. set to 1 if */ + /* given coordinates are already in meters */ + gdouble scale = (unit == CANVAS_UNIT_METER)?1.0:canvas_get_zoom(map->canvas); + + /* convert pixels to meters if necessary */ + gdouble sx_cu = *sx / scale; + gdouble sy_cu = *sy / scale; + + /* get size of visible area in canvas units (meters) */ + gint aw_cu = canvas_get_viewport_width(map->canvas, CANVAS_UNIT_METER); + gint ah_cu = canvas_get_viewport_height(map->canvas, CANVAS_UNIT_METER); + + // Data rect minimum and maximum + gint min_x, min_y, max_x, max_y; + min_x = map->appdata->osm->bounds->min.x; + min_y = map->appdata->osm->bounds->min.y; + max_x = map->appdata->osm->bounds->max.x; + max_y = map->appdata->osm->bounds->max.y; + + // limit stops - prevent scrolling beyond these + gint min_sy_cu = 0.95*(min_y - ah_cu); + gint min_sx_cu = 0.95*(min_x - aw_cu); + gint max_sy_cu = 0.95*(max_y); + gint max_sx_cu = 0.95*(max_x); + if (sy_cu < min_sy_cu) { *sy = min_sy_cu * scale; } + if (sx_cu < min_sx_cu) { *sx = min_sx_cu * scale; } + if (sy_cu > max_sy_cu) { *sy = max_sy_cu * scale; } + if (sx_cu > max_sx_cu) { *sx = max_sx_cu * scale; } } @@ -870,10 +889,12 @@ max_x = map->appdata->osm->bounds->max.x; max_y = map->appdata->osm->bounds->max.y; - // Canvas viewport dimensions - GtkAllocation *a = >K_WIDGET(map->canvas)->allocation; - gint ah_cu = a->height / *zoom; - gint aw_cu = a->width / *zoom; + /* get size of visible area in pixels and convert to meters of intended */ + /* zoom by deviding by zoom (which is basically pix/m) */ + gint aw_cu = + canvas_get_viewport_width(map->canvas, CANVAS_UNIT_PIXEL) / *zoom; + gint ah_cu = + canvas_get_viewport_height(map->canvas, CANVAS_UNIT_PIXEL) / *zoom; gdouble oldzoom = *zoom; if (ah_cu < aw_cu) { @@ -898,78 +919,71 @@ } -#if 0 -/* Scroll the map a little towards the centre from where it is right now. - * This is used as a cute recentring trick when the map is at its outer - * scroll limit. */ -static void map_scroll_towards_centre(map_t *map, gdouble amt) { - gint sx, sy, sx_orig, sy_orig; - canvas_get_scroll_offsets(map->canvas, &sx, &sy); - gdouble zoom = goo_canvas_get_scale(GOO_CANVAS(map->canvas)); - sx_orig=sx; - sy_orig=sy; - - // Work in canvas units - gdouble sx_cu = sx / zoom; - gdouble sy_cu = sy / zoom; - - // Map bounds - gdouble bmin_x_cu, bmin_y_cu, bmax_x_cu, bmax_y_cu; - bmin_x_cu = map->appdata->osm->bounds->min.x; - bmin_y_cu = map->appdata->osm->bounds->min.y; - bmax_x_cu = map->appdata->osm->bounds->max.x; - bmax_y_cu = map->appdata->osm->bounds->max.y; - - // Canvas viewport dimensions - GtkAllocation *a = >K_WIDGET(map->canvas)->allocation; - gdouble ah_cu = a->height / zoom; - gdouble aw_cu = a->width / zoom; - - // Scroll offsets that would recentre the map - gdouble centre_sx_cu, centre_sy_cu; - centre_sx_cu = - (aw_cu/2); - centre_sy_cu = - (ah_cu/2); - - // Move towards centre by a given fraction of the whole map - if (sx_cu > centre_sx_cu) { - sx_cu -= ((bmax_x_cu - bmin_x_cu) * amt); - if (sx_cu < centre_sx_cu) { - printf("force-centre-x\n"); - sx_cu = centre_sx_cu; - } - } - if (sx_cu < centre_sx_cu) { - sx_cu += ((bmax_x_cu - bmin_x_cu) * amt); - if (sx_cu > centre_sx_cu) { - printf("force-centre-x\n"); - sx_cu = centre_sx_cu; - } - } +/* + * Scroll the map to a point if that point is currently offscreen. + */ +void map_scroll_to_if_offscreen(map_t *map, lpos_t *lpos) { - if (sy_cu > centre_sy_cu) { - sy_cu -= ((bmax_y_cu - bmin_y_cu) * amt); - if (sy_cu < centre_sy_cu) { - printf("force-centre-y\n"); - sy_cu = centre_sy_cu; - } - } - if (sy_cu < centre_sy_cu) { - sy_cu += ((bmax_y_cu - bmin_y_cu) * amt); - if (sy_cu > centre_sy_cu) { - printf("force-centre-y\n"); - sy_cu = centre_sy_cu; - } - } + // Ignore anything outside the working area + if (!(map && map->appdata && map->appdata->osm)) { + return; + } + gint min_x, min_y, max_x, max_y; + min_x = map->appdata->osm->bounds->min.x; + min_y = map->appdata->osm->bounds->min.y; + max_x = map->appdata->osm->bounds->max.x; + max_y = map->appdata->osm->bounds->max.y; + if ( (lpos->x > max_x) || (lpos->x < min_x) + || (lpos->y > max_y) || (lpos->y < min_y)) { + printf("cannot scroll to (%d, %d): outside the working area\n", + lpos->x, lpos->y); + return; + } + + // Viewport dimensions in canvas space - // Back to pixels for setting the scroll - sx = (gint)(sx_cu * zoom); - sy = (gint)(sy_cu * zoom); - canvas_scroll_to(map->canvas, sx, sy); - map->state->scroll_offset.x = sx; - map->state->scroll_offset.y = sy; + /* get size of visible area in canvas units (meters) */ + gdouble pix_per_meter = canvas_get_zoom(map->canvas); + gdouble aw = canvas_get_viewport_width(map->canvas, CANVAS_UNIT_METER); + gdouble ah = canvas_get_viewport_height(map->canvas, CANVAS_UNIT_METER); + + // Is the point still onscreen? + gboolean vert_recentre_needed = FALSE; + gboolean horiz_recentre_needed = FALSE; + gint sx, sy; + canvas_scroll_get(map->canvas, CANVAS_UNIT_PIXEL, &sx, &sy); + gint viewport_left = (sx/pix_per_meter); + gint viewport_right = (sx/pix_per_meter)+aw; + gint viewport_top = (sy/pix_per_meter); + gint viewport_bottom = (sy/pix_per_meter)+ah; + if (lpos->x > viewport_right) { + printf("** off right edge (%d > %d)\n", lpos->x, viewport_right); + horiz_recentre_needed = TRUE; + } + if (lpos->x < viewport_left) { + printf("** off left edge (%d < %d)\n", lpos->x, viewport_left); + horiz_recentre_needed = TRUE; + } + if (lpos->y > viewport_bottom) { + printf("** off bottom edge (%d > %d)\n", lpos->y, viewport_bottom); + vert_recentre_needed = TRUE; + } + if (lpos->y < viewport_top) { + printf("** off top edge (%d < %d)\n", lpos->y, viewport_top); + vert_recentre_needed = TRUE; + } + + if (horiz_recentre_needed || vert_recentre_needed) { + gint new_sx, new_sy; + + // Just centre both at once + new_sx = pix_per_meter * (lpos->x - (aw/2)); + new_sy = pix_per_meter * (lpos->y - (ah/2)); + + map_limit_scroll(map, CANVAS_UNIT_PIXEL, &new_sx, &new_sy); + canvas_scroll_to(map->canvas, CANVAS_UNIT_PIXEL, new_sx, new_sy); + } } -#endif // #if 0 -#endif // #ifdef USE_GOOCANVAS /* Deselects the current way or node if its zoom_max * means that it's not going to render at the current map zoom. */ @@ -995,31 +1009,27 @@ void map_set_zoom(map_t *map, double zoom, gboolean update_scroll_offsets) { gboolean at_zoom_limit = 0; -#ifdef USE_GOOCANVAS at_zoom_limit = map_limit_zoom(map, &zoom); -#endif + map->state->zoom = zoom; canvas_set_zoom(map->canvas, map->state->zoom); map_deselect_if_zoom_below_zoom_max(map); - if (update_scroll_offsets) { + if(update_scroll_offsets) { if (!at_zoom_limit) { /* zooming affects the scroll offsets */ gint sx, sy; - canvas_get_scroll_offsets(map->canvas, &sx, &sy); -#ifdef USE_GOOCANVAS - map_limit_scroll(map, &sx, &sy); - canvas_scroll_to(map->canvas, sx, sy); // keep the map visible -#endif - map->state->scroll_offset.x = sx; - map->state->scroll_offset.y = sy; - } -#ifdef USE_GOOCANVAS - else { - // map_scroll_towards_centre(map, 0.20); + canvas_scroll_get(map->canvas, CANVAS_UNIT_PIXEL, &sx, &sy); + map_limit_scroll(map, CANVAS_UNIT_PIXEL, &sx, &sy); + + // keep the map visible + canvas_scroll_to(map->canvas, CANVAS_UNIT_PIXEL, sx, sy); } -#endif + + canvas_scroll_get(map->canvas, CANVAS_UNIT_METER, + &map->state->scroll_offset.x, + &map->state->scroll_offset.y); } } @@ -1044,17 +1054,9 @@ static gboolean distance_above(map_t *map, gint x, gint y, gint limit) { gint sx, sy; -#ifdef USE_GNOMECANVAS - gnome_canvas_get_scroll_offsets(GNOME_CANVAS(map->canvas), &sx, &sy); - - /* add offsets generated by mouse within map and map scrolling */ - sx = (x-map->pen_down.at.x) + (map->pen_down.so.x-sx); - sy = (y-map->pen_down.at.y) + (map->pen_down.so.y-sy); -#else /* add offsets generated by mouse within map and map scrolling */ sx = (x-map->pen_down.at.x); sy = (y-map->pen_down.at.y); -#endif return(sx*sx + sy*sy > limit*limit); } @@ -1063,32 +1065,31 @@ static void map_do_scroll(map_t *map, gint x, gint y) { gint sx, sy; - canvas_get_scroll_offsets(map->canvas, &sx, &sy); + canvas_scroll_get(map->canvas, CANVAS_UNIT_PIXEL, &sx, &sy); sx -= x-map->pen_down.at.x; sy -= y-map->pen_down.at.y; -#ifdef USE_GOOCANVAS - map_limit_scroll(map, &sx, &sy); -#endif - canvas_scroll_to(map->canvas, sx, sy); - map->state->scroll_offset.x = sx; - map->state->scroll_offset.y = sy; + map_limit_scroll(map, CANVAS_UNIT_PIXEL, &sx, &sy); + canvas_scroll_to(map->canvas, CANVAS_UNIT_PIXEL, sx, sy); + + canvas_scroll_get(map->canvas, CANVAS_UNIT_METER, + &map->state->scroll_offset.x, + &map->state->scroll_offset.y); } /* scroll a certain step */ static void map_do_scroll_step(map_t *map, gint x, gint y) { gint sx, sy; - canvas_get_scroll_offsets(map->canvas, &sx, &sy); + canvas_scroll_get(map->canvas, CANVAS_UNIT_PIXEL, &sx, &sy); sx += x; sy += y; -#ifdef USE_GOOCANVAS - map_limit_scroll(map, &sx, &sy); -#endif - canvas_scroll_to(map->canvas, sx, sy); - map->state->scroll_offset.x = sx; - map->state->scroll_offset.y = sy; -} + map_limit_scroll(map, CANVAS_UNIT_PIXEL, &sx, &sy); + canvas_scroll_to(map->canvas, CANVAS_UNIT_PIXEL, sx, sy); + canvas_scroll_get(map->canvas, CANVAS_UNIT_METER, + &map->state->scroll_offset.x, + &map->state->scroll_offset.y); +} gboolean map_item_is_selected_node(map_t *map, map_item_t *map_item) { printf("check if item is a selected node\n"); @@ -1307,12 +1308,6 @@ map->pen_down.at.y = y; map->pen_down.drag = FALSE; // don't assume drag yet -#ifdef USE_GNOMECANVAS - /* save initial scroll offset */ - gnome_canvas_get_scroll_offsets(GNOME_CANVAS(map->canvas), - &map->pen_down.so.x, &map->pen_down.so.y); -#endif - /* determine wether this press was on an item */ map->pen_down.on_item = map_real_item_at(map, x, y); @@ -1505,14 +1500,14 @@ /* reduce update frequency on hildon to keep screen update fluid */ static guint32 last_time = 0; - if(event->time - last_time < 100) return FALSE; + if(event->time - last_time < 250) return FALSE; last_time = event->time; #endif if(!map->pen_down.is) return FALSE; -#ifdef USE_GNOMECANVAS +#ifndef USE_GOOCANVAS /* handle hints, hints are handled by goocanvas directly */ if(event->is_hint) gdk_window_get_pointer(event->window, &x, &y, &state); @@ -1549,7 +1544,7 @@ case MAP_ACTION_NODE_ADD: map_hl_cursor_draw(map, x, y, FALSE, map->style->node.radius); break; - + case MAP_ACTION_WAY_ADD: map_hl_cursor_draw(map, x, y, FALSE, map->style->node.radius); map_touchnode_update(appdata, x, y); @@ -1654,6 +1649,11 @@ map_t *map = appdata->map = g_new0(map_t, 1); map->style = style_load(appdata, appdata->settings->style); + if(!map->style) { + errorf(NULL, _("Unable to load valid style, terminating.")); + g_free(map); + return NULL; + } if(appdata->project && appdata->project->map_state) { printf("Using projects map state\n"); @@ -1671,56 +1671,31 @@ map->appdata = appdata; map->action.type = MAP_ACTION_IDLE; -#ifdef USE_GNOMECANVAS - map->canvas = gnome_canvas_new_aa(); // _aa - - /* create the groups */ - canvas_group_t group; - for(group = 0; group < CANVAS_GROUPS; group++) - map->group[group] = gnome_canvas_item_new( - gnome_canvas_root(GNOME_CANVAS(map->canvas)), - GNOME_TYPE_CANVAS_GROUP, - NULL); + map->canvas = canvas_new(map->style->background.color); + canvas_set_antialias(map->canvas, !appdata->settings->no_antialias); - gtk_widget_modify_bg(map->canvas, GTK_STATE_NORMAL, - &map->canvas->style->white); + GtkWidget *canvas_widget = canvas_get_widget(map->canvas); -#else - map->canvas = goo_canvas_new(); - - g_object_set(G_OBJECT(map->canvas), "anchor", GTK_ANCHOR_CENTER, NULL); - g_object_set(G_OBJECT(map->canvas), "background-color-rgb", - map->style->background.color, NULL); - - GooCanvasItem *root = goo_canvas_get_root_item(GOO_CANVAS(map->canvas)); - - /* create the groups */ - canvas_group_t group; - for(group = 0; group < CANVAS_GROUPS; group++) - map->group[group] = goo_canvas_group_new(root, NULL); - -#endif - - gtk_widget_set_events(map->canvas, + gtk_widget_set_events(canvas_widget, GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK | GDK_SCROLL_MASK | GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK); - gtk_signal_connect(GTK_OBJECT(map->canvas), + gtk_signal_connect(GTK_OBJECT(canvas_widget), "button_press_event", G_CALLBACK(map_button_event), appdata); - gtk_signal_connect(GTK_OBJECT(map->canvas), + gtk_signal_connect(GTK_OBJECT(canvas_widget), "button_release_event", G_CALLBACK(map_button_event), appdata); - gtk_signal_connect(GTK_OBJECT(map->canvas), + gtk_signal_connect(GTK_OBJECT(canvas_widget), "motion_notify_event", G_CALLBACK(map_motion_notify_event), appdata); - gtk_signal_connect(GTK_OBJECT(map->canvas), + gtk_signal_connect(GTK_OBJECT(canvas_widget), "scroll_event", G_CALLBACK(map_scroll_event), appdata); - gtk_signal_connect(GTK_OBJECT(map->canvas), + gtk_signal_connect(GTK_OBJECT(canvas_widget), "destroy", G_CALLBACK(map_destroy_event), appdata); - return map->canvas; + return canvas_widget; } void map_init(appdata_t *appdata) { @@ -1739,11 +1714,13 @@ mult*appdata->osm->bounds->max.x, mult*appdata->osm->bounds->max.y); - printf("restore scroll offsets %d/%d\n", + printf("restore scroll position %d/%d\n", map->state->scroll_offset.x, map->state->scroll_offset.y); - canvas_scroll_to(map->canvas, - map->state->scroll_offset.x, map->state->scroll_offset.y); + map_limit_scroll(map, CANVAS_UNIT_METER, + &map->state->scroll_offset.x, &map->state->scroll_offset.y); + canvas_scroll_to(map->canvas, CANVAS_UNIT_METER, + map->state->scroll_offset.x, map->state->scroll_offset.y); } @@ -1766,7 +1743,7 @@ } } -void map_clear(appdata_t *appdata, gint layer_mask) { +void map_clear(appdata_t *appdata, gint group_mask) { map_t *map = appdata->map; printf("freeing map contents\n"); @@ -1776,32 +1753,15 @@ /* remove a possibly existing highlight */ map_item_deselect(appdata); - canvas_group_t group; - for(group=0;groupgroup[group]); - - /* and create an empty new one */ - map->group[group] = gnome_canvas_item_new( - gnome_canvas_root(GNOME_CANVAS(map->canvas)), - GNOME_TYPE_CANVAS_GROUP, - NULL); -#else - if(layer_mask & (1<group[group]); - printf("Removing %d children from layer %d\n", children, group); - while(children--) - goo_canvas_item_remove_child(map->group[group], children); - } -#endif - } + canvas_erase(map->canvas, group_mask); } void map_paint(appdata_t *appdata) { map_t *map = appdata->map; + /* user may have changed antialias settings */ + canvas_set_antialias(map->canvas, !appdata->settings->no_antialias); + josm_elemstyles_colorize_world(map->style, appdata->osm); map_draw(map, appdata->osm); } @@ -1933,6 +1893,8 @@ /* deleting the selected item de-selects it ... */ map_item_deselect(appdata); + undo_remember_delete(appdata, item.type, item.ptr); + switch(item.type) { case MAP_TYPE_NODE: printf("request to delete node #%ld\n", item.node->id); @@ -2017,7 +1979,7 @@ if(pnum == 1) { g_assert(!seg->item); - seg->item = canvas_circle_new(map, CANVAS_GROUP_TRACK, + seg->item = canvas_circle_new(map->canvas, CANVAS_GROUP_TRACK, seg->track_point->lpos.x, seg->track_point->lpos.y, map->style->track.width/2.0, 0, map->style->track.color, NO_COLOR); } @@ -2039,7 +2001,7 @@ if(seg->item) canvas_item_destroy(seg->item); - seg->item = canvas_polyline_new(map, CANVAS_GROUP_TRACK, + seg->item = canvas_polyline_new(map->canvas, CANVAS_GROUP_TRACK, points, map->style->track.width, map->style->track.color); canvas_points_free(points); @@ -2105,9 +2067,10 @@ } if(lpos) - appdata->track.gps_item = canvas_circle_new(appdata->map, CANVAS_GROUP_GPS, + appdata->track.gps_item = + canvas_circle_new(appdata->map->canvas, CANVAS_GROUP_GPS, lpos->x, lpos->y, appdata->map->style->track.width/2.0, 0, - RGB2CANVAS(appdata->map->style->track.gps_color), NO_COLOR); + appdata->map->style->track.gps_color, NO_COLOR); } /* ------------------- map background ------------------ */ @@ -2148,7 +2111,7 @@ map->bg.scale.y = (float)(bounds->max.y - bounds->min.y)/ (float)gdk_pixbuf_get_height(map->bg.pix); - map->bg.item = canvas_image_new(map, CANVAS_GROUP_BG, map->bg.pix, + map->bg.item = canvas_image_new(map->canvas, CANVAS_GROUP_BG, map->bg.pix, bounds->min.x, bounds->min.y, map->bg.scale.x, map->bg.scale.y); canvas_item_destroy_connect(map->bg.item, @@ -2193,3 +2156,4 @@ gtk_widget_set_sensitive(appdata->menu_item_map_show_all, FALSE); } +// vim:et:ts=8:sw=2:sts=2:ai