2008-11-05 09:21:04 -08:00
|
|
|
#ifdef HAVE_CONFIG_H
|
|
|
|
# include <config.h>
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#ifdef HAVE_EVIL
|
|
|
|
# include <Evil.h>
|
|
|
|
#endif
|
|
|
|
|
2006-08-12 02:16:30 -07:00
|
|
|
#include "evas_common.h"
|
|
|
|
#include "evas_private.h"
|
|
|
|
|
2010-04-08 15:55:54 -07:00
|
|
|
static int _evas_loader_xpm_log_dom = -1;
|
2010-04-08 10:39:01 -07:00
|
|
|
|
|
|
|
#ifdef ERR
|
|
|
|
# undef ERR
|
|
|
|
#endif
|
|
|
|
#define ERR(...) EINA_LOG_DOM_ERR(_evas_loader_xpm_log_dom, __VA_ARGS__)
|
|
|
|
|
2009-12-22 15:11:57 -08:00
|
|
|
static Eina_Bool evas_image_load_file_head_xpm(Image_Entry *ie, const char *file, const char *key, int *error) EINA_ARG_NONNULL(1, 2, 4);
|
|
|
|
static Eina_Bool evas_image_load_file_data_xpm(Image_Entry *ie, const char *file, const char *key, int *error) EINA_ARG_NONNULL(1, 2, 4);
|
2006-08-12 02:16:30 -07:00
|
|
|
|
2009-06-16 06:01:36 -07:00
|
|
|
static Evas_Image_Load_Func evas_image_load_xpm_func =
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2009-12-24 05:15:34 -08:00
|
|
|
EINA_FALSE,
|
2006-08-12 02:16:30 -07:00
|
|
|
evas_image_load_file_head_xpm,
|
2011-08-10 23:04:08 -07:00
|
|
|
evas_image_load_file_data_xpm,
|
2011-12-13 08:58:20 -08:00
|
|
|
NULL,
|
|
|
|
EINA_FALSE
|
2006-08-12 02:16:30 -07:00
|
|
|
};
|
|
|
|
|
2012-01-02 06:32:21 -08:00
|
|
|
static Eina_File *rgb_txt;
|
|
|
|
static void *rgb_txt_map;
|
2006-08-12 02:16:30 -07:00
|
|
|
|
|
|
|
static void
|
|
|
|
xpm_parse_color(char *color, int *r, int *g, int *b)
|
|
|
|
{
|
2012-01-02 06:32:21 -08:00
|
|
|
char *tmp;
|
|
|
|
char *max;
|
|
|
|
char *endline;
|
|
|
|
char buf[4096];
|
2006-08-12 02:16:30 -07:00
|
|
|
|
|
|
|
/* is a #ff00ff like color */
|
|
|
|
if (color[0] == '#')
|
|
|
|
{
|
|
|
|
int len;
|
|
|
|
char val[32];
|
2008-11-05 09:21:04 -08:00
|
|
|
|
2006-08-12 02:16:30 -07:00
|
|
|
len = strlen(color) - 1;
|
|
|
|
if (len < 96)
|
|
|
|
{
|
|
|
|
int i;
|
2008-11-05 09:21:04 -08:00
|
|
|
|
2006-08-12 02:16:30 -07:00
|
|
|
len /= 3;
|
|
|
|
for (i = 0; i < len; i++)
|
|
|
|
val[i] = color[1 + i + (0 * len)];
|
|
|
|
val[i] = 0;
|
|
|
|
sscanf(val, "%x", r);
|
|
|
|
for (i = 0; i < len; i++)
|
|
|
|
val[i] = color[1 + i + (1 * len)];
|
|
|
|
val[i] = 0;
|
|
|
|
sscanf(val, "%x", g);
|
|
|
|
for (i = 0; i < len; i++)
|
|
|
|
val[i] = color[1 + i + (2 * len)];
|
|
|
|
val[i] = 0;
|
|
|
|
sscanf(val, "%x", b);
|
|
|
|
if (len == 1)
|
|
|
|
{
|
|
|
|
*r = (*r << 4) | *r;
|
|
|
|
*g = (*g << 4) | *g;
|
|
|
|
*b = (*b << 4) | *b;
|
|
|
|
}
|
|
|
|
else if (len > 2)
|
|
|
|
{
|
|
|
|
*r >>= (len - 2) * 4;
|
|
|
|
*g >>= (len - 2) * 4;
|
|
|
|
*b >>= (len - 2) * 4;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
/* look in rgb txt database */
|
2006-09-24 06:03:39 -07:00
|
|
|
if (!rgb_txt) return;
|
2012-01-02 06:32:21 -08:00
|
|
|
tmp = rgb_txt_map;
|
|
|
|
max = tmp + eina_file_size_get(rgb_txt);
|
|
|
|
|
|
|
|
while (tmp < max)
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2012-01-02 06:32:21 -08:00
|
|
|
endline = memchr(tmp, '\n', max - tmp);
|
|
|
|
if (!endline) endline = max;
|
|
|
|
if ((*tmp != '!') && ((endline - tmp) < (int) (sizeof(buf) - 1)))
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
int rr, gg, bb;
|
|
|
|
char name[4096];
|
2008-11-05 09:21:04 -08:00
|
|
|
|
2012-01-02 06:32:21 -08:00
|
|
|
/* FIXME: not really efficient */
|
|
|
|
memcpy(buf, tmp, endline - tmp);
|
|
|
|
buf[endline - tmp + 1] = '\0';
|
|
|
|
|
2006-09-24 06:03:39 -07:00
|
|
|
if (sscanf(buf, "%i %i %i %[^\n]", &rr, &gg, &bb, name) == 4)
|
|
|
|
{
|
|
|
|
if (!strcasecmp(name, color))
|
|
|
|
{
|
|
|
|
*r = rr;
|
|
|
|
*g = gg;
|
|
|
|
*b = bb;
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
}
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
2012-01-02 06:32:21 -08:00
|
|
|
tmp = endline + 1;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/** FIXME: clean this up and make more efficient **/
|
2009-12-22 15:11:57 -08:00
|
|
|
static Eina_Bool
|
|
|
|
evas_image_load_file_xpm(Image_Entry *ie, const char *file, const char *key __UNUSED__, int load_data, int *error)
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
|
|
|
DATA32 *ptr, *end;
|
2012-01-02 06:32:21 -08:00
|
|
|
Eina_File *f;
|
|
|
|
const char *map;
|
|
|
|
size_t length;
|
|
|
|
size_t position;
|
2006-08-12 02:16:30 -07:00
|
|
|
|
|
|
|
int pc, c, i, j, k, w, h, ncolors, cpp, comment, transp,
|
2006-09-24 06:03:39 -07:00
|
|
|
quote, context, len, done, r, g, b, backslash, lu1, lu2;
|
2012-01-02 06:32:21 -08:00
|
|
|
char *line = NULL;
|
|
|
|
char s[256], tok[128], col[256], *tl;
|
2006-08-12 02:16:30 -07:00
|
|
|
int lsz = 256;
|
|
|
|
struct _cmap {
|
2009-12-21 07:52:12 -08:00
|
|
|
char str[6];
|
2006-09-24 06:03:39 -07:00
|
|
|
unsigned char transp;
|
|
|
|
short r, g, b;
|
2012-01-02 06:32:21 -08:00
|
|
|
} *cmap = NULL;
|
2006-08-12 02:16:30 -07:00
|
|
|
|
|
|
|
short lookup[128 - 32][128 - 32];
|
|
|
|
int count, pixels;
|
|
|
|
|
|
|
|
done = 0;
|
|
|
|
// transp = -1;
|
2006-09-24 06:03:39 -07:00
|
|
|
transp = 1;
|
2006-08-12 02:16:30 -07:00
|
|
|
|
|
|
|
/* if immediate_load is 1, then dont delay image laoding as below, or */
|
|
|
|
/* already data in this image - dont load it again */
|
|
|
|
|
2012-01-02 06:32:21 -08:00
|
|
|
f = eina_file_open(file, 0);
|
2006-08-12 02:16:30 -07:00
|
|
|
if (!f)
|
|
|
|
{
|
2012-04-24 21:07:12 -07:00
|
|
|
if (load_data)
|
|
|
|
ERR("XPM ERROR: file failed to open");
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_DOES_NOT_EXIST;
|
|
|
|
return EINA_FALSE;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
2012-01-02 06:32:21 -08:00
|
|
|
length = eina_file_size_get(f);
|
|
|
|
position = 0;
|
|
|
|
if (length < 9)
|
2007-10-28 03:08:32 -07:00
|
|
|
{
|
2012-04-24 21:07:12 -07:00
|
|
|
if (load_data)
|
|
|
|
ERR("XPM ERROR: file size, %zd, is to small", length);
|
2012-01-02 06:32:21 -08:00
|
|
|
eina_file_close(f);
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_CORRUPT_FILE;
|
|
|
|
return EINA_FALSE;
|
2007-10-28 03:08:32 -07:00
|
|
|
}
|
2012-01-02 06:32:21 -08:00
|
|
|
|
|
|
|
map = eina_file_map_all(f, EINA_FILE_SEQUENTIAL);
|
|
|
|
if (!map)
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2012-04-24 21:07:12 -07:00
|
|
|
if (load_data)
|
|
|
|
ERR("XPM ERROR: file failed to mmap");
|
2012-01-02 06:32:21 -08:00
|
|
|
eina_file_close(f);
|
|
|
|
*error = EVAS_LOAD_ERROR_CORRUPT_FILE;
|
2009-12-22 15:11:57 -08:00
|
|
|
return EINA_FALSE;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
2008-11-05 09:21:04 -08:00
|
|
|
|
2012-01-02 06:32:21 -08:00
|
|
|
if (strncmp("/* XPM */", map, 9))
|
|
|
|
{
|
|
|
|
*error = EVAS_LOAD_ERROR_UNKNOWN_FORMAT;
|
|
|
|
goto on_error;
|
|
|
|
}
|
|
|
|
|
2006-08-12 02:16:30 -07:00
|
|
|
i = 0;
|
|
|
|
j = 0;
|
|
|
|
cmap = NULL;
|
|
|
|
w = 10;
|
|
|
|
h = 10;
|
|
|
|
ptr = NULL;
|
|
|
|
end = NULL;
|
|
|
|
c = ' ';
|
|
|
|
comment = 0;
|
|
|
|
quote = 0;
|
|
|
|
context = 0;
|
|
|
|
pixels = 0;
|
|
|
|
count = 0;
|
|
|
|
line = malloc(lsz);
|
|
|
|
if (!line)
|
|
|
|
{
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_RESOURCE_ALLOCATION_FAILED;
|
2012-01-02 06:32:21 -08:00
|
|
|
goto on_error;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
backslash = 0;
|
|
|
|
memset(lookup, 0, sizeof(lookup));
|
|
|
|
while (!done)
|
|
|
|
{
|
|
|
|
pc = c;
|
2012-01-02 06:32:21 -08:00
|
|
|
if (position == length) break ;
|
|
|
|
c = (char) map[position++];
|
2006-08-12 02:16:30 -07:00
|
|
|
if (!quote)
|
|
|
|
{
|
|
|
|
if ((pc == '/') && (c == '*'))
|
2006-09-24 06:03:39 -07:00
|
|
|
comment = 1;
|
2006-08-12 02:16:30 -07:00
|
|
|
else if ((pc == '*') && (c == '/') && (comment))
|
2006-09-24 06:03:39 -07:00
|
|
|
comment = 0;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
if (!comment)
|
|
|
|
{
|
|
|
|
if ((!quote) && (c == '"'))
|
|
|
|
{
|
|
|
|
quote = 1;
|
|
|
|
i = 0;
|
|
|
|
}
|
|
|
|
else if ((quote) && (c == '"'))
|
|
|
|
{
|
|
|
|
line[i] = 0;
|
|
|
|
quote = 0;
|
|
|
|
if (context == 0)
|
|
|
|
{
|
|
|
|
/* Header */
|
2006-09-24 06:03:39 -07:00
|
|
|
if (sscanf(line, "%i %i %i %i", &w, &h, &ncolors, &cpp) != 4)
|
|
|
|
{
|
2009-10-22 09:39:20 -07:00
|
|
|
ERR("XPM ERROR: XPM file malformed header");
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_CORRUPT_FILE;
|
2012-01-02 06:32:21 -08:00
|
|
|
goto on_error;
|
2006-09-24 06:03:39 -07:00
|
|
|
}
|
2006-08-12 02:16:30 -07:00
|
|
|
if ((ncolors > 32766) || (ncolors < 1))
|
|
|
|
{
|
2009-10-22 09:39:20 -07:00
|
|
|
ERR("XPM ERROR: XPM files with colors > 32766 or < 1 not supported");
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_UNKNOWN_FORMAT;
|
2012-01-02 06:32:21 -08:00
|
|
|
goto on_error;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
if ((cpp > 5) || (cpp < 1))
|
|
|
|
{
|
2009-10-22 09:39:20 -07:00
|
|
|
ERR("XPM ERROR: XPM files with characters per pixel > 5 or < 1not supported");
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_UNKNOWN_FORMAT;
|
2012-01-02 06:32:21 -08:00
|
|
|
goto on_error;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
2009-09-11 06:44:53 -07:00
|
|
|
if ((w > IMG_MAX_SIZE) || (w < 1))
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2009-10-22 09:39:20 -07:00
|
|
|
ERR("XPM ERROR: Image width > IMG_MAX_SIZE or < 1 pixels for file");
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_GENERIC;
|
2012-01-02 06:32:21 -08:00
|
|
|
goto on_error;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
2009-09-11 06:44:53 -07:00
|
|
|
if ((h > IMG_MAX_SIZE) || (h < 1))
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2009-10-22 09:39:20 -07:00
|
|
|
ERR("XPM ERROR: Image height > IMG_MAX_SIZE or < 1 pixels for file");
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_GENERIC;
|
2012-01-02 06:32:21 -08:00
|
|
|
goto on_error;
|
2009-09-16 02:48:05 -07:00
|
|
|
}
|
|
|
|
if (IMG_TOO_BIG(w, h))
|
|
|
|
{
|
2009-10-22 09:39:20 -07:00
|
|
|
ERR("XPM ERROR: Image just too big to ever allocate");
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_RESOURCE_ALLOCATION_FAILED;
|
2012-01-02 06:32:21 -08:00
|
|
|
goto on_error;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
if (!cmap)
|
|
|
|
{
|
|
|
|
cmap = malloc(sizeof(struct _cmap) * ncolors);
|
|
|
|
if (!cmap)
|
|
|
|
{
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_RESOURCE_ALLOCATION_FAILED;
|
2012-01-02 06:32:21 -08:00
|
|
|
goto on_error;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
}
|
2008-06-03 02:09:39 -07:00
|
|
|
ie->w = w;
|
|
|
|
ie->h = h;
|
2006-08-12 02:16:30 -07:00
|
|
|
|
|
|
|
j = 0;
|
|
|
|
context++;
|
|
|
|
}
|
|
|
|
else if (context == 1)
|
|
|
|
{
|
|
|
|
/* Color Table */
|
|
|
|
if (j < ncolors)
|
|
|
|
{
|
|
|
|
int slen;
|
|
|
|
int hascolor, iscolor;
|
|
|
|
|
|
|
|
iscolor = 0;
|
|
|
|
hascolor = 0;
|
|
|
|
tok[0] = 0;
|
|
|
|
col[0] = 0;
|
|
|
|
s[0] = 0;
|
|
|
|
len = strlen(line);
|
|
|
|
strncpy(cmap[j].str, line, cpp);
|
|
|
|
cmap[j].str[cpp] = 0;
|
2006-09-24 06:03:39 -07:00
|
|
|
for (slen = 0; slen < cpp; slen++)
|
|
|
|
{
|
|
|
|
/* fix the ascii of the color string - if its < 32 - just limit to 32 */
|
|
|
|
if (cmap[j].str[slen] < 32) cmap[j].str[slen] = 0;
|
|
|
|
}
|
2006-08-12 02:16:30 -07:00
|
|
|
cmap[j].r = -1;
|
|
|
|
cmap[j].transp = 0;
|
|
|
|
for (k = cpp; k < len; k++)
|
|
|
|
{
|
|
|
|
if (line[k] != ' ')
|
|
|
|
{
|
|
|
|
s[0] = 0;
|
2006-09-24 06:03:39 -07:00
|
|
|
sscanf(&line[k], "%255s", s);
|
2006-08-12 02:16:30 -07:00
|
|
|
slen = strlen(s);
|
|
|
|
k += slen;
|
2012-10-10 00:23:45 -07:00
|
|
|
if (slen == 1 && *s == 'c') iscolor = 1;
|
|
|
|
if ((slen == 1 && ((s[0] == 'm') || (s[0] == 's') || (s[0] == 'g')) || (s[0] == 'c')) ||
|
2012-10-10 00:58:54 -07:00
|
|
|
(slen == 2 && (s[0] == 'g') && (s[1] == '4')) ||
|
2012-10-10 00:23:45 -07:00
|
|
|
(k >= len))
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
|
|
|
if (k >= len)
|
|
|
|
{
|
|
|
|
if (col[0])
|
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
if (strlen(col) < (sizeof(col) - 2))
|
2006-08-12 02:16:30 -07:00
|
|
|
strcat(col, " ");
|
|
|
|
else
|
|
|
|
done = 1;
|
|
|
|
}
|
2006-09-24 06:03:39 -07:00
|
|
|
if ((strlen(col) + strlen(s)) < (sizeof(col) - 1))
|
|
|
|
strcat(col, s);
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
if (col[0])
|
|
|
|
{
|
|
|
|
if (!strcasecmp(col, "none"))
|
|
|
|
{
|
|
|
|
transp = 1;
|
|
|
|
cmap[j].transp = 1;
|
2006-09-24 06:03:39 -07:00
|
|
|
cmap[j].r = 0;
|
|
|
|
cmap[j].g = 0;
|
|
|
|
cmap[j].b = 0;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
if ((((cmap[j].r < 0) || (!strcmp(tok, "c"))) && (!hascolor)))
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
r = g = b = 0;
|
|
|
|
xpm_parse_color(col, &r, &g, &b);
|
2006-08-12 02:16:30 -07:00
|
|
|
cmap[j].r = r;
|
|
|
|
cmap[j].g = g;
|
|
|
|
cmap[j].b = b;
|
2006-09-24 06:03:39 -07:00
|
|
|
if (iscolor) hascolor = 1;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
strcpy(tok, s);
|
|
|
|
col[0] = 0;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
if (col[0])
|
|
|
|
{
|
|
|
|
if (strlen(col) < ( sizeof(col) - 2))
|
|
|
|
strcat(col, " ");
|
|
|
|
else
|
|
|
|
done = 1;
|
|
|
|
}
|
2006-09-24 06:03:39 -07:00
|
|
|
if ((strlen(col) + strlen(s)) < (sizeof(col) - 1))
|
2006-08-12 02:16:30 -07:00
|
|
|
strcat(col, s);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
j++;
|
|
|
|
if (j >= ncolors)
|
|
|
|
{
|
|
|
|
if (cpp == 1)
|
2006-09-24 06:03:39 -07:00
|
|
|
{
|
|
|
|
for (i = 0; i < ncolors; i++)
|
|
|
|
lookup[(int)cmap[i].str[0] - 32][0] = i;
|
|
|
|
}
|
2006-08-12 02:16:30 -07:00
|
|
|
if (cpp == 2)
|
2006-09-24 06:03:39 -07:00
|
|
|
{
|
|
|
|
for (i = 0; i < ncolors; i++)
|
|
|
|
lookup[(int)cmap[i].str[0] - 32][(int)cmap[i].str[1] - 32] = i;
|
|
|
|
}
|
2006-08-12 02:16:30 -07:00
|
|
|
context++;
|
|
|
|
}
|
|
|
|
|
2008-06-03 02:09:39 -07:00
|
|
|
if (transp) ie->flags.alpha = 1;
|
2008-11-05 09:21:04 -08:00
|
|
|
|
2006-08-12 02:16:30 -07:00
|
|
|
if (load_data)
|
|
|
|
{
|
2008-06-03 02:09:39 -07:00
|
|
|
evas_cache_image_surface_alloc(ie, w, h);
|
|
|
|
ptr = evas_cache_image_pixels(ie);
|
|
|
|
if (!ptr)
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_RESOURCE_ALLOCATION_FAILED;
|
2012-01-02 06:32:21 -08:00
|
|
|
goto on_error;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
pixels = w * h;
|
2008-11-22 01:28:38 -08:00
|
|
|
end = ptr + pixels;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_NONE;
|
2012-01-02 06:32:21 -08:00
|
|
|
goto on_success;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
/* Image Data */
|
|
|
|
i = 0;
|
|
|
|
if (cpp == 0)
|
|
|
|
{
|
|
|
|
/* Chars per pixel = 0? well u never know */
|
|
|
|
}
|
2006-09-24 06:03:39 -07:00
|
|
|
/* it's xpm - don't care about speed too much. still faster
|
|
|
|
* that most xpm loaders anyway */
|
|
|
|
else if (cpp == 1)
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
|
|
|
if (transp)
|
|
|
|
{
|
|
|
|
for (i = 0;
|
|
|
|
((i < 65536) && (ptr < end) && (line[i]));
|
|
|
|
i++)
|
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
lu1 = (int)line[i] - 32;
|
|
|
|
if (lu1 < 0) continue;
|
|
|
|
if (cmap[lookup[lu1][0]].transp)
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
r = (unsigned char)cmap[lookup[lu1][0]].r;
|
|
|
|
g = (unsigned char)cmap[lookup[lu1][0]].g;
|
|
|
|
b = (unsigned char)cmap[lookup[lu1][0]].b;
|
2010-06-07 22:39:46 -07:00
|
|
|
*ptr = RGB_JOIN(r, g, b);
|
2006-09-24 06:03:39 -07:00
|
|
|
ptr++;
|
2006-08-12 02:16:30 -07:00
|
|
|
count++;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
r = (unsigned char)cmap[lookup[lu1][0]].r;
|
|
|
|
g = (unsigned char)cmap[lookup[lu1][0]].g;
|
|
|
|
b = (unsigned char)cmap[lookup[lu1][0]].b;
|
2010-06-07 22:39:46 -07:00
|
|
|
*ptr = ARGB_JOIN(0xff, r, g, b);
|
2006-09-24 06:03:39 -07:00
|
|
|
ptr++;
|
2006-08-12 02:16:30 -07:00
|
|
|
count++;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
for (i = 0;
|
|
|
|
((i < 65536) && (ptr < end) && (line[i]));
|
|
|
|
i++)
|
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
lu1 = (int)line[i] - 32;
|
|
|
|
if (lu1 < 0) continue;
|
|
|
|
r = (unsigned char)cmap[lookup[lu1][0]].r;
|
|
|
|
g = (unsigned char)cmap[lookup[lu1][0]].g;
|
|
|
|
b = (unsigned char)cmap[lookup[lu1][0]].b;
|
2010-06-07 22:39:46 -07:00
|
|
|
*ptr = ARGB_JOIN(0xff, r, g, b);
|
2006-09-24 06:03:39 -07:00
|
|
|
ptr++;
|
|
|
|
count++;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else if (cpp == 2)
|
|
|
|
{
|
|
|
|
if (transp)
|
|
|
|
{
|
|
|
|
for (i = 0;
|
|
|
|
((i < 65536) && (ptr < end) && (line[i]));
|
|
|
|
i++)
|
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
lu1 = (int)line[i] - 32;
|
|
|
|
i++;
|
|
|
|
lu2 = (int)line[i] - 32;
|
|
|
|
if (lu1 < 0) continue;
|
|
|
|
if (lu2 < 0) continue;
|
|
|
|
if (cmap[lookup[lu1][lu2]].transp)
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
r = (unsigned char)cmap[lookup[lu1][lu2]].r;
|
|
|
|
g = (unsigned char)cmap[lookup[lu1][lu2]].g;
|
|
|
|
b = (unsigned char)cmap[lookup[lu1][lu2]].b;
|
2010-06-07 22:39:46 -07:00
|
|
|
*ptr = RGB_JOIN(r, g, b);
|
2006-09-24 06:03:39 -07:00
|
|
|
ptr++;
|
2006-08-12 02:16:30 -07:00
|
|
|
count++;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
r = (unsigned char)cmap[lookup[lu1][lu2]].r;
|
|
|
|
g = (unsigned char)cmap[lookup[lu1][lu2]].g;
|
|
|
|
b = (unsigned char)cmap[lookup[lu1][lu2]].b;
|
2010-06-07 22:39:46 -07:00
|
|
|
*ptr = ARGB_JOIN(0xff, r, g, b);
|
2006-09-24 06:03:39 -07:00
|
|
|
ptr++;
|
2006-08-12 02:16:30 -07:00
|
|
|
count++;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
for (i = 0;
|
|
|
|
((i < 65536) && (ptr < end) && (line[i]));
|
|
|
|
i++)
|
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
lu1 = (int)line[i] - 32;
|
|
|
|
i++;
|
|
|
|
lu2 = (int)line[i] - 32;
|
|
|
|
if (lu1 < 0) continue;
|
|
|
|
if (lu2 < 0) continue;
|
|
|
|
r = (unsigned char)cmap[lookup[lu1][lu2]].r;
|
|
|
|
g = (unsigned char)cmap[lookup[lu1][lu2]].g;
|
|
|
|
b = (unsigned char)cmap[lookup[lu1][lu2]].b;
|
2010-06-07 22:39:46 -07:00
|
|
|
*ptr = ARGB_JOIN(0xff, r, g, b);
|
2006-09-24 06:03:39 -07:00
|
|
|
ptr++;
|
|
|
|
count++;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
if (transp)
|
|
|
|
{
|
|
|
|
for (i = 0;
|
|
|
|
((i < 65536) && (ptr < end) && (line[i]));
|
|
|
|
i++)
|
|
|
|
{
|
|
|
|
for (j = 0; j < cpp; j++, i++)
|
2006-09-24 06:03:39 -07:00
|
|
|
{
|
|
|
|
col[j] = line[i];
|
|
|
|
if (col[j] < 32) col[j] = 32;
|
|
|
|
}
|
2006-08-12 02:16:30 -07:00
|
|
|
col[j] = 0;
|
|
|
|
i--;
|
|
|
|
for (j = 0; j < ncolors; j++)
|
|
|
|
{
|
|
|
|
if (!strcmp(col, cmap[j].str))
|
|
|
|
{
|
|
|
|
if (cmap[j].transp)
|
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
r = (unsigned char)cmap[j].r;
|
|
|
|
g = (unsigned char)cmap[j].g;
|
|
|
|
b = (unsigned char)cmap[j].b;
|
2010-06-07 22:39:46 -07:00
|
|
|
*ptr = RGB_JOIN(r, g, b);
|
2006-09-24 06:03:39 -07:00
|
|
|
ptr++;
|
2006-08-12 02:16:30 -07:00
|
|
|
count++;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
r = (unsigned char)cmap[j].r;
|
|
|
|
g = (unsigned char)cmap[j].g;
|
|
|
|
b = (unsigned char)cmap[j].b;
|
2010-06-07 22:39:46 -07:00
|
|
|
*ptr = ARGB_JOIN(0xff, r, g, b);
|
2006-09-24 06:03:39 -07:00
|
|
|
ptr++;
|
2006-08-12 02:16:30 -07:00
|
|
|
count++;
|
|
|
|
}
|
2006-09-24 06:03:39 -07:00
|
|
|
break;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
for (i = 0;
|
|
|
|
((i < 65536) && (ptr < end) && (line[i]));
|
|
|
|
i++)
|
|
|
|
{
|
|
|
|
for (j = 0; j < cpp; j++, i++)
|
|
|
|
{
|
|
|
|
col[j] = line[i];
|
|
|
|
}
|
|
|
|
col[j] = 0;
|
|
|
|
i--;
|
|
|
|
for (j = 0; j < ncolors; j++)
|
|
|
|
{
|
|
|
|
if (!strcmp(col, cmap[j].str))
|
|
|
|
{
|
|
|
|
r = (unsigned char)cmap[j].r;
|
|
|
|
g = (unsigned char)cmap[j].g;
|
|
|
|
b = (unsigned char)cmap[j].b;
|
2010-06-07 22:39:46 -07:00
|
|
|
*ptr = ARGB_JOIN(0xff, r, g, b);
|
2006-09-24 06:03:39 -07:00
|
|
|
ptr++;
|
|
|
|
count++;
|
|
|
|
break;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
/* Scan in line from XPM file */
|
|
|
|
if ((!comment) && (quote) && (c != '"'))
|
|
|
|
{
|
2006-09-24 06:03:39 -07:00
|
|
|
if (c < 32) c = 32;
|
|
|
|
else if (c > 127) c = 127;
|
|
|
|
if (c =='\\')
|
|
|
|
{
|
|
|
|
if (++backslash < 2)
|
|
|
|
line[i++] = c;
|
|
|
|
else
|
|
|
|
backslash = 0;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
2006-09-24 06:03:39 -07:00
|
|
|
else
|
|
|
|
{
|
|
|
|
backslash = 0;
|
|
|
|
line[i++] = c;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
if (i >= lsz)
|
|
|
|
{
|
|
|
|
lsz += 256;
|
2006-09-24 06:03:39 -07:00
|
|
|
tl = realloc(line, lsz);
|
|
|
|
if (!tl) break;
|
|
|
|
line = tl;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
2010-09-18 16:07:31 -07:00
|
|
|
if (((ptr) && ((ptr - evas_cache_image_pixels(ie)) >= (w * h * (int)sizeof(DATA32)))) ||
|
2006-08-12 02:16:30 -07:00
|
|
|
((context > 1) && (count >= pixels)))
|
2006-09-24 06:03:39 -07:00
|
|
|
break;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
|
2012-01-02 06:32:21 -08:00
|
|
|
on_success:
|
2010-07-13 19:05:47 -07:00
|
|
|
free(cmap);
|
|
|
|
free(line);
|
2006-08-12 02:16:30 -07:00
|
|
|
|
2012-01-02 06:32:21 -08:00
|
|
|
eina_file_map_free(f, (void*) map);
|
|
|
|
eina_file_close(f);
|
|
|
|
|
2009-12-22 15:11:57 -08:00
|
|
|
*error = EVAS_LOAD_ERROR_NONE;
|
|
|
|
return EINA_TRUE;
|
2012-01-02 06:32:21 -08:00
|
|
|
|
|
|
|
on_error:
|
|
|
|
free(line);
|
|
|
|
eina_file_map_free(f, (void*) map);
|
|
|
|
eina_file_close(f);
|
|
|
|
return EINA_FALSE;
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
|
2009-12-22 15:11:57 -08:00
|
|
|
static Eina_Bool
|
|
|
|
evas_image_load_file_head_xpm(Image_Entry *ie, const char *file, const char *key, int *error)
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2009-12-22 15:11:57 -08:00
|
|
|
return evas_image_load_file_xpm(ie, file, key, 0, error);
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
|
2009-12-22 15:11:57 -08:00
|
|
|
static Eina_Bool
|
|
|
|
evas_image_load_file_data_xpm(Image_Entry *ie, const char *file, const char *key, int *error)
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2009-12-22 15:11:57 -08:00
|
|
|
return evas_image_load_file_xpm(ie, file, key, 1, error);
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
|
2009-06-16 06:01:36 -07:00
|
|
|
static int
|
2006-09-06 00:28:46 -07:00
|
|
|
module_open(Evas_Module *em)
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
|
|
|
if (!em) return 0;
|
2010-10-07 16:46:42 -07:00
|
|
|
_evas_loader_xpm_log_dom = eina_log_domain_register
|
|
|
|
("evas-xpm", EVAS_DEFAULT_LOG_COLOR);
|
2010-04-08 10:39:01 -07:00
|
|
|
if (_evas_loader_xpm_log_dom < 0)
|
|
|
|
{
|
2010-10-07 16:46:42 -07:00
|
|
|
EINA_LOG_ERR("Can not create a module log domain.");
|
2010-04-08 10:39:01 -07:00
|
|
|
return 0;
|
|
|
|
}
|
2012-01-02 06:32:21 -08:00
|
|
|
|
|
|
|
/* Shouldn't we make that PATH configurable ? */
|
|
|
|
rgb_txt = eina_file_open("/usr/lib/X11/rgb.txt", 0);
|
|
|
|
if (!rgb_txt) rgb_txt = eina_file_open("/usr/X11/lib/X11/rgb.txt", 0);
|
|
|
|
if (!rgb_txt) rgb_txt = eina_file_open("/usr/X11R6/lib/X11/rgb.txt", 0);
|
|
|
|
if (!rgb_txt) rgb_txt = eina_file_open("/usr/openwin/lib/X11/rgb.txt", 0);
|
|
|
|
if (rgb_txt)
|
|
|
|
rgb_txt_map = eina_file_map_all(rgb_txt, EINA_FILE_SEQUENTIAL);
|
2006-08-12 02:16:30 -07:00
|
|
|
em->functions = (void *)(&evas_image_load_xpm_func);
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
|
2009-06-16 06:01:36 -07:00
|
|
|
static void
|
cleanup: fix some "unused" errors from -Wextra.
As we're heading for a release we better remove as much errors as
possible and as the first step I'm removing warnings due unused
parameters, variables and functions. These tend to pollute real errors
spotted by -Wall and clang/llvm.
This does not fixes all, just the clear that could be set to
__UNUSED__, particularly to do (and I'd like some help from the
authors):
* src/lib/engines/common/evas_font_{draw,query}.c (tasn):
intl_props is just used while doing BIDI, but also used in other
#ifdef blocks :-/
* evas_map_* (raster):
huge amount of warnings, code is quite confusing and thus I'm not
touching it. I have no idea whenever the commented blocks or extra
parameters are intended to be used or no.
* src/modules/engines/fbevas_fb_main.c (raster?):
is fb_setvt() to be used? If not do you mind removing it?
* src/modules/engines/gl_{common,x11} (raster):
huge amount of warnings, code is quite nested and full of #ifdefs
that does not help to give a clear picture of what's going on.
* src/bin/evas_cserve_main.c (raster):
I could have ignored most of the errors, but is the code correct? I
mean, there is no unload of images being applied. If you confirm
none of those warnings are harmful I can flag them as unused.
* src/lib/engines/common_8 (dottedmag):
lots of unused functions that were acquired from common_16, they
are unused and if they will not, then they should be removed.
SVN revision: 52421
2010-09-18 12:17:41 -07:00
|
|
|
module_close(Evas_Module *em __UNUSED__)
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
2012-01-02 06:32:21 -08:00
|
|
|
if (rgb_txt)
|
|
|
|
{
|
|
|
|
eina_file_map_free(rgb_txt, rgb_txt_map);
|
|
|
|
eina_file_close(rgb_txt);
|
|
|
|
rgb_txt = NULL;
|
|
|
|
}
|
2010-04-08 10:39:01 -07:00
|
|
|
eina_log_domain_unregister(_evas_loader_xpm_log_dom);
|
2006-08-12 02:16:30 -07:00
|
|
|
}
|
|
|
|
|
2009-06-16 06:01:36 -07:00
|
|
|
static Evas_Module_Api evas_modapi =
|
2006-08-12 02:16:30 -07:00
|
|
|
{
|
|
|
|
EVAS_MODULE_API_VERSION,
|
2009-06-16 06:01:36 -07:00
|
|
|
"xpm",
|
|
|
|
"none",
|
|
|
|
{
|
|
|
|
module_open,
|
|
|
|
module_close
|
|
|
|
}
|
2006-08-12 02:16:30 -07:00
|
|
|
};
|
2009-06-16 06:01:36 -07:00
|
|
|
|
|
|
|
EVAS_MODULE_DEFINE(EVAS_MODULE_TYPE_IMAGE_LOADER, image_loader, xpm);
|
|
|
|
|
|
|
|
#ifndef EVAS_STATIC_BUILD_XPM
|
|
|
|
EVAS_EINA_MODULE_DEFINE(image_loader, xpm);
|
|
|
|
#endif
|