]> Pileus Git - ~andy/gtk/blobdiff - gtk/gtkcssimagecrossfade.c
filechooser: Rename _gtk_file_is_path_not_local() to _gtk_file_has_native_path()
[~andy/gtk] / gtk / gtkcssimagecrossfade.c
index 424703af85e7178dd280aeaa0368b583bb7eac52..1b02af94f73f5e8b6d1cd37f7587d38af3c12346 100644 (file)
@@ -19,6 +19,7 @@
 
 #include "config.h"
 
+#include <math.h>
 #include <string.h>
 
 #include "gtkcssimagecrossfadeprivate.h"
@@ -85,6 +86,18 @@ gtk_css_image_cross_fade_get_height (GtkCssImage *image)
   return start_height + (end_height - start_height) * cross_fade->progress;
 }
 
+static gboolean
+gtk_css_image_cross_fade_equal (GtkCssImage *image1,
+                                GtkCssImage *image2)
+{
+  GtkCssImageCrossFade *cross_fade1 = GTK_CSS_IMAGE_CROSS_FADE (image1);
+  GtkCssImageCrossFade *cross_fade2 = GTK_CSS_IMAGE_CROSS_FADE (image2);
+
+  return cross_fade1->progress == cross_fade2->progress &&
+         _gtk_css_image_equal (cross_fade1->start, cross_fade2->start) &&
+         _gtk_css_image_equal (cross_fade1->end, cross_fade2->end);
+}
+
 static void
 gtk_css_image_cross_fade_draw (GtkCssImage        *image,
                                cairo_t            *cr,
@@ -105,37 +118,36 @@ gtk_css_image_cross_fade_draw (GtkCssImage        *image,
     }
   else
     {
-      cairo_surface_t *surface;
-
       if (cross_fade->start && cross_fade->end)
         {
           /* to reduce the group size */
-          cairo_rectangle (cr, 0, 0, width, height);
+          cairo_rectangle (cr, 0, 0, ceil (width), ceil (height));
           cairo_clip (cr);
 
           cairo_push_group (cr);
 
+          /* performance trick */
+          cairo_reset_clip (cr);
+
           _gtk_css_image_draw (cross_fade->start, cr, width, height);
 
-          surface = _gtk_css_image_get_surface (cross_fade->end,
-                                                cairo_get_target (cr),
-                                                width, height);
-          cairo_set_source_surface (cr, surface, 0, 0);
+          cairo_push_group (cr);
+          _gtk_css_image_draw (cross_fade->end, cr, width, height);
+          cairo_pop_group_to_source (cr);
+
           cairo_set_operator (cr, CAIRO_OPERATOR_SOURCE);
           cairo_paint_with_alpha (cr, cross_fade->progress);
-          cairo_surface_destroy (surface);
 
           cairo_pop_group_to_source (cr);
           cairo_paint (cr);
         }
       else if (cross_fade->start || cross_fade->end)
         {
-          surface = _gtk_css_image_get_surface (cross_fade->start ? cross_fade->start : cross_fade->end,
-                                                cairo_get_target (cr),
-                                                width, height);
-          cairo_set_source_surface (cr, surface, 0, 0);
+          cairo_push_group (cr);
+          _gtk_css_image_draw (cross_fade->start ? cross_fade->start : cross_fade->end, cr, width, height);
+          cairo_pop_group_to_source (cr);
+
           cairo_paint_with_alpha (cr, cross_fade->start ? 1.0 - cross_fade->progress : cross_fade->progress);
-          cairo_surface_destroy (surface);
         }
     }
 }
@@ -145,32 +157,41 @@ gtk_css_image_cross_fade_parse (GtkCssImage  *image,
                                 GtkCssParser *parser)
 {
   GtkCssImageCrossFade *cross_fade = GTK_CSS_IMAGE_CROSS_FADE (image);
-  GtkCssValue *number;
-
   if (!_gtk_css_parser_try (parser, "cross-fade(", TRUE))
     {
       _gtk_css_parser_error (parser, "Expected 'cross-fade('");
       return FALSE;
     }
 
-  cross_fade->start = _gtk_css_image_new_parse (parser);
-  if (cross_fade->start == NULL)
-    return FALSE;
-
-  if (!_gtk_css_parser_try (parser, ",", TRUE))
+  if (_gtk_css_parser_has_number (parser))
     {
-      _gtk_css_parser_error (parser, "Missing comma after first image");
-      return FALSE;
+      GtkCssValue *number;
+      
+      number = _gtk_css_number_value_parse (parser, GTK_CSS_PARSE_PERCENT | GTK_CSS_POSITIVE_ONLY);
+      if (number == NULL)
+        return FALSE;
+      cross_fade->progress = _gtk_css_number_value_get (number, 1);
+      _gtk_css_value_unref (number);
+
+      if (cross_fade->progress > 1.0)
+        {
+          _gtk_css_parser_error (parser, "Percentages over 100%% are not allowed");
+          return FALSE;
+        }
     }
+  else
+    cross_fade->progress = 0.5;
 
-  cross_fade->end = _gtk_css_image_new_parse (parser);
-  if (cross_fade->end == NULL)
+  cross_fade->start = _gtk_css_image_new_parse (parser);
+  if (cross_fade->start == NULL)
     return FALSE;
 
-  if (!_gtk_css_parser_try (parser, ",", TRUE))
+  if (_gtk_css_parser_try (parser, ",", TRUE))
     {
-      _gtk_css_parser_error (parser, "Missing comma after second image");
-      return FALSE;
+      /* XXX: allow parsing colors here */
+      cross_fade->end = _gtk_css_image_new_parse (parser);
+      if (cross_fade->end == NULL)
+        return FALSE;
     }
 
   if (!_gtk_css_parser_try (parser, ")", TRUE))
@@ -179,19 +200,6 @@ gtk_css_image_cross_fade_parse (GtkCssImage  *image,
       return FALSE;
     }
 
-  number = _gtk_css_number_value_parse (parser, GTK_CSS_PARSE_PERCENT | GTK_CSS_POSITIVE_ONLY);
-  if (number == NULL)
-    return FALSE;
-  cross_fade->progress = _gtk_css_number_value_get (number, 1);
-  _gtk_css_value_unref (number);
-
-  if (cross_fade->progress > 100)
-    {
-      _gtk_css_parser_error (parser, "Percentages ovre 100%% are not allowed");
-      return FALSE;
-    }
-  cross_fade->progress /= 100.0;
-
   return TRUE;
 }
 
@@ -201,18 +209,21 @@ gtk_css_image_cross_fade_print (GtkCssImage *image,
 {
   GtkCssImageCrossFade *cross_fade = GTK_CSS_IMAGE_CROSS_FADE (image);
 
-  g_string_append (string, "cross_fade(");
+  g_string_append (string, "cross-fade(");
+  if (cross_fade->progress != 0.5)
+    {
+      g_string_append_printf (string, "%g%% ", cross_fade->progress * 100.0);
+    }
+
   if (cross_fade->start)
     _gtk_css_image_print (cross_fade->start, string);
   else
     g_string_append (string, "none");
-  g_string_append (string, ",");
   if (cross_fade->end)
-    _gtk_css_image_print (cross_fade->end, string);
-  else
-    g_string_append (string, "none");
-  g_string_append (string, ",");
-  g_string_append_printf (string, "%g%%", cross_fade->progress * 100.0);
+    {
+      g_string_append (string, ", ");
+      _gtk_css_image_print (cross_fade->end, string);
+    }
   g_string_append (string, ")");
 }
 
@@ -235,6 +246,7 @@ _gtk_css_image_cross_fade_class_init (GtkCssImageCrossFadeClass *klass)
 
   image_class->get_width = gtk_css_image_cross_fade_get_width;
   image_class->get_height = gtk_css_image_cross_fade_get_height;
+  image_class->equal = gtk_css_image_cross_fade_equal;
   image_class->draw = gtk_css_image_cross_fade_draw;
   image_class->parse = gtk_css_image_cross_fade_parse;
   image_class->print = gtk_css_image_cross_fade_print;