Marc Le Douarain - Fri, 26 Dec 2003 18:23:42 +0100
authorSam Lantinga <slouken@libsdl.org>
Sun, 04 Jan 2004 17:30:48 +0000
changeset 96cada40fddd77
parent 95 7fcb46931afc
child 97 e1161bd417c4
Marc Le Douarain - Fri, 26 Dec 2003 18:23:42 +0100
* Added EHB and HAM mode support to the ILBM loader
CHANGES
IMG_lbm.c
     1.1 --- a/CHANGES	Fri Dec 19 18:04:48 2003 +0000
     1.2 +++ b/CHANGES	Sun Jan 04 17:30:48 2004 +0000
     1.3 @@ -1,4 +1,6 @@
     1.4  1.2.4:
     1.5 +Marc Le Douarain - Fri, 26 Dec 2003 18:23:42 +0100
     1.6 + * Added EHB and HAM mode support to the ILBM loader
     1.7  Sam Lantinga - Wed Nov 19 00:23:44 PST 2003
     1.8   * Updated libtool support for new mingw32 DLL build process
     1.9  Holger Schemel - Mon, 04 Aug 2003 21:50:52 +0200
     2.1 --- a/IMG_lbm.c	Fri Dec 19 18:04:48 2003 +0000
     2.2 +++ b/IMG_lbm.c	Sun Jan 04 17:30:48 2004 +0000
     2.3 @@ -25,8 +25,10 @@
     2.4  /* This is a ILBM image file loading framework
     2.5     Load IFF pictures, PBM & ILBM packing methods, with or without stencil
     2.6     Written by Daniel Morais ( Daniel@Morais.com ) in September 2001.
     2.7 -   24 bits ILBM files support added by Marc Le Douarain (mavati@club-internet.fr)
     2.8 -   in December 2002.
     2.9 +   24 bits ILBM files support added by Marc Le Douarain (mavati AT club-internet
    2.10 +   POINT fr) in December 2002.
    2.11 +   EHB and HAM (specific Amiga graphic chip modes) support added by Marc Le Douarain
    2.12 +   (mavati AT club-internet POINT fr) in December 2003.
    2.13  */
    2.14  
    2.15  #include <stdio.h>
    2.16 @@ -86,12 +88,13 @@
    2.17  	Uint32      width;
    2.18  	BMHD	      bmhd;
    2.19  	char        *error;
    2.20 +	Uint8       flagHAM,flagEHB;
    2.21  
    2.22  	Image   = NULL;
    2.23  	error   = NULL;
    2.24  	MiniBuf = NULL;
    2.25  
    2.26 -	if ( !SDL_RWread( src, id, 4, 1 ) ) 
    2.27 +	if ( !SDL_RWread( src, id, 4, 1 ) )
    2.28  	{
    2.29  		error="error reading IFF chunk";
    2.30  		goto done;
    2.31 @@ -131,6 +134,8 @@
    2.32  	nbcolors = 0;
    2.33  
    2.34  	memset( &bmhd, 0, sizeof( BMHD ) );
    2.35 +	flagHAM = 0;
    2.36 +	flagEHB = 0;
    2.37  
    2.38  	while ( memcmp( id, "BODY", 4 ) != 0 )
    2.39  	{
    2.40 @@ -181,6 +186,23 @@
    2.41  			nbcolors = size / 3;
    2.42  		}
    2.43  
    2.44 +		if ( !memcmp( id, "CAMG", 4 ) ) /* Amiga ViewMode  */
    2.45 +		{
    2.46 +			Uint32 viewmodes;
    2.47 +			if ( !SDL_RWread( src, &viewmodes, sizeof(viewmodes), 1 ) )
    2.48 +			{
    2.49 +				error="error reading CAMG chunk";
    2.50 +				goto done;
    2.51 +			}
    2.52 +
    2.53 +			bytesloaded = size;
    2.54 +			viewmodes = SDL_SwapBE32( viewmodes );
    2.55 +			if ( viewmodes & 0x0800 )
    2.56 +				flagHAM = 1;
    2.57 +			if ( viewmodes & 0x0080 )
    2.58 +				flagEHB = 1;
    2.59 +		}
    2.60 +
    2.61  		if ( memcmp( id, "BODY", 4 ) )
    2.62  		{
    2.63  			if ( size & 1 )	++size;  	/* padding ! */
    2.64 @@ -215,13 +237,13 @@
    2.65  		goto done;
    2.66  	}
    2.67  
    2.68 -	if ( ( Image = SDL_CreateRGBSurface( SDL_SWSURFACE, width, bmhd.h, bmhd.planes==24?24:8, 0, 0, 0, 0 ) ) == NULL )
    2.69 +	if ( ( Image = SDL_CreateRGBSurface( SDL_SWSURFACE, width, bmhd.h, (bmhd.planes==24 || flagHAM==1)?24:8, 0, 0, 0, 0 ) ) == NULL )
    2.70  	   goto done;
    2.71  
    2.72  	/* Update palette informations */
    2.73  
    2.74  	/* There is no palette in 24 bits ILBM file */
    2.75 -	if ( nbcolors>0 )
    2.76 +	if ( nbcolors>0 && flagHAM==0 )
    2.77  	{
    2.78  		Image->format->palette->ncolors = nbcolors;
    2.79  
    2.80 @@ -233,6 +255,23 @@
    2.81  			Image->format->palette->colors[i].g = *ptr++;
    2.82  			Image->format->palette->colors[i].b = *ptr++;
    2.83  		}
    2.84 +
    2.85 +		/* Amiga EHB mode (Extra-Half-Bright) */
    2.86 +		/* 6 bitplanes mode with a 32 colors palette */
    2.87 +		/* The 32 last colors are the same but divided by 2 */
    2.88 +		/* Some Amiga pictures save 64 colors with 32 last wrong colors,
    2.89 +		/* they shouldn't !, and here we overwrite these 32 bad colors. */
    2.90 +		if ( (nbcolors==32 || flagEHB ) && (1<<bmhd.planes)==64 )
    2.91 +		{
    2.92 +			Image->format->palette->ncolors = 64;
    2.93 +			ptr = &colormap[0];
    2.94 +			for ( i=32; i<64; i++ )
    2.95 +			{
    2.96 +				Image->format->palette->colors[i].r = (*ptr++)/2;
    2.97 +				Image->format->palette->colors[i].g = (*ptr++)/2;
    2.98 +				Image->format->palette->colors[i].b = (*ptr++)/2;
    2.99 +			}
   2.100 +		}
   2.101  	}
   2.102  
   2.103  	/* Get the bitmap */
   2.104 @@ -298,7 +337,7 @@
   2.105  		/* One line has been read, store it ! */
   2.106  
   2.107  		ptr = Image->pixels;
   2.108 -		if ( nbplanes==24 )
   2.109 +		if ( nbplanes==24 || flagHAM==1 )
   2.110  			ptr += h * width * 3;
   2.111  		else
   2.112  			ptr += h * width;
   2.113 @@ -309,7 +348,7 @@
   2.114  		}
   2.115  		else		/* We have to un-interlace the bits ! */
   2.116  		{
   2.117 -			if ( nbplanes!=24 )
   2.118 +			if ( nbplanes!=24 && flagHAM==0 )
   2.119  			{
   2.120  				size = ( width + 7 ) / 8;
   2.121  
   2.122 @@ -335,34 +374,63 @@
   2.123  			}
   2.124  			else
   2.125  			{
   2.126 +				Uint32 finalcolor = 0;
   2.127  				size = ( width + 7 ) / 8;
   2.128  				/* 24 bitplanes ILBM : R0...R7,G0...G7,B0...B7 */
   2.129 +				/* or HAM (6 bitplanes) or HAM8 (8 bitplanes) modes */
   2.130  				for ( i=0; i<width; i=i+8 )
   2.131  				{
   2.132  					Uint8 maskBit = 0x80;
   2.133  					for ( j=0; j<8; j++ )
   2.134  					{
   2.135 -						Uint32 color24 = 0;
   2.136 -						Uint32 maskColor24 = 1;
   2.137 +						Uint32 pixelcolor = 0;
   2.138 +						Uint32 maskColor = 1;
   2.139  						Uint8 dataBody;
   2.140  						for ( plane=0; plane < nbplanes; plane++ )
   2.141  						{
   2.142  							dataBody = MiniBuf[ plane*size+i/8 ];
   2.143  							if ( dataBody&maskBit )
   2.144 -								color24 = color24 | maskColor24;
   2.145 -							maskColor24 = maskColor24<<1;
   2.146 +								pixelcolor = pixelcolor | maskColor;
   2.147 +							maskColor = maskColor<<1;
   2.148 +						}
   2.149 +						/* HAM : 12 bits RGB image (4 bits per color component) */
   2.150 +						/* HAM8 : 18 bits RGB image (6 bits per color component) */
   2.151 +						if ( flagHAM )
   2.152 +						{
   2.153 +							switch( pixelcolor>>(nbplanes-2) )
   2.154 +							{
   2.155 +								case 0: /* take direct color from palette */
   2.156 +									finalcolor = colormap[ pixelcolor*3 ] + (colormap[ pixelcolor*3+1 ]<<8) + (colormap[ pixelcolor*3+2 ]<<16);
   2.157 +									break;
   2.158 +								case 1: /* modify only blue component */
   2.159 +									finalcolor = finalcolor&0x00FFFF;
   2.160 +									finalcolor = finalcolor | (pixelcolor<<(16+(10-nbplanes)));
   2.161 +									break;
   2.162 +								case 2: /* modify only red component */
   2.163 +									finalcolor = finalcolor&0xFFFF00;
   2.164 +									finalcolor = finalcolor | pixelcolor<<(10-nbplanes);
   2.165 +									break;
   2.166 +								case 3: /* modify only green component */
   2.167 +									finalcolor = finalcolor&0xFF00FF;
   2.168 +									finalcolor = finalcolor | (pixelcolor<<(8+(10-nbplanes)));
   2.169 +									break;
   2.170 +							}
   2.171 +						}
   2.172 +						else
   2.173 +						{
   2.174 +							finalcolor = pixelcolor;
   2.175  						}
   2.176  						if ( SDL_BYTEORDER == SDL_LIL_ENDIAN )
   2.177  						{
   2.178 -							*ptr++ = color24>>16;
   2.179 -							*ptr++ = color24>>8;
   2.180 -							*ptr++ = color24;
   2.181 +							*ptr++ = finalcolor>>16;
   2.182 +							*ptr++ = finalcolor>>8;
   2.183 +							*ptr++ = finalcolor;
   2.184  						}
   2.185  						else
   2.186  						{
   2.187 -							*ptr++ = color24;
   2.188 -							*ptr++ = color24>>8;
   2.189 -							*ptr++ = color24>>16;
   2.190 +							*ptr++ = finalcolor;
   2.191 +							*ptr++ = finalcolor>>8;
   2.192 +							*ptr++ = finalcolor>>16;
   2.193  						}
   2.194  
   2.195  						maskBit = maskBit>>1;