X-Git-Url: https://git.donarmstrong.com/?a=blobdiff_plain;f=src%2Fxo-paint.c;h=6361af72e2d30cdc83dba3b189f89859330c1a2d;hb=fdfa727422da81ef7438fa2eb6d98fe814804391;hp=79099411aec7634bd41b6ed8dbeeb033a88e542b;hpb=dcbb0ab8521a5e166f257d86884407eb98ef63f0;p=xournal.git diff --git a/src/xo-paint.c b/src/xo-paint.c index 7909941..6361af7 100644 --- a/src/xo-paint.c +++ b/src/xo-paint.c @@ -16,6 +16,76 @@ #include "xo-misc.h" #include "xo-paint.h" +/***** Win32 fix for gdk_cursor_new_from_pixmap() by Dirk Gerrits ****/ + +#ifdef WIN32 +gboolean colors_too_similar(const GdkColor *colora, const GdkColor *colorb) +{ + return (abs(colora->red - colorb->red) < 256 && + abs(colora->green - colorb->green) < 256 && + abs(colora->blue - colorb->blue) < 256); +} + +/* gdk_cursor_new_from_pixmap is broken on Windows. + this is a workaround using gdk_cursor_new_from_pixbuf. */ +GdkCursor* fixed_gdk_cursor_new_from_pixmap(GdkPixmap *source, GdkPixmap *mask, + const GdkColor *fg, const GdkColor *bg, + gint x, gint y) +{ + GdkPixmap *rgb_pixmap; + GdkGC *gc; + GdkPixbuf *rgb_pixbuf, *rgba_pixbuf; + GdkCursor *cursor; + int width, height; + + /* HACK! It seems impossible to work with RGBA pixmaps directly in + GDK-Win32. Instead we pick some third color, different from fg + and bg, and use that as the 'transparent color'. We do this using + colors_too_similar (see above) because two colors could be + unequal in GdkColor's 16-bit/sample, but equal in GdkPixbuf's + 8-bit/sample. */ + GdkColor candidates[3] = {{0,65535,0,0}, {0,0,65535,0}, {0,0,0,65535}}; + GdkColor *trans = &candidates[0]; + if (colors_too_similar(trans, fg) || colors_too_similar(trans, bg)) { + trans = &candidates[1]; + if (colors_too_similar(trans, fg) || colors_too_similar(trans, bg)) { + trans = &candidates[2]; + } + } /* trans is now guaranteed to be unique from fg and bg */ + + /* create an empty pixmap to hold the cursor image */ + gdk_drawable_get_size(source, &width, &height); + rgb_pixmap = gdk_pixmap_new(NULL, width, height, 24); + + /* blit the bitmaps defining the cursor onto a transparent background */ + gc = gdk_gc_new(rgb_pixmap); + gdk_gc_set_fill(gc, GDK_SOLID); + gdk_gc_set_rgb_fg_color(gc, trans); + gdk_draw_rectangle(rgb_pixmap, gc, TRUE, 0, 0, width, height); + gdk_gc_set_fill(gc, GDK_OPAQUE_STIPPLED); + gdk_gc_set_stipple(gc, source); + gdk_gc_set_clip_mask(gc, mask); + gdk_gc_set_rgb_fg_color(gc, fg); + gdk_gc_set_rgb_bg_color(gc, bg); + gdk_draw_rectangle(rgb_pixmap, gc, TRUE, 0, 0, width, height); + gdk_gc_unref(gc); + + /* create a cursor out of the created pixmap */ + rgb_pixbuf = gdk_pixbuf_get_from_drawable( + NULL, rgb_pixmap, gdk_colormap_get_system(), 0, 0, 0, 0, width, height); + gdk_pixmap_unref(rgb_pixmap); + rgba_pixbuf = gdk_pixbuf_add_alpha( + rgb_pixbuf, TRUE, trans->red, trans->green, trans->blue); + gdk_pixbuf_unref(rgb_pixbuf); + cursor = gdk_cursor_new_from_pixbuf(gdk_display_get_default(), rgba_pixbuf, x, y); + gdk_pixbuf_unref(rgba_pixbuf); + + return cursor; +} +#define gdk_cursor_new_from_pixmap fixed_gdk_cursor_new_from_pixmap +#endif + + /************** drawing nice cursors *********/ static char cursor_pen_bits[] = { @@ -608,6 +678,7 @@ gboolean start_resizesel(GdkEvent *event) ui.selection->new_x1 = ui.selection->bbox.left; ui.selection->new_x2 = ui.selection->bbox.right; gnome_canvas_item_set(ui.selection->canvas_item, "dash", NULL, NULL); + update_cursor_for_resize(pt); return TRUE; } return FALSE; @@ -1045,7 +1116,7 @@ void clipboard_paste(void) } p+= 2*item->path->num_points*sizeof(double); if (item->brush.variable_width) { - g_memmove(p, item->widths, (item->path->num_points-1)*sizeof(double)); + item->widths = g_memdup(p, (item->path->num_points-1)*sizeof(double)); p+= (item->path->num_points-1)*sizeof(double); } else item->widths = NULL; @@ -1076,11 +1147,16 @@ void clipboard_paste(void) gtk_selection_data_free(sel_data); update_copy_paste_enabled(); + update_color_menu(); + update_thickness_buttons(); + update_color_buttons(); + update_font_button(); + update_cursor(); // FIXME: can't know if pointer is within selection! } // modify the color or thickness of pen strokes in a selection -void recolor_selection(int color) +void recolor_selection(int color_no, guint color_rgba) { GList *itemlist; struct Item *item; @@ -1102,8 +1178,8 @@ void recolor_selection(int color) g_memmove(brush, &(item->brush), sizeof(struct Brush)); undo->auxlist = g_list_append(undo->auxlist, brush); // repaint the stroke - item->brush.color_no = color; - item->brush.color_rgba = predef_colors_rgba[color]; + item->brush.color_no = color_no; + item->brush.color_rgba = color_rgba | 0xff; // no alpha if (item->canvas_item!=NULL) { if (!item->brush.variable_width) gnome_canvas_item_set(item->canvas_item, @@ -1205,8 +1281,9 @@ void start_text(GdkEvent *event, struct Item *item) GnomeCanvasItem *canvas_item; PangoFontDescription *font_desc; GdkColor color; - + get_pointer_coords(event, pt); + ui.cur_item_type = ITEM_TEXT; if (item==NULL) { @@ -1253,13 +1330,13 @@ void start_text(GdkEvent *event, struct Item *item) item->canvas_item = canvas_item; gtk_widget_show(item->widget); - gtk_widget_grab_focus(item->widget); ui.resize_signal_handler = g_signal_connect((gpointer) winMain, "check_resize", G_CALLBACK(resize_textview), NULL); update_font_button(); gtk_widget_set_sensitive(GET_COMPONENT("editPaste"), FALSE); gtk_widget_set_sensitive(GET_COMPONENT("buttonPaste"), FALSE); + gtk_widget_grab_focus(item->widget); } void end_text(void) @@ -1271,7 +1348,7 @@ void end_text(void) GnomeCanvasItem *tmpitem; if (ui.cur_item_type!=ITEM_TEXT) return; // nothing for us to do! - + // finalize the text that's been edited... buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(ui.cur_item->widget)); gtk_text_buffer_get_bounds(buffer, &start, &end); @@ -1404,7 +1481,6 @@ void process_font_sel(gchar *str) else *p=0; } else size=0.; - reset_focus(); g_free(ui.font_name); ui.font_name = str; if (size>0.) ui.font_size = size;