现在的位置: 首页 > 综合 > 正文

2008 November 25th Tuesday (十一月 二十五日 火曜日)

2013年11月07日 ⁄ 综合 ⁄ 共 7635字 ⁄ 字号 评论关闭
   I am going to implement a simply script language.  I am going to get some inspiration from lua.  However, the scripte will be
easier than lua.  The project will be start to launch at the begin of tomorrow year.

  Maybe the language style is not same as any other language.

DIB

  A DIB file has four main sections:

* A file header

* An information header

* An RGB color table (but not always)

The bitmap pixel bits

  You can think of the first two parts as C data structures and the third part as an array of data structures. These structures are
documented in the Windows header file WINGDI.H. A memory-based DIB in the packed-DIB format has three sections:

* An information header

* An RGB color table (but not always)

The bitmap pixel bits

It's exactly the same as a DIB stored in a file except that it doesn't have the file header.

The DIB file, but not the memory-based packed DIB, begins with a 14-byte file header defined as a structure like so:

typedef struct tagBITMAPFILEHEADER  // bmfh
{
     WORD  bfType ;        // signature word "BM" or 0x4D42
     DWORD bfSize ;        // entire size of file
     WORD  bfReserved1 ;   // must be zero
     WORD  bfReserved2 ;   // must be zero
     DWORD bfOffsetBits ;  // offset in file of DIB pixel bits
}
BITMAPFILEHEADER, * PBITMAPFILEHEADER ;

This may not be exactly the way the structure is defined in WINGDI.H (for example, the comments are mine), but it is
functionally the same. The first comment (that is, the text "bmfh") shows the recommended abbreviation when naming
a structure variable of this data type. If you see a variable in one of my programs named pbmfh, that will be a pointer
to a structure of type BITMAPFILEHEADER or a variable of type PBITMAPFILEHEADER.

The structure is 14 bytes in length. It begins with the two letters "BM" to indicate a bitmap file. This is the WORD
value 0x4D42. The "BM" indicator is followed by a DWORD indicating the entire size of the file, including the file header,
in bytes. The next two WORD fields are set to zero. (In a mouse cursor file, which is similar in format to a DIB file,
these two fields are used to indicate the "hot spot" of the cursor.) The structure concludes with a DWORD indicating
the byte offset within the file where the pixel bits begin. This number can be derived from information in the DIB
information header, but it is provided here for convenience.

In the OS/2-style DIB, the BITMAPFILEHEADER structure is followed immediately by a BITMAPCOREHEADER structure, which
provides the basic information about the DIB image. A packed DIB begins with the BITMAPCOREHEADER:

typedef struct tagBITMAPCOREHEADER  // bmch
{
     DWORD bcSize ;      // size of the structure = 12
     WORD  bcWidth ;     // width of image in pixels
     WORD  bcHeight ;    // height of image in pixels
     WORD  bcPlanes ;    // = 1
     WORD  bcBitCount ;  // bits per pixel (1, 4, 8, or 24)
}
BITMAPCOREHEADER, * PBITMAPCOREHEADER ;

The word "core" sounds a little odd in this context, and it is. It means that this format is the basis (thus the core)
of other bitmap formats derived from it.

The bcSize field in the BITMAPCOREHEADER structure indicates the size of the data structure, in this case 12 bytes.

The bcWidth and bcHeight fields contain the size of the bitmap in pixels. Although the use of a WORD for these fields
implies that a DIB may be 65,535 pixels high and wide, you'll rarely encounter anything quite that large.

The bcPlanes field is always 1. Always, always, always-from the time it was defined until this very second. The field
is a remnant of the earlier Windows GDI bitmap object that we encountered in the last chapter.

The bcBitCount field indicates the number of bits per pixel. For OS/2-style DIBs, this can be either 1, 4, 8, or 24.
The number of colors in the DIB image is equal to 2bmch.bcBitCount or, in C syntax, to

1 << bmch.bcBitCount

Thus, the bcBitCount field is equal to:

1 for a 2-color DIB

4 for a 16-color DIB

8 for a 256-color DIB

24 for a full-color DIB
When I refer to "an 8-bit DIB," I'll mean a DIB that has 8 bits per pixel.

For the first three cases (that is, for bit counts of 1, 4, and 8), the BITMAPCOREHEADER is followed by the color table.
The color table does not exist for 24-bit DIBs. The color table is an array of 3-byte RGBTRIPLE structures, one for each
color in the image:

typedef struct tagRGBTRIPLE  // rgbt
{
     BYTE rgbtBlue ;   // blue level
     BYTE rgbtGreen ;  // green level
     BYTE rgbtRed ;    // red level
}
RGBTRIPLE ;

It is recommended that the color table be arranged so that the most important colors in the DIB appear first. We'll see
why in the next chapter.

The WINGDI.H header file also defines the following structure:

typedef struct tagBITMAPCOREINFO  // bmci
{
     BITMAPCOREHEADER bmciHeader ;     // core-header structure
     RGBTRIPLE        bmciColors[1] ;  // color table array
}
BITMAPCOREINFO, * PBITMAPCOREINFO ;

This structure combines the information header with the color table. Although the number of RGBTRIPLE structures is seemingly
equal to 1 in this structure, you'll never find just one RGBTRIPLE in a DIB file. The size of the color table is always 2, 16,
or 256 RGBTRIPLE structures, depending on the number of bits per pixel. If you need to allocate a structure of PBITMAPCOREINFO
for an 8-bit DIB, you can do it like so:

pbmci = malloc (sizeof (BITMAPCOREINFO) + 255 * sizeof (RGBTRIPLE)) ;

Then you can access whatever RGBTRIPLE structure you need like so:

pbmci->bmciColors[i]

Because the RGBTRIPLE structure is 3 bytes in length, some of the RGBTRIPLE structures might begin at odd addresses within the DIB.
However, because there are always an even number of RGBTRIPLE structures in the DIB file, the data block that follows the color table
array always begins at a WORD address boundary.

The data that follow the color table (and what follows the information header for DIBs with a bit count of 24) are the pixel bits
themselves.

Bottoms Up!

  Well, it all goes back to the OS/2 Presentation Manager. Someone at IBM decided that all coordinate systems in PM-including those
for windows, graphics, and bitmaps-should be consistent. This provoked a debate: Most people, including programmers who have worked
with full-screen text programming or windowing environments, think in terms of vertical coordinates that increase going down the screen.
However, hardcore computer graphics programmers approach the video display from a perspective that originates in the mathematics of
analytic geometry. This involves a rectangular (or Cartesian) coordinate system where increasing vertical coordinates go up in space.

  In short, the mathematicians won. Everything in PM was saddled with a bottom-left origin, including window coordinates. And that's
how DIBs came to be this way.

The DIB Pixel Bits

  The last section of the DIB file-in most cases the great bulk of the DIB file-consists of the actual DIB pixel bits. The pixel bits
are organized in horizontal rows beginning with the bottom row of the image and proceeding up through the image.

The number of rows in a DIB is equal to the bcHeight field of the BITMAPCOREHEADER structure. Each row encodes a number of pixels equal
to the bcWidth field of the structure. Each row begins with the leftmost pixels and proceeds to the right of the image. The number of
bits per pixel is obtained from the bcBitCount field, which is either 1, 4, 8, or 24.

The length of each row in bytes is always a multiple of 4. The row length can be calculated like so:

RowLength = 4 * ((bmch.bcWidth * bmch.bcBitCount + 31) / 32) ;

Or, slightly more efficiently in C, like this:

RowLength = ((bmch.bcWidth * bmch.bcBitCount + 31) & ~31) >> 3 ;

The row is padded at the right (customarily with zeros), if necessary, to achieve this length. The total number of bytes of pixel data
is equal to the product of RowLength and bmch.bcHeight.

To see how the pixels are encoded, let's examine the four cases separately. In the diagrams shown below, the bits of each byte are shown
in boxes and are numbered with 7 indicating the most-significant bit and 0 indicating the least-significant bit. Pixels are also numbered
beginning with 0 for the leftmost pixel in the row.

For DIBs with 1 bit per pixel, each byte corresponds to 8 pixels. The leftmost pixel is the most-significant bit of the first byte:

Each pixel can be either a 0 or a 1. A 0 bit means that the color of that pixel is given by the first RGBTRIPLE entry in the color table.
A 1 bit is a pixel whose color is the second entry of the color table.

For DIBs with 4 bits per pixel, each byte corresponds to 2 pixels. The leftmost pixel is the high 4 bits of the first byte, and so on:

The value of each 4-bit pixel ranges from 0 to 15. This value is an index into the 16 entries in the color table.

For a DIB with 8 bits per pixel, each byte is 1 pixel:

The value of the byte is 0 through 255. Again, this is an index into the 256 entries in the color table.

For DIBs with 24 bits-per-pixel, each pixel requires 3 bytes for the red, green, and blue color values. Each row of pixel bits is basically
an array of RGBTRIPLE structures, possibly padded with 0 bytes at the end of each row so that the row has a multiple of 4 bytes:

Again, the 24-bit-per-pixel DIB has no color table.

抱歉!评论已关闭.