Working with Rectangles

These three drawing functions require a pointer to a rectangle structure:

FillRect (hdc, &rect, hBrush) ;

FrameRect (hdc, &rect, hBrush) ;

InvertRect (hdc, &rect) ;

In these functions, the rect parameter is a structure of type RECT with four fields: left, top, right, and bottom. The coordinates in this structure are treated as logical coordinates.

FillRect fills the rectangle (up to but not including the right and bottom coordinate) with the specified brush. This function doesn't require that you first select the brush into the device context. We used the FillRect function in the ROP2LOOK program earlier in this chapter to color the background with five stock brushes.

FrameRect uses the brush to draw a rectangular frame, but it does not fill in the rectangle. Using a brush to draw a frame may seem a little strange, because with the functions that you've seen so far (such as Rectangle), the border is drawn with the current pen. FrameRect allows you to draw a rectangular frame that isn't necessarily a pure color. This frame is one logical unit wide. If logical units are larger than device units, then the frame will be 2 or more pixels wide.

InvertRect inverts all the pixels in the rectangle, turning ones to zeros and zeros to ones. This function turns a white area to black, a black area to white, and a green area to magenta.

Windows also includes nine functions that allow you to manipulate RECT structures easily and cleanly. For instance, to set the four fields of a RECT structure to particular values, you would conventionally use code that looks like this:

rect.left = xLeft ;

rect.top = xTop ;

rect.right = xRight ;

rect.bottom = xBottom ;

By calling the SetRect function, however, you can achieve the same result with a single line:

SetRect (&rect, xLeft, yTop, xRight, yBottom) ;

The other eight functions can also come in handy when you want to do one of the following:

Move a rectangle a number of units along the x and y axes:

OffsetRect (&rect, x, y) ;

Increase or decrease the size of a rectangle:

InflateRect (&rect, x, y) ;

Set the fields of a rectangle equal to 0:

SetRectEmpty (&rect) ;

Copy one rectangle to another:

CopyRect (&DestRect, &SrcRect) ;

Obtain the intersection of two rectangles:

IntersectRect (&DestRect, &SrcRect1, &SrcRect2) ;

Obtain the union of two rectangles:

UnionRect (&DestRect, &SrcRect1, &SrcRect2) ;

Determine if a rectangle is empty:

bEmpty = IsRectEmpty (&rect) ;

Determine if a point is in a rectangle:

bInRect = PtInRect (&rect, point) ;

In most cases, the equivalent code for these functions is simple. Sometimes, you'll find that using one of these functions actually increases the size of your .EXE file. In some instances, in fact, equivalent code even takes up less space in your source code file. For example, you can duplicate the CopyRect function call with:

DestRect = SrcRect ;