4.2 Icon Resources

The ICON statement in the .RC script does not create a single resource object, but creates a group of resources. This allows Windows-based programs a degree of device independence through the use of different pixel bitmaps on hardware configurations with differing capabilities. Icons, most often designed for differing numbers of pixel planes and pixel counts, are grouped and treated by Windows as a single resource. In the .RES and .EXE files, however, they are stored as a group of resources. These groups are stored in a .RES file with the components first (in this case the different icons [type 3]) and a group header following (type 14). The group header contains the information necessary to allow Windows to select the proper icon to display.

The components have the following structure:


     [Resource header (type = 3)]

     [DIB Header]
     [Color DIBits of icon XOR mask]
     [Monochrome DIBits of AND mask]

Each component is given an ordinal ID that is unique from all other icon components.

The device independent bitmap (DIB) header's fields represent the masks' information separately with two exceptions. First, the height field represents both the XOR and AND masks. Before converting the two DIBs to device dependent bitmaps (DDBs), the height should be divided by two. The masks are always the same size and are one-half the size given in the DIB header. Second, the number of bits per pixel and bit count refer to the XOR mask. The AND mask is always monochrome and should be interpreted as having one plane and one bit per pixel. Before using an icon with Windows, refer to the Software Development Kit reference materials for more information on DIBs. Because the format of an icon component closely resembles the format of the .ICO file, the documentation in section 9.2 of the Windows SDK Reference is useful. DDBs should not be used for Win32 applications.

The group header is described here:


     [Resource header (type = 14)]

struct IconHeader {
     WORD     wReserved;     // Currently zero
     WORD     wType;         // 1 for icons
     WORD     wCount;       // Number of components
     WORD     padding;      // Filler for DWORD alignment
     };

The next portion is repeated for each component resource:


struct ResourceDirectory {
     BYTE     bWidth;
     BYTE     bHeight;
     BYTE     bColorCount;
     BYTE     bReserved;
     WORD     wPlanes;
     WORD     wBitCount;
     DWORD    lBytesInRes;
     WORD     wNameOrdinal;     // Points to component
     WORD     padding;          // Filler for DWORD alignment
     };

Notice that the group header consists of a fixed header and data that repeats for each group component. Both of these parts are fixed length allowing for random access of the group component information.

This group header contains all of the data from the .ICO header and from the individual resource descriptors.