Topic : The VGA Training Program
Author : Grant Smith
Page : << Previous 6  Next >>
Go to page :


      putpixel (x,y1,col);
    exit;
  END;
  if (dx=0) then BEGIN
    if dy<0 then for y:=y1 to y2 do
      putpixel (x1,y,col);
    if dy>0 then for y:=y2 to y1 do
      putpixel (x1,y,col);
    exit;
  END;
  xslope:=xlength/ylength;
  yslope:=ylength/xlength;
  if (yslope/xslope<1) and (yslope/xslope>-1) then BEGIN
    if dx<0 then for x:=x1 to x2 do BEGIN
                   y:= round (yslope*x);
                   putpixel (x,y,col);
                 END;
    if dx>0 then for x:=x2 to x1 do BEGIN
                   y:= round (yslope*x);
                   putpixel (x,y,col);
                 END;
  END
  ELSE
  BEGIN
    if dy<0 then for y:=y1 to y2 do BEGIN
                   x:= round (xslope*y);
                   putpixel (x,y,col);
                 END;
    if dy>0 then for y:=y2 to y1 do BEGIN
                   x:= round (xslope*y);
                   putpixel (x,y,col);
                 END;
  END;
END;

[C++]

void Line2(int x1, int y1, int x2, int y2, int col) {

  int   x, y, xlength, ylength, dx, dy;
  float xslope, yslope;

  xlength = abs(x1-x2);
  if ((x1-x2)  < 0) dx = -1;
  if ((x1-x2) == 0) dx =  0;
  if ((x1-x2)  > 0) dx = +1;

  ylength = abs(y1-y2);
  if ((y1-y2)  < 0) dy = -1;
  if ((y1-y2) == 0) dy =  0;
  if ((y1-y2)  > 0) dy = +1;

  if (dy == 0) {
    if (dx < 0)
      for (x=x1; x<x2+1; x++)
Putpixel (x,y1,col);
    if (dx > 0)
      for (x=x2; x<x1+1; x++)
Putpixel (x,y1,col);
  }

  if (dx == 0) {
    if (dy < 0)
      for (y=y1; y<y2+1; y++)
Putpixel (x1,y,col);
    if (dy > 0)
      for (y=y2; y<y1+1; y++)
Putpixel (x1,y,col);
  }

  if ((xlength != 0) && (ylength != 0)) {
    xslope = (float)xlength/(float)ylength;
    yslope = (float)ylength/(float)xlength;
  }
  else {
    xslope = 0.0;
    yslope = 0.0;
  }

  if ((xslope != 0) && (yslope != 0) &&
      (yslope/xslope < 1) && (yslope/xslope > -1)) {
    if (dx < 0)
      for (x=x1; x<x2+1; x++) {
y = round (yslope*x);
Putpixel (x,y,col);
      }
    if (dx > 0)
      for (x=x2; x<x1+1; x++) {
y = round (yslope*x);
Putpixel (x,y,col);
      }
  }
  else {
    if (dy < 0)
      for (y=x1; y<x2+1; y++) {
x = round (xslope*y);
Putpixel (x,y,col);
      }
    if (dy > 0)
      for (y=x2; y<x1+1; y++) {
x = round (xslope*y);
Putpixel (x,y,col);
      }
  }

}

Quite big, isn't it? Here is a much shorter way of doing much the same
thing :

[Pascal]

function sgn(a:real):integer;
begin
     if a>0 then sgn:=+1;
     if a<0 then sgn:=-1;
     if a=0 then sgn:=0;
end;

procedure line(a,b,c,d,col:integer);
var u,s,v,d1x,d1y,d2x,d2y,m,n:real;
    i:integer;
begin
     u:= c - a;
     v:= d - b;
     d1x:= SGN(u);
     d1y:= SGN(v);
     d2x:= SGN(u);
     d2y:= 0;
     m:= ABS(u);
     n := ABS(v);
     IF NOT (M>N) then
     BEGIN
          d2x := 0 ;
          d2y := SGN(v);
          m := ABS(v);
          n := ABS(u);
     END;
     s := INT(m / 2);
     FOR i := 0 TO round(m) DO
     BEGIN
          putpixel(a,b,col);
          s := s + n;
          IF not (s<m) THEN
          BEGIN
               s := s - m;
               a:= a +round(d1x);
               b := b + round(d1y);
          END
          ELSE
          BEGIN
               a := a + round(d2x);
               b := b + round(d2y);
          END;
     end;
END;

[C++]

int sgn (long a) {
  if (a > 0) return +1;
  else if (a < 0) return -1;
  else return 0;

}

void Line(int a, int b, int c, int d, int col) {

  long u,s,v,d1x,d1y,d2x,d2y,m,n;
  int  i;

  u   = c-a;
  v   = d-b;
  d1x = sgn(u);
  d1y = sgn(v);
  d2x = sgn(u);
  d2y = 0;
  m   = abs(u);
  n   = abs(v);

  if (m<=n) {
    d2x = 0;
    d2y = sgn(v);
    m   = abs(v);
    n   = abs(u);
  }

  s = (int)(m / 2);

  for (i=0;i<round(m);i++) {
    Putpixel(a,b,col);
    s += n;
    if (s >= m) {
      s -= m;
      a += d1x;
      b += d1y;
    }
    else {
      a += d2x;
      b += d2y;
    }
  }

}


This routine is very fast, and should meet almost all of your requirements
(ASPHYXIA used it for quite a while before we made our new one.)
In the end program, both the new line routine and the circle routine are
tested. A few of the procedures of the first parts are also used.

Line and circle routines may seem like fairly trivial things, but they are
a vital component of many programs, and you may like to look up other
methods of drawing them in books in the library (I know that here at the
varsity they have books for doing this kind of stuff all over the place)
A good line routine to look out for is the Bressenhams line routine ...
there is a Bressenhams circle routine too ... I have documentaiton for them
if anybody is interested, they are by far some of the fastest routines
you will use.



  In closing

Varsity has started again, so I am (shock) going to bed before three in
the morning, so my quote this week wasn't written in the same wasted way
my last weeks one was (For last week's one, I had gotten 8 hours sleep in
3 days, and thought up and wrote the quote at 2:23 am before I fell asleep.)

        [  "What does it do?" she asks.


Page : << Previous 6  Next >>