Skip to content

Instantly share code, notes, and snippets.

@lpereira
Created October 20, 2013 02:18
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save lpereira/7064088 to your computer and use it in GitHub Desktop.
Save lpereira/7064088 to your computer and use it in GitHub Desktop.
Arduino 7-segment display driver
namespace {
const char segment_pin[7] = {
[0] = 0,
[1] = 0,
[2] = 0,
[3] = 0,
[4] = 0,
[5] = 0,
[6] = 0,
};
constexpr int hassomething(char c) {
if (c == ' ')
return 0;
return 1;
}
constexpr unsigned char SegmentToFontData(const char *drawing) {
/*
* This function calculates which segments will light up according to a
* diagram of a 7-segment display:
*
* +------------ 5
* | +--------- 0
* | v
* | _
* +>|_| <------ 1 (6 is the middle segment)
* +>|_| <------ 2
* | ^
* | +--------- 3
* +------------ 4
*/
unsigned char data = 0;
data = hassomething(drawing[1]);
data |= 1<<(1 * hassomething(drawing[5]));
data |= 1<<(2 * hassomething(drawing[8]));
data |= 1<<(3 * hassomething(drawing[7]));
data |= 1<<(4 * hassomething(drawing[6]));
data |= 1<<(5 * hassomething(drawing[3]));
data |= 1<<(6 * hassomething(drawing[4]));
return data;
}
const char font[] = {
[0] = SegmentToFontData(
" _ "
"| |"
"|_|"),
[1] = SegmentToFontData(
" "
" |"
" |"),
[2] = SegmentToFontData(
" _ "
" _|"
"|_ "),
[3] = SegmentToFontData(
" _ "
" _|"
" _|"),
[4] = SegmentToFontData(
" "
"|_|"
" |"),
[5] = SegmentToFontData(
" _ "
"|_ "
" _|"),
[6] = SegmentToFontData(
" _ "
"|_ "
"|_|"),
[7] = SegmentToFontData(
" _ "
" |"
" |"),
[8] = SegmentToFontData(
" _ "
"|_|"
"|_|"),
[9] = SegmentToFontData(
" _ "
"|_|"
" _|"),
};
};
class DisplayDigit {
private:
int anode_pin_;
public:
DisplayDigit(int anode_pin) : anode_pin_(anode_pin) {}
void Deactivate();
void DisplayNumber(int number);
};
void DisplayDigit::Deactivate() {
digitalWrite(anode_pin_, LOW);
}
void DisplayDigit::DisplayNumber(int number) {
for (int segment = 0; segment < 7; segment++)
digitalWrite(segment_pin[segment], font[number] & 1<<segment);
digitalWrite(anode_pin_, HIGH);
}
class Display {
private:
DisplayDigit *digits_;
int n_digits_;
int number_;
public:
~Display();
void Init(int n_digits);
void DisplayNumber(int number);
void Loop();
};
void Display::Init(int n_digits) {
n_digits_ = n_digits;
digits_ = new DisplayDigit[n_digits];
}
Display::~Display() {
delete[] digits_;
}
void Display::DisplayNumber(int number) {
number_ = number;
}
void Display::Loop() {
int number, digit;
for (number = number_, digit = n_digits_;
number && digit; number /= 10, digit--) {
if (digit != n_digits_)
digits_[digit + 1]->Deactivate();
digits_[digit]->DisplayNumber(number % 10);
}
for (; digit; digit--)
digits_[digit]->Deactivate();
}
Display d;
void setup() {
d.Init(7);
d.DisplayNumber(42);
}
void loop() {
d.Loop();
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment