Gtk+中控件拖动,画虚线框的解决方式
时间:2010-06-21 来源:Hecate_Eos
每个问题都折腾好几天~~~
最近,为了拖动控件而折腾,控件倒是拖动了,但问题是总是闪烁!
Google了许久也没找到一些有用的代码。倒是发现了两句有用的话:
1.“窗口拖动我采用了,虚框方式”
2.超出无效区域的绘制会被裁剪掉,虽然这是针对windows,但我想对linux也是一样的。
不说废话了,把代码贴出来。。。(只是重绘代码)
static gint8 dash_list[] = {2,2};
static gint cb_expose_event_handler(GtkWidget *widget, GdkEventExpose *event, gpointer data)
{
if( is_pressed )
{
/*擦除上次绘制虚框*/
GdkGC* gc0 = gdk_gc_new(GTK_LAYOUT(widget)->bin_window);
GdkGCValues vals0;
vals0.function = GDK_COPY;// GDK_OR ;//GDK_NOOP;//GDK_AND;
vals0.line_style = GDK_LINE_ON_OFF_DASH;
vals0.foreground = widget->style->bg[GTK_STATE_NORMAL];
gdk_gc_set_values(gc0,
vals0,
GDK_GC_FOREGROUND|GDK_GC_FUNCTION|GDK_GC_LINE_STYLE);
gdk_gc_set_dashes(gc0, 0, dash_list, sizeof(dash_list));
gdk_draw_rectangle(GTK_LAYOUT(widget)->bin_window,
gc0,
FALSE,
last_rect.x,
last_rect.y,
last_rect.width-1,
last_rect.height-1);
/*绘制本次虚框*/
GdkGC* gc = gdk_gc_new(GTK_LAYOUT(widget)->bin_window);
GdkColormap *colormap;
colormap = gdk_colormap_get_system ();
GdkColor color;
color.red = 0x0000;
color.green = 0x0000;
color.blue = 0xFFFF;
gdk_colormap_alloc_color(colormap, &color, FALSE, TRUE);
GdkGCValues vals;
vals.foreground = color;
vals.line_style = GDK_LINE_ON_OFF_DASH;
gdk_gc_set_values(gc, &vals, GDK_GC_FOREGROUND|GDK_GC_LINE_STYLE);
gdk_gc_set_dashes(gc, 0, dash_list, sizeof(dash_list));
gdk_draw_rectangle(GTK_LAYOUT(widget)->bin_window,
gc,
FALSE,
curr_rect.x,
curr_rect.y,
curr_rect.width-1,
curr_rect.height-1);
g_object_unref(G_OBJECT(gc0));
g_object_unref(G_OBJECT(gc));
return FALSE;
}
return TRUE;
}
在一开始,我只是把当前控件大小的区域设置无效、重绘,但是这样不能擦除上一次绘制的虚框,所以为了能擦除上一次的虚框,我直接把控件的父容器,设置无效。
注意代码中虚线框宽度和高度都减一,是因为我发现在绘制时,容易超出实际控件大小,比控件宽度高度多一个像素。
最近,为了拖动控件而折腾,控件倒是拖动了,但问题是总是闪烁!
Google了许久也没找到一些有用的代码。倒是发现了两句有用的话:
1.“窗口拖动我采用了,虚框方式”
2.超出无效区域的绘制会被裁剪掉,虽然这是针对windows,但我想对linux也是一样的。
不说废话了,把代码贴出来。。。(只是重绘代码)
static gint8 dash_list[] = {2,2};
static gint cb_expose_event_handler(GtkWidget *widget, GdkEventExpose *event, gpointer data)
{
if( is_pressed )
{
/*擦除上次绘制虚框*/
GdkGC* gc0 = gdk_gc_new(GTK_LAYOUT(widget)->bin_window);
GdkGCValues vals0;
vals0.function = GDK_COPY;// GDK_OR ;//GDK_NOOP;//GDK_AND;
vals0.line_style = GDK_LINE_ON_OFF_DASH;
vals0.foreground = widget->style->bg[GTK_STATE_NORMAL];
gdk_gc_set_values(gc0,
vals0,
GDK_GC_FOREGROUND|GDK_GC_FUNCTION|GDK_GC_LINE_STYLE);
gdk_gc_set_dashes(gc0, 0, dash_list, sizeof(dash_list));
gdk_draw_rectangle(GTK_LAYOUT(widget)->bin_window,
gc0,
FALSE,
last_rect.x,
last_rect.y,
last_rect.width-1,
last_rect.height-1);
/*绘制本次虚框*/
GdkGC* gc = gdk_gc_new(GTK_LAYOUT(widget)->bin_window);
GdkColormap *colormap;
colormap = gdk_colormap_get_system ();
GdkColor color;
color.red = 0x0000;
color.green = 0x0000;
color.blue = 0xFFFF;
gdk_colormap_alloc_color(colormap, &color, FALSE, TRUE);
GdkGCValues vals;
vals.foreground = color;
vals.line_style = GDK_LINE_ON_OFF_DASH;
gdk_gc_set_values(gc, &vals, GDK_GC_FOREGROUND|GDK_GC_LINE_STYLE);
gdk_gc_set_dashes(gc, 0, dash_list, sizeof(dash_list));
gdk_draw_rectangle(GTK_LAYOUT(widget)->bin_window,
gc,
FALSE,
curr_rect.x,
curr_rect.y,
curr_rect.width-1,
curr_rect.height-1);
g_object_unref(G_OBJECT(gc0));
g_object_unref(G_OBJECT(gc));
return FALSE;
}
return TRUE;
}
在一开始,我只是把当前控件大小的区域设置无效、重绘,但是这样不能擦除上一次绘制的虚框,所以为了能擦除上一次的虚框,我直接把控件的父容器,设置无效。
注意代码中虚线框宽度和高度都减一,是因为我发现在绘制时,容易超出实际控件大小,比控件宽度高度多一个像素。
相关阅读 更多 +