The Boston Diaries

The ongoing saga of a programmer who doesn't live in Boston, nor does he even like Boston, but yet named his weblog/journal “The Boston Diaries.”

Go figure.

Saturday, April 02, 2005

All that for something barely anyone saw

One of the problems of providing an RSS feed is that most of my readers read it and not the site here, thus the format change I did for April 1st was lost, along with most of my AdSense revenue (one of the few things I can report about is my gross earnings from Google, which to the nearest cent is $0.00)—I suppose I may get more revenue if I inline the ads, such as:

But I don't really want to do that (nor add ads to my RSS feed, so don't worry—well, except possibly for this entry but that depends on if your RSS agregator filters out the <SCRIPT> tag (it'll be interesting to see).

Anyway …

Last year's April Fools theme was greenbar printer paper, where (through the wonders of CSS) it appeared as if this was being printed out (in all caps no less) and it took me quite a while to find an appropriate image of greenbar paper for the background. This years idea was to do an old fasion monochrome monitor (green on black) with a slight resync problem (you can see a bright green line of the electron gun being swept across the screen). A bit easier to munge up than last year's imagry and one I could make myself.

At first I tried a paint program, but it was a rather primitive paint program and I had problems trying to do the 2048x100 image (2048 pixels wide to make sure it was wide enough not to repeat for anyone). Too many problems using the program, leading it to taking way too long.

It was then I remembered I had the GD library installed.

Trivial!

How trivial?

#include <stdio.h>
#include <stdlib.h>
#include "gd.h"

int main(void)
{
  FILE       *fpout;
  gdImagePtr  imout;
  int         background;
  int         line[3];

  imout = gdImageCreate(2048,100);

  background = gdImageColorAllocate(imout,16, 32,16);
  line[0]    = gdImageColorAllocate(imout,16, 64,16);
  line[1]    = gdImageColorAllocate(imout,16, 96,16);
  line[2]    = gdImageColorAllocate(imout,16,128,16);

  gdImageLine(imout,0,13,2047,23,line[0]);
  gdImageLine(imout,0,14,2047,24,line[1]);
  gdImageLine(imout,0,15,2047,25,line[2]);
  gdImageLine(imout,0,16,2047,26,line[1]);
  gdImageLine(imout,0,17,2047,27,line[0]);

  fpout = fopen("vidline.png","wb");
  gdImagePng(imout,fpout);
  fclose(fpout);
  gdImageDestroy(imout);
  return(EXIT_SUCCESS);
}

A crude attempt at anti-aliasing a beam across the page. Very poor results no matter how I did it. It was then I remembered my Foley-van Dam book (Computer Graphics: Principles and Practice by Foley, van Dam, Feiner and Hughes, 2nd Edition)—surely it must have a section on anti-aliasing lines. Indeed, § 3.17 had just what I wanted—code for drawing anti-aliased lines. A few minutes typing in the code (a page's worth) and I had myself one nice anti-aliased beam across the page.

int g_brightness[100];

/********************/

void init_colors(gdImagePtr img)
{
  int i;
  
  for (i = 0 ; i < 100 ; i++)
    g_brightness[i] = gdImageColorAllocate(img,16,132-i,16);
}

/******************/

void pset(gdImagePtr img,int x,int y,double dist)
{
  int    intensity;
  
  intensity = (int)(fabs(dist) / 1.5 * 100.0);
  gdImageSetPixel(img,x,y,g_brightness[intensity]);
}

/***********************/

void line(gdImagePtr img,int x1,int y1,int x2,int y2)
{
  int    dx;
  int    dy;
  int    incrE;
  int    incrNE;
  int    d;
  int    x;
  int    y;
  int    two_v_dx;
  double invDenom;
  double two_dx_invDenom;
  
  dx              = x2 - x1;
  dy              = y2 - y1;
  d               = 2 * dy - dx;
  incrE           = 2 * dy;
  incrNE          = 2 * (dy - dx);
  two_v_dx        = 0;		
  invDenom        = 1.0 / (2.0 * sqrt(dx*dx + dy+dy));
  two_dx_invDenom = 2.0 * (double)dx * invDenom;
  x               = x1;
  y               = y1;
  
  pset(img,x,y    ,0.0);
  pset(img,x,y + 1,two_dx_invDenom);
  pset(img,x,y - 1,two_dx_invDenom);
  
  while(x < x2)
  {
    if (d < 0)
    {
      two_v_dx = d + dx;
      d += incrE;
      x++;
    }
    else
    {
      two_v_dx = d - dx;
      d += incrNE;
      x++;
      y++;
    }
  
    pset(img,x,y    ,two_v_dx * invDenom);
    pset(img,x,y + 1,two_dx_invDenom - two_v_dx * invDenom);
    pset(img,x,y - 1,two_dx_invDenom + two_v_dx * invDenom);
  }
}

See what I go through for stuff nobody will see?

Sigh.

(If you are curious to see the styles, and you are using Firefox, you can use the menu View/Page Style to select which style you want).

Obligatory Picture

[It's the most wonderful time of the year!]

Obligatory Contact Info

Obligatory Feeds

Obligatory Links

Obligatory Miscellaneous

You have my permission to link freely to any entry here. Go ahead, I won't bite. I promise.

The dates are the permanent links to that day's entries (or entry, if there is only one entry). The titles are the permanent links to that entry only. The format for the links are simple: Start with the base link for this site: http://boston.conman.org/, then add the date you are interested in, say 2000/08/01, so that would make the final URL:

http://boston.conman.org/2000/08/01

You can also specify the entire month by leaving off the day portion. You can even select an arbitrary portion of time.

You may also note subtle shading of the links and that's intentional: the “closer” the link is (relative to the page) the “brighter” it appears. It's an experiment in using color shading to denote the distance a link is from here. If you don't notice it, don't worry; it's not all that important.

It is assumed that every brand name, slogan, corporate name, symbol, design element, et cetera mentioned in these pages is a protected and/or trademarked entity, the sole property of its owner(s), and acknowledgement of this status is implied.

Copyright © 1999-2021 by Sean Conner. All Rights Reserved.