2012-09-03 66 views
5

我想在GTK 3中创建自定义小部件。我注意到绘图问题只出现在某些GTK主题中,而所有其他主题都很好。我通过调用gtk_render_background()将问题缩小到了描绘背景的代码。对于某些主题,背景呈现为纯黑色,但这不是主题的默认背景色。以下是我的绘图功能的简化版本。自定义GTK小部件的背景呈现为纯黑色

static void gtk_databox_ruler_draw_ticks(GtkDataboxRuler *ruler) 
{ 
    GtkWidget *widget; 
    GtkStateFlags state; 
    cairo_t *cr; 
    GtkStyleContext *style_context; 
    gint width, height; 

    if (!gtk_widget_is_drawable(GTK_WIDGET(ruler))) { 
     return; 
    } 

    widget = GTK_WIDGET(ruler); 
    state = gtk_widget_get_state_flags(widget); 
    style_context = gtk_widget_get_style_context(widget); 

    gtk_style_context_save(style_context); 
    gtk_style_context_add_class(style_context, GTK_STYLE_CLASS_DEFAULT); 
    gtk_style_context_set_state(style_context, state); 

    /* <test-code> */ 
    GdkRGBA test; 
    gtk_style_context_get_background_color(style_context, gtk_widget_get_state_flags(widget), &test); 
    /* </test-code> */ 

    width = gtk_widget_get_allocated_width(widget); 
    height = gtk_widget_get_allocated_height(widget); 

    cr = cairo_create(ruler->priv->backing_surface); 

    gtk_render_background(style_context, cr, 0, 0, width, height); 

    gtk_style_context_restore(style_context); 
    cairo_destroy(cr); 
} 

我添加了一些测试代码来查询的背景颜色,并设置在gdb断点:

在使用Ubuntu的氛围主题:

(gdb) print test 
$1: test = {red = 0.94901960784313721, green = 0.94509803921568625, 
    blue = 0.94117647058823528, alpha = 1} 

在使用Ubuntu的高对比度主题:

(gdb) print test 
$1: test = {red = 0, green = 0, blue = 0, alpha = 0} 

我现在不知道如果我在一个错误的方式使用新的GtkStyleContext,或是否在主题被打破。我怎样才能缩小问题的根源?

如果有人能指出我对GtkStyleContext的一个很好的介绍,我也很感激。官方的API文档对于理解基本概念没有多大帮助。

+0

我不知道你在哪里绘图,但是你只能在绘制虚拟方法中绘制一个小部件,你的代码中有太多东西会导致意外的行为,任何事情都可能这样做 – erick2red

+0

”上面显示的gtk_databox_ruler_draw_ticks'函数是从小部件的绘图函数('GtkWidgetClass-> draw')中调用的。你能指出上面代码中需要修复的东西吗? – dasup

+0

不知道是否有帮助,但你可以看看[这里] (http://erick2red.github.com/blog/2012/08/21/making-you-own-widget/) – erick2red

回答

4

一年多过去后,我不得不考虑这个问题再次,因为它使用GTK3时默认(内置)样式,即当我的程序是没有主题等的系统上使用时,也会发生。安装。

看起来问题的根源在于某些GTK主题为“默认情况”定义了背景色,而其他GTK主题则没有。

GTK3 default theme

… 
* { 
    color: @fg_color; 
    border-color: shade (@bg_color, 0.6); 
    padding: 2px; 
    -GtkWindow-resize-grip-width: 0; 
    -GtkWindow-resize-grip-height: 0; 
    -GtkWindow-decoration-button-layout: 'icon:minimize,maximize,close'; 
} 

GtkWindow, .button, .slider { 
    background-color: @bg_color; 
} 
… 

的阿德维塔主题:

… 
* { 
    /* inherit the color from parent by default */ 
    color: inherit; 
    background-color: @theme_bg_color; 
} 
… 

来获取背景画,我只需要选择具有所有定义的背景颜色的小部件类(最)主题。我使用按钮类为:

gtk_style_context_add_class(style_context, GTK_STYLE_CLASS_BUTTON); 
2

你使用的是什么版本的Ubuntu和GTK3?可能需要拨打gtk_style_context_set_junction_sides()

您可能也有兴趣从GTK的开发者之一Benjamin Otte获得此信息。 How GTK styling works,也可用GTK+3 Styling

+0

我使用的是Ubuntu 12.04,libgtk在3.4.2-0ubuntu0版本中,我添加了'gtk_style_context_set_junction_sides 'GTK_JUNCTION_BOTTOM'设置在'gtk_style_context_add_class'之后,但没有解决它。感谢链接,但我认为它更侧重于CSS端,而我需要更多关于GtkStyl的信息eContext侧(即渲染,保存/恢复是什么,这些类是如何工作的)。 – dasup

1

这里的部分catch可能越来越多,不一定有单一的背景颜色了。

https://developer.gnome.org/gtk3/stable/GtkStyleContext.html#gtk-style-context-get-background-color文档:

“,此功能是远远超过它似乎用处不大,它不应该在新编写的代码中使用CSS没有概念‘背景颜色’,作为背景可以是图像,或渐变,或任何其他模式,包括纯色。“

+0

感谢您指出这一点!请注意,在上面的代码中,我使用'gtk_style_context_get_background_color'只是为了测试/调试目的。真正的代码调用'gtk_render_background',我假定它处理各种背景定义。然而,调用'gtk_render_background'会产生一个黑色的背景,并带有某些主题。 – dasup