| I need a really fast line-drawing routine...

Previous | Graphics and Display | Next

Q: | I want to make a program which draw a lot of lines (for example which does some kind of 3D graphic). But, it seems that DrawLine function is not too fast for my purposes. What I can do?

A:

Yes, TIOS drawing routines are not championes in speed. Note that really fast line drawing function may be written only in ASM. But don't underestimate the power of C: even in pure C it is possible to make better (read: faster) line drawing routine than TIOS routine. As a programming exercise, I started with one trivial line drawing routine, and tried to optimize it. What I got is the routine which is in general 3-4 times faster than TIOS DrawLine routine. In some special cases, TIOS routine may be faster (for example, TIOS routine handles special cases when the line is horizontal or vertical), but in general case (slope lines) my routine is much better. Maybe (and probably) it may be speed-optimized yet; this is a challenge for you. Here is the routine (example "Draw Line"):

    // Example of a fast line-drawing routine

    #define USE_TI89              // Compile for TI-89
    #define USE_TI92PLUS          // Compile for TI-92 Plus
    #define USE_V200              // Compile for V200

    #define MIN_AMS 100           // Compile for AMS 1.00 or higher
    #define SAVE_SCREEN           // Save/Restore LCD Contents

    #include <tigcclib.h>         // Include All Header Files

    // Draws a line from (x1,y2) to (x2,y2).
    void DrawLineFast(short x1, short y1, short x2, short y2)
    {
      short x = x1, y = y1;
      short dx = abs (x2 - x1), dy = abs (y2 - y1);
      short ystep = (y1 < y2) ? 1 : -1, pystep = 30 * ystep;
      short mov = dx ? 0 : -1;
      unsigned char *ptr = (char*)LCD_MEM + 30 * y + (x >> 3);
      short mask = 1 << (~x & 7);
      if (x1 < x2)
        while (x != x2 || y != y2)
          {
            *ptr |= mask;
            if (mov < 0) y += ystep, ptr += pystep, mov += dx;
            else
              {
                mov -= dy;
                if (++x & 7) mask >>= 1;
                else ptr++, mask = 0x80;
              }
          }
      else
        while (x != x2 || y != y2)
          {
            *ptr |= mask;
            if (mov < 0) y += ystep, ptr += pystep, mov += dx;
            else
              {
                mov -= dy;
                if (x-- & 7) mask <<= 1;
                else ptr--, mask = 1;
              }
          }
    }

    // Main Function
    void _main(void)
    {
      DrawLineFast (10, 10, 60, 70);
      ngetchx ();
    }

If you need a line erasing or line inverting routine, replace `'*ptr |= mask'` with `'*ptr &= ~mask'` or `'*ptr ^= mask'` respectively.