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:
parent
73b5d6a7ce
commit
8a957fb01b
73
api.c
73
api.c
|
@ -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
32
api.h
|
@ -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
75
blend.c
|
@ -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
6
grab.c
|
@ -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
32
image.c
|
@ -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();
|
||||
}
|
||||
}
|
||||
|
|
3
image.h
3
image.h
|
@ -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
95
main.c
|
@ -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;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue