Usage:
CopyCode The Code is as follows: imageras _ Ras = new imageras (@ "D: \ temp \ test. RAS ");
Picturebox1.image = _ RAS. image;
_ RAS. saveras (@ "D: \ temp \ OK. RAS ");
I only implemented the 24-bit color and 8-bit color structure, which is too simple. Only the file header and data area are supported. The 8-bit color table has some special features.
First, the red table, the green table, and the blue table are usually RGB and RGB. In this case, the Rrrr... ggg... B ....
I don't know what to think.
There is little time to do these things when there are too many projects. The next target is the IFF file.
All code
Copy code The Code is as follows: using system;
Using system. Collections. Generic;
Using system. text;
Using system. runtime. interopservices;
Using system. Drawing. imaging;
Using system. drawing;
Using system. IO;
Namespace zgke. myimage. imagefile
{
/// <Summary>
/// Sun Raster image RAS
// Zgke@sina.com
/// QQ: 116149
/// </Summary>
Public class imageras
{
Public imageras (string p_imagefile)
{
If (system. Io. file. exists (p_imagefile ))
{
LoadImage (system. Io. file. readallbytes (p_imagefile ));
}
}
Public imageras ()
{
}
# Region private
/// <Summary>
/// File Header 956aa659
/// </Summary>
Private uint m_mageic = 0x956aa659;
/// <Summary>
/// Width
/// </Summary>
Private uint m_width = 0;
/// <Summary>
/// High
/// </Summary>
Private uint m_height = 0;
/// <Summary>
/// Color depth
/// </Summary>
Private uint m_depth = 0;
/// <Summary>
/// Data size in the graphic Area
/// </Summary>
Private uint m_length = 0;
/// <Summary>
/// Data Type
/// </Summary>
Private uint m_type = 0;
/// <Summary>
/// Color image type
/// </Summary>
Private uint m_maptype = 0;
/// <Summary>
/// Color Length
/// </Summary>
Private uint m_maplength = 0;
/// <Summary>
/// Color table
/// </Summary>
Private color [] m_colorlist = new color [256];
/// <Summary>
/// Image
/// </Summary>
Private bitmap m_image;
# Endregion
/// <Summary>
/// Obtain the image
/// </Summary>
Public bitmap image
{
Get
{
Return m_image;
}
Set
{
If (value! = NULL)
{
M_image = value;
M_width = (uint) value. width;
M_height = (uint) value. height;
Switch (value. pixelformat)
{
Case pixelformat. format8bppindexed:
Break;
Case pixelformat. format32bppargb:
Break;
Default:
M_depth = 24;
Break;
}
}
}
}
/// <Summary>
/// Obtain data
/// </Summary>
/// <Param name = "p_imagebytes"> </param>
Private void LoadImage (byte [] p_imagebytes)
{
If (bitconverter. touint32 (p_imagebytes, 0 )! = M_mageic) throw new exception ("incorrect file header! ");
M_width = bytestouint (p_imagebytes, 4 );
M_height = bytestouint (p_imagebytes, 8 );
M_depth = bytestouint (p_imagebytes, 12 );
M_length = bytestouint (p_imagebytes, 16 );
M_type = bytestouint (p_imagebytes, 20 );
M_maptype = bytestouint (p_imagebytes, 24 );
M_maplength = bytestouint (p_imagebytes, 28 );
Int _ starindex = 32;
Switch (m_maptype)
{
Case 1:
Int _ colortable = (INT) m_maplength/3;
For (INT I = 0; I! = _ Colortable; I ++)
{
M_colorlist [I] = color. fromargb (p_imagebytes [_ starindex], p_imagebytes [_ starindex + _ colortable], p_imagebytes [_ starindex + (_ colortable * 2)]);
_ Starindex ++;
}
_ Starindex + = _ colortable * 2;
Break;
Default:
Break;
}
Loaddata (p_imagebytes, _ starindex );
}
/// <Summary>
/// Convert byte to uint
/// </Summary>
/// <Param name = "p_value"> byte array </param>
/// <Param name = "p_index"> Start position </param>
/// <Returns> </returns>
Private uint bytestouint (byte [] p_value, int p_index)
{
Byte [] _ valuebytes = new byte [4];
_ Valuebytes [0] = p_value [p_index + 3];
_ Valuebytes [1] = p_value [p_index + 2];
_ Valuebytes [2] = p_value [p_index + 1];
_ Valuebytes [3] = p_value [p_index];
Return bitconverter. touint32 (_ valuebytes, 0 );
}
/// <Summary>
/// Obtain the reversed bytes
/// </Summary>
/// <Param name = "p_value"> </param>
/// <Returns> </returns>
Private byte [] uinttobytes (uint p_value)
{
Byte [] _ valuebytes = bitconverter. getbytes (p_value );
Array. Reverse (_ valuebytes );
Return _ valuebytes;
}
/// <Summary>
/// Obtain Graphic Data
/// </Summary>
/// <Param name = "p_valuebytes"> file retention </param>
/// <Param name = "p_starindex"> Leave the start position in RGB format </param>
Private void loaddata (byte [] p_valuebytes, int p_starindex)
{
Pixelformat _ format = pixelformat. format24bpprgb;
Switch (m_depth)
{
Case 8:
_ Format = pixelformat. format8bppindexed;
Break;
Case 24:
_ Format = pixelformat. format24bpprgb;
Break;
Default:
Throw new exception ("not implemented! ");
}
M_image = new Bitmap (INT) m_width, (INT) m_height, _ format );
Bitmapdata _ DATA = m_image.lockbits (New rectangle (0, 0, m_image.width, m_image.height), imagelockmode. readwrite, m_image.pixelformat );
Byte [] _ writebytes = new byte [_ data. Height * _ data. stride];
Int _ starindex = 0;
Int _ writeindex = 0;
For (INT I = 0; I! = _ Data. height; I ++)
{
_ Writeindex = I * _ data. stride;
_ Starindex = I * (INT) m_length/(INT) m_height) + p_starindex;
For (INT z = 0; Z! = _ Data. width; Z ++)
{
Switch (m_depth)
{
Case 8:
_ Writebytes [_ writeindex] = p_valuebytes [_ starindex];
_ Writeindex ++;
_ Starindex ++;
Break;
Case 24:
_ Writebytes [_ writeindex] = p_valuebytes [_ starindex + 2];
_ Writebytes [_ writeindex + 1] = p_valuebytes [_ starindex + 1];
_ Writebytes [_ writeindex + 2] = p_valuebytes [_ starindex];
_ Writeindex + = 3;
_ Starindex + = 3;
Break;
}
}
}
Switch (m_depth)
{
Case 8:
Colorpalette _ palette = m_image.palette;
For (INT I = 0; I! = M_colorlist.length; I ++)
{
_ Palette. Entries [I] = m_colorlist [I];
}
M_image.palette = _ palette;
Break;
Default:
Break;
}
Marshal. Copy (_ writebytes, 0, _ data. scan0, _ writebytes. Length );
M_image.unlockbits (_ data );
}
/// <Summary>
/// Save the image
/// </Summary>
/// <Returns> </returns>
Private byte [] saveimageofras ()
{
If (m_image = NULL) return New byte [0];
Memorystream _ stream = new memorystream ();
_ Stream. Write (bitconverter. getbytes (m_mageic), 0, 4 );
_ Stream. Write (uinttobytes (m_width), 0, 4 );
_ Stream. Write (uinttobytes (m_height), 0, 4 );
Switch (m_depth)
{
Case 8:
Bitmapdata _ data256 = m_image.lockbits (New rectangle (0, 0, m_image.width, m_image.height), imagelockmode. readonly, m_image.pixelformat );
Byte [] _ databytes = new byte [_ data256.stride * _ data256.height];
Int _ stride = _ data256.stride;
Marshal. Copy (_ data256.scan0, _ databytes, 0, _ databytes. Length );
M_image.unlockbits (_ data256 );
_ Stream. Write (uinttobytes (8), 0, 4 );
Uint _ widthcount = (uint) m_image.width;
If (m_image.width % 2! = 0) _ widthcount = (uint) m_image.width + 1;
Uint _ allcount = _ widthcount * (uint) m_image.height;
_ Stream. Write (uinttobytes (_ allcount), 0, 4 );
_ Stream. Write (uinttobytes (0), 0, 4 );
_ Stream. Write (uinttobytes (1), 0, 4 );
_ Stream. Write (uinttobytes (768), 0, 4 );
Byte [] _ redbytes = new byte [1, 256];
Byte [] _ greenbytes = new byte [1, 256];
Byte [] _ bluebytes = new byte [256];
For (INT I = 0; I! = 256; I ++)
{
_ Redbytes [I] = m_image.palette.entries [I]. R;
_ Greenbytes [I] = m_image.palette.entries [I]. g;
_ Bluebytes [I] = m_image.palette.entries [I]. B;
}
_ Stream. Write (_ redbytes, 0, _ redbytes. Length );
_ Stream. Write (_ greenbytes, 0, _ greenbytes. Length );
_ Stream. Write (_ bluebytes, 0, _ bluebytes. Length );
Byte [] _ write = new byte [_ widthcount];
For (INT I = 0; I! = M_image.height; I ++)
{
Array. Copy (_ databytes, I * _ stride, _ write, 0, _ widthcount );
_ Stream. Write (_ write, 0, _ write. Length );
}
Break;
Default:
Bitmap _ newbitmap = new Bitmap (m_image.width, m_image.height, pixelformat. format24bpprgb );
Graphics _ graphics = graphics. fromimage (_ newbitmap );
_ Graphics. drawimage (m_image, new rectangle (0, 0, m_image.width, m_image.height ));
_ Graphics. Dispose ();
Bitmapdata _ data24 = _ newbitmap. lockbits (New rectangle (0, 0, _ newbitmap. Width, _ newbitmap. Height), imagelockmode. readonly, _ newbitmap. pixelformat );
Byte [] _ databytes24 = new byte [_ data24.stride * _ data24.height];
Int _ stride24 = _ data24.stride;
Marshal. Copy (_ data24.scan0, _ databytes24, 0, _ databytes24.length );
_ Newbitmap. unlockbits (_ data24 );
_ Stream. Write (uinttobytes (24), 0, 4 );
Uint _ widthcount24 = (uint) _ newbitmap. width;
If (_ newbitmap. Width % 2! = 0) _ widthcount24 = (uint) _ newbitmap. Width + 1;
Uint _ allcount24 = _ widthcount24 * (uint) _ newbitmap. Height * 3;
_ Widthcount24 = _ widthcount24 * 3;
_ Stream. Write (uinttobytes (_ allcount24), 0, 4 );
_ Stream. Write (uinttobytes (0), 0, 4 );
_ Stream. Write (uinttobytes (0), 0, 4 );
_ Stream. Write (uinttobytes (0), 0, 4 );
Byte [] _ write24 = new byte [0];
For (INT I = 0; I! = M_image.height; I ++)
{
_ Write24 = new byte [_ widthcount24];
Int _ writeindex = 0;
Int _ starindex = I * _ stride24;
For (INT z = 0; Z! = M_image.width; Z ++)
{
_ Write24 [_ writeindex] = _ databytes24 [_ starindex + 2];
_ Write24 [_ writeindex + 1] = _ databytes24 [_ starindex + 1];
_ Write24 [_ writeindex + 2] = _ databytes24 [_ starindex];
_ Writeindex + = 3;
_ Starindex + = 3;
}
_ Stream. Write (_ write24, 0, _ write24.length );
}
_ Newbitmap. Dispose ();
Break;
}
Byte [] _ return = _ stream. toarray ();
Return _ return;
}
/// <Summary>
/// Save the image to the RAS File
/// </Summary>
/// <Param name = "p_file"> </param>
Public void saveras (string p_file)
{
Byte [] _ value = saveimageofras ();
If (_ value. length! = 0) file. writeallbytes (p_file, _ value );
}
}
}