rFactor LED display

Thu 22 November 2012 // posts

The idea behind this project was to create a physical display for rFactor simulator that could display game data in real time. In this case, gear and rpm data is displayed.

How it is built

  • Two 74hc595 shift registers take care of 8 LEDs and a 7 segment display.
  • The 8 independent LEDs display the engine's RPM.
  • The 7 segment display shows the current gear.
  • The buzzer beeps each time gear changes.
  • Although the display┬áis controlled with an Arduino, with some modifications, it is possible to add a microcontroller to the board, making the circuit even simpler.

Arduino code

const int SER   = 5;
const int SCLK  = 6;
const int SRCLK = 7;
const int BUZZ  = 3;

unsigned long beep_start = 0;
int           gear       = 0;
int           rpm        = 0;

byte int_to_7seg(int value)
{
   const byte N1       = B00000110;
   const byte N2       = B01011011;
   const byte N3       = B01001111;
   const byte N4       = B01100110;
   const byte N5       = B01101101;
   const byte N6       = B01111101;
   const byte N7       = B00000111;
   const byte N8       = B01111111;
   const byte N9       = B01100111;
   const byte N0       = B00111111;
   const byte WITH_DOT = B10000000;

   switch (value)
   {
   case 0:
      return N0;

   case 1:
      return N1;

   case 2:
      return N2;

   case 3:
      return N3;

   case 4:
      return N4;

   case 5:
      return N5;

   case 6:
      return N6;

   case 7:
      return N7;

   case 8:
      return N8;

   case 9:
      return N9;

   default:
      return -1;
   }
}


byte int_to_rpm_led(int value)
{
   byte b = 0;

   for (int i = 0; i < value; i++)
   {
      b = b << 1 | 1;
   }
   return b;
}


void setup()
{
   pinMode(SER, OUTPUT);
   pinMode(SCLK, OUTPUT);
   pinMode(SRCLK, OUTPUT);
   pinMode(BUZZ, OUTPUT);
   Serial.begin(9600);
   analogWrite(BUZZ, 0);

   // checkup
   for (int j = 0; j < 3; j++)
   {
      for (int i = 0; i < 9; i++)
      {
         digitalWrite(SCLK, LOW);
         shiftOut(SER,
                  SRCLK, MSBFIRST, int_to_7seg(i));
         shiftOut(SER, SRCLK, MSBFIRST,
                  int_to_rpm_led(i));
         digitalWrite(SCLK, HIGH);
         analogWrite(BUZZ, 240);
         delay(50);
         analogWrite(BUZZ, 0);
      }
   }
   digitalWrite(SCLK, LOW);
   shiftOut(SER, SRCLK, MSBFIRST, 0x00);
   shiftOut(SER, SRCLK, MSBFIRST,
            0x00);
   digitalWrite(SCLK, HIGH);
}


void loop()
{
   byte v = 0;

   if

   (beep_start && (millis() - beep_start > 500))
   {
      beep_start = 0;
      analogWrite(BUZZ, 0);
   }

   while (Serial.available())
   {
      v = Serial.read();
      int new_gear = v >> 4;
      int new_rpm  = (v << 4 & 0xFF) >> 4;
      if ((new_gear != gear) || (new_rpm != rpm))
      {
         digitalWrite(SCLK, LOW);
         shiftOut(SER, SRCLK, MSBFIRST, int_to_7seg(new_gear));
         shiftOut(SER, SRCLK, MSBFIRST, int_to_rpm_led(new_rpm));
         digitalWrite(SCLK, HIGH);

         if (new_gear != gear)
         {
            analogWrite(BUZZ, 240);
            beep_start = millis();
         }

         gear = new_gear;
         rpm  = new_rpm;
      }
   }
   delay(20);
}

Demo

RFACTOR 1 - 1st prototype

rFactor 1

rFactor 2


social