X-Git-Url: http://pileus.org/git/?a=blobdiff_plain;f=src%2Fobjects%2Fgrits-marker.c;h=35103538dfa6975454932adc822c9a1f8f8b7d70;hb=2f0edbabb90eb0c421419433e8893521257bc614;hp=148289cc9db43e3dc469618c31c41cca080ceaae;hpb=7cadfa1814f09c99cbd3f2555b0717792a124513;p=grits diff --git a/src/objects/grits-marker.c b/src/objects/grits-marker.c index 148289c..3510353 100644 --- a/src/objects/grits-marker.c +++ b/src/objects/grits-marker.c @@ -39,8 +39,9 @@ static void render_point(GritsMarker *marker) { /* Draw outline */ - cairo_set_source_rgba(marker->cairo, 0, 0, 0, 1); + cairo_set_line_join(marker->cairo, CAIRO_LINE_JOIN_ROUND); cairo_set_line_width(marker->cairo, marker->outline*2); + cairo_set_source_rgba(marker->cairo, 0, 0, 0, 1); cairo_arc(marker->cairo, marker->xoff, marker->yoff, marker->radius, 0, 2*G_PI); @@ -58,6 +59,9 @@ static void render_label(GritsMarker *marker) { g_assert(marker->label); + /* Draw outline */ + cairo_set_line_join(marker->cairo, CAIRO_LINE_JOIN_ROUND); + cairo_set_line_width(marker->cairo, marker->outline*2); cairo_set_source_rgba(marker->cairo, 0, 0, 0, 1); cairo_select_font_face(marker->cairo, "sans-serif", CAIRO_FONT_SLANT_NORMAL, CAIRO_FONT_WEIGHT_BOLD); @@ -78,37 +82,9 @@ static void render_icon(GritsMarker *marker) { g_assert(marker->icon_img != NULL); - /* This code assumes the icon is an image pointing toward 0 degrees - * (ie. north/up). If marker->flip is set, then it will rotate the - * icon appropriately then reflect it across the vertical axis so - * it's never upside down. */ - gdouble flip = 1.0; - gdouble angle = marker->angle % 360; - if (marker->flip && (angle < 360 && angle > 180)) { - /* if icon rotates to the left half it will be upside down */ - flip = -1.0; /* flip horizontally */ - } - - cairo_save(marker->cairo); - /* move to marker location */ cairo_translate(marker->cairo, marker->xoff, marker->yoff); - /* perform rotation and flip in one transformation */ - gdouble C = cos(angle*(M_PI/180.0)); - gdouble S = sin(angle*(M_PI/180.0)); - gdouble fx = flip; - gdouble fy = 1.0; - gdouble tx = 0.0; - gdouble ty = 0.0; - cairo_matrix_t matrix; - cairo_matrix_init(&matrix, - fx*C, fx*S, - -S*fy, C*fy, - C*tx*(1-fx)-S*ty*(fy-1)+tx-C*tx+S*ty, - S*tx*(1-fx)+C*ty*(fy-1)+ty-S*tx-C*ty); - cairo_transform(marker->cairo, &matrix); - /* center image */ cairo_translate(marker->cairo, -marker->icon_width/2, -marker->icon_height/2); @@ -116,7 +92,6 @@ static void render_icon(GritsMarker *marker) cairo_set_source_surface(marker->cairo, marker->icon_img, 0, 0); cairo_paint(marker->cairo); - cairo_restore(marker->cairo); } static void render_all(GritsMarker *marker) @@ -140,8 +115,8 @@ static void render_all(GritsMarker *marker) glTexImage2D(GL_TEXTURE_2D, 0, 4, marker->width, marker->height, 0, GL_BGRA, GL_UNSIGNED_BYTE, cairo_image_surface_get_data(cairo_get_target(marker->cairo))); - glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); - glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); + glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); + glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); } @@ -158,6 +133,8 @@ GritsMarker *grits_marker_new(const gchar *label) { GritsMarker *marker = g_object_new(GRITS_TYPE_MARKER, NULL); + GRITS_OBJECT(marker)->skip = GRITS_SKIP_CENTER; + marker->display_mask = GRITS_MARKER_DMASK_POINT | GRITS_MARKER_DMASK_LABEL; @@ -177,8 +154,6 @@ GritsMarker *grits_marker_new(const gchar *label) marker->label = g_strdup(label); - render_all(marker); - return marker; } @@ -236,6 +211,7 @@ GritsMarker *grits_marker_icon_new(const gchar *label, const gchar *filename, marker->outline = 2; marker->radius = 3; + /* this is the surface size, a guess really */ marker->width = marker->icon_width + 128; marker->height = marker->icon_height + 64; @@ -244,6 +220,7 @@ GritsMarker *grits_marker_icon_new(const gchar *label, const gchar *filename, marker->yoff = marker->height/2; marker->cairo = cairo_create(cairo_image_surface_create( CAIRO_FORMAT_ARGB32, marker->width, marker->height)); + /* clear the surface just in case */ cairo_set_operator(marker->cairo, CAIRO_OPERATOR_SOURCE); //cairo_set_source_rgba(marker->cairo, 1.0, 0.0, 0.0, 0.3); // debug @@ -265,28 +242,45 @@ static void grits_marker_draw(GritsObject *_marker, GritsOpenGL *opengl) { GritsMarker *marker = GRITS_MARKER(_marker); GritsPoint *point = grits_object_center(marker); - gdouble px, py, pz; - grits_viewer_project(GRITS_VIEWER(opengl), - point->lat, point->lon, point->elev, - &px, &py, &pz); - - gint win_width = GTK_WIDGET(opengl)->allocation.width; - gint win_height = GTK_WIDGET(opengl)->allocation.height; - py = win_height - py; - if (pz > 1) - return; - - //g_debug("GritsOpenGL: draw_marker - %s pz=%f ", marker->label, pz); cairo_surface_t *surface = cairo_get_target(marker->cairo); gdouble width = cairo_image_surface_get_width(surface); gdouble height = cairo_image_surface_get_height(surface); - glMatrixMode(GL_PROJECTION); glLoadIdentity(); - glMatrixMode(GL_MODELVIEW); glLoadIdentity(); - glOrtho(0, win_width, win_height, 0, -1, 1); - glTranslated(px - marker->xoff, - py - marker->yoff, 0); + if (!marker->tex) + render_all(marker); + + if (marker->ortho) { + gdouble px, py, pz; + grits_viewer_project(GRITS_VIEWER(opengl), + point->lat, point->lon, point->elev, + &px, &py, &pz); + + gint win_height = GTK_WIDGET(opengl)->allocation.height; + if (pz > 1) + return; + + glTranslated(px, win_height-py, 0); + glRotatef(marker->angle, 0, 0, -1); + glTranslated(-marker->xoff, -marker->yoff, 0); + } else { + gdouble scale, eye[3], pos[3] = + {point->lat, point->lon, point->elev}; + grits_viewer_get_location(GRITS_VIEWER(opengl), + &eye[0], &eye[1], &eye[2]); + lle2xyz(eye[0], eye[1], eye[2], + &eye[0], &eye[1], &eye[2]); + lle2xyz(pos[0], pos[1], pos[2], + &pos[0], &pos[1], &pos[2]); + scale = MPPX(distd(eye, pos)); + + glRotatef(marker->angle, 0, 0, -1); + glRotatef(180, 1, 0, 0); + glScalef(scale, scale, 1); + glTranslated(-marker->xoff, -marker->yoff, 0); + } + + //g_debug("GritsOpenGL: draw_marker - %s pz=%f ", marker->label, pz); glDisable(GL_LIGHTING); glDisable(GL_COLOR_MATERIAL); @@ -295,10 +289,10 @@ static void grits_marker_draw(GritsObject *_marker, GritsOpenGL *opengl) glBindTexture(GL_TEXTURE_2D, marker->tex); glDisable(GL_CULL_FACE); glBegin(GL_QUADS); - glTexCoord2f(1, 0); glVertex3f(width, 0 , 0); - glTexCoord2f(1, 1); glVertex3f(width, height, 0); - glTexCoord2f(0, 1); glVertex3f(0 , height, 0); - glTexCoord2f(0, 0); glVertex3f(0 , 0 , 0); + glTexCoord2f(1, 0); glVertex3f(width, 0 , 0); // 0 - 3 0 + glTexCoord2f(1, 1); glVertex3f(width, height, 0); // 1 - | | + glTexCoord2f(0, 1); glVertex3f(0 , height, 0); // 2 - | | + glTexCoord2f(0, 0); glVertex3f(0 , 0 , 0); // 3 - 2----1 glEnd(); } @@ -307,18 +301,21 @@ static void grits_marker_draw(GritsObject *_marker, GritsOpenGL *opengl) G_DEFINE_TYPE(GritsMarker, grits_marker, GRITS_TYPE_OBJECT); static void grits_marker_init(GritsMarker *marker) { + marker->ortho = TRUE; } static void grits_marker_finalize(GObject *_marker) { //g_debug("GritsMarker: finalize - %s", marker->label); GritsMarker *marker = GRITS_MARKER(_marker); - glDeleteTextures(1, &marker->tex); - cairo_surface_t *surface = cairo_get_target(marker->cairo); - cairo_surface_destroy(surface); - cairo_destroy(marker->cairo); + if (marker->tex) + glDeleteTextures(1, &marker->tex); + if (marker->cairo) { + cairo_surface_t *surface = cairo_get_target(marker->cairo); + cairo_surface_destroy(surface); + cairo_destroy(marker->cairo); + } g_free(marker->label); - glDeleteTextures(1, &marker->tex); } static void grits_marker_class_init(GritsMarkerClass *klass)