bitblt.c

Thu, 27 Dec 2001 11:17:28 +0000

author
eric
date
Thu, 27 Dec 2001 11:17:28 +0000
changeset 3
317de52d8a63
parent 2
8ca2aaf0513f
child 4
86a98659662f
permissions
-rw-r--r--

*** empty log message ***

     1 #include <stdlib.h>
     3 #include "bitblt.h"
     5 static inline u8 pixel_mask (x)
     6 {
     7 #ifdef LSB_LEFT
     8   return (1 << x);
     9 #else
    10   return (1 << (7 - x));
    11 #endif
    12 }
    14 static inline u32 rect_width (Rect r)
    15 {
    16   return (r.lower_right.x - r.upper_left.x);
    17 }
    19 static inline u32 rect_height (Rect r)
    20 {
    21   return (r.lower_right.y - r.upper_left.y);
    22 }
    24 Bitmap *create_bitmap (u32 width, u32 height)
    25 {
    26   Bitmap *bitmap;
    28   bitmap = calloc (1, sizeof (Bitmap));
    29   if (! bitmap)
    30     return (NULL);
    31   bitmap->width = width;
    32   bitmap->height = height;
    33   bitmap->rowbytes = (width - 1) / 8 + 1;
    34   bitmap->bits = calloc (height * bitmap->rowbytes, 1);
    35   if (! bitmap->bits)
    36     {
    37       free (bitmap);
    38       return (NULL);
    39     }
    40   return (bitmap);
    41 }
    43 void free_bitmap (Bitmap *bitmap)
    44 {
    45   free (bitmap->bits);
    46   free (bitmap);
    47 }
    49 boolean get_pixel (Bitmap *bitmap, Point coord)
    50 {
    51   u8 *p;
    52   if ((coord.x >= bitmap->width) || (coord.y >= bitmap->height))
    53     return (0);
    54   p = bitmap->bits + coord.y * bitmap->rowbytes + coord.x / 8;
    55   return ((*p & pixel_mask (coord.x & 7)) != 0);
    56 }
    58 void set_pixel (Bitmap *bitmap, Point coord, boolean value)
    59 {
    60   u8 *p;
    61   if ((coord.x >= bitmap->width) || (coord.y >= bitmap->height))
    62     return;
    63   p = bitmap->bits + coord.y * bitmap->rowbytes + coord.x / 8;
    64   if (value)
    65     *p |= pixel_mask (coord.x & 7);
    66   else
    67     *p &= (0xff ^ pixel_mask (coord.x & 7));
    68 }
    71 Bitmap *bitblt (Bitmap *src_bitmap,
    72 		Rect src_rect,
    73 		Bitmap *dest_bitmap,
    74 		Point dest_upper_left,
    75 		int scan,
    76 		int tfn)
    77 {
    78   Point src_point, dest_point;
    79   boolean src_pixel, dest_pixel;
    81   if (! dest_bitmap)
    82     {
    83       if (scan & TRANSPOSE)
    84 	dest_bitmap = create_bitmap (rect_height (src_rect),
    85 				     rect_width (src_rect));
    86       else
    87 	dest_bitmap = create_bitmap (rect_width (src_rect),
    88 				     rect_height (src_rect));
    89       if (! dest_bitmap)
    90 	return (NULL);
    91     }
    93   for (src_point.y = src_rect.upper_left.y;
    94        src_point.y < src_rect.lower_right.y;
    95        src_point.y++)
    96     {
    97       for (src_point.x = src_rect.upper_left.x;
    98 	   src_point.x < src_rect.lower_right.x;
    99 	   src_point.x++)
   100 	{
   101 	  boolean a, b, c;
   103 	  if (scan & TRANSPOSE)
   104 	    {
   105 	      dest_point.x = src_point.y - src_rect.upper_left.y;
   106 	      dest_point.y = src_point.x - src_rect.upper_left.x;
   108 	      if (scan & FLIP_H)
   109 		dest_point.x = (rect_height (src_rect) - 1) - dest_point.x;
   111 	      if (scan & FLIP_V)
   112 		dest_point.y = (rect_width (src_rect) - 1) - dest_point.y;
   113 	    }
   114 	  else
   115 	    {
   116 	      dest_point.x = src_point.x - src_rect.upper_left.x;
   117 	      dest_point.y = src_point.y - src_rect.upper_left.y;
   119 	      if (scan & FLIP_H)
   120 		dest_point.x = (rect_width (src_rect) - 1) - dest_point.x;
   122 	      if (scan & FLIP_V)
   123 		dest_point.y = (rect_height (src_rect) - 1) - dest_point.y;
   124 	    }
   126 	  dest_point.x += dest_upper_left.x;
   127 	  dest_point.y += dest_upper_left.y;
   129 	  a = get_pixel (src_bitmap, src_point);
   130 	  b = get_pixel (dest_bitmap, dest_point);
   131 	  c = (tfn & (1 << (a * 2 + b))) != 0;
   133 	  set_pixel (dest_bitmap, dest_point, c);
   134 	}
   135     }
   136   return (dest_bitmap);
   137 }