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.

Code tweaking on Reset_Vector

So I was still getting glitches on my inputs for Reset_Vector. I couldn’t figure out what was causing it because it would happen randomly and I couldn’t repeat the problem. The false inputs caused issues with ball triggering, score detection, and playfield actions. I figured it had to be glitches on the lines caused by EMF or something on the input driver. I knew it was the input driver cause when a solenoid fired randomly like the pop bumper it would register a hit which means that the microcontroller detected a hit.

To fix this issue I added a simple debouncer routine. Basically it makes sure a input is pressed for at least 2 Kernel cycles before saying that it was a hit. This keeps random spikes from registering as hits.

What it does is read in the inputs into a variable called new_inputs. The new_inputs then gets anded with a variable called old_inputs and the result is the inputs that where held for two kernel cycles. Then the new_inputs is copied into old_inputs for the next cycle to happen.

This system can be easily expanded to 3,4,ect cycles so the debouncer is extremely configurable in its sensitivity.