IMG_xcf.c
changeset 343 5bf0f0d6a74e
parent 320 aa5d55b11751
child 347 ad5034cad524
equal deleted inserted replaced
341:18ab81286e51 343:5bf0f0d6a74e
   206 
   206 
   207 
   207 
   208 /* See if an image is contained in a data source */
   208 /* See if an image is contained in a data source */
   209 int IMG_isXCF(SDL_RWops *src)
   209 int IMG_isXCF(SDL_RWops *src)
   210 {
   210 {
   211 	int start;
   211 	Sint64 start;
   212 	int is_XCF;
   212 	int is_XCF;
   213 	char magic[14];
   213 	char magic[14];
   214 
   214 
   215 	if ( !src )
   215 	if ( !src )
   216 		return 0;
   216 		return 0;
   217 	start = SDL_RWtell(src);
   217 	start = SDL_RWtell(src);
   218 	is_XCF = 0;
   218 	is_XCF = 0;
   219 	if ( SDL_RWread(src, magic, sizeof(magic), 1) ) {
   219 	if ( SDL_RWread(src, magic, sizeof(magic), 1) ) {
   220 		if (strncmp(magic, "gimp xcf ", 9) == 0) {
   220 		if (SDL_strncmp(magic, "gimp xcf ", 9) == 0) {
   221 			is_XCF = 1;
   221 			is_XCF = 1;
   222 		}
   222 		}
   223 	}
   223 	}
   224 	SDL_RWseek(src, start, RW_SEEK_SET);
   224 	SDL_RWseek(src, start, RW_SEEK_SET);
   225 	return(is_XCF);
   225 	return(is_XCF);
   309 
   309 
   310   // Just read, don't save
   310   // Just read, don't save
   311   do {
   311   do {
   312     xcf_read_property (src, &prop);
   312     xcf_read_property (src, &prop);
   313     if (prop.id == PROP_COMPRESSION)
   313     if (prop.id == PROP_COMPRESSION)
   314       h->compr = prop.data.compression;
   314       h->compr = (xcf_compr_type)prop.data.compression;
   315     else if (prop.id == PROP_COLORMAP) {
   315     else if (prop.id == PROP_COLORMAP) {
   316       // unused var: int i;
   316       // unused var: int i;
   317 
   317 
   318       h->cm_num = prop.data.colormap.num;
   318       h->cm_num = prop.data.colormap.num;
   319       h->cm_map = (unsigned char *) malloc (sizeof (unsigned char) * 3 * h->cm_num);
   319       h->cm_map = (unsigned char *) SDL_malloc (sizeof (unsigned char) * 3 * h->cm_num);
   320       memcpy (h->cm_map, prop.data.colormap.cmap, 3*sizeof (char)*h->cm_num);
   320       memcpy (h->cm_map, prop.data.colormap.cmap, 3*sizeof (char)*h->cm_num);
   321       free (prop.data.colormap.cmap);
   321       free (prop.data.colormap.cmap);
   322     }
   322     }
   323   } while (prop.id != PROP_END);
   323   } while (prop.id != PROP_END);
   324 
   324 
   364 
   364 
   365 static xcf_channel * read_xcf_channel (SDL_RWops * src) {
   365 static xcf_channel * read_xcf_channel (SDL_RWops * src) {
   366   xcf_channel * l;
   366   xcf_channel * l;
   367   xcf_prop    prop;
   367   xcf_prop    prop;
   368 
   368 
   369   l = (xcf_channel *) malloc (sizeof (xcf_channel));
   369   l = (xcf_channel *) SDL_malloc (sizeof (xcf_channel));
   370   l->width  = SDL_ReadBE32 (src);
   370   l->width  = SDL_ReadBE32 (src);
   371   l->height = SDL_ReadBE32 (src);
   371   l->height = SDL_ReadBE32 (src);
   372 
   372 
   373   l->name = read_string (src);
   373   l->name = read_string (src);
   374 
   374 
   431 
   431 
   432 static xcf_level * read_xcf_level (SDL_RWops * src) {
   432 static xcf_level * read_xcf_level (SDL_RWops * src) {
   433   xcf_level * l;
   433   xcf_level * l;
   434   int i;
   434   int i;
   435 
   435 
   436   l = (xcf_level *) malloc (sizeof (xcf_level));
   436   l = (xcf_level *) SDL_malloc (sizeof (xcf_level));
   437   l->width  = SDL_ReadBE32 (src);
   437   l->width  = SDL_ReadBE32 (src);
   438   l->height = SDL_ReadBE32 (src);
   438   l->height = SDL_ReadBE32 (src);
   439 
   439 
   440   l->tile_file_offsets = NULL;
   440   l->tile_file_offsets = NULL;
   441   i = 0;
   441   i = 0;
   442   do {
   442   do {
   443     l->tile_file_offsets = (Uint32 *) realloc (l->tile_file_offsets, sizeof (Uint32) * (i+1));
   443     l->tile_file_offsets = (Uint32 *) SDL_realloc (l->tile_file_offsets, sizeof (Uint32) * (i+1));
   444     l->tile_file_offsets [i] = SDL_ReadBE32 (src);
   444     l->tile_file_offsets [i] = SDL_ReadBE32 (src);
   445   } while (l->tile_file_offsets [i++]);
   445   } while (l->tile_file_offsets [i++]);
   446 
   446 
   447   return l;
   447   return l;
   448 }
   448 }
   452 }
   452 }
   453 
   453 
   454 static unsigned char * load_xcf_tile_none (SDL_RWops * src, Uint32 len, int bpp, int x, int y) {
   454 static unsigned char * load_xcf_tile_none (SDL_RWops * src, Uint32 len, int bpp, int x, int y) {
   455   unsigned char * load;
   455   unsigned char * load;
   456 
   456 
   457   load = (unsigned char *) malloc (len); // expect this is okay
   457   load = (unsigned char *) SDL_malloc (len); // expect this is okay
   458   SDL_RWread (src, load, len, 1);
   458   SDL_RWread (src, load, len, 1);
   459 
   459 
   460   return load;
   460   return load;
   461 }
   461 }
   462 
   462 
   464   unsigned char * load, * t, * data, * d;
   464   unsigned char * load, * t, * data, * d;
   465   Uint32 reallen;
   465   Uint32 reallen;
   466   int i, size, count, j, length;
   466   int i, size, count, j, length;
   467   unsigned char val;
   467   unsigned char val;
   468 
   468 
   469   t = load = (unsigned char *) malloc (len);
   469   t = load = (unsigned char *) SDL_malloc (len);
   470   reallen = SDL_RWread (src, t, 1, len);
   470   reallen = SDL_RWread (src, t, 1, len);
   471 
   471 
   472   data = (unsigned char *) malloc (x*y*bpp);
   472   data = (unsigned char *) malloc (x*y*bpp);
   473   for (i = 0; i < bpp; i++) {
   473   for (i = 0; i < bpp; i++) {
   474     d    = data + i;
   474     d    = data + i;
   512 	}
   512 	}
   513       }
   513       }
   514     }
   514     }
   515   }
   515   }
   516 
   516 
   517   free (load);
   517   SDL_free (load);
   518   return (data);
   518   return (data);
   519 }
   519 }
   520 
   520 
   521 static Uint32 rgb2grey (Uint32 a) {
   521 static Uint32 rgb2grey (Uint32 a) {
   522   Uint8 l;
   522   Uint8 l;
   523   l = 0.2990 * ((a && 0x00FF0000) >> 16)
   523   l = (Uint8)(0.2990 * ((a && 0x00FF0000) >> 16)
   524     + 0.5870 * ((a && 0x0000FF00) >>  8)
   524     + 0.5870 * ((a && 0x0000FF00) >>  8)
   525     + 0.1140 * ((a && 0x000000FF));
   525     + 0.1140 * ((a && 0x000000FF)));
   526 
   526 
   527   return (l << 16) | (l << 8) | l;
   527   return (l << 16) | (l << 8) | l;
   528 }
   528 }
   529 
   529 
   530 static void create_channel_surface (SDL_Surface * surf, xcf_image_type itype, Uint32 color, Uint32 opacity) {
   530 static void create_channel_surface (SDL_Surface * surf, xcf_image_type itype, Uint32 color, Uint32 opacity) {
   547   xcf_level     * level;
   547   xcf_level     * level;
   548   unsigned char * tile;
   548   unsigned char * tile;
   549   Uint8  * p8;
   549   Uint8  * p8;
   550   Uint16 * p16;
   550   Uint16 * p16;
   551   Uint32 * p;
   551   Uint32 * p;
   552   int x, y, tx, ty, ox, oy, i, j;
   552   int i, j;
       
   553   Uint32 x, y, tx, ty, ox, oy;
   553   Uint32 *row;
   554   Uint32 *row;
   554 
   555 
   555   SDL_RWseek (src, layer->hierarchy_file_offset, RW_SEEK_SET);
   556   SDL_RWseek (src, layer->hierarchy_file_offset, RW_SEEK_SET);
   556   hierarchy = read_xcf_hierarchy (src);
   557   hierarchy = read_xcf_hierarchy (src);
   557 
   558 
   671   return 0;
   672   return 0;
   672 }
   673 }
   673 
   674 
   674 SDL_Surface *IMG_LoadXCF_RW(SDL_RWops *src)
   675 SDL_Surface *IMG_LoadXCF_RW(SDL_RWops *src)
   675 {
   676 {
   676   int start;
   677   Sint64 start;
   677   const char *error = NULL;
   678   const char *error = NULL;
   678   SDL_Surface *surface, *lays;
   679   SDL_Surface *surface, *lays;
   679   xcf_header * head;
   680   xcf_header * head;
   680   xcf_layer  * layer;
   681   xcf_layer  * layer;
   681   xcf_channel ** channel;
   682   xcf_channel ** channel;
   682   int chnls, i, offsets;
   683   int chnls, i, offsets;
   683   Uint32 offset, fp;
   684   Sint64 offset, fp;
   684 
   685 
   685   unsigned char * (* load_tile) (SDL_RWops *, Uint32, int, int, int);
   686   unsigned char * (* load_tile) (SDL_RWops *, Uint32, int, int, int);
   686 
   687 
   687   if ( !src ) {
   688   if ( !src ) {
   688     /* The error message has been set in SDL_RWFromFile */
   689     /* The error message has been set in SDL_RWFromFile */
   720   head->layer_file_offsets = NULL;
   721   head->layer_file_offsets = NULL;
   721   offsets = 0;
   722   offsets = 0;
   722 
   723 
   723   while ((offset = SDL_ReadBE32 (src))) {
   724   while ((offset = SDL_ReadBE32 (src))) {
   724     head->layer_file_offsets = (Uint32 *) realloc (head->layer_file_offsets, sizeof (Uint32) * (offsets+1));
   725     head->layer_file_offsets = (Uint32 *) realloc (head->layer_file_offsets, sizeof (Uint32) * (offsets+1));
   725     head->layer_file_offsets [offsets] = offset;
   726     head->layer_file_offsets [offsets] = (Uint32)offset;
   726     offsets++;
   727     offsets++;
   727   }
   728   }
   728   fp = SDL_RWtell (src);
   729   fp = SDL_RWtell (src);
   729  
   730  
   730   lays = SDL_CreateRGBSurface(SDL_SWSURFACE, head->width, head->height, 32,
   731   lays = SDL_CreateRGBSurface(SDL_SWSURFACE, head->width, head->height, 32,
   762 
   763 
   763   // read channels
   764   // read channels
   764   channel = NULL;
   765   channel = NULL;
   765   chnls   = 0;
   766   chnls   = 0;
   766   while ((offset = SDL_ReadBE32 (src))) {
   767   while ((offset = SDL_ReadBE32 (src))) {
   767     channel = (xcf_channel **) realloc (channel, sizeof (xcf_channel *) * (chnls+1));
   768     channel = (xcf_channel **) SDL_realloc (channel, sizeof (xcf_channel *) * (chnls+1));
   768     fp = SDL_RWtell (src);
   769     fp = SDL_RWtell (src);
   769     SDL_RWseek (src, offset, RW_SEEK_SET);
   770     SDL_RWseek (src, offset, RW_SEEK_SET);
   770     channel [chnls++] = (read_xcf_channel (src));
   771     channel [chnls++] = (read_xcf_channel (src));
   771     SDL_RWseek (src, fp, RW_SEEK_SET);    
   772     SDL_RWseek (src, fp, RW_SEEK_SET);    
   772   }
   773   }
   782       goto done;
   783       goto done;
   783     }
   784     }
   784     for (i = 0; i < chnls; i++) {
   785     for (i = 0; i < chnls; i++) {
   785       //      printf ("CNLBLT %i\n", i);
   786       //      printf ("CNLBLT %i\n", i);
   786       if (!channel [i]->selection && channel [i]->visible) {
   787       if (!channel [i]->selection && channel [i]->visible) {
   787 	create_channel_surface (chs, head->image_type, channel [i]->color, channel [i]->opacity);
   788 	create_channel_surface (chs, (xcf_image_type)head->image_type, channel [i]->color, channel [i]->opacity);
   788 	SDL_BlitSurface (chs, NULL, surface, NULL);
   789 	SDL_BlitSurface (chs, NULL, surface, NULL);
   789       }
   790       }
   790       free_xcf_channel (channel [i]);
   791       free_xcf_channel (channel [i]);
   791     }
   792     }
   792 
   793