Mark Daniel Belarmino
Published © MIT

RGB Large Digital Clock

Not your typical wall clock that tells time, it also becomes your wall light panels that lit up your scifi-like bedroom.

IntermediateWork in progressOver 1 day6,737
RGB Large Digital Clock

Things used in this project

Hardware components

WS2812 Addressable LED Strip
Digilent WS2812 Addressable LED Strip
×1
Arduino Pro Mini 328 - 5V/16MHz
SparkFun Arduino Pro Mini 328 - 5V/16MHz
×1
Grove - RTC
Seeed Grove - RTC
×1

Software apps and online services

Arduino IDE
Arduino IDE

Hand tools and fabrication machines

3D Printer (generic)
3D Printer (generic)
Soldering iron (generic)
Soldering iron (generic)

Story

Read more

Custom parts and enclosures

STL File

Just download and use slicer like Cura

The files include the main part and its diffuser for each digit.
Another 2 files are also uploaded to contain your microcontroller and RTC

Code

Arduino Code

C/C++
#include <Adafruit_NeoPixel.h>
#include <EEPROM.h>
#include <Wire.h>
#include "RTClib.h"
RTC_DS1307 RTC;

#define PIN  2
#define BTN  3

uint8_t NUM_DIGIT = 4;
const uint8_t LEDS_PER_DIGIT = 35;
uint16_t NUM_LEDS = LEDS_PER_DIGIT * NUM_DIGIT;

uint8_t time_h = 0;
uint8_t time_m = 0;
int num = 0;

float ambiant_light = 1.0;

bool mask_digit[10][35] =
{
  { //0
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1
  },
  { //1
    0, 0, 0, 0, 0,
    0, 0, 0, 0, 0,
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1,
    0, 0, 0, 0, 0,
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1
  },
  { //2
    1, 1, 1, 1, 1,
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    0, 0, 0, 0, 0
  },
  { //3
    0, 0, 0, 0, 0,
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1
  },
  { //4
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1,
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1
  },
  { //5
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1
  },
  { //6
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1
  },
  { //7
    0, 0, 0, 0, 0,
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    0, 0, 0, 0, 0,
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1
  },
  { //8
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1
  },
  {
    0, 0, 0, 0, 0,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1,
    1, 1, 1, 1, 1
  },
};
Adafruit_NeoPixel strip = Adafruit_NeoPixel(NUM_LEDS, PIN, NEO_GRB + NEO_KHZ800);
byte colors[3][3] = { {0xff, 0, 0},
  {0xff, 0xff, 0xff},
  {0   , 0   , 0xff}
};

void setup()
{
  Serial.begin(9600);
  Wire.begin();
  RTC.begin();
  if (! RTC.isrunning())
  {
    Serial.println("RTC is NOT running!");
    // Following line sets the RTC to the date & time this sketch was compiled
//     RTC.adjust(DateTime(__DATE__, __TIME__));
  }
  strip.begin();
  strip.show(); // Initialize all pixels to 'off'
  pinMode(BTN, INPUT);
}

void loop()
{
  DateTime now = RTC.now();
  time_h = now.hour();
  time_m = now.minute();
  int digit_4 = time_h / 10; //10 states, 0-9
  int digit_3 = time_h % 10; //10 states, 0-9
  int digit_2 = time_m / 10; //10 states, 0-9
  int digit_1 = time_m % 10; //10 states, 0-9
  //  Serial.println(digit_4);
  //  Serial.println(digit_3);
  //  Serial.println(digit_2);
  //  Serial.println(digit_1);

  //  rainbowCycle(10, digit_4, digit_3, digit_2, digit_1, ambiant_light);

  byte *c;
  bool map_num[NUM_LEDS] = {};
  for (int i = 0; i < LEDS_PER_DIGIT; i++)
  {
    map_num[i] = mask_digit[digit_4][i];
  }
  for (int i = LEDS_PER_DIGIT; i < 2 * LEDS_PER_DIGIT; i++)
  {
    map_num[i] = mask_digit[digit_3][i - LEDS_PER_DIGIT];
  }
  for (int i = 2 * LEDS_PER_DIGIT; i < 3 * LEDS_PER_DIGIT; i++)
  {
    map_num[i] = mask_digit[digit_2][i - 2 * LEDS_PER_DIGIT];
  }
  for (int i = 3 * LEDS_PER_DIGIT; i < 4 * LEDS_PER_DIGIT; i++)
  {
    map_num[i] = mask_digit[digit_1][i - 3 * LEDS_PER_DIGIT];
  }

  for (uint16_t j = 256; j > 0; j--) { // 5 cycles of all colors on wheel
    for (uint16_t i = 0; i < NUM_LEDS; i++) {
//      c = Wheel(((i * 256 / (NUM_LEDS/4)) + j) & 255); //each digit is rainbow
      c = Wheel(((i * 256 / (NUM_LEDS*8)) + j) & 255); //slow transition
      if (map_num[i] == 1)
      {
        uint8_t R = *c * ambiant_light;
        uint8_t G = *(c + 1) * ambiant_light;
        uint8_t B = *(c + 2) * ambiant_light;
        setPixel(i, R, G, B);
      }
      else
        setPixel(i, 0, 0, 0);
    }
    showStrip();
    delay(20);
  }
}


void rainbowCycle(uint8_t SpeedDelay, int d4, int d3, int d2, int d1, float ambiant_light)
{
  byte *c;
  uint16_t i, j;
  bool map_num[NUM_LEDS] = {};
  for (int i = 0; i < LEDS_PER_DIGIT; i++)
  {
    map_num[i] = mask_digit[d4][i];
  }
  for (int i = LEDS_PER_DIGIT; i < 2 * LEDS_PER_DIGIT; i++)
  {
    map_num[i] = mask_digit[d3][i - LEDS_PER_DIGIT];
  }
  for (int i = 2 * LEDS_PER_DIGIT; i < 3 * LEDS_PER_DIGIT; i++)
  {
    map_num[i] = mask_digit[d2][i - 2 * LEDS_PER_DIGIT];
  }
  for (int i = 3 * LEDS_PER_DIGIT; i < 4 * LEDS_PER_DIGIT; i++)
  {
    map_num[i] = mask_digit[d1][i - 3 * LEDS_PER_DIGIT];
  }

  for (j = 0; j < 256; j++) { // 5 cycles of all colors on wheel
    for (i = 0; i < NUM_LEDS; i++) {
      c = Wheel(((i * 256 / (NUM_LEDS)) + j) & 255);
      if (map_num[i] == 1)
      {
        uint8_t R = *c * ambiant_light;
        uint8_t G = *(c + 1) * ambiant_light;
        uint8_t B = *(c + 2) * ambiant_light;
        setPixel(i, R, G, B);
      }
      else
        setPixel(i, 0, 0, 0);
    }
    showStrip();
    delay(1);
  }
}

// *** REPLACE TO HERE ***

void showStrip() {
#ifdef ADAFRUIT_NEOPIXEL_H
  // NeoPixel
  strip.show();
#endif
#ifndef ADAFRUIT_NEOPIXEL_H
  // FastLED
  FastLED.show();
#endif
}

void setPixel(int Pixel, byte red, byte green, byte blue) {
#ifdef ADAFRUIT_NEOPIXEL_H
  // NeoPixel
  strip.setPixelColor(Pixel, strip.Color(red, green, blue));
#endif
#ifndef ADAFRUIT_NEOPIXEL_H
  // FastLED
  leds[Pixel].r = red;
  leds[Pixel].g = green;
  leds[Pixel].b = blue;
#endif
}

void setAll(byte red, byte green, byte blue) {
  for (int i = 0; i < NUM_LEDS; i++ ) {
    setPixel(i, red, green, blue);
    delay(1);
  }
  showStrip();
}

byte * Wheel(byte WheelPos) {
  static byte c[3];

  if (WheelPos < 85) {
    c[0] = WheelPos * 3;
    c[1] = 255 - WheelPos * 3;
    c[2] = 0;
  } else if (WheelPos < 170) {
    WheelPos -= 85;
    c[0] = 255 - WheelPos * 3;
    c[1] = 0;
    c[2] = WheelPos * 3;
  } else {
    WheelPos -= 170;
    c[0] = 0;
    c[1] = WheelPos * 3;
    c[2] = 255 - WheelPos * 3;
  }

  return c;
}

Credits

Mark Daniel Belarmino

Mark Daniel Belarmino

3 projects • 4 followers
R&D Engineer

Comments