Exemple #1
0
static
void mw_paint_tip(GtkWidget *widget, GdkEventExpose *event)
{
	GtkStyle *style;
	GdkWindow *window;
	char *tooltiptext = get_tooltip_text();

	if(tooltiptext == NULL) tooltiptext = g_strdup("oeps");
	pango_layout_set_markup(layout, tooltiptext, strlen(tooltiptext));
	pango_layout_set_wrap(layout, PANGO_WRAP_WORD);
	pango_layout_set_width(layout, 300000);
	style = gtk_widget_get_style (tipwindow);
	window = gtk_widget_get_window (tipwindow);

	gtk_paint_flat_box (style, window, GTK_STATE_NORMAL, GTK_SHADOW_OUT,
			NULL, tipwindow, "tooltip", 0, 0, -1, -1);


	gtk_paint_layout (style, window, GTK_STATE_NORMAL, TRUE,
			NULL, tipwindow, "tooltip", 4, 4, layout);
	/*
	   g_object_unref(layout);
	   */
	g_free(tooltiptext);
	return;
}
Exemple #2
0
static VALUE
style_paint_layout(VALUE self, VALUE gdkwindow, VALUE state_type, VALUE use_text, VALUE area, VALUE widget, VALUE detail, VALUE x, VALUE y, VALUE layout)
{
    gtk_paint_layout(_SELF(self), GDK_WINDOW(RVAL2GOBJ(gdkwindow)),
                     RVAL2STATE(state_type), RVAL2CBOOL(use_text), RVAL2REC(area),
                     GTK_WIDGET(RVAL2GOBJ(widget)), 
                     NIL_P(detail) ? NULL : RVAL2CSTR(detail),
                     NUM2INT(x), NUM2INT(y), PANGO_LAYOUT(RVAL2GOBJ(layout)));
    return self;
}
Exemple #3
0
static gint timeout(gpointer user_data)
{
    GtkWidget *image = user_data;
    PangoLayout *layout;
    GdkRectangle area;
    gint offset_x = 0;

    if (about_timeout < 0)
        return FALSE;

    layout = gtk_widget_create_pango_layout(image, NULL);

    pango_layout_set_markup(layout, about_text, -1);
    pango_layout_set_alignment(layout, PANGO_ALIGN_CENTER);
    pango_layout_set_justify(layout, TRUE);

    if (about_y <= 0 && about_area_y <= 0)
    {
        about_y = image->allocation.width - 80;
        pango_layout_get_pixel_size(layout, &about_area_x, &about_area_y);
        if (about_area_x > image->allocation.width)
        {
            GdkPixmap *old = pixmap;
            gtk_widget_set_size_request(image, about_area_x, 200);

            pixmap = gdk_pixmap_new(image->window, about_area_x, image->allocation.height, -1);
            gdk_pixmap_unref(old);
        }
    }

    if (image->allocation.width > about_area_x)
        offset_x = (image->allocation.width - about_area_x) / 2;

    if (about_y <= 0)
        about_area_y--;

    about_y--;

    area.x = 0;
    area.y = 0;
    area.width = image->allocation.width;
    area.height = image->allocation.height;

    gdk_draw_rectangle(pixmap, gc, TRUE, 0, 0, image->allocation.width, image->allocation.height);

    gtk_paint_layout(image->style, pixmap, GTK_WIDGET_STATE(image), FALSE, &area, image, "about", image->allocation.x + offset_x, about_y, layout);

    gdk_draw_drawable(image->window, gc, pixmap, 0, 0, 0, 0, image->allocation.width, image->allocation.height);

    g_object_unref(layout);

    return TRUE;
}
Exemple #4
0
static void
draw_centered_text (GtkWidget *widget, cairo_t *cr, gint x, gint y, gchar *text)
{
	int width;
	PangoLayout *layout;

	layout = gtk_widget_create_pango_layout (widget, text);

	pango_layout_get_pixel_size (layout, &width, NULL);

	x -= width/2;

	gtk_paint_layout (gtk_widget_get_style(widget), cr,
			  GTK_STATE_NORMAL, TRUE, 
			  widget, NULL, x, y,
			  layout);
	g_object_unref (layout);
}
static void
thunar_text_renderer_render (GtkCellRenderer     *renderer,
                             GdkWindow           *window,
                             GtkWidget           *widget,
                             GdkRectangle        *background_area,
                             GdkRectangle        *cell_area,
                             GdkRectangle        *expose_area,
                             GtkCellRendererState flags)
{
  ThunarTextRenderer *text_renderer = THUNAR_TEXT_RENDERER (renderer);
  GtkStateType        state;
#if !GTK_CHECK_VERSION(2,8,0)
  GdkPoint            points[8];
#else
  cairo_t            *cr;
#endif
  gint                x0, x1, y0, y1;
  gint                text_width;
  gint                text_height;
  gint                x_offset;
  gint                y_offset;

  /* setup the new widget */
  thunar_text_renderer_set_widget (text_renderer, widget);

  if ((flags & GTK_CELL_RENDERER_SELECTED) == GTK_CELL_RENDERER_SELECTED)
    {
      if (GTK_WIDGET_HAS_FOCUS (widget))
        state = GTK_STATE_SELECTED;
      else
        state = GTK_STATE_ACTIVE;
    }
  else if ((flags & GTK_CELL_RENDERER_PRELIT) == GTK_CELL_RENDERER_PRELIT
        && GTK_WIDGET_STATE (widget) == GTK_STATE_PRELIGHT)
    {
      state = GTK_STATE_PRELIGHT;
    }
  else
    {
      if (GTK_WIDGET_STATE (widget) == GTK_STATE_INSENSITIVE)
        state = GTK_STATE_INSENSITIVE;
      else
        state = GTK_STATE_NORMAL;
    }

  /* check if we should follow the prelit state (used for single click support) */
  if (text_renderer->follow_prelit && (flags & GTK_CELL_RENDERER_PRELIT) != 0)
    pango_layout_set_attributes (text_renderer->layout, thunar_pango_attr_list_underline_single ());
  else
    pango_layout_set_attributes (text_renderer->layout, NULL);

  /* setup the wrapping */
  if (text_renderer->wrap_width < 0)
    {
      pango_layout_set_width (text_renderer->layout, -1);
      pango_layout_set_wrap (text_renderer->layout, PANGO_WRAP_CHAR);
    }
  else
    {
      pango_layout_set_width (text_renderer->layout, text_renderer->wrap_width * PANGO_SCALE);
      pango_layout_set_wrap (text_renderer->layout, text_renderer->wrap_mode);
    }

  pango_layout_set_text (text_renderer->layout, text_renderer->text, -1);

  /* calculate the real text dimension */
  pango_layout_get_pixel_size (text_renderer->layout, &text_width, &text_height);

  /* take into account the state indicator (required for calculation) */
  if (text_renderer->follow_state)
    {
      text_width += 2 * text_renderer->focus_width;
      text_height += 2 * text_renderer->focus_width;
    }

  /* calculate the real x-offset */
  x_offset = ((gtk_widget_get_direction (widget) == GTK_TEXT_DIR_RTL) ? (1.0 - renderer->xalign) : renderer->xalign)
           * (cell_area->width - text_width - (2 * renderer->xpad));
  x_offset = MAX (x_offset, 0);

  /* calculate the real y-offset */
  y_offset = renderer->yalign * (cell_area->height - text_height - (2 * renderer->ypad));
  y_offset = MAX (y_offset, 0);

  /* render the state indicator */
  if ((flags & GTK_CELL_RENDERER_SELECTED) == GTK_CELL_RENDERER_SELECTED && text_renderer->follow_state)
    {
      /* calculate the text bounding box (including the focus padding/width) */
      x0 = cell_area->x + x_offset;
      y0 = cell_area->y + y_offset;
      x1 = x0 + text_width;
      y1 = y0 + text_height;

#if GTK_CHECK_VERSION(2,8,0)
      /* Cairo produces nicer results than using a polygon
       * and so we use it directly if possible.
       */
      cr = gdk_cairo_create (window);
      cairo_move_to (cr, x0 + 5, y0);
      cairo_line_to (cr, x1 - 5, y0);
      cairo_curve_to (cr, x1 - 5, y0, x1, y0, x1, y0 + 5);
      cairo_line_to (cr, x1, y1 - 5);
      cairo_curve_to (cr, x1, y1 - 5, x1, y1, x1 - 5, y1);
      cairo_line_to (cr, x0 + 5, y1);
      cairo_curve_to (cr, x0 + 5, y1, x0, y1, x0, y1 - 5);
      cairo_line_to (cr, x0, y0 + 5);
      cairo_curve_to (cr, x0, y0 + 5, x0, y0, x0 + 5, y0);
      gdk_cairo_set_source_color (cr, &widget->style->base[state]);
      cairo_fill (cr);
      cairo_destroy (cr);
#else
      /* calculate a (more or less rounded) polygon */
      points[0].x = x0 + 2; points[0].y = y0;
      points[1].x = x1 - 2; points[1].y = y0;
      points[2].x = x1;     points[2].y = y0 + 2;
      points[3].x = x1;     points[3].y = y1 - 2;
      points[4].x = x1 - 2; points[4].y = y1;
      points[5].x = x0 + 2; points[5].y = y1;
      points[6].x = x0;     points[6].y = y1 - 2;
      points[7].x = x0;     points[7].y = y0 + 2;

      /* render the indicator */
      gdk_draw_polygon (window, widget->style->base_gc[state], TRUE, points, G_N_ELEMENTS (points));
#endif
    }

  /* draw the focus indicator */
  if (text_renderer->follow_state && (flags & GTK_CELL_RENDERER_FOCUSED) != 0)
    {
      gtk_paint_focus (widget->style, window, GTK_WIDGET_STATE (widget), NULL, widget, "icon_view",
                       cell_area->x + x_offset, cell_area->y + y_offset, text_width, text_height);
    }

  /* get proper sizing for the layout drawing */
  if (text_renderer->follow_state)
    {
      text_width -= 2 * text_renderer->focus_width;
      text_height -= 2 * text_renderer->focus_width;
      x_offset += text_renderer->focus_width;
      y_offset += text_renderer->focus_width;
    }

  /* draw the text */
  gtk_paint_layout (widget->style, window, state, TRUE,
                    expose_area, widget, "cellrenderertext",
                    cell_area->x + x_offset + renderer->xpad,
                    cell_area->y + y_offset + renderer->ypad,
                    text_renderer->layout);
}
Exemple #6
0
static gboolean
git_source_view_expose_event (GtkWidget *widget,
                              GdkEventExpose *event)
{
  GitSourceView *sview = (GitSourceView *) widget;
  GitSourceViewPrivate *priv = sview->priv;
  gsize line_start, line_end, line_num, n_lines;
  gint y;
  PangoLayout *layout;
  cairo_t *cr;

  if (priv->paint_source && priv->line_height)
    {
      layout = gtk_widget_create_pango_layout (widget, NULL);
      cr = gdk_cairo_create (widget->window);

      n_lines = git_annotated_source_get_n_lines (priv->paint_source);
      line_start = (event->area.y + priv->y_offset) / priv->line_height;
      line_end = (event->area.y + priv->y_offset
                  + event->area.height + priv->line_height - 1)
        / priv->line_height;

      if (line_end > n_lines)
        line_end = n_lines;
      if (line_start > line_end)
        line_start = line_end;

      for (line_num = line_start; line_num < line_end; line_num++)
        {
          GdkRectangle clip_rect;
          const GitAnnotatedSourceLine *line
            = git_annotated_source_get_line (priv->paint_source, line_num);
          GdkColor color;
          y = line_num * priv->line_height - priv->y_offset;

          git_source_view_set_text_for_commit (layout, line->commit);
          git_commit_get_color (line->commit, &color);

          cairo_set_source_rgb (cr, color.red / 65535.0, color.green / 65535.0,
                                color.blue / 65535.0);
          cairo_rectangle (cr, 0, y, priv->max_hash_length, priv->line_height);
          cairo_fill_preserve (cr);

          /* Invert the color so that the text is guaranteed to be a
             different (albeit clashing) colour */
          color.red = ~color.red;
          color.green = ~color.green;
          color.blue = ~color.blue;
          cairo_set_source_rgb (cr, color.red / 65535.0, color.green / 65535.0,
                                color.blue / 65535.0);
          cairo_save (cr);
          cairo_clip (cr);
          cairo_move_to (cr, 0, y);
          pango_cairo_show_layout (cr, layout);
          cairo_restore (cr);

          git_source_view_set_text_for_line (layout, line);

          clip_rect.x = priv->max_hash_length + GIT_SOURCE_VIEW_GAP;
          clip_rect.width = widget->allocation.width;
          clip_rect.y = y;
          clip_rect.height = priv->line_height;

          gtk_paint_layout (widget->style,
                            widget->window,
                            GTK_WIDGET_STATE (widget),
                            TRUE,
                            &clip_rect,
                            widget,
                            NULL,
                            -priv->x_offset + priv->max_hash_length
                            + GIT_SOURCE_VIEW_GAP,
                            y,
                            layout);
        }

      cairo_destroy (cr);
      g_object_unref (layout);
    }

  return FALSE;
}
Exemple #7
0
static void
gimp_ruler_draw_ticks (GimpRuler *ruler)
{
  GtkWidget        *widget = GTK_WIDGET (ruler);
  GtkStyle         *style  = gtk_widget_get_style (widget);
  GimpRulerPrivate *priv   = GIMP_RULER_GET_PRIVATE (ruler);
  GtkStateType      state  = gtk_widget_get_state (widget);
  GtkAllocation     allocation;
  cairo_t          *cr;
  gint              i;
  gint              width, height;
  gint              xthickness;
  gint              ythickness;
  gint              length, ideal_length;
  gdouble           lower, upper;  /* Upper and lower limits, in ruler units */
  gdouble           increment;     /* Number of pixels per unit */
  gint              scale;         /* Number of units per major unit */
  gdouble           start, end, cur;
  gchar             unit_str[32];
  gint              digit_height;
  gint              digit_offset;
  gint              text_size;
  gint              pos;
  gdouble           max_size;
  GimpUnit          unit;
  PangoLayout      *layout;
  PangoRectangle    logical_rect, ink_rect;

  if (! gtk_widget_is_drawable (widget))
    return;

  gtk_widget_get_allocation (widget, &allocation);

  xthickness = style->xthickness;
  ythickness = style->ythickness;

  layout = gimp_ruler_get_layout (widget, "0123456789");
  pango_layout_get_extents (layout, &ink_rect, &logical_rect);

  digit_height = PANGO_PIXELS (ink_rect.height) + 2;
  digit_offset = ink_rect.y;

  if (priv->orientation == GTK_ORIENTATION_HORIZONTAL)
    {
      width  = allocation.width;
      height = allocation.height - ythickness * 2;
    }
  else
    {
      width  = allocation.height;
      height = allocation.width - ythickness * 2;
    }

  cr = cairo_create (priv->backing_store);
  gdk_cairo_set_source_color (cr, &style->bg[state]);

#if 0
  gtk_paint_box (style, priv->backing_store,
                 GTK_STATE_NORMAL, GTK_SHADOW_OUT,
                 NULL, widget,
                 priv->orientation == GTK_ORIENTATION_HORIZONTAL ?
                 "hruler" : "vruler",
                 0, 0,
                 allocation.width, allocation.height);
#else
  cairo_paint (cr);
#endif

  gdk_cairo_set_source_color (cr, &style->fg[state]);

  if (priv->orientation == GTK_ORIENTATION_HORIZONTAL)
    {
      cairo_rectangle (cr,
                       xthickness,
                       height + ythickness,
                       allocation.width - 2 * xthickness,
                       1);
    }
  else
    {
      cairo_rectangle (cr,
                       height + xthickness,
                       ythickness,
                       1,
                       allocation.height - 2 * ythickness);
    }

  gimp_ruler_get_range (ruler, &lower, &upper, &max_size);

  if ((upper - lower) == 0)
    goto out;

  increment = (gdouble) width / (upper - lower);

  /* determine the scale
   *   use the maximum extents of the ruler to determine the largest
   *   possible number to be displayed.  Calculate the height in pixels
   *   of this displayed text. Use this height to find a scale which
   *   leaves sufficient room for drawing the ruler.
   *
   *   We calculate the text size as for the vruler instead of
   *   actually measuring the text width, so that the result for the
   *   scale looks consistent with an accompanying vruler.
   */
  scale = ceil (max_size);
  g_snprintf (unit_str, sizeof (unit_str), "%d", scale);
  text_size = strlen (unit_str) * digit_height + 1;

  for (scale = 0; scale < G_N_ELEMENTS (ruler_metric.ruler_scale); scale++)
    if (ruler_metric.ruler_scale[scale] * fabs (increment) > 2 * text_size)
      break;

  if (scale == G_N_ELEMENTS (ruler_metric.ruler_scale))
    scale = G_N_ELEMENTS (ruler_metric.ruler_scale) - 1;

  unit = gimp_ruler_get_unit (ruler);

  /* drawing starts here */
  length = 0;
  for (i = G_N_ELEMENTS (ruler_metric.subdivide) - 1; i >= 0; i--)
    {
      gdouble subd_incr;

      /* hack to get proper subdivisions at full pixels */
      if (unit == GIMP_UNIT_PIXEL && scale == 1 && i == 1)
        subd_incr = 1.0;
      else
        subd_incr = ((gdouble) ruler_metric.ruler_scale[scale] /
                     (gdouble) ruler_metric.subdivide[i]);

      if (subd_incr * fabs (increment) <= MINIMUM_INCR)
        continue;

      /* don't subdivide pixels */
      if (unit == GIMP_UNIT_PIXEL && subd_incr < 1.0)
        continue;

      /* Calculate the length of the tickmarks. Make sure that
       * this length increases for each set of ticks
       */
      ideal_length = height / (i + 1) - 1;
      if (ideal_length > ++length)
        length = ideal_length;

      if (lower < upper)
        {
          start = floor (lower / subd_incr) * subd_incr;
          end   = ceil  (upper / subd_incr) * subd_incr;
        }
      else
        {
          start = floor (upper / subd_incr) * subd_incr;
          end   = ceil  (lower / subd_incr) * subd_incr;
        }

      for (cur = start; cur <= end; cur += subd_incr)
        {
          pos = ROUND ((cur - lower) * increment);

          if (priv->orientation == GTK_ORIENTATION_HORIZONTAL)
            {
              cairo_rectangle (cr,
                               pos, height + ythickness - length,
                               1,   length);
            }
          else
            {
              cairo_rectangle (cr,
                               height + xthickness - length, pos,
                               length,                       1);
            }

          /* draw label */
          if (i == 0)
            {
              g_snprintf (unit_str, sizeof (unit_str), "%d", (int) cur);

              if (priv->orientation == GTK_ORIENTATION_HORIZONTAL)
                {
                  pango_layout_set_text (layout, unit_str, -1);
                  pango_layout_get_extents (layout, &logical_rect, NULL);

#if 0
                  gtk_paint_layout (style,
                                    priv->backing_store,
                                    state,
                                    FALSE,
                                    NULL,
                                    widget,
                                    "hruler",
                                    pos + 2,
                                    ythickness + PANGO_PIXELS (logical_rect.y - digit_offset),
                                    layout);
#else
                  cairo_move_to (cr,
                                 pos + 2,
                                 ythickness + PANGO_PIXELS (logical_rect.y - digit_offset));
                  pango_cairo_show_layout (cr, layout);
#endif
                }
              else
                {
                  gint j;

                  for (j = 0; j < (int) strlen (unit_str); j++)
                    {
                      pango_layout_set_text (layout, unit_str + j, 1);
                      pango_layout_get_extents (layout, NULL, &logical_rect);

#if 0
                      gtk_paint_layout (style,
                                        priv->backing_store,
                                        state,
                                        FALSE,
                                        NULL,
                                        widget,
                                        "vruler",
                                        xthickness + 1,
                                        pos + digit_height * j + 2 + PANGO_PIXELS (logical_rect.y - digit_offset),
                                        layout);
#else
                      cairo_move_to (cr,
                                     xthickness + 1,
                                     pos + digit_height * j + 2 + PANGO_PIXELS (logical_rect.y - digit_offset));
                      pango_cairo_show_layout (cr, layout);
#endif

                    }
                }
            }
        }
    }

  cairo_fill (cr);
out:
  cairo_destroy (cr);
}
Exemple #8
0
static gboolean _label_expose(GtkWidget *widget, GdkEventExpose *event)
{
  g_return_val_if_fail(widget != NULL, FALSE);
  g_return_val_if_fail(DTGTK_IS_LABEL(widget), FALSE);
  g_return_val_if_fail(event != NULL, FALSE);
  GtkStyle *style=gtk_rc_get_style_by_paths(gtk_settings_get_default(), NULL,"GtkButton", GTK_TYPE_BUTTON);
  if(!style) style = gtk_rc_get_style(widget);
  // uninitialized?
  if(style->depth == -1) return FALSE;
  int state = gtk_widget_get_state(widget);
  GtkAllocation allocation;
  gtk_widget_get_allocation(widget, &allocation);
  int x = allocation.x;
  int y = allocation.y;
  int width = allocation.width;
  int height = allocation.height;

  // Formating the display of text and draw it...
  PangoLayout *layout;
  layout = gtk_widget_create_pango_layout(widget,NULL);
  pango_layout_set_font_description(layout,style->font_desc);
  const gchar *text=gtk_label_get_text(GTK_LABEL(widget));
  pango_layout_set_text(layout,text,-1);
  GdkRectangle t= {x,y,x+width,y+height};
  int pw,ph;
  pango_layout_get_pixel_size(layout,&pw,&ph);


  // Begin cairo drawing

  cairo_t *cr;
  cr = gdk_cairo_create(gtk_widget_get_window(widget));

  cairo_set_source_rgba(cr,
                        /* style->fg[state].red/65535.0,
                         style->fg[state].green/65535.0,
                         style->fg[state].blue/65535.0,*/
                        1,1,1,
                        0.10
                       );

  cairo_set_antialias(cr,CAIRO_ANTIALIAS_NONE);

  cairo_set_line_width(cr,1.0);
  cairo_set_line_cap(cr,CAIRO_LINE_CAP_ROUND);
  if( DTGTK_LABEL(widget)->flags&DARKTABLE_LABEL_UNDERLINED )
  {
    cairo_move_to(cr,x,y+height-2);
    cairo_line_to(cr,x+width,y+height-2);
    cairo_stroke(cr);
  }
  else if( DTGTK_LABEL(widget)->flags&DARKTABLE_LABEL_BACKFILLED )
  {
    cairo_rectangle(cr,x,y,width,height);
    cairo_fill(cr);
  }
  else if( DTGTK_LABEL(widget)->flags&DARKTABLE_LABEL_TAB )
  {
    int rx=x,rw=pw+2;
    if( DTGTK_LABEL(widget)->flags&DARKTABLE_LABEL_ALIGN_RIGHT ) rx=x+width-pw-8;
    cairo_rectangle(cr,rx,y,rw+4,height-1);
    cairo_fill(cr);

    if( DTGTK_LABEL(widget)->flags&DARKTABLE_LABEL_ALIGN_RIGHT )
    {
      // /|
      cairo_move_to(cr,x+width-rw-6,y);
      cairo_line_to(cr,x+width-rw-6-15,y+height-2);
      cairo_line_to(cr,x+width-rw-6,y+height-2);
      cairo_fill(cr);

      // hline
      cairo_move_to(cr,x,y+height-1);
      cairo_line_to(cr,x+width-rw-6,y+height-1);
      cairo_stroke(cr);
    }
    else
    {
      // |
      cairo_move_to(cr,x+rw+4,y);
      cairo_line_to(cr,x+rw+4+15,y+height-2);
      cairo_line_to(cr,x+rw+4,y+height-2);
      cairo_fill(cr);

      // hline
      cairo_move_to(cr,x+rw+4,y+height-1);
      cairo_line_to(cr,x+width,y+height-1);
      cairo_stroke(cr);
    }
  }
  cairo_set_antialias(cr,CAIRO_ANTIALIAS_DEFAULT);
  cairo_destroy(cr);

  // draw text
  int lx=x+4, ly=y+((height/2.0)-(ph/2.0));
  if( DTGTK_LABEL(widget)->flags&DARKTABLE_LABEL_ALIGN_RIGHT ) lx=x+width-pw-6;
  else if( DTGTK_LABEL(widget)->flags&DARKTABLE_LABEL_ALIGN_CENTER ) lx=(width/2.0)-(pw/2.0);
  gtk_paint_layout(style, gtk_widget_get_window(widget), state,TRUE,&t,widget,"label",lx,ly,layout);

  return FALSE;
}
Exemple #9
0
static gboolean
_button_expose (GtkWidget *widget, GdkEventExpose *event)
{
  g_return_val_if_fail (widget != NULL, FALSE);
  g_return_val_if_fail (DTGTK_IS_BUTTON(widget), FALSE);
  g_return_val_if_fail (event != NULL, FALSE);
  GtkStyle *style=gtk_widget_get_style(widget);
  int state = gtk_widget_get_state(widget);

  /* update paint flags depending of states */
  int flags = DTGTK_BUTTON (widget)->icon_flags;

  /* set inner border */
  int border = (flags&CPF_DO_NOT_USE_BORDER)?2:4;

  /* prelight */
  if (state == GTK_STATE_PRELIGHT)
    flags |= CPF_PRELIGHT;
  else
    flags &=~CPF_PRELIGHT;


  /* create pango text settings if label exists */
  PangoLayout *layout=NULL;
  int pw=0,ph=0;
  const gchar *text=gtk_button_get_label (GTK_BUTTON (widget));
  if (text)
  {
    layout = gtk_widget_create_pango_layout (widget,NULL);
    pango_layout_set_font_description (layout,style->font_desc);
    pango_layout_set_text (layout,text,-1);
    pango_layout_get_pixel_size (layout,&pw,&ph);
  }

  /* begin cairo drawing */
  cairo_t *cr;
  cr = gdk_cairo_create (gtk_widget_get_window(widget));

  GtkAllocation allocation;
  gtk_widget_get_allocation(widget, &allocation);
  int x = allocation.x;
  int y = allocation.y;
  int width = allocation.width;
  int height = allocation.height;

  /* draw standard button background if not transparent */
  if( (flags & CPF_STYLE_FLAT ))
  {
    if( state != GTK_STATE_NORMAL )
    {
      cairo_rectangle (cr,x,y,width,height);
      cairo_set_source_rgba (cr,
                             style->bg[state].red/65535.0,
                             style->bg[state].green/65535.0,
                             style->bg[state].blue/65535.0,
                             0.5);
      cairo_fill (cr);
    }
  }
  else if( !(flags & CPF_BG_TRANSPARENT) )
  {
    /* draw default boxed button */
    gtk_paint_box (gtk_widget_get_style(widget), gtk_widget_get_window(widget),
                   gtk_widget_get_state(widget),
                   GTK_SHADOW_OUT, NULL, widget, "button",
                   x, y, width, height);
  }

  if (flags & CPF_IGNORE_FG_STATE)
    state = GTK_STATE_NORMAL;

  cairo_set_source_rgb (cr,
                        style->fg[state].red/65535.0,
                        style->fg[state].green/65535.0,
                        style->fg[state].blue/65535.0);

  /* draw icon */
  if (DTGTK_BUTTON (widget)->icon)
  {
    if (text)
      DTGTK_BUTTON (widget)->icon (cr,x+border,y+border,height-(border*2),height-(border*2),flags);
    else
      DTGTK_BUTTON (widget)->icon (cr,x+border,y+border,width-(border*2),height-(border*2),flags);
  }
  cairo_destroy (cr);

  /* draw label */
  if (text)
  {
    int lx=x+2, ly=y+((height/2.0)-(ph/2.0));
    if (DTGTK_BUTTON (widget)->icon) lx += width;
    GdkRectangle t= {x,y,x+width,y+height};
    gtk_paint_layout(style,gtk_widget_get_window(widget), GTK_STATE_NORMAL,TRUE,&t,widget,"label",lx,ly,layout);
  }

  return FALSE;
}
Exemple #10
0
static void 
draw_ping_graph (Netinfo *netinfo)
{
	cairo_t *cr;
	GtkStyle *style;
	GtkWidget *widget;
	PangoLayout *layout;
	gint ntodisplay = 5;
	gint rangemin, rangemax;
	PingGraphBarData *bar_data;
	gdouble max;
	gint width, height;
	gint font_height, offset;
	gint bar_height, separator_height;
	gdouble scale_factor;
	gint line1h, line2h;
	gint index;
	gint step, x, h;
	gchar *tmpstr;

	widget = netinfo->graph;
	cr = gdk_cairo_create (gtk_widget_get_window(widget));
	style = gtk_widget_get_style(widget);

	rangemax = packets_transmitted;
	rangemin = MAX (0, rangemax - ntodisplay);

	bar_data = g_newa (PingGraphBarData, ntodisplay);
	max = get_bar_data (netinfo, bar_data, ntodisplay, rangemin,
			    rangemax);

	/* Created up here so we can get the geometry info. */
	layout = gtk_widget_create_pango_layout (widget, _("Time (ms):"));
	/* We guess that the first label is representative. */
	pango_layout_get_pixel_size (layout, NULL, &font_height);
	width = gtk_widget_get_allocated_width (widget);
	height = gtk_widget_get_allocated_height (widget);

	offset = 0.05*height;
	bar_height = height - 2.5*font_height - offset;
	scale_factor = bar_height / max;
	separator_height = bar_height + offset;
	line1h = bar_height + 0.125*font_height + offset;
	line2h = bar_height + 1.25*font_height + offset;

	gtk_paint_box (style, cr, GTK_STATE_NORMAL, GTK_SHADOW_ETCHED_IN, 
		       widget, NULL, 0, 0, width, height);

	gtk_paint_layout (style, cr, GTK_STATE_NORMAL, TRUE, 
			  widget, NULL, 0.02*width, line1h,
			  layout);
	g_object_unref (layout);

	layout = gtk_widget_create_pango_layout (widget, _("Seq. No.:"));
	gtk_paint_layout (style, cr, GTK_STATE_NORMAL, TRUE, 
			  widget, NULL, 0.02*width, line2h,
			  layout);
	g_object_unref (layout);

	gtk_paint_hline (style, cr, GTK_STATE_NORMAL, widget, NULL,
			 0.02*width, 0.98*width, separator_height);

	index = 0;
	step = width / (ntodisplay + 1.0);
	for (x = 1.5*step; x < width; x += step) {
		if (bar_data[index].valid) {
			h = scale_factor*bar_data[index].value;
			gtk_paint_flat_box (style, cr, GTK_STATE_SELECTED,
					    GTK_SHADOW_ETCHED_IN, widget,
					    NULL, x - 0.4*step,
					    offset + bar_height - h,
					    0.8*step, h);
			tmpstr = g_strdup_printf ("%.2f", bar_data[index].value);
		} else {
			tmpstr = g_strdup ("-");
		}
		draw_centered_text (widget, cr, x, line1h, tmpstr);
		g_free (tmpstr);
		if (index + rangemin + 1 <= rangemax) {
			tmpstr = g_strdup_printf ("%d", index + rangemin + 1);
		} else {
			tmpstr = g_strdup ("-");
		}
		draw_centered_text (widget, cr, x, line2h, tmpstr);
		g_free (tmpstr);
		index++;
	}

	cairo_destroy (cr);
}
Exemple #11
0
static void
gwy_vruler_real_draw_ticks(GwyRuler *ruler,
                           gint pixelsize,
                           gint min_label_spacing,
                           gint min_tick_spacing)
{
    gdouble lower, upper, max;
    gint text_size, labels, i, scale_depth;
    gdouble range, measure, base, step, first;
    GwyScaleScale scale;
    GwySIValueFormat *format;
    PangoLayout *layout;
    PangoRectangle rect;
    gchar *unit_str;
    gint unitstr_len, j;
    gint width, tick_length, xthickness, ythickness;
    gboolean units_drawn;
    GtkWidget *widget;
    GdkGC *gc;
    gint digit_width, digit_xoffset;
    const gchar *utf8p, *utf8next;
    gint ascent, descent, ypos;
    struct { GwyScaleScale scale; double base; } tick_info[4];

    widget = GTK_WIDGET(ruler);
    xthickness = widget->style->xthickness;
    ythickness = widget->style->ythickness;

    format = ruler->vformat;
    upper = ruler->upper;
    lower = ruler->lower;
    if (upper <= lower || pixelsize < 2 || pixelsize > 10000)
        return;
    max = ruler->max_size;
    if (max == 0)
        max = MAX(fabs(lower), fabs(upper));

    range = upper - lower;
    measure = range/format->magnitude / pixelsize;
    max /= format->magnitude;

    switch (ruler->units_placement && ruler->units) {
        case GWY_UNITS_PLACEMENT_AT_ZERO:
        unit_str
            = g_strdup_printf("%d %s",
                              (lower > 0) ? (gint)(lower/format->magnitude) : 0,
                              format->units);
        break;

        default:
        unit_str = g_strdup_printf("%d", (gint)max);
        break;
    }

    layout = gtk_widget_create_pango_layout(widget, "012456789");
    pango_layout_get_extents(layout, NULL, &rect);

    digit_width = PANGO_PIXELS(rect.width)/10 + 1;
    digit_xoffset = rect.x;

    pango_layout_set_markup(layout, unit_str, -1);
    pango_layout_get_extents(layout, &rect, NULL);
    ascent = PANGO_ASCENT(rect);
    descent = PANGO_DESCENT(rect);

    text_size = g_utf8_strlen(pango_layout_get_text(layout), -1);
    text_size = PANGO_PIXELS(ascent + descent)*text_size;

    /* reallocate unit_str with some margin */
    unitstr_len = strlen(unit_str) + 16;
    unit_str = g_renew(gchar, unit_str, unitstr_len);

    /* fit as many labels as you can */
    labels = floor(pixelsize/(text_size + ythickness + min_label_spacing));
    labels = MAX(labels, 1);
    if (labels > 6)
        labels = 6 + (labels - 5)/2;

    step = range/format->magnitude / labels;
    base = compute_base(step, 10);
    step /= base;
    if (step >= 5.0 || base < 1.0) {
        scale = GWY_SCALE_1;
        base *= 10;
    }
    else if (step >= 2.5)
        scale = GWY_SCALE_5;
    else if (step >= 2.0)
        scale = GWY_SCALE_2_5;
    else
        scale = GWY_SCALE_2;
    step = steps[scale];

    /* draw labels */
    width = widget->allocation.width - 2*xthickness;
    units_drawn = FALSE;
    first = floor(lower/format->magnitude / (base*step))*base*step;
    for (i = 0; ; i++) {
        gint pos;
        gdouble val;

        val = i*step*base + first;
        pos = floor((val - lower/format->magnitude)/measure);
        if (pos >= pixelsize)
            break;
        if (pos < 0)
            continue;
        if (!units_drawn
            && (upper < 0 || val >= 0)
            && ruler->units_placement == GWY_UNITS_PLACEMENT_AT_ZERO
            && ruler->units) {
            g_snprintf(unit_str, unitstr_len, "%d %s",
                       ROUND(val), format->units);
            units_drawn = TRUE;
        }
        else
            g_snprintf(unit_str, unitstr_len, "%d", ROUND(val));

        pango_layout_set_markup(layout, unit_str, -1);
        utf8p = unit_str;
        utf8next = g_utf8_next_char(utf8p);
        j = 0;
        ypos = pos + ythickness + 1;
        while (*utf8p) {
            pango_layout_set_text(layout, utf8p, utf8next - utf8p);
            pango_layout_get_extents(layout, &rect, NULL);
            gtk_paint_layout(widget->style,
                             ruler->backing_store,
                             GTK_WIDGET_STATE(widget),
                             FALSE,
                             NULL,
                             widget,
                             "vruler",
                             xthickness + 1 + PANGO_PIXELS(digit_xoffset),
                             ypos,
                             layout);
            utf8p = utf8next;
            utf8next = g_utf8_next_char(utf8p);
            ypos += PANGO_PIXELS(PANGO_ASCENT(rect) + PANGO_DESCENT(rect)) + 2;
            j++;
        }
    }

    /* draw tick marks, from smallest to largest */
    scale_depth = 0;
    while (scale && scale_depth < (gint)G_N_ELEMENTS(tick_info)) {
        tick_info[scale_depth].scale = scale;
        tick_info[scale_depth].base = base;
        scale = next_scale(scale, &base, measure, min_tick_spacing);
        scale_depth++;
    }
    scale_depth--;

    gc = widget->style->fg_gc[GTK_STATE_NORMAL];
    while (scale_depth > -1) {
        tick_length = width/(scale_depth + 1) - 2;
        scale = tick_info[scale_depth].scale;
        base = tick_info[scale_depth].base;
        step = steps[scale];
        first = floor(lower/format->magnitude / (base*step))*base*step;
        for (i = 0; ; i++) {
            gint pos;
            gdouble val;

            val = (i + 0.000001)*step*base + first;
            pos = floor((val - lower/format->magnitude)/measure);
            if (pos >= pixelsize)
                break;
            if (pos < 0)
                continue;

            gdk_draw_line(ruler->backing_store, gc,
                          width + xthickness - tick_length, pos,
                          width + xthickness, pos);
        }
        scale_depth--;
    }

    g_free(unit_str);
    g_object_unref(layout);
}
Exemple #12
0
static gint
line_numbers_expose (GtkWidget      *widget,
                     GdkEventExpose *event)
{
	GtkTextView *text_view;
	GdkWindow *win;
//	GtkStyle *style;
	PangoLayout *layout;
	PangoAttrList *alist;
	PangoAttribute *attr;
	GArray *numbers;
	GArray *pixels;
	gint y1, y2;
	gint count;
	gint layout_width;
	gint justify_width = 0;
	gint i;
//	gchar *str;
	gchar str [8];  /* we don't expect more than ten million lines */
	GdkGC *gc;
	gint height;
	
	if (line_number_visible){{{{{	// omit calculation
	
	text_view = GTK_TEXT_VIEW (widget);
	
	/* See if this expose is on the line numbers window */
/*	left_win = gtk_text_view_get_window (text_view,
	                                     GTK_TEXT_WINDOW_LEFT);
	right_win = gtk_text_view_get_window (text_view,
	                                      GTK_TEXT_WINDOW_RIGHT);
	
	if (event->window == left_win)
	{
		type = GTK_TEXT_WINDOW_LEFT;
		target = event->window;
	}
	else if (event->window == right_win)
	{
		type = GTK_TEXT_WINDOW_RIGHT;
		target = right_win;
	}
	else
		return FALSE;
*/	
	win = gtk_text_view_get_window (text_view,
	                                GTK_TEXT_WINDOW_LEFT);
	if (event->window != win)
		return FALSE;
	
//	style = gtk_style_copy (widget->style);
//	style = gtk_style_copy (gtk_widget_get_default_style());
	
	y1 = event->area.y;
	y2 = y1 + event->area.height;
	
	gtk_text_view_window_to_buffer_coords (text_view,
	                                       GTK_TEXT_WINDOW_LEFT,
	                                       0,
	                                       y1,
	                                       NULL,
	                                       &y1);
	
	gtk_text_view_window_to_buffer_coords (text_view,
	                                       GTK_TEXT_WINDOW_LEFT,
	                                       0,
	                                       y2,
	                                       NULL,
	                                       &y2);
	
	numbers = g_array_new (FALSE, FALSE, sizeof (gint));
	pixels = g_array_new (FALSE, FALSE, sizeof (gint));
	
	get_lines (text_view,
	           y1,
	           y2,
	           pixels,
	           numbers,
	           &count);
	
	/* a zero-lined document should display a "1"; we don't need to worry about
	scrolling effects of the text widget in this special case */
	
	if (count == 0)
	{
		gint y = 0;
		gint n = 0;
		count = 1;
		g_array_append_val (pixels, y);
		g_array_append_val (numbers, n);
	}
	
DV({g_print("Painting line numbers %d - %d\n",
			g_array_index(numbers, gint, 0),
			g_array_index(numbers, gint, count - 1));	});
	
	layout = gtk_widget_create_pango_layout (widget, "");
	
//	str = g_strdup_printf ("%d", gtk_text_buffer_get_line_count(text_view->buffer));
	g_snprintf (str, sizeof (str),
			"%d", MAX (99, gtk_text_buffer_get_line_count(text_view->buffer)));
	pango_layout_set_text (layout, str, -1);
//	g_free (str);
	
	pango_layout_get_pixel_size (layout, &layout_width, NULL);
	
	min_number_window_width = calculate_min_number_window_width(widget);
	if (layout_width > min_number_window_width)
		gtk_text_view_set_border_window_size (text_view,
			GTK_TEXT_WINDOW_LEFT, layout_width + margin + submargin);
	else {
//		if ((gtk_text_view_get_border_window_size (text_view, GTK_TEXT_WINDOW_LEFT) - 5) > layout_width) {
			gtk_text_view_set_border_window_size (text_view,
				GTK_TEXT_WINDOW_LEFT, min_number_window_width + margin + submargin);
//		}
		justify_width = min_number_window_width - layout_width;
	}
	
	pango_layout_set_width (layout, layout_width);
	pango_layout_set_alignment (layout, PANGO_ALIGN_RIGHT);
	
	alist = pango_attr_list_new();
	attr = pango_attr_foreground_new(
		widget->style->text_aa->red,
		widget->style->text_aa->green,
		widget->style->text_aa->blue);
	attr->start_index = 0;
	attr->end_index = G_MAXUINT;
	pango_attr_list_insert(alist, attr);
	pango_layout_set_attributes(layout, alist);
	pango_attr_list_unref(alist);
	
	/* Draw fully internationalized numbers! */
	
	i = 0;
	while (i < count)
	{
		gint pos;
		
		gtk_text_view_buffer_to_window_coords (text_view,
		                                       GTK_TEXT_WINDOW_LEFT,
		                                       0,
		                                       g_array_index (pixels, gint, i),
		                                       NULL,
		                                       &pos);
		
//		str = g_strdup_printf ("%d", g_array_index (numbers, gint, i) + 1);
		g_snprintf (str, sizeof (str),
				"%d", g_array_index (numbers, gint, i) + 1);
		
		pango_layout_set_text (layout, str, -1);
		
		gtk_paint_layout (widget->style,
		                  win,
		                  GTK_WIDGET_STATE (widget),
		                  FALSE,
		                  NULL,
		                  widget,
		                  NULL,
#if GTK_CHECK_VERSION(2, 6, 0)  // Is this solution???
		                  layout_width + justify_width + margin / 2 + 1,
#else
		                  layout_width + justify_width + margin / 2,
#endif
		                  pos,
		                  layout);
//		g_free (str);
		
		++i;
	}
	
	g_array_free (pixels, TRUE);
	g_array_free (numbers, TRUE);
	
	g_object_unref (G_OBJECT (layout));
//	g_object_ref (G_OBJECT (style));
	
	/* don't stop emission, need to draw children */
	
	}}}}}
/* TODO remove redundant code */
static void 
i7_cell_renderer_transcript_render(GtkCellRenderer *self, GdkWindow *window, GtkWidget *widget, GdkRectangle *background_area, GdkRectangle *cell_area, GdkRectangle *expose_area, GtkCellRendererState flags) 
{
	I7_CELL_RENDERER_TRANSCRIPT_USE_PRIVATE;
	
	int x, y, width, height;
	unsigned xpad, ypad, transcript_width;
	GtkStateType state;
	cairo_t *cr;
	PangoRectangle command_rect;
	PangoLayout *layout;
	GtkStyle *style = gtk_widget_get_style(widget);

	/* Get the size we calculated earlier and then take the padding into account */
	g_object_get(self, "xpad", &xpad, "ypad", &ypad, NULL);
	gtk_cell_renderer_get_size(self, widget, cell_area, &x, &y, &width, &height);
	x += cell_area->x + (int)xpad;
	y += cell_area->y + (int)ypad;
	width -= (int)xpad * 2;
	height -= (int)ypad * 2;
	
	/* Decide what state to draw the widget components in */ 
	switch(flags) {
		case GTK_CELL_RENDERER_PRELIT:
			state = GTK_STATE_PRELIGHT;
			break;
		case GTK_CELL_RENDERER_INSENSITIVE:
			state = GTK_STATE_INSENSITIVE;
			break;
		default:
			state = GTK_STATE_NORMAL;
	}

	/* Get a cairo context to draw the rectangles on directly; use GTK themed
	 drawing to draw everything else */
	cr = gdk_cairo_create(GDK_DRAWABLE(window));

	/* Draw the command */
	layout = gtk_widget_create_pango_layout(widget, priv->command);
	pango_layout_get_pixel_extents(layout, NULL, &command_rect);

	set_rgb_style(cr, STYLE_COMMAND);
	cairo_rectangle(cr, (double)x, (double)y, 
	    (double)width, (double)(command_rect.height + priv->text_padding * 2));
	cairo_fill(cr);
	gtk_paint_layout(style, window, state, TRUE, cell_area, widget, NULL, 
	    	x + priv->text_padding, y + priv->text_padding, 
	    	layout);
	g_object_unref(layout);

	/* Draw the transcript text */
	transcript_width = priv->default_width / 2 - xpad;
	if(priv->changed)
		set_rgb_style(cr, STYLE_CHANGED);
	else
		set_rgb_style(cr, STYLE_UNCHANGED);

	cairo_rectangle(cr, 
	    (double)x, 
	    (double)(y + command_rect.height + priv->text_padding * 2), 
	    (double)(width / 2), 
	    (double)(height - command_rect.height - priv->text_padding * 2));
	cairo_fill(cr);
	layout = gtk_widget_create_pango_layout(widget, NULL);
	pango_layout_set_markup(layout, priv->transcript_text, -1);
	pango_layout_set_width(layout, (int)(transcript_width - priv->text_padding * 2) * PANGO_SCALE);
	pango_layout_set_wrap(layout, PANGO_WRAP_WORD_CHAR);
	gtk_paint_layout(style, window, state, TRUE, cell_area, widget, NULL, 
	    x + (int)priv->text_padding, 
	    y + command_rect.height + (int)priv->text_padding * 3, 
		layout);
	g_object_unref(layout);
	
	/* Draw the expected text */
	switch(priv->match_type) {
		case CANT_COMPARE:
			set_rgb_style(cr, STYLE_NO_EXPECTED);
			break;
		case NO_MATCH:
			set_rgb_style(cr, STYLE_NO_MATCH);
			break;
		case NEAR_MATCH:
			set_rgb_style(cr, STYLE_NEAR_MATCH);
			break;
		case EXACT_MATCH:
		default:
			set_rgb_style(cr, STYLE_EXACT_MATCH);
			break;
	}

	cairo_rectangle(cr, 
	    (double)(x + width / 2), 
	    (double)(y + command_rect.height + priv->text_padding * 2), 
	    (double)(width / 2), 
	    (double)(height - command_rect.height - priv->text_padding * 2));
	cairo_fill(cr);
	layout = gtk_widget_create_pango_layout(widget, NULL);
	pango_layout_set_markup(layout, priv->expected_text, -1);
	pango_layout_set_width(layout, (int)(transcript_width - priv->text_padding * 2) * PANGO_SCALE);
	pango_layout_set_wrap(layout, PANGO_WRAP_WORD_CHAR);
	gtk_paint_layout(style, window, state, TRUE, cell_area, widget, NULL,
	    x + width / 2 + (int)priv->text_padding, 
	    y + command_rect.height + (int)priv->text_padding * 3, 
		layout);
	g_object_unref(layout);

	/* Draw some lines */
	gtk_paint_hline(style, window, state, cell_area, widget, NULL, 
	    x, x + width, 
	    y + command_rect.height + priv->text_padding * 2);
	gtk_paint_vline(style, window, state, cell_area, widget, NULL, 
	    y + command_rect.height + priv->text_padding * 2, y + height, 
	    x + width / 2);
	
	/* Draw a border around the highlighted node */
	if(priv->current) {
		cairo_set_line_width(cr, 4.0);
		set_rgb_style(cr, STYLE_HIGHLIGHT);
		cairo_rectangle(cr, (double)x + 2.0, (double)y + 2.0, 
			(double)width - 4.0, (double)height - 4.0);
		cairo_stroke(cr);
	}

	/* Draw a border around the active node */
	if(priv->played) {
		cairo_set_line_width(cr, 2.0);
		set_rgb_style(cr, STYLE_ACTIVE);
		cairo_rectangle(cr, (double)x + 1.0, (double)y + 1.0, 
			(double)width - 2.0, (double)height - 2.0);
		cairo_stroke(cr);
	}
	
	cairo_destroy(cr);
}
static void
freetuxtv_cellrenderer_channelslist_render (GtkCellRenderer *cell,
    GdkWindow       *window,
    GtkWidget       *widget,
    GdkRectangle    *background_area,
    GdkRectangle    *cell_area,
    GdkRectangle    *expose_area,
    guint            flags)
#endif
{
	FreetuxTVCellRendererChannelsList *self = FREETUXTV_CELLRENDERER_CHANNELSLIST (cell);
	
	gint width, height;
	PangoLayout *layout;

	gboolean is_selected = FALSE;
	gboolean is_playing = FALSE;
	
	if ((flags & GTK_CELL_RENDERER_SELECTED) != 0){
		is_selected = TRUE;
	}

	if(self->type == CELLRENDERER_TYPE_CHANNEL){
		if(self->is_playing){
			is_playing = TRUE;
		}
	}

#if GTK_API_VERSION == 3
	
	// Set the cell state
	GtkStateFlags state = GTK_STATE_FLAG_NORMAL;
	if(is_selected){
		if(self->type == CELLRENDERER_TYPE_CHANNEL){
			state = GTK_STATE_FLAG_SELECTED;
		}else{
			state = GTK_STATE_FLAG_ACTIVE;
		}
	}

	// Define the style of the row.
	GtkStyleContext *pStyleContext;
	pStyleContext = gtk_widget_get_style_context (GTK_WIDGET(widget));
	gtk_style_context_save(pStyleContext);
	gtk_style_context_set_state(pStyleContext, state);
	if(self->type == CELLRENDERER_TYPE_CHANNEL){
		gtk_style_context_add_class (pStyleContext, GTK_STYLE_CLASS_CELL);
	}else{
		gtk_style_context_add_class (pStyleContext, GTK_STYLE_CLASS_BUTTON);
	}

	freetuxtv_cellrenderer_channelslist_get_preferred_width(cell, widget, NULL, &width);
	freetuxtv_cellrenderer_channelslist_get_preferred_height_for_width(cell, widget, width, NULL, &height);
#else
	GtkStyle* pStyle;
	pStyle = widget->style;

	GtkStateType state;
	state = GTK_STATE_NORMAL;
	if(is_selected){
		state = GTK_STATE_SELECTED;
	}

	freetuxtv_cellrenderer_channelslist_get_size (cell, widget, cell_area,
	    NULL, NULL,
	    &width, &height);
#endif

	// Build the layout
	layout = gtk_widget_create_pango_layout (widget, self->name);
	//pango_layout_set_width(layout, 700);
	//pango_layout_set_height(layout, 20);
	pango_layout_set_ellipsize (layout, PANGO_ELLIPSIZE_END);
	if(is_playing){
		PangoFontDescription *desc;
		desc = pango_font_description_new();
		pango_font_description_set_weight (desc, PANGO_WEIGHT_BOLD);
		pango_font_description_set_style (desc, PANGO_STYLE_ITALIC);
		pango_layout_set_font_description (layout, desc);
		pango_font_description_free(desc);
	}

	// gtk_paint_flat_box (widget->style, window, GTK_STATE_SELECTED,
	//     GTK_SHADOW_NONE , NULL, widget,
	//     NULL,
	//     0, cell_area->y,
	//     cell_area->x + width, cell_area->height);
	
	// gtk_paint_hline (widget->style, window, state,
	//     NULL, widget, NULL,
	//     0, widget->allocation.width, cell_area->y);
	//	 gtk_paint_hline (widget->style, window, state,
	//	     NULL, widget, NULL,
	//	     cell_area->x, cell_area->width, cell_area->y + 2);
	//		 gtk_paint_hline (widget->style, window, state,
	//		     NULL, widget, NULL,
	//		     0, 176, cell_area->y + 3);

	GdkPixbuf* logo;

	// If the cell contain a channel
	if(self->type == CELLRENDERER_TYPE_CHANNEL){

		// Backgroung of the cell
#if GTK_API_VERSION == 3
		gtk_style_context_set_state (pStyleContext, state);
		// gtk_style_context_set_background (pStyleContext, window); // This block the main loop

		gtk_render_background (pStyleContext, cr,
		    0, cell_area->y,
		    cell_area->x + width, cell_area->height);
		gtk_render_frame (pStyleContext, cr, 0, cell_area->y, cell_area->x + width, cell_area->height);
#else
		if(state != GTK_STATE_NORMAL){
			// gtk_style_set_background (pStyle, window, state); // This block the main loop
			gtk_style_apply_default_background  (pStyle, window, TRUE, state, NULL,
				0, cell_area->y, cell_area->x + width, cell_area->height);
		}
#endif

		//static int count = 0;
		//count++;
		//g_print("cell(%d) : %d %d\n", count, cell_area->x, width);

		// Display the logo and text of the cell
		logo = gdk_pixbuf_new_from_file(self->logo, NULL);

		int cell_xpad;
		int cell_ypad;

#if GTK_API_VERSION == 3
		gtk_cell_renderer_get_padding (cell, &cell_xpad, &cell_ypad);

		// Render the logo
		gdk_cairo_set_source_pixbuf(cr, logo,
		    (double)cell_xpad + 1.0, cell_area->y + (double)cell_ypad + 1.0);
		cairo_paint(cr);

		// Render the channel name
		gtk_render_layout (pStyleContext, cr,
		    cell_xpad * 2 + gdk_pixbuf_get_width(logo) + 5,
		    cell_area->y + 15,
		    layout);

#else
		cell_xpad = cell->xpad;
		cell_ypad = cell->ypad;

		// Render the logo
		gdk_draw_pixbuf (GDK_DRAWABLE(window), NULL, logo,
		    0, 0, cell_xpad + 1, cell_area->y + cell_ypad + 1,
		    -1, -1,
		    GDK_RGB_DITHER_NONE, 0,0);
		
		// Render the channel name
		gtk_paint_layout (widget->style, window, state,
		    TRUE, NULL, widget, NULL,
		    cell->xpad * 2 + gdk_pixbuf_get_width(logo) + 5, cell_area->y + 15,
		    layout);
#endif

		if(logo){
			g_object_unref(logo);
			logo = NULL;
		}
	}

	// If the cell contain a group
	if(self->type == CELLRENDERER_TYPE_CHANNELS_GROUP){

#if GTK_API_VERSION == 3
		int x = background_area->x;
        int y = background_area->y;
		width = background_area->width;
		height = background_area->height;

		// Background of the cell
		gtk_render_background (pStyleContext, cr,
		    x, y, width, height);
		gtk_render_frame (pStyleContext, cr,
		    x, y, width, height);

		//g_print("cell_bg %s : x=%d, y=%d\n", self->name, background_area->x, background_area->y);
		//g_print("cell %s : x=%d, y=%d, w=%d, h=%d\n", self->name, x, y, width, height);

		// Render the group name
		gtk_render_layout (pStyleContext, cr,
		    cell_area->x, cell_area->y + 3,
		    layout);
#else
		// Background of the cell
		gtk_style_apply_default_background  (widget->style, window, TRUE,
		    state, NULL,
		    0, cell_area->y, cell_area->x + width, cell_area->height);

		// Render the group name
		gtk_paint_layout (widget->style, window, state,
		    TRUE, NULL, widget, NULL,
		    cell_area->x, cell_area->y + 3, layout);
#endif
	}

#if GTK_API_VERSION == 3
	gtk_style_context_restore(pStyleContext);
#endif
}
static void fm_cell_renderer_text_render(GtkCellRenderer *cell,
                                         GdkDrawable *window,
                                         GtkWidget *widget,
                                         GdkRectangle *background_area,
                                         GdkRectangle *cell_area,
                                         GdkRectangle *expose_area,
                                         GtkCellRendererState flags)
#endif
{
    FmCellRendererText *self = FM_CELL_RENDERER_TEXT(cell);
#if GTK_CHECK_VERSION(3, 0, 0)
    GtkStyleContext* style;
    GtkStateFlags state;
#else
    GtkStyle* style;
    GtkStateType state;
#endif
    gchar* text;
    gint text_width;
    gint text_height;
    gint x_offset;
    gint y_offset;
    gint x_align_offset;
    GdkRectangle rect;
    PangoWrapMode wrap_mode;
    gint wrap_width;
    PangoAlignment alignment;
    gfloat xalign, yalign;
    gint xpad, ypad;

    /* FIXME: this is time-consuming since it invokes pango_layout.
     *        if we want to fix this, we must implement the whole cell
     *        renderer ourselves instead of derived from GtkCellRendererText. */
    PangoContext* context = gtk_widget_get_pango_context(widget);

    PangoLayout* layout = pango_layout_new(context);

    g_object_get(G_OBJECT(cell),
                 "wrap-mode" , &wrap_mode,
                 "wrap-width", &wrap_width,
                 "alignment" , &alignment,
                 "text", &text,
                 NULL);

    pango_layout_set_alignment(layout, alignment);

    /* Setup the wrapping. */
    if (wrap_width < 0)
    {
        pango_layout_set_width(layout, -1);
        pango_layout_set_wrap(layout, PANGO_WRAP_CHAR);
    }
    else
    {
        pango_layout_set_width(layout, wrap_width * PANGO_SCALE);
        pango_layout_set_wrap(layout, wrap_mode);
        if(self->height > 0)
        {
            /* FIXME: add custom ellipsize from object? */
            pango_layout_set_ellipsize(layout, PANGO_ELLIPSIZE_END);
            pango_layout_set_height(layout, self->height * PANGO_SCALE);
        }
        else
            pango_layout_set_ellipsize(layout, PANGO_ELLIPSIZE_NONE);
    }

    pango_layout_set_text(layout, text, -1);

    pango_layout_set_auto_dir(layout, TRUE);

    pango_layout_get_pixel_size(layout, &text_width, &text_height);

    gtk_cell_renderer_get_alignment(cell, &xalign, &yalign);
    gtk_cell_renderer_get_padding(cell, &xpad, &ypad);
    /* Calculate the real x and y offsets. */
    x_offset = ((gtk_widget_get_direction(widget) == GTK_TEXT_DIR_RTL) ? (1.0 - xalign) : xalign)
             * (cell_area->width - text_width - (2 * xpad));
    x_offset = MAX(x_offset, 0);

    y_offset = yalign * (cell_area->height - text_height - (2 * ypad));
    y_offset = MAX (y_offset, 0);

    if(flags & (GTK_CELL_RENDERER_SELECTED|GTK_CELL_RENDERER_FOCUSED))
    {
        rect.x = cell_area->x + x_offset;
        rect.y = cell_area->y + y_offset;
        rect.width = text_width + (2 * xpad);
        rect.height = text_height + (2 * ypad);
    }

#if GTK_CHECK_VERSION(3, 0, 0)
    style = gtk_widget_get_style_context(widget);
#else
    style = gtk_widget_get_style(widget);
#endif
    if(flags & GTK_CELL_RENDERER_SELECTED) /* item is selected */
    {
#if GTK_CHECK_VERSION(3, 0, 0)
        GdkRGBA clr;

        if(flags & GTK_CELL_RENDERER_INSENSITIVE) /* insensitive */
            state = GTK_STATE_FLAG_INSENSITIVE;
        else
            state = GTK_STATE_FLAG_SELECTED;

        gtk_style_context_get_background_color(style, state, &clr);
        gdk_cairo_rectangle(cr, &rect);
        gdk_cairo_set_source_rgba(cr, &clr);
#else
        cairo_t *cr = gdk_cairo_create (window);
        GdkColor clr;

        if(flags & GTK_CELL_RENDERER_INSENSITIVE) /* insensitive */
            state = GTK_STATE_INSENSITIVE;
        else
            state = GTK_STATE_SELECTED;

        clr = style->bg[state];

        /* paint the background */
        if(expose_area)
        {
            gdk_cairo_rectangle(cr, expose_area);
            cairo_clip(cr);
        }
        gdk_cairo_rectangle(cr, &rect);

        cairo_set_source_rgb(cr, clr.red / 65535., clr.green / 65535., clr.blue / 65535.);
#endif
        cairo_fill (cr);

#if !GTK_CHECK_VERSION(3, 0, 0)
        cairo_destroy (cr);
#endif
    }
#if !GTK_CHECK_VERSION(3, 0, 0)
    else
        state = GTK_STATE_NORMAL;
#endif

    x_align_offset = (alignment == PANGO_ALIGN_CENTER) ? (wrap_width - text_width) / 2 : 0;

#if GTK_CHECK_VERSION(3, 0, 0)
    gtk_render_layout(style, cr,
                      cell_area->x + x_offset + xpad - x_align_offset,
                      cell_area->y + y_offset + ypad, layout);
#else
    gtk_paint_layout(style, window, state, TRUE,
                     expose_area, widget, "cellrenderertext",
                     cell_area->x + x_offset + xpad - x_align_offset,
                     cell_area->y + y_offset + ypad, layout);
#endif

    g_object_unref(layout);

    if(G_UNLIKELY( flags & GTK_CELL_RENDERER_FOCUSED) ) /* focused */
    {
#if GTK_CHECK_VERSION(3, 0, 0)
        gtk_render_focus(style, cr, rect.x, rect.y, rect.width, rect.height);
#else
        gtk_paint_focus(style, window, state, background_area,
                        widget, "cellrenderertext", rect.x, rect.y,
                        rect.width, rect.height);
#endif
    }

    if(flags & GTK_CELL_RENDERER_PRELIT) /* hovered */
        g_object_set(G_OBJECT(widget), "tooltip-text", text, NULL);
    else
        g_object_set(G_OBJECT(widget), "tooltip-text", NULL, NULL);
    g_free(text);
}
Exemple #16
0
static void
gtk_hruler_draw_ticks (GtkRuler *ruler)
{
  GtkWidget *widget;
  GdkGC *gc, *bg_gc;
  gint i;
  gint width, height;
  gint xthickness;
  gint ythickness;
  gint length, ideal_length;
  gdouble lower, upper;		/* Upper and lower limits, in ruler units */
  gdouble increment;		/* Number of pixels per unit */
  gint scale;			/* Number of units per major unit */
  gdouble subd_incr;
  gdouble start, end, cur;
  gchar unit_str[32];
  gint digit_height;
  gint digit_offset;
  gint text_width;
  gint pos;
  PangoLayout *layout;
  PangoRectangle logical_rect, ink_rect;

  if (!GTK_WIDGET_DRAWABLE (ruler)) 
    return;

  widget = GTK_WIDGET (ruler);

  gc = widget->style->fg_gc[GTK_STATE_NORMAL];
  bg_gc = widget->style->bg_gc[GTK_STATE_NORMAL];

  xthickness = widget->style->xthickness;
  ythickness = widget->style->ythickness;

  digit_height = PANGO_PIXELS (ink_rect.height) + 2;
  digit_offset = ink_rect.y;

  layout = gtk_widget_create_pango_layout (widget, "012456789");
  pango_layout_get_extents (layout, &ink_rect, &logical_rect);
  
  digit_height = PANGO_PIXELS (ink_rect.height) + 1;
  digit_offset = ink_rect.y;

  width = widget->allocation.width;
  height = widget->allocation.height - ythickness * 2;
   
  gtk_paint_box (widget->style, ruler->backing_store,
		 GTK_STATE_NORMAL, GTK_SHADOW_OUT, 
		 NULL, widget, "hruler",
		 0, 0, 
		 widget->allocation.width, widget->allocation.height);
  
  
  gdk_draw_line (ruler->backing_store, gc,
		 xthickness,
		 height + ythickness,
		 widget->allocation.width - xthickness,
		 height + ythickness);

  upper = ruler->upper / ruler->metric->pixels_per_unit;
  lower = ruler->lower / ruler->metric->pixels_per_unit;

  if ((upper - lower) == 0) 
    return;
  increment = (gdouble) width / (upper - lower);

  /* determine the scale
   *  We calculate the text size as for the vruler instead of using
   *  text_width = gdk_string_width(font, unit_str), so that the result
   *  for the scale looks consistent with an accompanying vruler
   */
  scale = ceil (ruler->max_size / ruler->metric->pixels_per_unit);
  g_snprintf (unit_str, sizeof (unit_str), "%d", scale);
  text_width = strlen (unit_str) * digit_height + 1;

  for (scale = 0; scale < MAXIMUM_SCALES; scale++)
    if (ruler->metric->ruler_scale[scale] * fabs(increment) > 2 * text_width)
      break;

  if (scale == MAXIMUM_SCALES)
    scale = MAXIMUM_SCALES - 1;

  /* drawing starts here */
  length = 0;
  for (i = MAXIMUM_SUBDIVIDE - 1; i >= 0; i--)
    {
      subd_incr = (gdouble) ruler->metric->ruler_scale[scale] / 
	          (gdouble) ruler->metric->subdivide[i];
      if (subd_incr * fabs(increment) <= MINIMUM_INCR) 
	continue;

      /* Calculate the length of the tickmarks. Make sure that
       * this length increases for each set of ticks
       */
      ideal_length = height / (i + 1) - 1;
      if (ideal_length > ++length)
	length = ideal_length;

      if (lower < upper)
	{
	  start = floor (lower / subd_incr) * subd_incr;
	  end   = ceil  (upper / subd_incr) * subd_incr;
	}
      else
	{
	  start = floor (upper / subd_incr) * subd_incr;
	  end   = ceil  (lower / subd_incr) * subd_incr;
	}

  
      for (cur = start; cur <= end; cur += subd_incr)
	{
	  pos = ROUND ((cur - lower) * increment);

	  gdk_draw_line (ruler->backing_store, gc,
			 pos, height + ythickness, 
			 pos, height - length + ythickness);

	  /* draw label */
	  if (i == 0)
	    {
	      g_snprintf (unit_str, sizeof (unit_str), "%d", (int) cur);
	      
	      pango_layout_set_text (layout, unit_str, -1);
	      pango_layout_get_extents (layout, &logical_rect, NULL);

              gtk_paint_layout (widget->style,
                                ruler->backing_store,
                                GTK_WIDGET_STATE (widget),
				FALSE,
                                NULL,
                                widget,
                                "hruler",
                                pos + 2, ythickness + PANGO_PIXELS (logical_rect.y - digit_offset),
                                layout);
	    }
	}
    }

  g_object_unref (layout);
}
Exemple #17
0
static void
dma_sparse_view_paint_margin (DmaSparseView *view,
			      GdkEventExpose *event)
{
	GtkTextView *text_view;
	GdkWindow *win;
	PangoLayout *layout;
	gint y1, y2;
	gint y, height;
	gchar str [16];
	gint margin_width;
	gint margin_length;
	gint text_width;
	DmaSparseIter buf_iter;
	GtkTextIter text_iter;
	guint prev_address = G_MAXUINT;

	
	text_view = GTK_TEXT_VIEW (view);

	if (!view->priv->show_line_numbers && !view->priv->show_line_markers)
	{
		gtk_text_view_set_border_window_size (text_view,
						      GTK_TEXT_WINDOW_LEFT,
						      0);

		return;
	}
	
	win = gtk_text_view_get_window (text_view,
					GTK_TEXT_WINDOW_LEFT);	

	y1 = event->area.y;
	y2 = y1 + event->area.height;

	/* get the extents of the line printing */
	gtk_text_view_window_to_buffer_coords (text_view,
					       GTK_TEXT_WINDOW_LEFT,
					       0,
					       y1,
					       NULL,
					       &y1);

	gtk_text_view_window_to_buffer_coords (text_view,
					       GTK_TEXT_WINDOW_LEFT,
					       0,
					       y2,
					       NULL,
					       &y2);

	/* set size. */
	g_snprintf (str, sizeof (str), "0x%X", G_MAXUINT);
	margin_length = strlen(str) - 2;
	layout = gtk_widget_create_pango_layout (GTK_WIDGET (view), str);

	pango_layout_get_pixel_size (layout, &text_width, NULL);
	
	pango_layout_set_width (layout, text_width);
	pango_layout_set_alignment (layout, PANGO_ALIGN_RIGHT);

	/* determine the width of the left margin. */
	if (view->priv->show_line_numbers)
		margin_width = text_width + 4;
	else
		margin_width = 0;
	
	if (view->priv->show_line_markers)
		margin_width += GUTTER_PIXMAP;

	g_return_if_fail (margin_width != 0);
	
	gtk_text_view_set_border_window_size (GTK_TEXT_VIEW (text_view),
					      GTK_TEXT_WINDOW_LEFT,
					      margin_width);

	/* Display all addresses */
	dma_sparse_iter_copy (&buf_iter, &view->priv->start);
	gtk_text_buffer_get_start_iter (gtk_text_view_get_buffer (text_view), &text_iter);
	

	
	/* Skip line while position doesn't need to be repaint */
	gtk_text_view_get_line_yrange (text_view, &text_iter, &y, &height);
	if (y < y1)
	{
		do
		{
			if (!dma_sparse_iter_forward_lines (&buf_iter, 1)) return;
			if (!gtk_text_iter_forward_line (&text_iter)) return;
			gtk_text_view_get_line_yrange (text_view, &text_iter, &y, &height);
		} while (y < y1);
	}
		

	/* Display address */
	do
	{
		gint pos;
		guint address;
		
		gtk_text_view_buffer_to_window_coords (text_view,
						       GTK_TEXT_WINDOW_LEFT,
						       0,
						       y,
						       NULL,
						       &pos);

		address = dma_sparse_iter_get_address (&buf_iter);
		
		if (view->priv->show_line_numbers) 
		{
			g_snprintf (str, sizeof (str),"0x%0*lX", margin_length, (long unsigned int)address);
			pango_layout_set_markup (layout, str, -1);

			gtk_paint_layout (gtk_widget_get_style (GTK_WIDGET (view)),
					  win,
					  gtk_widget_get_state (GTK_WIDGET (view)),
					  FALSE,
					  NULL,
					  GTK_WIDGET (view),
					  NULL,
					  text_width + 2, 
					  pos,
					  layout);
		}

		/* Display marker */
		if ((prev_address != address) && (view->priv->show_line_markers)) 
		{
			gint current_marker = dma_sparse_buffer_get_marks (view->priv->buffer, address);

			if (current_marker)
			{
				gint x;
				
				if (view->priv->show_line_numbers)
					x = text_width + 4;
				else
					x = 0;
				
				draw_line_markers (view, current_marker, x, pos);
				prev_address = address;
			}
		}
		
		if (!dma_sparse_iter_forward_lines (&buf_iter, 1)) return;
		if (!gtk_text_iter_forward_line (&text_iter)) return;
		gtk_text_view_get_line_yrange (text_view, &text_iter, &y, &height);
		
	} while (y < y2);
		
	g_object_unref (G_OBJECT (layout));	
}
static gint
gdl_dock_item_grip_expose (GtkWidget      *widget,
			   GdkEventExpose *event)
{
    GdlDockItemGrip *grip;
    GdkRectangle     title_area;
    GdkRectangle     expose_area;
    GtkStyle        *bg_style;
    gint             layout_width;
    gint             layout_height;
    gint             text_x;
    gint             text_y;
    gboolean         item_or_child_has_focus;

    grip = GDL_DOCK_ITEM_GRIP (widget);
    gdl_dock_item_grip_get_title_area (grip, &title_area);

    /* draw background, highlight it if the dock item or any of its
     * descendants have focus */
    bg_style = (gdl_dock_item_or_child_has_focus (grip->item) ?
                gtk_widget_get_style (widget)->dark_gc[widget->state] :
                gtk_widget_get_style (widget)->mid_gc[widget->state]);

    gdk_draw_rectangle (GDK_DRAWABLE (widget->window), bg_style, TRUE,
                        1, 0, widget->allocation.width - 1, widget->allocation.height);

    if (grip->_priv->icon_pixbuf) {
        GdkRectangle pixbuf_rect;
        
        pixbuf_rect.width = gdk_pixbuf_get_width (grip->_priv->icon_pixbuf);
        pixbuf_rect.height = gdk_pixbuf_get_height (grip->_priv->icon_pixbuf);
        if (gtk_widget_get_direction (widget) == GTK_TEXT_DIR_RTL) {
            pixbuf_rect.x = title_area.x + title_area.width - pixbuf_rect.width;
        } else {
            pixbuf_rect.x = title_area.x;
            title_area.x += pixbuf_rect.width + 1;
        }
        /* shrink title area by the pixbuf width plus a 1px spacing */
        title_area.width -= pixbuf_rect.width + 1;
        pixbuf_rect.y = title_area.y + (title_area.height - pixbuf_rect.height) / 2;

        if (gdk_rectangle_intersect (&event->area, &pixbuf_rect, &expose_area)) {
            GdkGC *gc;
            GtkStyle *style;

            style = gtk_widget_get_style (widget);
            gc = style->bg_gc[widget->state];
            gdk_draw_pixbuf (GDK_DRAWABLE (widget->window), gc,
                             grip->_priv->icon_pixbuf,
                             0, 0, pixbuf_rect.x, pixbuf_rect.y,
                             pixbuf_rect.width, pixbuf_rect.height,
                             GDK_RGB_DITHER_NONE, 0, 0);
	}
    }

    if (gdk_rectangle_intersect (&title_area, &event->area, &expose_area)) {
        pango_layout_get_pixel_size (grip->_priv->title_layout, &layout_width,
                                     &layout_height);

        if (gtk_widget_get_direction (widget) == GTK_TEXT_DIR_RTL)
            text_x = title_area.x + title_area.width - layout_width;
        else
            text_x = title_area.x;

        text_y = title_area.y + (title_area.height - layout_height) / 2;

        gtk_paint_layout (widget->style, widget->window, widget->state, TRUE,
                          &expose_area, widget, NULL, text_x, text_y,
                          grip->_priv->title_layout);
    }

    return GTK_WIDGET_CLASS (parent_class)->expose_event (widget, event);
}  
Exemple #19
0
static gboolean gx_selector_expose (GtkWidget *widget, GdkEventExpose *event)
{
	g_assert(GX_IS_SELECTOR(widget));
	GxSelector *selector = GX_SELECTOR(widget);
	GxSelectorPrivate *priv = selector->priv;
	int selectorstate = get_selector_state(selector);
    
    gx_selector_create_icon(selector);
    
	PangoLayout *layout = gtk_widget_create_pango_layout(widget, NULL);
	GdkRectangle arrow, text;
	gint off_x, off_y;
	gx_selector_get_positions(widget, &arrow, &text, &off_x, &off_y);
    gint rad;
    float bevel;
    gtk_widget_style_get(widget, "border-radius", &rad, "bevel", &bevel, NULL);
    if (!rad)
        rad = 0;
    if (!bevel)
        bevel = 0;
    cairo_t * cr = gdk_cairo_create(GDK_DRAWABLE(widget->window));
    GdkRegion *reg = gdk_region_rectangle(&widget->allocation);
    if (event->region)
        gdk_region_intersect(reg, event->region);
    gdk_cairo_region(cr, reg);
    cairo_clip (cr);
   
    gx_draw_rect(widget, "bg", NULL, widget->allocation.x,
        widget->allocation.y + (widget->allocation.height - widget->requisition.height) / 2,
        widget->allocation.width,
        widget->requisition.height,
        rad,
        bevel);
    
    if (widget->style->ythickness >= 3)
        gx_draw_inset(widget, text.x, text.y, text.width, text.height,
            std::max(rad - std::max(widget->style->ythickness, widget->style->ythickness), 0), 1);
        
    gx_draw_rect(widget, "base", NULL, text.x,
        text.y,
        text.width,
        text.height,
        std::max(rad - std::max(widget->style->ythickness, widget->style->ythickness), 0),
        0);
    
    gx_draw_glass(widget, text.x, text.y, text.width, text.height,
        std::max(rad - std::max(widget->style->ythickness, widget->style->ythickness), 0));
    
    gdk_cairo_set_source_pixbuf(cr, selector->icon, arrow.x, arrow.y);
    cairo_rectangle(cr, arrow.x, arrow.y, arrow.width, arrow.height);
    cairo_fill(cr);
    
	cairo_destroy(cr);
    
	if (selector->model) {
		gint x, y;
		PangoRectangle logical;
		char *s;
		GtkTreeIter iter;
		gtk_tree_model_iter_nth_child(selector->model, &iter, NULL, selectorstate);
		gtk_tree_model_get(selector->model, &iter, 0, &s, -1);
		pango_layout_set_text(layout, s, -1);
		pango_layout_get_pixel_extents(layout, NULL, &logical);
		x = text.x + (text.width - logical.width) / 2;
		y = text.y + off_y + (priv->textsize.height - logical.height)/ 2;
		gtk_paint_layout(widget->style, widget->window, gtk_widget_get_state(widget),
		                 FALSE, NULL, widget, "label", x, y, layout);
		g_free(s);
	}
	g_object_unref(layout);
	gdk_region_destroy(reg);
	return TRUE;
}