Confusion about line drawing code - "Strange" use of floating-point type.

Hello. I was following a tutorial about how to draw a line https://joshbeam.com/articles/simple_line_drawing/. I want to understand it as best I can, but I have a question:

Why are x1, y1, x2, and y2 passed as floats? I don't understand this because this: Suppose I were to pass 1.5 as x1. I don't understand. I'm sure it's not going to go right 1.5 pixels and color half the pixel... Is there something simple that I am missing, or is it advanced?

I hope that I have made my question clear enough, if not, please ask for clarification.
Last edited on
It has to do with when the truncation occurs. SetPixel takes in integer arguments, so the truncation is done here. The end-result pixel coordinate is always a pair of ints. But the truncation only takes place at the very end of all intermediate calculations.

You can see slight differences if you change the arguments to become ints.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
// Example program
#include <iostream>
#include <cmath>

void
SetPixel(unsigned int x, unsigned int y)
{
    std::cout << "SetPixel(" << x << ", " << y << ")\n";
}


// https://github.com/joshb/linedrawing/blob/master/Rasterizer.cpp
void
DrawLine_float(float x1, float y1,
               float x2, float y2)
{
	float xdiff = (x2 - x1);
	float ydiff = (y2 - y1);

	// degenerate case; same points
	if (xdiff == 0.0f && ydiff == 0.0f) {
		SetPixel(x1, y1);
		return;
	}

	if (fabs(xdiff) > fabs(ydiff)) {
		float xmin, xmax;

		// set xmin to the lower x value given
		// and xmax to the higher value
		if (x1 < x2) {
			xmin = x1;
			xmax = x2;
		} else {
			xmin = x2;
			xmax = x1;
		}

		// draw line in terms of y slope
		float slope = ydiff / xdiff;
		for(float x = xmin; x <= xmax; x += 1.0f) {
			float y = y1 + ((x - x1) * slope);
			SetPixel(x, y);
		}
	} else {
		float ymin, ymax;

		// set ymin to the lower y value given
		// and ymax to the higher value
		if(y1 < y2) {
			ymin = y1;
			ymax = y2;
		} else {
			ymin = y2;
			ymax = y1;
		}

		// draw line in terms of x slope
		float slope = xdiff / ydiff;
		for(float y = ymin; y <= ymax; y += 1.0f) {
			float x = x1 + ((y - y1) * slope);
			SetPixel(x, y);
		}
	}
}

void
DrawLine_int(int x1, int y1,
             int x2, int y2)
{
    DrawLine_float(x1, y1, x2, y2);   
}

int main()
{
    float x0 = 1.0f;
    float y0 = 9.0f;
    
    float x1 = 32.5f;
    float y1 = 1.5f;
    
                
    DrawLine_float(x0, y0, x1, y1);
    std::cout << '\n';
    DrawLine_int(x0, y0, x1, y1);
}


...
SetPixel(22, 4)
SetPixel(23, 3)
SetPixel(24, 3)
SetPixel(25, 3)
SetPixel(26, 3)
SetPixel(27, 2)
SetPixel(28, 2)
SetPixel(29, 2)
SetPixel(30, 2)
SetPixel(31, 1)
SetPixel(32, 1)



...
SetPixel(22, 3)
SetPixel(23, 3)
SetPixel(24, 3)
SetPixel(25, 2)
SetPixel(26, 2)
SetPixel(27, 2)
SetPixel(28, 2)
SetPixel(29, 1)
SetPixel(30, 1)
SetPixel(31, 1)
SetPixel(32, 1)


Significant enough to matter? You be the judge.
Last edited on
Alright. So, for instance, x1 + ((y - y1) * slope) will have a different output? I think I have it now. Thank you!
Topic archived. No new replies allowed.