abrash-black-book/42-01.md
2013-12-30 20:26:41 +11:00

119 lines
6.5 KiB
Markdown
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

Chapter 42\
Wu'ed in Haste; Fried, Stewed at Leisure {#Heading1}
-----------------------------------------
### Fast Antialiased Lines Using Wu's Algorithm {#Heading2}
The thought first popped into my head as I unenthusiastically picked
through the salad bar at a local "family" restaurant, trying to decide
whether the meatballs, the fried clams, or the lasagna was likely to
shorten my life the least. I decided on the chicken in mystery sauce.
The thought recurred when my daughter asked, "Dad, is that fried
chicken?"
"I don't think so," I said. "I think it's stewed chicken."
"It looks like fried chicken."
"Maybe it's fried, stewed chicken," my wife volunteered hopefully. I
took a bite. It was, indeed, fried, stewed chicken. I can now,
unhesitatingly and without reservation, recommend that you avoid fried,
stewed chicken at all costs.
The thought I had was as follows: *This is not good food*. Not a
profound thought, but it raises an interesting question: Why was I
eating in this restaurant? The answer, to borrow a phrase from E.F.
Schumacher, is *appropriate technology*. For a family on a budget, with
a small child, tired of staring at each other over the kitchen table,
this was a perfect place to eat. It was cheap, it had greasy food and
ice cream, no one cared if children dropped things or talked loudly or
walked around, and, most important of all, it wasn't home. So what if
the food was lousy? Good food was a luxury, a bonus; everything on the
above list was necessary. A family restaurant was the appropriate
dining-out technology, given the parameters within which we had to work.
When I read through SIGGRAPH proceedings and other state-of-the-art
computer-graphics material, all too often I feel like I'm dining at a
four-star restaurant with two-year-old triplets and an empty wallet.
We're talking incredibly inappropriate technology for PC graphics here.
Sure, I say to myself as I read about an antialiasing technique, that
sounds wonderful—if I had 24-bpp color, and dedicated hardware to do the
processing, and all day to wait to generate one image. Yes, I think,
that is a good way to do hidden surface removal—in a system with
hardware z-buffering. Most of the stuff in the journal *Computer
Graphics* is riveting, but, alas, pretty much useless on PCs. When an
x86 has to do all the work, speed becomes the overriding parameter,
especially for real-time graphics.
Literature that's applicable to fast PC graphics is hard enough to find,
but what we'd really like is above-average image quality combined with
terrific speed, and there's almost no literature of that sort around.
There is some, however, and you folks are right on top of it. For
example, alert reader Michael Chaplin, of San Diego, wrote to suggest
that I might enjoy the line-antialiasing algorithm presented in Xiaolin
Wu's article, "An Efficient Antialiasing Technique," in the July 1991
issue of *Computer Graphics*. Michael was dead-on right. This is a great
algorithm, combining excellent antialiased line quality with speed
that's close to that of non-antialiased Bresenham's line drawing. This
is the sort of algorithm that makes you want to go out and write a
wire-frame animation program, just so you can see how good those smooth
lines look in motion. Wu antialiasing is a wonderful example of what can
be accomplished on inexpensive, mass-market hardware with the proper
programming perspective. In short, it's a splendid example of
appropriate technology for PCs.
### Wu Antialiasing {#Heading3}
Antialiasing, as we've been discussing for the past few chapters, is the
process of smoothing lines and edges so that they appear less jagged.
Antialiasing is partly an aesthetic issue, because it makes images more
attractive. It's also partly an accuracy issue, because it makes it
possible to position and draw images with effectively more precision
than the resolution of the display. Finally, it's partly a flat-out
necessity, to avoid the horrible, crawling, jagged edges of temporal
aliasing when performing animation.
The basic premise of Wu antialiasing is almost ridiculously simple: As
the algorithm steps one pixel unit at a time along the major (longer)
axis of a line, it draws the two pixels bracketing the line along the
minor axis at each point. Each of the two bracketing pixels is drawn
with a weighted fraction of the full intensity of the drawing color,
with the weighting for each pixel equal to one minus the pixel's
distance along the minor axis from the ideal line. Yes, it's a mouthful,
but Figure 42.1 illustrates the concept.
The intensities of the two pixels that bracket the line are selected so
that they always sum to exactly 1; that is, to the intensity of one
fully illuminated pixel of the drawing color. The presence of aggregate
full-pixel intensity means that at each step, the line has the same
brightness it would have if a single pixel were drawn at precisely the
correct location. Moreover, thanks to the distribution of the intensity
weighting, that brightness is centered at the ideal line. Not
coincidentally, a line drawn with pixel pairs of aggregate single-pixel
intensity, centered on the ideal line, is perceived by the eye not as a
jagged collection of pixel pairs, but as a smooth line centered on the
ideal line. Thus, by weighting the bracketing pixels properly at each
step, we can readily produce what looks like a smooth line at precisely
the right location, rather than the jagged pattern of line segments that
non-antialiased line-drawing algorithms such as Bresenham's (see
Chapters 35, 36, and 37) trace out.
![](images/42-01.jpg)\
**Figure 42.1**  *The basic concept of Wu antialiasing.*
You might expect that the implementation of Wu antialiasing would fall
into two distinct areas: tracing out the line (that is, finding the
appropriate pixel pairs to draw) and calculating the appropriate
weightings for each pixel pair. Not so, however. The weighting
calculations involve only a few shifts, XORs, and adds; for all
practical purposes, tracing and weighting are rolled into one step—and a
very fast step it is. How fast is it? On a 33-MHz 486 with a fast VGA, a
good but not maxed-out assembly implementation of Wu antialiasing draws
a more than respectable 5,000 150-pixel-long vectors per second. That's
especially impressive considering that about 1,500,000 actual pixels are
drawn per second, meaning that Wu antialiasing is drawing at around 50
percent of the maximum memory bandwidth—half the fastest theoretically
possible drawing speed—of an AT-bus VGA. In short, Wu antialiasing is
about as fast an antialiased line approach as you could ever hope to
find for the VGA.