all i have to say is.... OH YEAH! animated alpha blends on my root window...

got a 640x480 image blending WIHT its alpha channel on my root window...
drawing at... 20 frames per second... now if that dont make me happy.. i
dont know what will :)


SVN revision: 36
This commit is contained in:
Carsten Haitzler 1999-08-06 02:08:36 +00:00
parent 73b5d6a7ce
commit 8a957fb01b
7 changed files with 278 additions and 38 deletions

73
api.c
View File

@ -20,6 +20,7 @@ char
imlib_init(void)
{
__imlib_RGBA_init();
return 1;
}
int
@ -289,3 +290,75 @@ imlib_render_image_on_drawable_at_size(Imlib_Image image, Display *display,
dithered_rendering,
alpha_blending, 0);
}
void
imlib_blend_image_onto_image(Imlib_Image source_image,
Imlib_Image destination_image,
int source_x, int source_y,
int source_width, int source_height,
int destination_x, int destination_y,
int destination_width, int destination_height)
{
ImlibImage *im_src, *im_dst;
CAST_IMAGE(im_src, source_image);
CAST_IMAGE(im_dst, destination_image);
/* FIXME: doesnt do clipping in any way or form - must fix */
__imlib_BlendRGBAToRGBA(im_src->data, 0, im_dst->data, 0,
source_width, source_height);
}
Imlib_Image
imlib_create_image_using_data(int width, int height,
DATA32 *data)
{
return (Imlib_Image)__imlib_CreateImage(width, height, data);
}
Imlib_Image
imlib_create_image_using_copied_data(int width, int height,
DATA32 *data)
{
ImlibImage *im;
im = __imlib_CreateImage(width, height, NULL);
im->data = malloc(width * height *sizeof(DATA32));
memcpy(im->data, data, width * height *sizeof(DATA32));
return (Imlib_Image)im;
}
Imlib_Image
imlib_create_image_from_drawable(Display *display,
Drawable drawable,
Pixmap mask, Visual *visual,
Colormap colormap, int depth,
int x, int y,
int width, int height)
{
ImlibImage *im;
char domask = 0;
if (mask)
domask = 1;
im = __imlib_CreateImage(width, height, NULL);
im->data = __imlib_GrabDrawableToRGBA(display, drawable, mask, visual,
colormap, depth, x, y, width, height,
domask);
return (Imlib_Image)im;
}
Imlib_Image
imlib_clone_image(Imlib_Image image)
{
ImlibImage *im, *im_old;
CAST_IMAGE(im_old, image);
im = __imlib_CreateImage(im_old->w, im_old->h, NULL);
im->data = malloc(im->w * im->h *sizeof(DATA32));
memcpy(im->data, im_old->data, im->w * im->h *sizeof(DATA32));
return (Imlib_Image)im;
}

32
api.h
View File

@ -2,10 +2,10 @@
#define __IMLIB_API_H 1
#ifndef DATA64
#define DATA64 unsigned long long
#define DATA32 unsigned int
#define DATA16 unsigned short
#define DATA8 unsigned char
# define DATA64 unsigned long long
# define DATA32 unsigned int
# define DATA16 unsigned short
# define DATA8 unsigned char
#endif
/* data types - guess what - no transparent datatypes - all hidden */
@ -54,6 +54,8 @@ void imlib_image_get_border(Imlib_Image image, Imlib_Border *border);
void imlib_image_set_border(Imlib_Image image, Imlib_Border *border);
char *imlib_image_format(Imlib_Image image);
/* image drawing/rendering functions */
void imlib_render_pixmaps_for_whole_image(Imlib_Image image, Display *display,
Drawable drawable, Visual *visual,
Colormap colormap, int depth,
@ -85,5 +87,25 @@ void imlib_render_image_on_drawable_at_size(Imlib_Image image, Display *display,
char dithered_rendering,
char alpha_blending,
int x, int y, int width, int height);
/* image drawing/rendering functions */
/* rgba space ops */
void imlib_blend_image_onto_image(Imlib_Image source_image,
Imlib_Image destination_image,
int source_x, int source_y,
int source_width, int source_height,
int destination_x, int destination_y,
int destination_width, int destination_height);
/* image creation and grabbing */
Imlib_Image imlib_create_image_using_data(int width, int height,
DATA32 *data);
Imlib_Image imlib_create_image_using_copied_data(int width, int height,
DATA32 *data);
Imlib_Image imlib_create_image_from_drawable(Display *display,
Drawable drawable,
Pixmap mask, Visual *visual,
Colormap colormap, int depth,
int x, int y,
int width, int height);
Imlib_Image imlib_clone_image(Imlib_Image image);
#endif

75
blend.c
View File

@ -5,32 +5,51 @@ void
__imlib_BlendRGBAToRGBA(DATA32 *src, int src_jump, DATA32 *dst, int dst_jump,
int w, int h)
{
int x, y;
DATA32 *p1, *p2;
for (y = 0; y < h; y++)
{
DATA8 a, nr, ng, nb, r, g, b, rr, gg, bb;
int tmp;
p1 = src + (y * (w + src_jump));
p2 = dst + (y * (w + dst_jump));
for (x = 0; x < w; x++)
{
a = (*p1 >> 24) & 0xff;
if (a < 255)
{
r = 255 - a;
*p2 =
((((*p1 & 0x00ff00ff) * a) >> 8) & 0x00ff00ff) +
((((*p1 >> 8) & 0x00ff00ff) * a) & 0xff00ff00) +
((((*p2 & 0x00ff00ff) * r) >> 8) & 0x00ff00ff) +
((((*p2 >> 8) & 0x00ff00ff) * r) & 0xff00ff00);
}
else
*p2 = *p1;
p1++;
p2++;
}
}
int x, y;
DATA32 *p1, *p2;
for (y = 0; y < h; y++)
{
DATA8 a, nr, ng, nb, r, g, b, rr, gg, bb;
int tmp;
p1 = src + (y * (w + src_jump));
p2 = dst + (y * (w + dst_jump));
for (x = 0; x < w; x++)
{
a = (*p1 >> 24) & 0xff;
if (a < 255)
{
/* funny - i cant tell much of a speed diff between these 2 */
#if 0
r = 255 - a;
*p2 =
((((*p1 & 0x00ff00ff) * a) >> 8) & 0x00ff00ff) +
((((*p1 >> 8) & 0x00ff00ff) * a) & 0xff00ff00) +
((((*p2 & 0x00ff00ff) * r) >> 8) & 0x00ff00ff) +
((((*p2 >> 8) & 0x00ff00ff) * r) & 0xff00ff00);
#else
r = (*p1 ) & 0xff;
g = (*p1 >> 8 ) & 0xff;
b = (*p1 >> 16) & 0xff;
rr = (*p2 ) & 0xff;
gg = (*p2 >> 8 ) & 0xff;
bb = (*p2 >> 16) & 0xff;
tmp = (r - rr) * a;
nr = rr + ((tmp + (tmp >> 8) + 0x80) >> 8);
tmp = (g - gg) * a;
ng = gg + ((tmp + (tmp >> 8) + 0x80) >> 8);
tmp = (b - bb) * a;
nb = bb + ((tmp + (tmp >> 8) + 0x80) >> 8);
*p2 = ((nb & 0xff) << 16) | ((ng & 0xff) << 8) | (nr & 0xff);
#endif
}
else
*p2 = *p1;
p1++;
p2++;
}
}
}

6
grab.c
View File

@ -64,6 +64,8 @@ __imlib_GrabDrawableToRGBA(Display *d, Drawable p, Pixmap m, Visual *v, Colormap
Window dw;
XGetWindowAttributes(d, xatt.root, &ratt);
XTranslateCoordinates(d, p, xatt.root, 0, 0, &src_x, &src_y, &dw);
src_w = xatt.width;
src_h = xatt.height;
if ((xatt.map_state != IsViewable) &&
(xatt.backing_store == NotUseful))
{
@ -75,8 +77,8 @@ __imlib_GrabDrawableToRGBA(Display *d, Drawable p, Pixmap m, Visual *v, Colormap
/* clip to the drawable tree and screen */
clipx = 0;
clipy = 0;
width = xatt.width - x;
height = xatt.height - y;
width = src_w - x;
height = src_h - y;
if (width > w)
width = w;
if (height > h)

32
image.c
View File

@ -184,7 +184,7 @@ __imlib_CleanupImageCache(void)
__imlib_ConsumeImage(im_last);
}
}
while ((current_cache > cache_size) || (operation));
while ((current_cache > cache_size) || (operation))
{
im_last = NULL;
operation = 0;
@ -320,7 +320,7 @@ __imlib_CleanupImagePixmapCache()
__imlib_ConsumeImagePixmap(ip_last);
}
}
while ((current_cache > cache_size) || (operation));
while ((current_cache > cache_size) || (operation))
{
ip_last = NULL;
operation = 0;
@ -594,6 +594,28 @@ __imlib_FindBestLoaderForFile(char *file)
return l;
}
void
__imlib_SetImageAlphaFlag(ImlibImage *im, char alpha)
{
if (alpha)
SET_FLAG(im->flags, F_HAS_ALPHA);
else
UNSET_FLAG(im->flags, F_HAS_ALPHA);
}
ImlibImage *
__imlib_CreateImage(int w, int h, DATA32 *data)
{
ImlibImage *im;
im = __imlib_ProduceImage();
im->w = w;
im->h = h;
im->data = data;
im->references = 1;
SET_FLAG(im->flags, F_UNCACHEABLE);
}
ImlibImage *
__imlib_LoadImage(char *file,
void (*progress)(ImlibImage *im, char percent,
@ -711,6 +733,12 @@ __imlib_FreeImage(ImlibImage *im)
if (im->references > 0)
{
im->references--;
if (IMAGE_IS_UNCACHEABLE(im))
{
if (im->references == 0)
__imlib_ConsumeImage(im);
}
else
__imlib_CleanupImageCache();
}
}

View File

@ -81,6 +81,7 @@ void __imlib_ConsumeImage(ImlibImage *im);
ImlibImage *__imlib_FindCachedImage(char *file);
void __imlib_AddImageToCache(ImlibImage *im);
void __imlib_RemoveImageFromCache(ImlibImage *im);
int __imlib_CurrentCacheSize(void);
void __imlib_CleanupImageCache(void);
ImlibImagePixmap *__imlib_ProduceImagePixmap(void);
void __imlib_ConsumeImagePixmap(ImlibImagePixmap *ip);
@ -99,6 +100,8 @@ void __imlib_RescanLoaders(void);
void __imlib_RemoveAllLoaders(void);
void __imlib_LoadAllLoaders(void);
ImlibLoader *__imlib_FindBestLoaderForFile(char *file);
void __imlib_SetImageAlphaFlag(ImlibImage *im, char alpha);
ImlibImage *__imlib_CreateImage(int w, int h, DATA32 *data);
ImlibImage *__imlib_LoadImage(char *file,
void (*progress)(ImlibImage *im, char percent,
int update_x, int update_y,

95
main.c
View File

@ -4,15 +4,24 @@
#include <X11/extensions/shape.h>
#include <X11/Xatom.h>
#include <X11/Xos.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <unistd.h>
/*
#include <sys/time.h>
#include "common.h"
#include "image.h"
#include "rend.h"
#include "rgba.h"
#include "ximage.h"
#include "color.h"
*/
#include "api.h"
Display *disp;
#if 0
int main (int argc, char **argv)
{
Window win;
@ -151,3 +160,87 @@ int main (int argc, char **argv)
printf("%3.3f Mpixels / sec\n", (double)(pixels) / (sec * 1000000));
return 0;
}
#endif
int main (int argc, char **argv)
{
Window win;
/*
Pixmap back, scratch;
GC gc;
*/
XGCValues gcv;
Imlib_Image *im = NULL, tmp, grab;
int x, y, start, i, w, h;
Visual *vis;
int depth;
int dith = 0;
int blend = 0;
DATA32 *data1, *data2;
Colormap cm;
start = 1;
x = 0;
y = 0;
for (i = 1; i < argc; i++)
{
if (!strcmp(argv[i], "-blend"))
blend = 1;
else if (!strcmp(argv[i], "-dither"))
dith = 1;
else if (!strcmp(argv[i], "-pos"))
{
i++;
x = atoi(argv[i++]);
y = atoi(argv[i]);
}
else
{
start = i;
i = argc;
}
}
disp = XOpenDisplay(NULL);
imlib_init();
printf("load\n");
im = malloc(sizeof(Imlib_Image) * (argc - start));
for (i = start; i < argc; i++)
im[i - start] = imlib_load_image(argv[i]);
win = DefaultRootWindow(disp);
vis = DefaultVisual(disp, DefaultScreen(disp));
depth = DefaultDepth(disp, DefaultScreen(disp));
cm = DefaultColormap(disp, DefaultScreen(disp));
if (depth == 8)
__imlib_AllocColorTable(disp, cm);
__imlib_SetMaxXImageCount(disp, 0);
XSync(disp, False);
printf("init\n");
w = imlib_get_image_width(im[0]);
h = imlib_get_image_height(im[0]);
/*
gc = XCreateGC(disp, win, 0, &gcv);
back = XCreatePixmap(disp, win, w, h, depth);
scratch = XCreatePixmap(disp, win, w, h, depth);
XCopyArea(disp, win, back, gc, x, y, w, h, 0, 0);
XCopyArea(disp, back, scratch, gc, 0, 0, w, h, 0, 0);
*/
grab = imlib_create_image_from_drawable(disp, win, 0, vis, cm, depth,
x, y, w, h);
tmp = imlib_clone_image(grab);
data1 = imlib_get_image_data(grab);
data2 = imlib_get_image_data(tmp);
printf("animate\n");
for(;;)
{
for (i = 0; i < (argc - start); i++)
{
imlib_blend_image_onto_image(im[i], tmp, 0, 0, w, h, 0, 0, w, h);
imlib_render_image_on_drawable(tmp, disp, win, vis, cm, depth,
0, dith, 0,
x, y);
memcpy(data2, data1, w * h *sizeof(DATA32));
}
}
return 0;
}