Tweaking the 128×32 LEDDMD Verilog

There was a few problems with the code for the 128×32 LEDDMD. Every so often there was flickering at random spots on the screen. This was because of the way the display memory was updated. I already fixed it by putting a dummy state at the end of the display memory update. Doing so actually increased the speed that data could be sent to the FPGA. There is no waiting between the Latch pulls.

The last problem is that there is some slight ghosting on the screen. Due to the way the screen updates it looks like the Column data is updating slightly before the rows are updated. Because of this you get a ghost effect on the opposite side of the screen that is up one row.

I think the reason why is because there is a slight delay in the rows caused by the decoders. The current plan of attack is to buffer the Column data a couple cycles before outputting.

LEDDMD 128×32 Complete

So I finally finished the prototype of the 128 x 32 Light Emitting Diode Dot Matrix Display V1.0 (LEDDMD). The protocol to write to the display is almost exactly like a shift register. There is a clock, latch, and data lines. It works in either 1 bit mode or 8 bit mode data line modes.

In 1 bit mode there is only 1 data line and in 8 bit mode this is 8 data lines. 8 bit mode enables you to clock in an entire byte of data at a time speeding up the transfer process by a factor of 8. In either mode you can do animations smoothly. All processing of the data is done on the microcontroller. The Display stores the data and takes care of running the display.

The bulk of the hardware is in the FPGA. I am using a Cyclone II EP2C8Q208C8N FPGA breakout board. There are some darlington transistor arrays that sink the current from a single row. To expand the I/O of the FPGA some decoders are used.

Here are the links to all the code:
FPGA:
Main Routine
Memory

Propeller:
Transmission Protocol and Test

Bitmap Converter Code

This is the code I talked about earlier. Just rips the bottom 2 bits out of a 4-bit bitmap to make a 2-bit bitmap. So to use this you make a 4-bit bitmap with grayscale. Black, 50% Gray, 25% Gray, White. Paint is where I made the bitmaps. It must be 128×32. The program doesn’t do any checks on this, its fairly stupid.


#include <stdio.h>

void main(void)
{
  char str[80];
  char nstr[80];
  int image[2048];
  int ripped[1024];
  int flipped[1024];
  int i,j;
  int header_junk;
  FILE *fp, *nfp;
  
  printf("4-Bit BMP File Name? : ");
  gets(str);
  printf("Opening File. : %s\n",str);
  fp = fopen(str, "r");
  if (fp == NULL) 
  {
    fprintf(stderr, "File Can Not Be Opened.\n");
    exit(1);
  }
  printf("File Opened Successful!\n");
  printf("2-Bit DMD File Name? (format XXX.DMD) : ");
  gets(nstr);
  printf("\nCreating New File Named: %s.dmd\n",str);
  nfp = fopen(nstr, "w");
  
  printf("Reading Header.\n");
  for( i = 0 ; i < 118 ; i++)
  {
    header_junk = fgetc (fp);
    printf("0x%.2X ", header_junk);
  }
  printf("\nHeader Ripped.\n");
  printf("Reading Image Data\n");
  for( i = 0 ; i < 2048 ; i ++)
  {
    image[i] = fgetc (fp);
    printf("0x%.2X ", image[i]);
  }
  printf("\nRipping bits out and Rotating!\n");
  
  for( i = 0 ; i < 1024 ; i ++)
  {
    ripped[i] = (((image[2*i] & 0x80))| ((image[2*i] & 0x40)) | ((image[2*i] & 0x08)<<2) | ((image[2*i] & 0x04)<<2) | ((image[2*i+1] & 0x80) >> 4) | ((image[2*i+1] & 0x40) >> 4) | ((image[2*i+1] & 0x08) >>2) | ((image[2*i+1] & 0x04) >>2));
    printf("0x%.2X ", ripped[i]);
  }
  
  printf("\nFlipping Image.\n");

  for( j = 0 ; j < 32 ; j ++)
  {  
    for( i = 0 ; i < 32 ; i++)
    {
      flipped [(992-(32*j))+i] =  ripped[(32*j)+i]; 
    }
  }  
  
  printf("\nWriting To New File\n");
  
  for( i = 0 ; i < 1024 ; i++)
  {
    fputc(flipped[i],nfp);
    printf("0x%.2X ", flipped[i]);
  }
  fclose(nfp);
  fclose(fp);
  
  printf("\nDone!\n");
  printf("Press Any Key To Quit...");
  gets(str);
  exit(1);
}

128×32 DMD Update

The verilog code is almost fully debugged. The demo code that will run on a Parallax Propeller is in the works. Right now the demo is fairly basic. Today I wrote a C program that takes a 4-bit bitmap image and strips out the header and and converts it to a 2-bit image. It then reorientates the data so the image is “correct”. Bitmap images data reads the image from bottom left to top right. This is essentially backwards. So the program corrects this which means less work for the microcontroller and faster transmission of pixels.

Tommy System Specifications

Here are the loose specs for the Tommy System.

  • Parallax Propeller running at standard 80Mhz. Can be overclocked to 100Mhz.
  • Three SD cards. Music, sound effects, bitmaps for animations.
  • Two Stereo sound channels. Plays PCM WAV files.
  • 64 Bits of Input.
  • 64 Bits of Output. Can be divided between solenoid/motor control and light control and way. Standard will be 24 bits of solenoid/motor control and 40 bits of light.
  • General Illumination via RGB LEDs built in.
  • Compatible with 96×16 DMD and 128×32 DMD (only in 1 bit mode).

The goal is to keep this low cost.

Have a suggestion or want to discuss the Tommy System? We have a forum now!

Pinball Homebrew Platform: Tommy

I have had lots of requests for people wanting the hardware and PCBs for Reset Vector. I will be designing a pinball homebrew platform named Tommy. Key goals will be keeping cost down and complexity of the circuit down so it will be easy to build on .1″ perf board. Will be all through hole parts. Support for the 128×32 Display built in. Goal is to get the PCBs down to $15 a piece.

8×8 LED Matrix Modules in 1.9mm size

So for the new 128×32 DMD I am using a smaller dot pitch LED Matrix with a size of 1.9mm. This means they are the same size as standard DMDs used on production machines. I secured a supplier and I can provide any color LED for the DMDs. Red, Orange, Amber, Blue, Green, ect. These are currently not compatible with production machines but are intended for Home Brew Pinball machines. They are very easy to work with.

Instead of the wacky voltages of a standard DMD mine only needs a +5V supply. Standard DMDs also are hard to drive with microcontrollers because you have to fill each “level” individually and you have to do it fast enough to keep up with the refresh rate. My DMD runs off a FPGA which means you don’t have to worry about how fast you send the data to the display. The FPGA takes care of all the matrixing and color levels. All you have to do is send the data in 1byte wide chunks which is perfect for Microcontroller use. If you are doing animations you can stream data off an SD card by doing byte writes and then pushing that data directly to the DMD.

Prices will be $250 for quantities 1-9 and $240 for anything over 10. They come with the SMD parts soldered on and the FPGA pre-programmed. You will need to solder the LED modules on. The LED modules will be tested to ensure that they are in full working order.