/* Definitions for Xconq images.
   Copyright (C) 1992-1998 Stanley T. Shebs.

Xconq is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2, or (at your option)
any later version.  See the file COPYING.  */

/* An image family is like a Mac Finder icon family, but allows
   multiple kinds of images of an arbitrary set of sizes.  Individual
   images in a family may have both "lisp" form and "raw" form, the
   former being used for reading and writing, while the raw form is an
   intermediary for conversion to and from platform-specific
   representations. */

typedef struct a_image {
    short w, h;			/* Nominal size of the image */
    short istile;		/* True if image may be used as tile */
    short style;		/* Info about any special style */
    char *embedname;		/* Name of an embedded subimage (imf name) */
    short embedx, embedy;	/* Position to draw an embedded subimage */
    short embedw, embedh;	/* Size of space for embedded subimage */
    Obj *monodata;		/* Monochrome data, in GDL form */
    Obj *colrdata;		/* Color data, in GDL form */
    Obj *maskdata;		/* Mask data, in GDL form */
    short actualw, actualh;
    short pixelsize;		/* Number of bits per pixel */
    Obj *palette;		/* Color palette, in list form */
    Obj *notes;			/* designer notes about the image */
    short synthetic;		/* True if image was computed */
    char *rawmonodata;		/* Monochrome data, as array of bytes */
    char *rawcolrdata;		/* Color data, as array of bytes */
    char *rawmaskdata;		/* Mask data, as array of bytes */
    int *rawpalette;		/* Color palette, in raw form */
    short numcolors;		/* Number of colors in raw palette */
    short bboxx, bboxy;		/* Position of actual data within image */
    short bboxw, bboxh;		/* Dimensions of actual data within image */
    char *hook;			/* Pointer to interface-specific data */
    struct a_image *next;	/* Pointer to next image in family */
} Image;

typedef struct a_image_family {
    char *name;			/* Name of the family */
    short ersatz;		/* True if this image is a substitute */
    short preferred_style;	/* Info about preferred style */
    struct a_image_file *location;  /* File or whatever to look for data */
    Obj *notes;			/* designer notes about the image family */
    char *hook;			/* Pointer to interface-specific data */
    short numsizes;		/* Number of images in the list */
    Image *images;		/* Pointer to chain of images */
} ImageFamily;

typedef struct a_image_palette {
    char *name;			/* Name of the palette */
    struct a_image_file *location;  /* File or whatever to look for data */
    Obj *notes;			/* designer notes about the palette */
    Obj *palette;		/* List of colors */
    int numcolors;		/* Number of colors in the palette */
} ImagePalette;

typedef struct a_image_file {
    char *name;			/* Name of the file */
    short loaded;		/* True if it has already been loaded */
    struct a_image_file *next;	/* Link to the next file. */
} ImageFile;

extern ImageFamily **images;

extern int numimages;

extern ImagePalette **palettes;

extern int numpalettes;

extern ImageFile *image_files;

extern ImageFamily *(*imf_load_hook) PARAMS ((ImageFamily *imf));

extern ImageFamily *(*imf_interp_hook) PARAMS ((ImageFamily *imf, Image *img, int force));

#define computed_rowbytes(w, pixelsize) (((w * pixelsize) + 7) / 8)

#define hextoi(c) (((c) >= '0' && (c) <= '9') ? ((c) - '0') : ((c) - 'a' + 10))

#define for_all_images(imf,img) \
  for ((img) = (imf)->images; (img) != NULL; (img) = (img)->next)

typedef void (*readimf_hook) PARAMS ((ImageFamily *, int));

extern ImageFamily *clone_imf PARAMS ((ImageFamily *imf));
extern ImageFamily *get_imf PARAMS ((char *name));
extern ImageFamily *find_imf PARAMS ((char *name));
extern Image *find_img PARAMS ((ImageFamily *imf, int w, int h));
extern Image *get_img PARAMS ((ImageFamily *imf, int w, int h, int style));
extern int valid_imf_name PARAMS ((char *name));

extern char *canonical_palette_name PARAMS ((char *str));
extern ImagePalette *new_image_palette PARAMS ((char *name));
extern ImagePalette *get_imp PARAMS ((char *name));
extern ImagePalette *find_imp PARAMS ((char *name));

extern ImageFile *get_image_file PARAMS ((char *name));
extern void load_image_families PARAMS ((FILE *fp, int loadnow,
					 readimf_hook callback));
extern int load_imf_file PARAMS ((char *filename,
				  readimf_hook callback));
extern void interp_imf_form PARAMS ((Obj *form,
				     readimf_hook callback));

extern ImageFamily *interp_imf PARAMS ((Obj *form));
extern void interp_imf_contents PARAMS ((ImageFamily *imf, Obj *form));
extern void interp_image PARAMS ((ImageFamily *imf, Obj *size, Obj *parts));
extern void interp_bytes PARAMS ((Obj *datalist, int numbytes, char *destaddr,
			  int jump));
extern ImagePalette *interp_palette PARAMS ((Obj *form));

extern Image *best_image PARAMS ((ImageFamily *imf, int w, int h));
extern Image *smallest_image PARAMS ((ImageFamily *imf));
extern int emblem_position PARAMS ((Image *uimg, char *ename,
				    ImageFamily *eimf, int sw, int sh,
				    int *exxp, int *eyyp, int *ewp, int *ehp));

extern void sort_all_images PARAMS ((void));
extern void sort_all_palettes PARAMS ((void));

extern void check_imf PARAMS ((ImageFamily *imf));

extern void write_imf PARAMS ((FILE *fp, ImageFamily *imf));
extern void write_imp PARAMS ((FILE *fp, ImagePalette *imp));

extern void make_generic_image_data PARAMS ((ImageFamily *imf));

extern void validify_imf_name PARAMS ((char *buf));
extern void compute_image_bboxes PARAMS ((ImageFamily *imf));
extern void compute_image_bbox PARAMS ((Image *img));
extern void write_imf_dir PARAMS ((char *filename, ImageFamily **images,
				   int num));
extern char *find_color_name PARAMS ((int r, int g, int b));
extern void parse_lisp_palette_entry PARAMS ((Obj *palentry, int *c,
					      int *r, int *g, int *b));
