This section describes how to read *. PSD files and provides complete functions. M_rect is the target area, m_lpdds7 is the target DirectDraw surface, and m_pbalphamask is the target aplha announcement pointer. The read16 function reads a word from the current position of the specified file, and the read32 function reads a DWORD from the current position of the specified file. Max_psd_channels is 24. The following is how to read the *. PSD file. If you are interested, you can continue to study it in depth. Don't forget to send me a copy.
Hresult loadpsd (lpstr strfilename) // read the PSD file <br/>{< br/> DWORD dwwidth, dwheight; // width and height <br/> long lsurfwidth = m_rect.right-m_rect.left; <br/> long lsurfheight = m_rect.bottom-m_rect.top; <br/> word compressiontype; // compression type <br/> HDC; <br/> file * fppsd; <br/> word channelcount; // number of channels </P> <p> // open the PSD file <br/> If (fppsd = fopen (strfilename, "rb") = NULL) {<br/> return e_fail; <br/>}</P> <P> // the first four bytes are "8bps" <br/> char signature [5]; <br/> signature [0] = fgetc (fppsd ); <br/> signature [1] = fgetc (fppsd); <br/> signature [2] = fgetc (fppsd ); <br/> signature [3] = fgetc (fppsd); <br/> signature [4] = '/0'; <br/> If (strcmp (signature, "8bps ")! = 0) {<br/> return e_fail; <br/>}</P> <p> // version must be 1 <br/> If (read16 (fppsd )! = 1) {<br/> return e_fail; <br/>}</P> <p> // skip some data (always 0) <br/> read32 (fppsd); <br/> read16 (fppsd ); </P> <p> // Number of read channels <br/> channelcount = read16 (fppsd ); </P> <p> // confirm that there is at least one channel <br/> If (channelcount <0) | (channelcount> max_psd_channels )) {<br/> return e_fail; <br/>}</P> <p> // read width and height <br/> dwheight = read32 (fppsd ); <br/> dwwidth = read32 (fppsd); <br/> If (dwwidth! = (DWORD) lsurfwidth | dwheight! = (DWORD) lsurfheight) {<br/> return e_fail; <br/>}</P> <p> // read-only 8-bit channel <br/> If (read16 (fppsd )! = 8) {<br/> return e_fail; <br/>}</P> <p> // confirm that the mode is RGB. <br/> // possible value: <br/> // 0: bitmap <br/> // 1: grayscale <br/> // 2: index <br/> // 3: RGB <br/> // 4: CMYK <br/> // 7: Multichannel <br/> // 8: duotone <br/> // 9: lab <br/> If (read16 (fppsd )! = 3) {<br/> return e_fail; <br/>}</P> <p> // skip data (such as the color palette) <br/> int modedatacount = read32 (fppsd); <br/> If (modedatacount) <br/> fseek (fppsd, modedatacount, seek_cur ); </P> <p> // skip data (for example, Pen tool paths, etc) <br/> int resourcedatacount = read32 (fppsd); <br/> If (resourcedatacount) <br/> fseek (fppsd, resourcedatacount, seek_cur); </P> <p> // retained data <br/> int reserveddatacount = read32 (fppsd ); <br/> If (Reserveddatacount) <br/> fseek (fppsd, reserveddatacount, seek_cur); </P> <p> // 0: Non-compressed <br/> // 1: RLE compression <br/> compressiontype = read16 (fppsd); <br/> If (compressiontype> 1) {<br/> return e_fail; <br/>}</P> <p> byte * psdpixels = new byte [(lsurfwidth * lsurfheight) * 4]; </P> <p> // unpack data <br/> unpackpsd (fppsd, lsurfwidth, lsurfheight, psdpixels, channelcount, compressiontype); </P> <p> fclose (FPP SD); </P> <p> // copy information <br/> bitmapinfo; <br/> zeromemory (& bitmapinfo, sizeof (bitmapinfo )); <br/> bitmapinfo. bmiheader. bisize = sizeof (bitmapinfo. bmiheader); <br/> bitmapinfo. bmiheader. biwidth = lsurfwidth; <br/> bitmapinfo. bmiheader. biheight =-lsurfheight; <br/> bitmapinfo. bmiheader. biplanes = 1; <br/> bitmapinfo. bmiheader. bibitcount = 32; </P> <p> m_lpdds7-> getdc (& HDC); </P> <p> int rc = Str Etchdibits (HDC, <br/> 0, <br/> 0, <br/> lsurfwidth, <br/> lsurfheight, <br/> 0, <br/> 0, <br/> lsurfwidth, <br/> lsurfheight, <br/> psdpixels, <br/> & bitmapinfo, <br/> dib_rgb_colors, <br/> srccopy ); </P> <p> m_lpdds7-> releasedc (HDC); </P> <p> If (rc = gdi_error) {<br/> h_array_delete (psdpixels ); </P> <p> # ifdef _ debug <br/> g_pherr-> outdebugmsg (3, h2dserr_invalid_psd); <br/> # endif <br/> return e_fail; </P> <p>} </P> <p> // whether to read the Alpha hybrid channel <br/> If (channelcount> 3) {<br/> m_pbalphamask = new byte [lsurfwidth * lsurfheight]; </P> <p> for (INT x = 0; x <lsurfwidth; X ++) <br/> for (INT y = 0; y <lsurfheight; Y ++) {<br/> m_pbalphamask [(y * lsurfwidth) + x] = <br/> psdpixels [(y * lsurfheight) + x) * 4) + 3]; <br/>}< br/> else {<br/> m_pbalphamask = NULL; <br/>}</P> <p> h_array_delete (psdpi Xels); </P> <p> return dd_ OK; <br/>}</P> <p> // unpack the PSD file <br/> void chades2dsurface: unpackpsd (File * FP, // FP is the PSD file pointer. <br/> DWORD dwwidth, // dwwidth and dwheight are width and height. <br/> DWORD dwheight, <br/> byte * pixels, // pixels indicates the target pointer for unpacking, <br/> word channelcnt, // channelcnt indicates the number of channels, and <br/> word compression) // compression bit compression type. </P> <p >{< br/> int default [4] = {0, 0, 0,255}; <br/> int CHN [4] = {2, 1, 0, 3 }; <br/> int pixelcount = dwwidth * dwheight; </P> <p> If (compression) {<br/> fseek (FP, dwheight * channelcnt * 2, seek_cur); </P> <p> for (int c = 0; C <4; C ++) {<br/> int Pn = 0; <br/> int channel = CHN [c]; </P> <p> If (Channel> = channelcnt) {<br/> for (Pn = 0; PN <pixelcount; PN ++) {<br/> pixels [(PN * 4) + channel] = default [Channel]; <br/>}< br/> else // non-compressed <br/>{< br/> int COUNT = 0; <br/> while (count <pixelcount) {<br/> int Len = fgetc (FP); <br/> If (LEN = 128) {}< br/> else if (LEN <128) // non-RLE <br/>{< br/> Len ++; <br/> count + = Len; <br/> while (LEN) {<br/> pixels [(PN * 4) + channel] = fgetc (FP); <br/> PN ++; <br/> Len --; <br/>}< br/> else if (LEN> 128) // RLE package <br/>{< br/> Len ^ = 0x0ff; <br/> Len + = 2; <br/> unsigned char val = fgetc (FP ); <br/> count + = Len; <br/> while (LEN) {<br/> pixels [(PN * 4) + channel] = val; <br/> PN ++; <br/> Len --; <br/>}< br/> else <br/> {<br/> for (int c = 0; c <4; C ++) {<br/> int channel = CHN [c]; <br/> If (Channel> channelcnt) {<br/> for (INT Pn = 0; PN <pixelcount; PN ++) {<br/> pixels [(PN * 4) + channel] = default [Channel]; <br/>}< br/> else {<br/> for (INT n = 0; n <pixelcount; N ++) {<br/> pixels [(n * 4) + channel] = fgetc (FP ); <br/>}</P> <p>