154 lines
3.3 KiB
C
154 lines
3.3 KiB
C
/*
|
|
col4bits.c
|
|
|
|
this module is dedicated to functions who works on
|
|
4096 colors images. You got four bits by components.
|
|
*/
|
|
|
|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
|
|
#include "../tthimage.h"
|
|
|
|
/*::------------------------------------------------------------------::*/
|
|
int Image_col4bits_and(Image_Desc *src, Image_Desc *dst)
|
|
{
|
|
int foo;
|
|
|
|
if ((foo=Image_compare_desc(src, dst))) {
|
|
fprintf(stderr, "%s : images not compatibles\n", __func__);
|
|
return foo;
|
|
}
|
|
|
|
foo = Image_copy(src, dst);
|
|
if (foo) {
|
|
fprintf(stderr, "In %s: copy: err #%d %s\n", __func__,
|
|
foo, Image_err2str(foo));
|
|
return foo;
|
|
}
|
|
foo = Image_and_pix(dst, 0xf0, 0xf0, 0xf0);
|
|
if (foo) {
|
|
fprintf(stderr, "In %s: and pix: err #%d %s\n", __func__,
|
|
foo, Image_err2str(foo));
|
|
return foo;
|
|
}
|
|
|
|
return OLL_KORRECT;
|
|
}
|
|
/*::------------------------------------------------------------------::*/
|
|
struct elem
|
|
{
|
|
long compte;
|
|
int rgb;
|
|
};
|
|
|
|
static int compare_compteur(struct elem *p1, struct elem *p2)
|
|
{
|
|
/* printf("%8d %8d\n", p1->compte, p2->compte); */
|
|
return (p2->compte - p1->compte);
|
|
}
|
|
static int compare_teinte(struct elem *p1, struct elem *p2)
|
|
{
|
|
int r1, g1, b1, r2, b2, g2;
|
|
|
|
r1 = (( (p1->rgb) >>8)&0xf)<<4;
|
|
g1 = (( (p1->rgb) >>4)&0xf)<<4;
|
|
b1 = ( (p1->rgb) &0xf)<<4;
|
|
|
|
r2 = (( (p2->rgb) >>8)&0xf)<<4;
|
|
g2 = (( (p2->rgb) >>4)&0xf)<<4;
|
|
b2 = ( (p2->rgb) &0xf)<<4;
|
|
|
|
/* printf("%8d %8d\n", p1->compte, p2->compte);
|
|
return (p1->rgb - p2->rgb); */
|
|
|
|
return ( (r1+g1+b1) - (r2+g2+b2) );
|
|
}
|
|
|
|
/*::------------------------------------------------------------------::*/
|
|
|
|
#define TAILLE (1<<12)
|
|
int Image_calc_Map_4bits(Image_Desc *img, RGB_map *map, int nbre)
|
|
{
|
|
long surface, maxi;
|
|
int x, y, r, g, b, idx;
|
|
|
|
struct elem elems[TAILLE];
|
|
|
|
#if DEBUG_LEVEL
|
|
fprintf(stderr, " Calc map 4 bits: nbre = %d\n", nbre);
|
|
#endif
|
|
|
|
if ( (nbre<1) || (nbre>255) ) {
|
|
fprintf(stderr, "Calc map 4 bits: nbre %d out of range\n", nbre);
|
|
return BAD_COLOR_NUMBER;
|
|
}
|
|
|
|
surface = img->width * img->height;
|
|
#if DEBUG_LEVEL
|
|
fprintf(stderr, " calc Map 4 bits: surface de l'image = %ld pixels\n", surface);
|
|
#endif
|
|
|
|
for (x=0; x<TAILLE; x++) {
|
|
elems[x].compte = 0L;
|
|
elems[x].rgb = x;
|
|
}
|
|
|
|
maxi = 0L;
|
|
for (x=0; x<img->width; x++) {
|
|
for (y=0; y<img->height; y++) {
|
|
r = (img->Rpix[y])[x] >> 4;
|
|
g = (img->Gpix[y])[x] >> 4;
|
|
b = (img->Bpix[y])[x] >> 4;
|
|
idx = (r<<8) | (g<<4) | b;
|
|
|
|
if (idx >= TAILLE) {
|
|
fprintf(stderr, "FATAL ERROR in %s\n", __func__);
|
|
exit(5);
|
|
}
|
|
elems[idx].compte++;
|
|
if (elems[idx].compte > maxi)
|
|
maxi = elems[idx].compte;
|
|
}
|
|
}
|
|
#if DEBUG_LEVEL
|
|
fprintf(stderr, " Map4bits: compte maximum = %ld\n", maxi);
|
|
#endif
|
|
|
|
/*
|
|
* trier la table pour avoir les couleurs les plus
|
|
* frequentes en haut.
|
|
*/
|
|
qsort(elems, TAILLE, sizeof(struct elem), compare_compteur);
|
|
|
|
/*
|
|
* trier la palette, certe, mais dans quel ordre ?
|
|
* 28 Jan 2002: why ?
|
|
*/
|
|
qsort(elems, nbre, sizeof(struct elem), compare_teinte);
|
|
|
|
/*
|
|
* recopier les 'nbre' entrees hautes dans la palette
|
|
*/
|
|
for(x=0; x<nbre; x++) {
|
|
y = elems[x].rgb;
|
|
|
|
r = ((y>>8)&0xf)<<4;
|
|
g = ((y>>4)&0xf)<<4;
|
|
b = (y&0xf)<<4;
|
|
|
|
/* printf("%06x %02x %02x %02x\n", x, r, g, b); */
|
|
map->red[x] = r;
|
|
map->green[x] = g;
|
|
map->blue[x] = b;
|
|
}
|
|
map->nbre = nbre;
|
|
|
|
#if DEBUG_LEVEL
|
|
fprintf(stderr, "Image_calc_Map_4bits: fini!\n");
|
|
#endif
|
|
|
|
return FUNC_IS_BETA;
|
|
}
|
|
/*::------------------------------------------------------------------::*/
|