Xiaolin Wu's line algorithm: Difference between revisions
Content added Content deleted
(→{{header|Python}}: Fixed a bug related to endpoint drawing. Removed list concatenation to allow e.g. numpy arrays as inputs.) |
Thundergnat (talk | contribs) (Rename Perl 6 -> Raku, alphabetize, minor clean-up) |
||
Line 651: | Line 651: | ||
</lang> |
</lang> |
||
=={{header|AutoHotkey}}== |
=={{header|AutoHotkey}}== |
||
{{libheader|GDIP}} |
{{libheader|GDIP}} |
||
Line 1,235: | Line 1,236: | ||
im2.savePPM6("xiaolin_lines2.ppm"); |
im2.savePPM6("xiaolin_lines2.ppm"); |
||
}</lang> |
}</lang> |
||
=={{header|FreeBASIC}}== |
=={{header|FreeBASIC}}== |
||
This implementation follows the pseudocode given on Wikipedia. |
This implementation follows the pseudocode given on Wikipedia. |
||
Line 2,304: | Line 2,306: | ||
plot 9 1 0.1 |
plot 9 1 0.1 |
||
plot 9 2 0.9</pre> |
plot 9 2 0.9</pre> |
||
=={{header|Perl 6}}== |
|||
<lang perl6>sub plot(\x, \y, \c) { say "plot {x} {y} {c}" } |
|||
sub fpart(\x) { x - floor(x) } |
|||
sub draw-line(@a is copy, @b is copy) { |
|||
my Bool \steep = abs(@b[1] - @a[1]) > abs(@b[0] - @a[0]); |
|||
my $plot = &OUTER::plot; |
|||
if steep { |
|||
$plot = -> $y, $x, $c { plot($x, $y, $c) } |
|||
@a.=reverse; |
|||
@b.=reverse; |
|||
} |
|||
if @a[0] > @b[0] { my @t = @a; @a = @b; @b = @t } |
|||
my (\x0,\y0) = @a; |
|||
my (\x1,\y1) = @b; |
|||
my \dx = x1 - x0; |
|||
my \dy = y1 - y0; |
|||
my \gradient = dy / dx; |
|||
# handle first endpoint |
|||
my \x-end1 = round(x0); |
|||
my \y-end1 = y0 + gradient * (x-end1 - x0); |
|||
my \x-gap1 = 1 - round(x0 + 0.5); |
|||
my \x-pxl1 = x-end1; # this will be used in the main loop |
|||
my \y-pxl1 = floor(y-end1); |
|||
my \c1 = fpart(y-end1) * x-gap1; |
|||
$plot(x-pxl1, y-pxl1 , 1 - c1) unless c1 == 1; |
|||
$plot(x-pxl1, y-pxl1 + 1, c1 ) unless c1 == 0; |
|||
# handle second endpoint |
|||
my \x-end2 = round(x1); |
|||
my \y-end2 = y1 + gradient * (x-end2 - x1); |
|||
my \x-gap2 = fpart(x1 + 0.5); |
|||
my \x-pxl2 = x-end2; # this will be used in the main loop |
|||
my \y-pxl2 = floor(y-end2); |
|||
my \c2 = fpart(y-end2) * x-gap2; |
|||
my \intery = y-end1 + gradient; |
|||
# main loop |
|||
for (x-pxl1 + 1 .. x-pxl2 - 1) |
|||
Z |
|||
(intery, intery + gradient ... *) |
|||
-> (\x,\y) { |
|||
my \c = fpart(y); |
|||
$plot(x, floor(y) , 1 - c) unless c == 1; |
|||
$plot(x, floor(y) + 1, c ) unless c == 0; |
|||
} |
|||
$plot(x-pxl2, y-pxl2 , 1 - c2) unless c2 == 1; |
|||
$plot(x-pxl2, y-pxl2 + 1, c2 ) unless c2 == 0; |
|||
} |
|||
draw-line [0,1], [10,2];</lang> |
|||
{{out}} |
|||
<pre>plot 0 1 1 |
|||
plot 1 1 0.9 |
|||
plot 1 2 0.1 |
|||
plot 2 1 0.8 |
|||
plot 2 2 0.2 |
|||
plot 3 1 0.7 |
|||
plot 3 2 0.3 |
|||
plot 4 1 0.6 |
|||
plot 4 2 0.4 |
|||
plot 5 1 0.5 |
|||
plot 5 2 0.5 |
|||
plot 6 1 0.4 |
|||
plot 6 2 0.6 |
|||
plot 7 1 0.3 |
|||
plot 7 2 0.7 |
|||
plot 8 1 0.2 |
|||
plot 8 2 0.8 |
|||
plot 9 1 0.1 |
|||
plot 9 2 0.9 |
|||
plot 10 2 1</pre> |
|||
=={{header|Phix}}== |
=={{header|Phix}}== |
||
Line 2,817: | Line 2,735: | ||
[[Image:xiaolin-wu-racket-2.png]] |
[[Image:xiaolin-wu-racket-2.png]] |
||
=={{header|Raku}}== |
|||
(formerly Perl 6) |
|||
<lang perl6>sub plot(\x, \y, \c) { say "plot {x} {y} {c}" } |
|||
sub fpart(\x) { x - floor(x) } |
|||
sub draw-line(@a is copy, @b is copy) { |
|||
my Bool \steep = abs(@b[1] - @a[1]) > abs(@b[0] - @a[0]); |
|||
my $plot = &OUTER::plot; |
|||
if steep { |
|||
$plot = -> $y, $x, $c { plot($x, $y, $c) } |
|||
@a.=reverse; |
|||
@b.=reverse; |
|||
} |
|||
if @a[0] > @b[0] { my @t = @a; @a = @b; @b = @t } |
|||
my (\x0,\y0) = @a; |
|||
my (\x1,\y1) = @b; |
|||
my \dx = x1 - x0; |
|||
my \dy = y1 - y0; |
|||
my \gradient = dy / dx; |
|||
# handle first endpoint |
|||
my \x-end1 = round(x0); |
|||
my \y-end1 = y0 + gradient * (x-end1 - x0); |
|||
my \x-gap1 = 1 - round(x0 + 0.5); |
|||
my \x-pxl1 = x-end1; # this will be used in the main loop |
|||
my \y-pxl1 = floor(y-end1); |
|||
my \c1 = fpart(y-end1) * x-gap1; |
|||
$plot(x-pxl1, y-pxl1 , 1 - c1) unless c1 == 1; |
|||
$plot(x-pxl1, y-pxl1 + 1, c1 ) unless c1 == 0; |
|||
# handle second endpoint |
|||
my \x-end2 = round(x1); |
|||
my \y-end2 = y1 + gradient * (x-end2 - x1); |
|||
my \x-gap2 = fpart(x1 + 0.5); |
|||
my \x-pxl2 = x-end2; # this will be used in the main loop |
|||
my \y-pxl2 = floor(y-end2); |
|||
my \c2 = fpart(y-end2) * x-gap2; |
|||
my \intery = y-end1 + gradient; |
|||
# main loop |
|||
for (x-pxl1 + 1 .. x-pxl2 - 1) |
|||
Z |
|||
(intery, intery + gradient ... *) |
|||
-> (\x,\y) { |
|||
my \c = fpart(y); |
|||
$plot(x, floor(y) , 1 - c) unless c == 1; |
|||
$plot(x, floor(y) + 1, c ) unless c == 0; |
|||
} |
|||
$plot(x-pxl2, y-pxl2 , 1 - c2) unless c2 == 1; |
|||
$plot(x-pxl2, y-pxl2 + 1, c2 ) unless c2 == 0; |
|||
} |
|||
draw-line [0,1], [10,2];</lang> |
|||
{{out}} |
|||
<pre>plot 0 1 1 |
|||
plot 1 1 0.9 |
|||
plot 1 2 0.1 |
|||
plot 2 1 0.8 |
|||
plot 2 2 0.2 |
|||
plot 3 1 0.7 |
|||
plot 3 2 0.3 |
|||
plot 4 1 0.6 |
|||
plot 4 2 0.4 |
|||
plot 5 1 0.5 |
|||
plot 5 2 0.5 |
|||
plot 6 1 0.4 |
|||
plot 6 2 0.6 |
|||
plot 7 1 0.3 |
|||
plot 7 2 0.7 |
|||
plot 8 1 0.2 |
|||
plot 8 2 0.8 |
|||
plot 9 1 0.1 |
|||
plot 9 2 0.9 |
|||
plot 10 2 1</pre> |
|||
=={{header|REXX}}== |
=={{header|REXX}}== |
||
Line 2,981: | Line 2,982: | ||
end |
end |
||
bitmap.draw_line_antialised(Pixel[10, 10], Pixel[490,490], RGBColour::YELLOW)</lang> |
bitmap.draw_line_antialised(Pixel[10, 10], Pixel[490,490], RGBColour::YELLOW)</lang> |
||
=={{header|Scala}}== |
=={{header|Scala}}== |
||
Uses [[Bitmap#Scala]]. |
Uses [[Bitmap#Scala]]. |