示例#1
0
文件: gtklevelbar.c 项目: Therzok/gtk
static void
gtk_level_bar_get_min_block_size (GtkLevelBar *self,
                                  gint        *block_width,
                                  gint        *block_height)
{
  GtkWidget *widget = GTK_WIDGET (self);
  GtkStyleContext *context;
  GtkStateFlags state;
  GtkBorder border, tmp, tmp2;
  gint min_width, min_height;

  context = gtk_widget_get_style_context (widget);
  gtk_style_context_save_to_node (context, self->priv->block_node[0]);
  state = gtk_style_context_get_state (context);
  gtk_style_context_get_border (context, state, &border);
  gtk_style_context_get_padding (context, state, &tmp);
  gtk_style_context_get_margin (context, state, &tmp2);
  gtk_style_context_restore (context);

  gtk_style_context_get_style (context,
                               "min-block-width", &min_width,
                               "min-block-height", &min_height,
                               NULL);

  border.top += tmp.top;
  border.right += tmp.right;
  border.bottom += tmp.bottom;
  border.left += tmp.left;

  border.top += tmp2.top;
  border.right += tmp2.right;
  border.bottom += tmp2.bottom;
  border.left += tmp2.left;

  if (block_width)
    *block_width = MAX (border.left + border.right, min_width);
  if (block_height)
    *block_height = MAX (border.top + border.bottom, min_height);
}
示例#2
0
文件: gtklevelbar.c 项目: Therzok/gtk
static gboolean
gtk_level_bar_draw (GtkWidget *widget,
                    cairo_t   *cr)
{
  GtkLevelBar *self = GTK_LEVEL_BAR (widget);
  GtkStyleContext *context;
  gint width, height;

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

  context = gtk_widget_get_style_context (widget);
  gtk_style_context_save_to_node (context, self->priv->trough_node);

  gtk_render_background (context, cr, 0, 0, width, height);
  gtk_render_frame (context, cr, 0, 0, width, height);

  gtk_style_context_restore (context);

  gtk_level_bar_draw_fill (self, cr);

  return FALSE;
}
示例#3
0
文件: gtklevelbar.c 项目: Therzok/gtk
static void
gtk_level_bar_get_borders (GtkLevelBar *self,
                           GtkBorder   *borders_out)
{
  GtkWidget *widget = GTK_WIDGET (self);
  GtkStyleContext *context;
  GtkStateFlags state;
  GtkBorder border, tmp;

  context = gtk_widget_get_style_context (widget);
  gtk_style_context_save_to_node (context, self->priv->trough_node);
  state = gtk_style_context_get_state (context);
  gtk_style_context_get_border (context, state, &border);
  gtk_style_context_get_padding (context, state, &tmp);
  gtk_style_context_restore (context);

  border.top += tmp.top;
  border.right += tmp.right;
  border.bottom += tmp.bottom;
  border.left += tmp.left;

  if (borders_out)
    *borders_out = border;
}
示例#4
0
static gboolean
swatch_draw (GtkWidget *widget,
             cairo_t   *cr)
{
  GtkColorSwatch *swatch = (GtkColorSwatch*)widget;
  gdouble width, height;
  GtkStyleContext *context;
  GtkStateFlags state;
  GtkIconTheme *theme;
  GtkBorder border, padding;
  GdkRectangle rect;
  GtkIconInfo *icon_info = NULL;
  gint scale;

  theme = gtk_icon_theme_get_default ();
  context = gtk_widget_get_style_context (widget);
  state = gtk_style_context_get_state (context);
  width = gtk_widget_get_allocated_width (widget);
  height = gtk_widget_get_allocated_height (widget);

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

  if (swatch->priv->has_color)
    {
      cairo_pattern_t *pattern;
      cairo_matrix_t matrix;

      gtk_render_content_path (context, cr, 0, 0, width, height);

      if (swatch->priv->use_alpha)
        {
          cairo_save (cr);

          cairo_clip_preserve (cr);

          cairo_set_source_rgb (cr, 0.33, 0.33, 0.33);
          cairo_fill_preserve (cr);

          pattern = _gtk_color_chooser_get_checkered_pattern ();
          cairo_matrix_init_scale (&matrix, 0.125, 0.125);
          cairo_pattern_set_matrix (pattern, &matrix);

          cairo_set_source_rgb (cr, 0.66, 0.66, 0.66);
          cairo_mask (cr, pattern);
          cairo_pattern_destroy (pattern);

          cairo_restore (cr);

          gdk_cairo_set_source_rgba (cr, &swatch->priv->color);
        }
      else
        {
          cairo_set_source_rgb (cr,
                                swatch->priv->color.red,
                                swatch->priv->color.green,
                                swatch->priv->color.blue);
        }

      cairo_fill (cr);
    }

  gtk_render_frame (context, cr, 0, 0, width, height);

  scale = gtk_widget_get_scale_factor (widget);
  if (swatch->priv->icon)
    {
      icon_info = gtk_icon_theme_lookup_icon_for_scale (theme, swatch->priv->icon, PIXBUF_SIZE,
                                                        scale,
                                                        GTK_ICON_LOOKUP_GENERIC_FALLBACK
                                                        | GTK_ICON_LOOKUP_USE_BUILTIN);
    }
  else if ((state & GTK_STATE_FLAG_SELECTED) != 0)
    {
      GIcon *gicon;

      gicon = g_themed_icon_new ("object-select-symbolic");
      /* fallback for themes that don't have object-select-symbolic */
      g_themed_icon_append_name (G_THEMED_ICON (gicon), "gtk-apply");

      icon_info = gtk_icon_theme_lookup_by_gicon_for_scale (theme, gicon, PIXBUF_SIZE,
                                                            scale,
                                                            GTK_ICON_LOOKUP_GENERIC_FALLBACK
                                                            | GTK_ICON_LOOKUP_USE_BUILTIN);
      g_object_unref (gicon);
    }

  /* now draw the overlay image */
  gtk_style_context_get_border (context, state, &border);
  gtk_style_context_get_padding (context, state, &padding);
  rect.width = width - (border.left + border.right + padding.left + padding.right);
  rect.height = height - (border.top + border.bottom + padding.top + padding.bottom);
  rect.x = border.left + padding.left;
  rect.y = border.top + padding.top;

  gtk_style_context_save_to_node (context, swatch->priv->overlay_node);

  gtk_render_background (context, cr, rect.x, rect.y, rect.width, rect.height);
  gtk_render_frame (context, cr, rect.x, rect.y, rect.width, rect.height);

  if (icon_info != NULL)
    {
      GdkPixbuf *pixbuf;

      pixbuf = gtk_icon_info_load_symbolic_for_context (icon_info, context, NULL, NULL);
      if (pixbuf != NULL)
        {
          cairo_surface_t *surface;

          surface = gdk_cairo_surface_create_from_pixbuf (pixbuf, scale, gtk_widget_get_window (widget));
          gtk_render_icon_surface (context, cr, surface,
                                   rect.x + (rect.width - (gdk_pixbuf_get_width (pixbuf) / scale)) / 2,
                                   rect.y + (rect.height - (gdk_pixbuf_get_height (pixbuf) / scale)) / 2);
          cairo_surface_destroy (surface);
          g_object_unref (pixbuf);
        }

      g_object_unref (icon_info);
    }

  if (gtk_widget_has_visible_focus (widget))
    gtk_render_focus (context, cr, 0, 0, width, height);

  gtk_style_context_restore (context);

  return FALSE;
}
示例#5
0
文件: gtklevelbar.c 项目: Therzok/gtk
static void
gtk_level_bar_draw_fill_discrete (GtkLevelBar           *self,
                                  cairo_t               *cr,
                                  cairo_rectangle_int_t *fill_area)
{
  GtkWidget *widget = GTK_WIDGET (self);
  GtkStyleContext *context;
  gint num_blocks, i;
  gint block_width, block_height;
  gint block_draw_width, block_draw_height;
  GtkBorder block_margin;
  cairo_rectangle_int_t block_area;

  context = gtk_widget_get_style_context (widget);
  gtk_level_bar_get_min_block_size (self, &block_width, &block_height);

  block_area = *fill_area;
  num_blocks = (gint) round (self->priv->max_value) - (gint) round (self->priv->min_value);

  if (self->priv->orientation == GTK_ORIENTATION_HORIZONTAL)
    block_width = MAX (block_width, (gint) floor (block_area.width / num_blocks));
  else
    block_height = MAX (block_height, (gint) floor (block_area.height / num_blocks));

  gtk_style_context_save_to_node (context, self->priv->block_node[0]);
  gtk_style_context_get_margin (context, gtk_style_context_get_state (context), &block_margin);
  gtk_style_context_restore (context);

  block_draw_width = block_width - block_margin.left - block_margin.right;
  block_draw_height = block_height - block_margin.top - block_margin.bottom;

  if (self->priv->orientation == GTK_ORIENTATION_HORIZONTAL)
    {
      block_draw_height = MAX (block_draw_height, block_area.height - block_margin.top - block_margin.bottom);
      block_area.y += block_margin.top;
    }
  else
    {
      block_draw_width = MAX (block_draw_width, block_area.width - block_margin.left - block_margin.right);
      block_area.x += block_margin.left;
    }

  for (i = 0; i < num_blocks; i++)
    {
      if (self->priv->orientation == GTK_ORIENTATION_HORIZONTAL)
        block_area.x += block_margin.left;
      else
        block_area.y += block_margin.top;

      gtk_style_context_save_to_node (context, self->priv->block_node[i]);

      gtk_render_background (context, cr,
                             block_area.x, block_area.y,
                             block_draw_width, block_draw_height);
      gtk_render_frame (context, cr,
                        block_area.x, block_area.y,
                        block_draw_width, block_draw_height);

      gtk_style_context_restore (context);

      if (self->priv->orientation == GTK_ORIENTATION_HORIZONTAL)
        block_area.x += block_draw_width + block_margin.right;
      else
        block_area.y += block_draw_height + block_margin.bottom;
    }
}
示例#6
0
文件: gtklevelbar.c 项目: Therzok/gtk
static void
gtk_level_bar_draw_fill_continuous (GtkLevelBar           *self,
                                    cairo_t               *cr,
                                    cairo_rectangle_int_t *fill_area)
{
  GtkWidget *widget = GTK_WIDGET (self);
  GtkStyleContext *context;
  cairo_rectangle_int_t base_area, block_area;
  GtkBorder block_margin;
  gdouble fill_percentage;
  gboolean inverted;

  inverted = self->priv->inverted;
  if (gtk_widget_get_direction (GTK_WIDGET (self)) == GTK_TEXT_DIR_RTL)
    {
      if (self->priv->orientation == GTK_ORIENTATION_HORIZONTAL)
        inverted = !inverted;
    }

  context = gtk_widget_get_style_context (widget);

  /* render the empty (unfilled) part */
  gtk_style_context_save_to_node (context, self->priv->block_node[inverted ? 0 : 1]);
  gtk_style_context_get_margin (context, gtk_style_context_get_state (context), &block_margin);

  base_area = *fill_area;
  base_area.x += block_margin.left;
  base_area.y += block_margin.top;
  base_area.width -= block_margin.left + block_margin.right;
  base_area.height -= block_margin.top + block_margin.bottom;

  gtk_render_background (context, cr, base_area.x, base_area.y,
                         base_area.width, base_area.height);
  gtk_render_frame (context, cr, base_area.x, base_area.y,
                    base_area.width, base_area.height);

  gtk_style_context_restore (context);

  /* now render the filled part on top of it */

  block_area = base_area;

  fill_percentage = (self->priv->cur_value - self->priv->min_value) /
    (self->priv->max_value - self->priv->min_value);

  if (self->priv->orientation == GTK_ORIENTATION_HORIZONTAL)
    {
      block_area.width = (gint) floor (block_area.width * fill_percentage);

      if (inverted)
        block_area.x += base_area.width - block_area.width;
    }
  else
    {
      block_area.height = (gint) floor (block_area.height * fill_percentage);

      if (inverted)
        block_area.y += base_area.height - block_area.height;
    }

  gtk_style_context_save_to_node (context, self->priv->block_node[inverted ? 1 : 0]);

  gtk_render_background (context, cr, block_area.x, block_area.y,
                         block_area.width, block_area.height);
  gtk_render_frame (context, cr, block_area.x, block_area.y,
                    block_area.width, block_area.height);

  gtk_style_context_restore (context);
}
示例#7
0
static void
gtk_real_check_menu_item_draw_indicator (GtkCheckMenuItem *check_menu_item,
                                         cairo_t          *cr)
{
  GtkCheckMenuItemPrivate *priv = check_menu_item->priv;
  GtkWidget *widget;
  gint x, y;

  widget = GTK_WIDGET (check_menu_item);

  if (gtk_widget_is_drawable (widget))
    {
      GtkAllocation allocation;
      GtkStyleContext *context;
      guint border_width;
      guint offset;
      guint toggle_size;
      guint toggle_spacing;
      guint horizontal_padding;
      guint indicator_size;
      GtkStateFlags state;
      GtkBorder padding;

      context = gtk_widget_get_style_context (widget);
      state = gtk_widget_get_state_flags (widget);
      gtk_style_context_get_padding (context, state, &padding);

      gtk_widget_get_allocation (widget, &allocation);

      gtk_widget_style_get (widget,
                            "toggle-spacing", &toggle_spacing,
                            "horizontal-padding", &horizontal_padding,
                            "indicator-size", &indicator_size,
                            NULL);

      toggle_size = GTK_MENU_ITEM (check_menu_item)->priv->toggle_size;
      border_width = gtk_container_get_border_width (GTK_CONTAINER (widget));
      offset = border_width + padding.left + 2;

      if (gtk_widget_get_direction (widget) == GTK_TEXT_DIR_LTR)
        {
          x = offset + horizontal_padding +
            (toggle_size - toggle_spacing - indicator_size) / 2;
        }
      else
        {
          x = allocation.width -
            offset - horizontal_padding - toggle_size + toggle_spacing +
            (toggle_size - toggle_spacing - indicator_size) / 2;
        }

      y = (allocation.height - indicator_size) / 2;

      gtk_style_context_save_to_node (context, priv->indicator_node);

      if (priv->draw_as_radio)
        gtk_render_option (context, cr, x, y,
                           indicator_size, indicator_size);
      else
        gtk_render_check (context, cr, x, y,
                          indicator_size, indicator_size);

      gtk_style_context_restore (context);
    }
}