GRASS Programmer's Manual
6.4.1(2011)
|
00001 /* This routine is public only because source is in different files. 00002 * It should NEVER be called directly. 00003 * It is used by G_add_color_rule() and G__read_old_colors(). 00004 * These routines know when it is approriate to call this routine. 00005 */ 00006 #include <grass/gis.h> 00007 #define umalloc(n) (unsigned char *) G_malloc((size_t)n) 00008 #define urealloc(s,n) (unsigned char *) G_realloc(s,(size_t)n) 00009 00010 #define LIMIT(x) if (x < 0) x = 0; else if (x > 255) x = 255; 00011 00012 int G__insert_color_into_lookup(CELL cat, 00013 int red, int grn, int blu, 00014 struct _Color_Info_ *cp) 00015 { 00016 long nalloc; 00017 long i; 00018 long newlen, curlen, gap; 00019 00020 LIMIT(red); 00021 LIMIT(grn); 00022 LIMIT(blu); 00023 00024 /* first color? */ 00025 if (!cp->lookup.active) { 00026 cp->lookup.active = 1; 00027 cp->lookup.nalloc = 256; 00028 cp->lookup.red = umalloc(cp->lookup.nalloc); 00029 cp->lookup.grn = umalloc(cp->lookup.nalloc); 00030 cp->lookup.blu = umalloc(cp->lookup.nalloc); 00031 cp->lookup.set = umalloc(cp->lookup.nalloc); 00032 cp->max = cp->min = cat; 00033 } 00034 00035 /* extend the color table? */ 00036 else if (cat > cp->max) { 00037 curlen = cp->max - cp->min + 1; 00038 newlen = cat - cp->min + 1; 00039 nalloc = newlen; 00040 if (nalloc != (int)nalloc) /* check for int overflow */ 00041 return -1; 00042 00043 if (nalloc > cp->lookup.nalloc) { 00044 while (cp->lookup.nalloc < nalloc) 00045 cp->lookup.nalloc += 256; 00046 nalloc = cp->lookup.nalloc; 00047 00048 cp->lookup.red = urealloc((char *)cp->lookup.red, nalloc); 00049 cp->lookup.grn = urealloc((char *)cp->lookup.grn, nalloc); 00050 cp->lookup.blu = urealloc((char *)cp->lookup.blu, nalloc); 00051 cp->lookup.set = urealloc((char *)cp->lookup.set, nalloc); 00052 } 00053 00054 /* fill in gap with white */ 00055 for (i = curlen; i < newlen; i++) { 00056 cp->lookup.red[i] = 255; 00057 cp->lookup.grn[i] = 255; 00058 cp->lookup.blu[i] = 255; 00059 cp->lookup.set[i] = 0; 00060 } 00061 cp->max = cat; 00062 } 00063 else if (cat < cp->min) { 00064 curlen = cp->max - cp->min + 1; 00065 newlen = cp->max - cat + 1; 00066 gap = newlen - curlen; 00067 nalloc = newlen; 00068 if (nalloc != (int)nalloc) /* check for int overflow */ 00069 return -1; 00070 00071 if (nalloc > cp->lookup.nalloc) { 00072 while (cp->lookup.nalloc < nalloc) 00073 cp->lookup.nalloc += 256; 00074 nalloc = cp->lookup.nalloc; 00075 00076 cp->lookup.red = urealloc((char *)cp->lookup.red, nalloc); 00077 cp->lookup.grn = urealloc((char *)cp->lookup.grn, nalloc); 00078 cp->lookup.blu = urealloc((char *)cp->lookup.blu, nalloc); 00079 cp->lookup.set = urealloc((char *)cp->lookup.set, nalloc); 00080 } 00081 00082 /* shift the table to make room in front */ 00083 for (i = 1; i <= curlen; i++) { 00084 cp->lookup.red[newlen - i] = cp->lookup.red[curlen - i]; 00085 cp->lookup.grn[newlen - i] = cp->lookup.grn[curlen - i]; 00086 cp->lookup.blu[newlen - i] = cp->lookup.blu[curlen - i]; 00087 cp->lookup.set[newlen - i] = cp->lookup.set[curlen - i]; 00088 } 00089 00090 /* fill in gap with white */ 00091 for (i = 1; i < gap; i++) { 00092 cp->lookup.red[i] = 255; 00093 cp->lookup.grn[i] = 255; 00094 cp->lookup.blu[i] = 255; 00095 cp->lookup.set[i] = 0; 00096 } 00097 cp->min = cat; 00098 } 00099 00100 /* set the color! */ 00101 i = cat - cp->min; 00102 cp->lookup.red[i] = red; 00103 cp->lookup.grn[i] = grn; 00104 cp->lookup.blu[i] = blu; 00105 cp->lookup.set[i] = 1; 00106 00107 return 1; 00108 }