Add code to initialize images, based on picture.c from the X server
authorSoren Sandmann Pedersen <ssp@dhcp83-218.boston.redhat.com>
Sat, 5 May 2007 02:07:19 +0000 (22:07 -0400)
committerSoren Sandmann Pedersen <ssp@dhcp83-218.boston.redhat.com>
Sat, 5 May 2007 02:07:19 +0000 (22:07 -0400)
pixman/Makefile.am
pixman/pixman-image.c
pixman/pixman-private.h [new file with mode: 0644]
pixman/pixman.h

index e53d3af..ef378d5 100644 (file)
@@ -2,9 +2,12 @@ lib_LTLIBRARIES = libpixman.la
 
 libpixman_la_LIBADD = @DEP_LIBS@
 
-libpixman_la_SOURCES =  \
-        pixman.h        \
-        pixman-region.c
+libpixman_la_SOURCES =    \
+        pixman.h         \
+        pixman-region.c  \
+        pixman-private.h \
+        pixman-image.c
+#       pixman-compose.c
 
 libpixmanincludedir = $(includedir)/libcomp
 libpixmaninclude_HEADERS = pixman.h
index 9439199..dca04cd 100644 (file)
  * Author:  Soren Sandmann, Red Hat, Inc.
  */
 
-#include "pixman.h"
-
-typedef struct image image_t;
+#include <stdlib.h>
 
-struct image
-{
-    pixman_format_code_t       format;
-    int                                width;
-    int                                height;
-    uint8_t *                  bits;
-    int                                rowstride; /* in bytes */
-};
+#include "pixman.h"
+#include "pixman-private.h"
 
 void
 pixman_image_init_bits (pixman_image_t         *image,
                        pixman_format_code_t    format,
                        int                     width,
-                       int                     height
+                       int                     height,
                        uint8_t                *bits,
                        int                     rowstride)
 {
     image_t *img = (image_t *)image;
 
-    img->format = format;
-    img->width = width;
-    img->height = height;
-    img->bits = bits;
-    img->rowstride = rowstride;
+    img->type = BITS;
+    img->bits.format = format;
+    img->bits.width = width;
+    img->bits.height = height;
+    img->bits.bits = bits;
+    img->bits.rowstride = rowstride;
 }
 
 void
@@ -58,6 +51,178 @@ pixman_set_clip_region (pixman_image_t    *image,
     
 }
 
+enum
+{
+    PIXMAN_BAD_VALUE,
+    PIXMAN_BAD_ALLOC
+};
+
+static void
+init_source_image (source_image_t *image)
+{
+    image->class = SOURCE_IMAGE_CLASS_UNKNOWN;
+}
+
+static void
+init_gradient (gradient_t     *gradient,
+              int             stop_count,
+              pixman_fixed_t *stop_points,
+              pixman_color_t *stop_colors,
+              int *error)
+{
+    int i;
+    pixman_fixed_t dpos;
+
+    if (stop_count <= 0)
+    {
+        *error = PIXMAN_BAD_VALUE;
+        return;
+    }
+
+    init_source_image (&gradient->common);
+    
+    dpos = -1;
+    for (i = 0; i < stop_count; ++i)
+    {
+        if (stop_points[i] < dpos || stop_points[i] > (1<<16))
+       {
+            *error = PIXMAN_BAD_VALUE;
+            return;
+        }
+        dpos = stop_points[i];
+    }
+
+    gradient->stops = malloc (stop_count * sizeof (gradient_stop_t));
+    if (!gradient->stops)
+    {
+        *error = PIXMAN_BAD_ALLOC;
+        return;
+    }
+
+    gradient->n_stops = stop_count;
+
+    for (i = 0; i < stop_count; ++i)
+    {
+        gradient->stops[i].x = stop_points[i];
+        gradient->stops[i].color = stop_colors[i];
+    }
+
+    gradient->stop_range = 0xffff;
+    gradient->color_table = NULL;
+    gradient->color_table_size = 0;
+}
+
+static uint32_t
+color_to_uint32 (const pixman_color_t *color)
+{
+    return
+       (color->alpha >> 8 << 24) |
+       (color->red >> 8 << 16) |
+        (color->green & 0xff00) |
+       (color->blue >> 8);
+}
+
+void
+pixman_image_init_solid_fill (pixman_image_t *image,
+                             pixman_color_t *color,
+                             int            *error)
+{
+    image_t *priv = (image_t *)image;
+    priv->type = SOLID;
+    priv->solid.color = color_to_uint32 (color);
+}
+
+void
+pixman_image_init_linear_gradient (pixman_image_t       *image,
+                                  pixman_point_fixed_t *p1,
+                                  pixman_point_fixed_t *p2,
+                                  int                   n_stops,
+                                  pixman_fixed_t       *stops,
+                                  pixman_color_t       *colors,
+                                  int                  *error)
+{
+    image_t *priv = (image_t *)image;
+    linear_gradient_t *linear = &priv->linear;
+    
+    if (n_stops < 2)
+    {
+        *error = PIXMAN_BAD_VALUE;
+        return;
+    }
+    
+    init_gradient (&linear->common, n_stops, stops, colors, error);
+
+    linear->p1 = *p1;
+    linear->p2 = *p2;
+
+    priv->type = LINEAR;
+}
+
+
+void
+pixman_image_init_radial_gradient (pixman_image_t *image,
+                                  pixman_point_fixed_t *inner,
+                                  pixman_point_fixed_t *outer,
+                                  pixman_fixed_t inner_radius,
+                                  pixman_fixed_t outer_radius,
+                                  int             n_stops,
+                                  pixman_fixed_t *stops,
+                                  pixman_color_t *colors,
+                                  int            *error)
+{
+    image_t *priv = (image_t *)image;
+    radial_gradient_t *radial = &priv->radial;
+
+    if (n_stops < 2)
+    {
+        *error = PIXMAN_BAD_VALUE;
+       return;
+    }
+
+    init_gradient (&radial->common, n_stops, stops, colors, error);
+
+    priv->type = RADIAL;
+    
+    radial->c1.x = inner->x;
+    radial->c1.y = inner->y;
+    radial->c1.radius = inner_radius;
+    radial->c2.x = outer->x;
+    radial->c2.y = outer->y;
+    radial->c2.radius = outer_radius;
+    radial->cdx = (radial->c2.x - radial->c1.x) / 65536.;
+    radial->cdy = (radial->c2.y - radial->c1.y) / 65536.;
+    radial->dr = (radial->c2.radius - radial->c1.radius) / 65536.;
+    radial->A = (  radial->cdx * radial->cdx
+                  + radial->cdy * radial->cdy
+                  - radial->dr  * radial->dr);
+}
+
+void
+pixman_image_init_conical_gradient (pixman_image_t *image,
+                                   pixman_point_fixed_t *center,
+                                   pixman_fixed_t angle,
+                                   int n_stops,
+                                   pixman_fixed_t *stops,
+                                   pixman_color_t *colors,
+                                   int *error)
+{
+    image_t *priv = (image_t *)image;
+    conical_gradient_t *conical = &priv->conical;
+
+    if (n_stops < 2)
+    {
+       *error = PIXMAN_BAD_VALUE;
+       return;
+    }
+
+    init_gradient (&conical->common, n_stops, stops, colors, error);
+
+    priv->type = CONICAL;
+    conical->center = *center;
+    conical->angle = angle;
+}
+
+#define SCANLINE_BUFFER_LENGTH 1024
 
 void
 pixman_composite (pixman_image_t       *src_img,
diff --git a/pixman/pixman-private.h b/pixman/pixman-private.h
new file mode 100644 (file)
index 0000000..695342c
--- /dev/null
@@ -0,0 +1,157 @@
+typedef union  image image_t;
+typedef struct source_image source_image_t;
+typedef struct solid_fill solid_fill_t;
+typedef struct gradient gradient_t;
+typedef struct linear_gradient linear_gradient_t;
+typedef struct horizontal_gradient horizontal_gradient_t;
+typedef struct vertical_gradient vertical_gradient_t;
+typedef struct conical_gradient conical_gradient_t;
+typedef struct radial_gradient radial_gradient_t;
+typedef struct bits_image bits_image_t;
+typedef struct gradient_stop gradient_stop_t;
+typedef struct circle circle_t;
+
+typedef enum
+{
+    BITS,
+    LINEAR,
+    CONICAL,
+    RADIAL,
+    SOLID
+} image_type_t;
+
+struct gradient_stop
+{
+    pixman_fixed_t x;
+    pixman_color_t color;
+};
+
+typedef enum
+{
+    SOURCE_IMAGE_CLASS_UNKNOWN,
+    SOURCE_IMAGE_CLASS_HORIZONTAL,
+    SOURCE_IMAGE_CLASS_VERTICAL
+} source_pict_class_t;
+
+struct source_image
+{
+    image_type_t       type;
+    unsigned int       class;          /* FIXME: should be an enum */
+};
+
+struct solid_fill
+{
+    source_image_t     common;
+    uint32_t           color;          /* FIXME: shouldn't this be a pixman_color_t? */
+};
+    
+struct gradient
+{
+    source_image_t     common;
+    int                        n_stops;
+    gradient_stop_t *  stops;
+    int                        stop_range;
+    uint32_t *         color_table;
+    int                        color_table_size;
+};
+
+struct linear_gradient
+{
+    gradient_t                 common;
+    pixman_point_fixed_t       p1;
+    pixman_point_fixed_t       p2;
+};
+
+struct circle
+{
+    pixman_fixed_t x;
+    pixman_fixed_t y;
+    pixman_fixed_t radius;
+};
+
+struct radial_gradient
+{
+    gradient_t common;
+
+    circle_t   c1;
+    circle_t   c2;
+    double     cdx;
+    double     cdy;
+    double     dr;
+    double     A;
+};
+
+struct conical_gradient
+{
+    gradient_t                 common;
+    pixman_point_fixed_t       center;
+    pixman_fixed_t             angle;
+}; 
+
+struct bits_image
+{
+    image_type_t               type;
+    pixman_format_code_t       format;
+    int                                width;
+    int                                height;
+    uint8_t *                  bits;
+    int                                rowstride; /* in bytes */
+};
+
+union image
+{
+    image_type_t               type;
+    bits_image_t               bits;
+    linear_gradient_t          linear;
+    conical_gradient_t         conical;
+    radial_gradient_t          radial;
+    solid_fill_t               solid;
+};
+
+
+
+
+#if 0
+typedef struct _Picture {
+    DrawablePtr            pDrawable;
+    PictFormatPtr   pFormat;
+    PictFormatShort format;        /* PICT_FORMAT */
+    int                    refcnt;
+    CARD32         id;
+    PicturePtr     pNext;          /* chain on same drawable */
+
+    unsigned int    repeat : 1;
+    unsigned int    graphicsExposures : 1;
+    unsigned int    subWindowMode : 1;
+    unsigned int    polyEdge : 1;
+    unsigned int    polyMode : 1;
+    unsigned int    freeCompClip : 1;
+    unsigned int    clientClipType : 2;
+    unsigned int    componentAlpha : 1;
+    unsigned int    repeatType : 2;
+    unsigned int    unused : 21;
+
+    PicturePtr     alphaMap;
+    DDXPointRec            alphaOrigin;
+
+    DDXPointRec            clipOrigin;
+    pointer        clientClip;
+
+    Atom           dither;
+
+    unsigned long   stateChanges;
+    unsigned long   serialNumber;
+
+    RegionPtr      pCompositeClip;
+
+    DevUnion       *devPrivates;
+
+    PictTransform   *transform;
+
+    int                    filter;
+    xFixed         *filter_params;
+    int                    filter_nparams;
+    SourcePictPtr   pSourcePict;
+} PictureRec;
+#endif
+
index 233e531..09f3625 100644 (file)
@@ -45,6 +45,7 @@ SOFTWARE.
 ******************************************************************/
 /*
  * Copyright © 1998 Keith Packard
+ * Copyright   2007 Red Hat, Inc.
  *
  * Permission to use, copy, modify, distribute, and sell this software and its
  * documentation for any purpose is hereby granted without fee, provided that
@@ -92,6 +93,10 @@ typedef unsigned __int64 uint64_t;
 #endif
 
 typedef int pixman_bool_t;
+typedef uint32_t pixman_fixed_t;
+typedef struct pixman_color pixman_color_t;
+typedef struct pixman_point_fixed pixman_point_fixed_t;
+typedef struct pixman_line_fixed pixman_line_fixed_t;
 
 #ifndef FALSE
 #define FALSE 0
@@ -101,6 +106,25 @@ typedef int pixman_bool_t;
 #define TRUE 1
 #endif
 
+struct pixman_color
+{
+    uint16_t   red;
+    uint16_t    green;
+    uint16_t    blue;
+    uint16_t    alpha;
+};
+
+struct pixman_point_fixed
+{
+    pixman_fixed_t     x;
+    pixman_fixed_t     y;
+};
+
+struct pixman_line_fixed
+{
+    pixman_point_fixed_t       p1, p2;
+};
+
 /*
  * Regions
  */