Jump to content

Bitmap/Bresenham's line algorithm: Difference between revisions

→‎version 1: re-worked program to handle multiple-line segments.
(→‎version 1: simplified the program, eliminated the re-calculating of the min and max point values, removed the STYLE from the PRE html tag.)
(→‎version 1: re-worked program to handle multiple-line segments.)
Line 1,978:
=={{header|REXX}}==
===version 1===
This REXX version has automatic scaling (for displaying the plot) and handles multiple line segments.
<lang rexx>/*REXX program plots/draws a line(s) using the Bresenham's line algorithm.*/
@.='·' /*fill the array with middle─dots*/
parse arg x1data y1 x2 y2 . /*allow specifying line─enddata pts.point specifications*/
if x1=data='' | x1==',' then x1 data= -'(1,8) (8,16) (16,8) /*if(8,1) not specified(1, use default. */8)'
data=translate(data,,'()[]{}/,:;') /*elide chaff from data points. */
if y1=='' | y1==',' then y1 = -3 /* " " " " " */
if x2=='' | x2==',' then x2 = 6 /* " " " " " /* [↓] data pt pairs ──► !.array.*/
if y2 do points==''1 |while y2=data\=',' then y2 = 10 /*put " " " " "data points into an array. */
parse var data x y data; !.points=x y /*extract line segments.*/
if points==1 then do; minX=x; maxX=x; minY=y; maxY=y; end /*1st case*/
minX=min(minX,x); maxX=max(maxX,x); minY=min(minY,y); maxY=max(maxY,y)
end /*points*/ /* [↑] data points pairs in !. */
 
border=2 /*border=extra space around plot.*/
minX=min(x1,x2)minX-border*2; maxX=max(x1,x2)maxX+border*2 /*min,max X for the plot display.*/
minY=min(y1,y2)minY-border ; maxY=max(y1,y2)maxY+border /* " " Y " " " " */
do x=minX to maxX; @.x.0='─'; end /*draw dash from left──► right.*/
do y=minY to maxY; @.0.y='│'; end /*draw pipe from lowest──►highest*/
@.0.0='┼' /*define the plot's axis point. */
call draw_line x1, y1, x2, y2 do seg=2 to points-1; _=seg-1 /*callobtain subroutinethe and drawX,Y line. coördinates*/
call draw_line !._, !.seg /*draw (plot) a line segment. */
end /*seg*/ /* [↑] drawing the line segments*/
/* [↓] display the plot to term.*/
do y=maxY to minY by -1; _= /*display plot one line at a time*/
Line 2,002 ⟶ 2,009:
exit /*stick a fork in it, we're done.*/
/*────────────────────────────────DRAW_LINE subroutine──────────────────*/
draw_line: procedure expose @.; parse arg x, y,xf, yf; plotChar='Θ'
dx=abs(xf-x); if x<xf then dysx=abs(yf-y)+1 /*obtain X range, determine slope*/
else sx=-1
if x<xf then sx=+1
dy=abs(yf-y); if y<yf then sy=+1 /*obtain Y range, determine slope*/
else sx=-1
else sy=-1
if y<yf then sy=+1
err=dx-dy /*calc error between adjustments.*/
else sy=-1
err=dx-dy
do forever; @.x.y=plotChar /*plot the points until complete.*/
if x=xf & y=yf then leave /*are plot points at the finish? */
if 2*err2=err+err > -dy then do; err=err-dy; x=x+sx; end /*this is faster than err*2. */
if 2*errerr2 <> dx-dy then do; err=err+dx-dy; yx=yx+sysx; end
if err2 < dx then do; err=err+dx; y=y+sy; end
end /*while ··· */
return</lang>
'''output''' when using the default input:
<pre>
···│····················
···│····················
··········Θ············
·········Θ·Θ···········
········Θ···Θ··········
···│····Θ·····Θ·········
···│···Θ·······Θ········
···│···Θ········Θ·······
·····│··Θ··········Θ······
·····│·Θ············Θ·····
···│Θ···Θ···········Θ····
····Θ·│Θ···········Θ·····
···│··Θ··········Θ······
─────┼Θ─────────
···│···Θ·······ΘΘ·······
···│····Θ·····Θ·········
····Θ│····Θ···Θ··········
·········Θ·Θ···········
···│·······Θ············
───┼────────────────────
···│····················
</pre>
 
Cookies help us deliver our services. By using our services, you agree to our use of cookies.