[comp.graphics] Variable-width Bresenham

neil@calvin.ksu.ksu.edu (Neil Erdwien) (10/18/89)

I'm looking for references/ideas for implementing a variable-width
version of Bresenham's algorithm for quantising line segments.

In other words, I'm not content with single-pixel lines that result
from the standard algorithm.  I'd like to be able to draw 2, 3, and
perhaps even fractional line widths.  This seems like a common problem
and I assume someone has a more elegant solution than just drawing
multiple closely spaced lines.

--
Neil Erdwien
Kansas State University
neil@ksuvm.ksu.edu  or  neil@calvin.ksu.ksu.edu

sarathy@gpu.utcs.utoronto.ca (Rajiv Sarathy) (10/18/89)

In article <4162@deimos.cis.ksu.edu> neil@calvin (Neil Erdwien) writes:
>I'm looking for references/ideas for implementing a variable-width
>version of Bresenham's algorithm for quantising line segments.
>
>In other words, I'm not content with single-pixel lines that result
>from the standard algorithm.  I'd like to be able to draw 2, 3, and
>perhaps even fractional line widths.  This seems like a common problem
>and I assume someone has a more elegant solution than just drawing
>multiple closely spaced lines.

How about the next-most obvious way?:

	In the algorithm, plot more pixels:

		If you're stepping by x, then plot as many more pixels as you
		need vertically.

		If you're stepping by y, then plot as many more pixels as you
		need horizontally.


		Example:

			For a 2-pixel-width line with horizontal stepping:

			xx
			**xxxx
			  ****xxx
			      ***

			Where '*' is drawn by Bresenham, and 'x' is drawn
			by your additional SetPixel().

		Of course, you'd need to build in some intelligence to not
		draw over viewport/window/screen boundaries.  You might also 
		want to check to make sure that your lines have even density.

-- 
 _____________________________________________________________________________
| Disclaimer:  I'm just an undergrad. All views and opinions are therefore  _ |
| 	       my own.   /\    /\    /-----------------------------------oO(_)|
|                       /  \  /  \  /     NetNorth: sarathy@utorgpu           |
| Rajiv Partha Sarathy /    \/    \/     sarathy@gpu.utcs.utoronto.ca         |
| --------------------/       {uunet!attcan mnetor att pyramid}!utgpu!sarathy |
|_____________________________________________________________________________|

ritter@versatc.VERSATEC.COM (Jack Ritter) (10/20/89)

In article <4162@deimos.cis.ksu.edu>, neil@calvin.ksu.ksu.edu (Neil Erdwien) writes:
> I'm looking for references/ideas for implementing a variable-width
> version of Bresenham's algorithm for quantising line segments.
> --
A simple solution, as already suggested by
someone, is to do the Brez. walk, and simply
replicate N pixels each step, for width N lines.
The problem is, the eye is VERY GOOD at detecting
different effective widths. Consider the following
two lines of width 3:

***             ***
 ***               ***
  ***      &         ***
   ***                  ***
	***                   ***

They will look very different to the eye.
For small N, I would recommend a table, describing
how to step, for a variety of angles & widths. A step description
should be more than just "do 3 pixels". It should be
a more complex sequence like, "do 3,4,4, [repeat]".
You'll have to experiment.

If you connect lines end to end (as in text), you
must position the lines consistently; a line
that is an EVEN number of pixels wide cannot be
exactly centered. You must chose one of the 2 possibilities
(plus, or minus, the half pixel). This scheme must
be consistent for ALL DIRECTIONS.

Note that you arent really drawing thin rectangles,
but rather thin parellograms. For large N, the eye will notice.
For these cases, you must do a Brezenham
walk of half a width from the end point, in a direction
perpendicular to the line's direction, to find the 2
corners of the rectangle. You then fracture the rectangle
into an upper triangle, a middle parellelogram, and a
bottom triangle. Each of these pieces is then drawn by doing 2
simultaneous Brez. walks down its left & right edges, and filling the
pixels in between. This is the fastest way.
  An alternative to fracturing is to walk along the end segment,
drawing N single width, parallel lines. This may cause holes to
appear. To avoid holes, draw the CORNER PIXEL whenever you
take a Brez. step.

-- 
   Versatec, Inc.
   Jack Ritter, M.S. 1-7
   2710 Walsh Ave.
   P.O. Box 58091
   Santa Clara, CA 95052-8091
   (408)982-4332, or (408)988-2800 X 5743
   UUCP:  {ames,apple,sun,pyramid}!versatc!ritter

   --( / __ - .. ((  /
   / / -- ) . \ \ // . (
	/ ** ) // _*_ // * ..
	) (( . \ / . * ) //

nelson@m.cs.uiuc.edu (10/25/89)

FYI, there was an article on a similar subject (termed variable-width
  paintbrush or somesuch) in Transactions on Computer Graphics about 3
  issues back.  Sorry I don't have the reference handy.