hi @jgarland79,
here is my VFDTube.h:
/*
* VFDTube.h
*
* Created on: Oct 29, 2012
* Author: agu
*/
#ifndef VFDTUBE_H_
#define VFDTUBE_H_
/* #include "Arduino.h" */
#include "application.h"
enum Color
{
White, Yellow, Magenta, Red,
Cyan, Green, Blue, Black,
};
const uint8_t VFDTUBE_FONT[] =
{
// 0-9
0xb7, 0x22, 0x9b, 0xab, 0x2e,
0xad, 0xbd, 0x23, 0xbf, 0xaf,
// a-z
0xbb, 0xbc, 0x98, 0xba, 0x9f,
0x1d, 0xb5, 0x3c, 0x14, 0xa2,
0x9c, 0x94, 0x37, 0x38, 0xb8,
0x1f, 0x2f, 0x18, 0x2c, 0x1c,
0xb0, 0x90, 0x0e, 0x0f, 0x2a, 0x1a,
};
class VFDTube
{
public:
VFDTube(uint8_t pin_din, uint8_t pin_oe, uint8_t pin_st, uint8_t pin_sh,
byte section_count);
virtual ~VFDTube();
void display();
void putWord(byte index, uint16_t value = 0xff00);
void clear(int value = 0xff00);
void setBackgroundColor(Color color);
void setBackgroundColor(byte index, Color color);
void setBrightness(byte brightness = 0xff);
void setPoint(byte index);
bool setChar(byte index, char c);
void setChar(char c);
void printf(const char *__fmt, ...);
private:
int *_buff;
const uint8_t _pin_din; // DIN
const uint8_t _pin_oe; // OE, pin with PWM output is recommended to enable brightness adjustment
const uint8_t _pin_st; // STCP
const uint8_t _pin_sh; // SHCP
const byte _section_count;
void send(byte data) const;
bool displayable(char c);
};
#endif /* VFDTUBE_H_ */
and my VFDTube.cpp:
/*
* VFDTube.cpp
*
* Created on: Oct 29, 2012
* Author: agu
*/
#include "VFDTube.h"
#include "application.h"
#include <stdarg.h>
/* STUFF FOR PHOTON */
#define abs(x) ((x)>0?(x):-(x))
#define radians(deg) ((deg)*DEG_TO_RAD)
#define degrees(rad) ((rad)*RAD_TO_DEG)
#define sq(x) ((x)*(x))
#define lowByte(w) ((uint8_t) ((w) & 0xff))
#define highByte(w) ((uint8_t) ((w) >> 8))
#define bitRead(value, bit) (((value) >> (bit)) & 0x01)
#define bitSet(value, bit) ((value) |= (1UL << (bit)))
#define bitClear(value, bit) ((value) &= ~(1UL << (bit)))
#define bitWrite(value, bit, bitvalue) (bitvalue ? bitSet(value, bit) : bitClear(value, bit))
typedef uint16_t word;
#define bit(b) (1UL << (b))
// #define pgm_read_byte(addr) (*(const unsigned char *)(addr))
#define pgm_read_byte_near(addr) (*(const unsigned char *)(addr))
extern const uint8_t digital_pin_to_timer_PGM[];
#define digitalPinToTimer(P) ( pgm_read_byte( digital_pin_to_timer_PGM + (P) ) )
#define NOT_ON_TIMER 0
/* STUFF FOR PHOTON */
VFDTube::VFDTube(uint8_t pin_din, uint8_t pin_oe, uint8_t pin_st,
uint8_t pin_sh, byte section_count) :
_pin_din(pin_din), _pin_oe(pin_oe), _pin_st(pin_st), _pin_sh(pin_sh), _section_count(
section_count)
{
_buff = (int *) malloc(sizeof(uint16_t) * section_count);
pinMode(_pin_din, OUTPUT);
pinMode(_pin_st, OUTPUT);
pinMode(_pin_sh, OUTPUT);
pinMode(_pin_oe, OUTPUT);
this->setBrightness();
}
VFDTube::~VFDTube()
{
free(_buff);
}
void VFDTube::send(byte data) const
{
for (byte i = 8; i > 0; i--)
{
digitalWrite(_pin_din, bitRead(data, i - 1));
digitalWrite(_pin_sh, HIGH);
digitalWrite(_pin_sh, LOW);
}
}
void VFDTube::display()
{
for (byte i = 0; i < _section_count; i++)
{
this->send(highByte(_buff[i]));
this->send(lowByte(_buff[i]));
}
digitalWrite(_pin_st, HIGH);
digitalWrite(_pin_st, LOW);
}
void VFDTube::putWord(byte index, word value)
{
index %= _section_count;
_buff[index] = value;
}
void VFDTube::clear(int value)
{
for (byte i = 0; i < _section_count; i++)
this->putWord(i, value);
}
void VFDTube::setBackgroundColor(Color color)
{
for (byte i = 0; i < _section_count; i++)
{
this->setBackgroundColor(i, color);
}
}
void VFDTube::setBackgroundColor(byte index, Color color)
{
index %= _section_count;
_buff[index] &= 0xff;
_buff[index] |= color << 8;
}
void VFDTube::setPoint(byte index)
{
index %= _section_count;
_buff[index] |= 0x40;
}
bool VFDTube::setChar(byte index, char c)
{
index %= _section_count;
bool val = displayable(c);
if (val)
{
word tmp = _buff[index] & 0xff00;
if (c >= '0' && c <= '9')
tmp |= pgm_read_byte_near(VFDTUBE_FONT + c - '0');
else if (c >= 'A' && c <= 'Z')
tmp |= pgm_read_byte_near(VFDTUBE_FONT + c - 'A' + 10);
else if (c >= 'a' && c <= 'z')
tmp |= pgm_read_byte_near(VFDTUBE_FONT + c - 'a' + 10);
this->putWord(index, tmp);
}
return val;
}
void VFDTube::setChar(char c)
{
for (byte i = 0; i < _section_count; i++)
this->setChar(i, c);
}
void VFDTube::printf(const char *__fmt, ...)
{
word cache_length = _section_count * 2 + 1;
char * cache = (char *) malloc(sizeof(char) * cache_length);
va_list ap;
va_start(ap, __fmt);
vsnprintf(cache, cache_length, __fmt, ap);
va_end(ap);
byte index = 0;
byte ptr = 0;
for (byte i=0; i<_section_count; i++)
_buff[i] &= 0xff00;
while (cache[index] && ptr < _section_count)
{
if (this->setChar(ptr, cache[index]))
ptr++;
else if (cache[index] == '.')
this->setPoint(ptr ? ptr - 1 : 0);
else
{
_buff[ptr] &= 0xff00;
ptr++;
}
index++;
}
free(cache);
}
bool VFDTube::displayable(char c)
{
return ((c >= '0' && c <= '9') or (c >= 'A' && c <= 'Z')
or (c >= 'a' && c <= 'z'));
}
void VFDTube::setBrightness(byte brightness)
{
// if (digitalPinToTimer(_pin_oe) == NOT_ON_TIMER)
digitalWrite(_pin_oe, brightness ? LOW : HIGH);
// else
// analogWrite(_pin_oe, 0xff - brightness);
}
good luck!