* implemented filter_black_stuff to remove black dots. * allow threshold to be negative in filter_equalize; in this case, invert colours. * implemented filter_crop. git-svn-id: file:///srv/caca.zoy.org/var/lib/svn/pwntcha/trunk@413 92316355-f0b4-4df1-b90c-862c8a59935fmaster
@@ -27,9 +27,10 @@ char *decode_slashdot(struct image *img); | |||||
char *decode_test(struct image *img); | char *decode_test(struct image *img); | ||||
/* image operations */ | /* image operations */ | ||||
struct image *image_load(char *name); | |||||
struct image *image_load(const char *name); | |||||
struct image *image_new(int width, int height); | struct image *image_new(int width, int height); | ||||
void image_free(struct image *img); | void image_free(struct image *img); | ||||
void image_save(struct image *img, const char *name); | |||||
void image_display(struct image *img); | void image_display(struct image *img); | ||||
int getgray(struct image *img, int x, int y, int *g); | int getgray(struct image *img, int x, int y, int *g); | ||||
int getpixel(struct image *img, int x, int y, int *r, int *g, int *b); | int getpixel(struct image *img, int x, int y, int *r, int *g, int *b); | ||||
@@ -39,11 +40,14 @@ int setpixel(struct image *img, int x, int y, int r, int g, int b); | |||||
void filter_flood_fill(struct image *img, int x, int y, int r, int g, int b); | void filter_flood_fill(struct image *img, int x, int y, int r, int g, int b); | ||||
struct image *filter_fill_holes(struct image *img); | struct image *filter_fill_holes(struct image *img); | ||||
struct image *filter_dup(struct image *img); | struct image *filter_dup(struct image *img); | ||||
struct image *filter_black_stuff(struct image *img); | |||||
struct image *filter_detect_lines(struct image *img); | struct image *filter_detect_lines(struct image *img); | ||||
struct image *filter_equalize(struct image *img, int threshold); | struct image *filter_equalize(struct image *img, int threshold); | ||||
struct image *filter_trick(struct image *img); | struct image *filter_trick(struct image *img); | ||||
struct image *filter_smooth(struct image *img); | struct image *filter_smooth(struct image *img); | ||||
struct image *filter_median(struct image *img); | struct image *filter_median(struct image *img); | ||||
struct image *filter_contrast(struct image *img); | struct image *filter_contrast(struct image *img); | ||||
struct image *filter_crop(struct image *img, | |||||
int xmin, int ymin, int xmax, int ymax); | |||||
int filter_count(struct image *img); | int filter_count(struct image *img); | ||||
@@ -120,6 +120,46 @@ struct image *filter_fill_holes(struct image *img) | |||||
return dst; | return dst; | ||||
} | } | ||||
struct image *filter_black_stuff(struct image *img) | |||||
{ | |||||
struct image *dst; | |||||
int x, y; | |||||
int r, ra, rb, g, b; | |||||
dst = image_new(img->width, img->height); | |||||
/* Remove vertical stuff */ | |||||
for(y = 0; y < img->height; y++) | |||||
for(x = 0; x < img->width; x++) | |||||
{ | |||||
getpixel(img, x, y, &r, &g, &b); | |||||
setpixel(dst, x, y, r, g, b); | |||||
if(y > 0 && y < img->height - 1) | |||||
{ | |||||
getpixel(img, x, y - 1, &ra, &g, &b); | |||||
getpixel(img, x, y + 1, &rb, &g, &b); | |||||
if(r < ra && (r - ra) * (r - rb) > 5000) | |||||
setpixel(dst, x, y, ra, ra, ra); | |||||
} | |||||
} | |||||
/* Remove horizontal stuff */ | |||||
for(y = 0; y < img->height; y++) | |||||
for(x = 0; x < img->width; x++) | |||||
{ | |||||
getpixel(img, x, y, &r, &g, &b); | |||||
if(x > 0 && x < img->width - 1) | |||||
{ | |||||
getpixel(dst, x - 1, y, &ra, &g, &b); | |||||
getpixel(dst, x + 1, y, &rb, &g, &b); | |||||
if(r < ra && (r - ra) * (r - rb) > 5000) | |||||
setpixel(dst, x, y, ra, ra, ra); | |||||
} | |||||
} | |||||
return dst; | |||||
} | |||||
struct image *filter_detect_lines(struct image *img) | struct image *filter_detect_lines(struct image *img) | ||||
{ | { | ||||
struct image *dst; | struct image *dst; | ||||
@@ -165,15 +205,25 @@ struct image *filter_equalize(struct image *img, int threshold) | |||||
struct image *dst; | struct image *dst; | ||||
int x, y; | int x, y; | ||||
int r, g, b; | int r, g, b; | ||||
int min = 0, max = 255; | |||||
dst = image_new(img->width, img->height); | dst = image_new(img->width, img->height); | ||||
if(threshold < 0) | |||||
{ | |||||
min = 255; | |||||
max = 0; | |||||
threshold = -threshold; | |||||
} | |||||
for(y = 0; y < img->height; y++) | for(y = 0; y < img->height; y++) | ||||
for(x = 0; x < img->width; x++) | for(x = 0; x < img->width; x++) | ||||
{ | { | ||||
getpixel(img, x, y, &r, &g, &b); | getpixel(img, x, y, &r, &g, &b); | ||||
if(r < threshold) r = 0; else r = 255; | |||||
setpixel(dst, x, y, r, r, r); | |||||
if(r < threshold) | |||||
setpixel(dst, x, y, min, min, min); | |||||
else | |||||
setpixel(dst, x, y, max, max, max); | |||||
} | } | ||||
return dst; | return dst; | ||||
@@ -329,6 +379,37 @@ struct image *filter_contrast(struct image *img) | |||||
return dst; | return dst; | ||||
} | } | ||||
struct image *filter_crop(struct image *img, | |||||
int xmin, int ymin, int xmax, int ymax) | |||||
{ | |||||
struct image *dst; | |||||
int x, y; | |||||
int r, g, b; | |||||
if(xmin < 0) | |||||
xmin = 0; | |||||
if(ymin < 0) | |||||
ymin = 0; | |||||
if(xmax >= img->width) | |||||
xmax = img->width - 1; | |||||
if(ymax >= img->height) | |||||
ymax = img->height - 1; | |||||
if(xmin >= xmax || ymin >= ymax) | |||||
return NULL; | |||||
dst = image_new(xmax - xmin, ymax - ymin); | |||||
for(y = 0; y < dst->height; y++) | |||||
for(x = 0; x < dst->width; x++) | |||||
{ | |||||
getpixel(img, xmin + x, ymin + y, &r, &g, &b); | |||||
setpixel(dst, x, y, r, g, b); | |||||
} | |||||
return dst; | |||||
} | |||||
int filter_count(struct image *img) | int filter_count(struct image *img) | ||||
{ | { | ||||
int histo[256]; | int histo[256]; | ||||
@@ -26,7 +26,7 @@ | |||||
# error "No imaging library" | # error "No imaging library" | ||||
#endif | #endif | ||||
struct image *image_load(char *name) | |||||
struct image *image_load(const char *name) | |||||
{ | { | ||||
struct image *img; | struct image *img; | ||||
#if defined(HAVE_SDL_IMAGE_H) | #if defined(HAVE_SDL_IMAGE_H) | ||||
@@ -76,12 +76,12 @@ struct image *image_new(int width, int height) | |||||
rmask = 0xff000000; | rmask = 0xff000000; | ||||
gmask = 0x00ff0000; | gmask = 0x00ff0000; | ||||
bmask = 0x0000ff00; | bmask = 0x0000ff00; | ||||
amask = 0x000000ff; | |||||
amask = 0x00000000; | |||||
# else | # else | ||||
rmask = 0x000000ff; | rmask = 0x000000ff; | ||||
gmask = 0x0000ff00; | gmask = 0x0000ff00; | ||||
bmask = 0x00ff0000; | bmask = 0x00ff0000; | ||||
amask = 0xff000000; | |||||
amask = 0x00000000; | |||||
# endif | # endif | ||||
priv = SDL_CreateRGBSurface(SDL_SWSURFACE, width, height, 32, | priv = SDL_CreateRGBSurface(SDL_SWSURFACE, width, height, 32, | ||||
rmask, gmask, bmask, amask); | rmask, gmask, bmask, amask); | ||||
@@ -136,6 +136,18 @@ void image_free(struct image *img) | |||||
free(img); | free(img); | ||||
} | } | ||||
void image_save(struct image *img, const char *name) | |||||
{ | |||||
#if defined(HAVE_SDL_IMAGE_H) | |||||
SDL_SaveBMP(img->priv, name); | |||||
#elif defined(HAVE_IMLIB2_H) | |||||
imlib_context_set_image(img->priv); | |||||
imlib_save_image(name); | |||||
#elif defined(HAVE_CV_H) | |||||
cvSaveImage(name, img->priv); | |||||
#endif | |||||
} | |||||
int getgray(struct image *img, int x, int y, int *g) | int getgray(struct image *img, int x, int y, int *g) | ||||
{ | { | ||||
if(x < 0 || y < 0 || x >= img->width || y >= img->height) | if(x < 0 || y < 0 || x >= img->width || y >= img->height) | ||||