summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSøren Sandmann Pedersen <sandmann@redhat.com>2009-09-18 11:54:21 -0400
committerSøren Sandmann Pedersen <ssp@redhat.com>2010-02-24 23:20:27 -0500
commitf27f17ce22b6d0ac587600930c3657180066aac8 (patch)
treeccf7de5e872bc85a6a406bac8bddcd9057aaa35c
parent2a6ba862abd8859014d11a742247fa1f1225729b (diff)
Eliminate _pixman_image_is_opaque() in favor of a new FAST_PATH_IS_OPAQUE flag
The new FAST_PATH_IS_OPAQUE flag is computed along with the others in _pixman_image_validate().
-rw-r--r--pixman/pixman-image.c96
-rw-r--r--pixman/pixman-private.h4
-rw-r--r--pixman/pixman.c7
3 files changed, 45 insertions, 62 deletions
diff --git a/pixman/pixman-image.c b/pixman/pixman-image.c
index ff0fbbb..1014e64 100644
--- a/pixman/pixman-image.c
+++ b/pixman/pixman-image.c
@@ -298,6 +298,9 @@ compute_image_info (pixman_image_t *image)
if (image->type == SOLID)
{
code = PIXMAN_solid;
+
+ if (image->solid.color.alpha == 0xffff)
+ flags |= FAST_PATH_IS_OPAQUE;
}
else if (image->common.type == BITS)
{
@@ -317,10 +320,48 @@ compute_image_info (pixman_image_t *image)
flags |= FAST_PATH_SIMPLE_REPEAT;
}
}
+
+ if (image->common.repeat != PIXMAN_REPEAT_NONE &&
+ !PIXMAN_FORMAT_A (image->bits.format))
+ {
+ flags |= FAST_PATH_IS_OPAQUE;
+ }
}
else
{
code = PIXMAN_unknown;
+
+ if (image->type == LINEAR || image->type == RADIAL)
+ {
+ if (image->common.repeat != PIXMAN_REPEAT_NONE)
+ {
+ int i;
+
+ flags |= FAST_PATH_IS_OPAQUE;
+
+ for (i = 0; i < image->gradient.n_stops; ++i)
+ {
+ if (image->gradient.stops[i].color.alpha != 0xffff)
+ {
+ flags &= ~FAST_PATH_IS_OPAQUE;
+ break;
+ }
+ }
+ }
+ }
+ }
+
+ /* Both alpha maps and convolution filters can introduce
+ * non-opaqueness in otherwise opaque images. Also
+ * an image with component alpha turned on is only opaque
+ * if all channels are opaque, so we simply turn it off
+ * unconditionally for those images.
+ */
+ if (image->common.alpha_map ||
+ image->common.filter == PIXMAN_FILTER_CONVOLUTION ||
+ image->common.component_alpha)
+ {
+ flags &= ~FAST_PATH_IS_OPAQUE;
}
image->common.flags = flags;
@@ -628,58 +669,3 @@ _pixman_image_get_solid (pixman_image_t * image,
return result;
}
-
-pixman_bool_t
-_pixman_image_is_opaque (pixman_image_t *image)
-{
- int i;
-
- if (image->common.alpha_map)
- return FALSE;
-
- switch (image->type)
- {
- case BITS:
- if (image->common.repeat == PIXMAN_REPEAT_NONE)
- return FALSE;
-
- if (PIXMAN_FORMAT_A (image->bits.format))
- return FALSE;
- break;
-
- case LINEAR:
- case RADIAL:
- if (image->common.repeat == PIXMAN_REPEAT_NONE)
- return FALSE;
-
- for (i = 0; i < image->gradient.n_stops; ++i)
- {
- if (image->gradient.stops[i].color.alpha != 0xffff)
- return FALSE;
- }
- break;
-
- case CONICAL:
- /* Conical gradients always have a transparent border */
- return FALSE;
- break;
-
- case SOLID:
- if (image->solid.color.alpha != 0xffff)
- return FALSE;
- break;
-
- default:
- return FALSE;
- break;
- }
-
- /* Convolution filters can introduce translucency if the sum of the
- * weights is lower than 1.
- */
- if (image->common.filter == PIXMAN_FILTER_CONVOLUTION)
- return FALSE;
-
- return TRUE;
-}
-
diff --git a/pixman/pixman-private.h b/pixman/pixman-private.h
index 1ad452a..d08440e 100644
--- a/pixman/pixman-private.h
+++ b/pixman/pixman-private.h
@@ -284,9 +284,6 @@ _pixman_image_reset_clip_region (pixman_image_t *image);
void
_pixman_image_validate (pixman_image_t *image);
-pixman_bool_t
-_pixman_image_is_opaque (pixman_image_t *image);
-
uint32_t
_pixman_image_get_solid (pixman_image_t * image,
pixman_format_code_t format);
@@ -579,6 +576,7 @@ _pixman_choose_implementation (void);
#define FAST_PATH_SCALE_TRANSFORM (1 << 10)
#define FAST_PATH_NEAREST_FILTER (1 << 11)
#define FAST_PATH_SIMPLE_REPEAT (1 << 12)
+#define FAST_PATH_IS_OPAQUE (1 << 13)
#define _FAST_PATH_STANDARD_FLAGS \
(FAST_PATH_ID_TRANSFORM | \
diff --git a/pixman/pixman.c b/pixman/pixman.c
index e1bef17..905c7b2 100644
--- a/pixman/pixman.c
+++ b/pixman/pixman.c
@@ -88,14 +88,13 @@ pixman_optimize_operator (pixman_op_t op,
pixman_bool_t is_source_opaque;
pixman_bool_t is_dest_opaque;
const optimized_operator_info_t *info = pixman_operator_can_be_optimized (op);
-
if (!info || mask_image)
return op;
- is_source_opaque = _pixman_image_is_opaque (src_image);
- is_dest_opaque = _pixman_image_is_opaque (dst_image);
+ is_source_opaque = src_image->common.flags & FAST_PATH_IS_OPAQUE;
+ is_dest_opaque = dst_image->common.flags & FAST_PATH_IS_OPAQUE;
- if (is_source_opaque == FALSE && is_dest_opaque == FALSE)
+ if (!is_source_opaque && !is_dest_opaque)
return op;
if (is_source_opaque && is_dest_opaque)