Initial import of the Cool Arduino Libraries Repository

git-svn-id: svn+ssh://oldsvn/home/mlalondesvn/svn/cral@1 3ee9b42a-b53c-0410-a25e-f0b6218d5d5b
master
mlalondesvn 17 years ago
commit 20f384ee55

@ -0,0 +1,37 @@
#include "../global.h"
// call with printString(PSTR("My string"))
void SPrint_P(const char *data)
{
char ch;
for (;;) {
ch = pgm_read_byte( data++ );
if ( !ch ) return;
Serial.print(ch);
}
}
void SPrintln_P(const char *data)
{
SPrint_P(data);
SPrint_P(PSTR("\r\n"));
}
void SPrintHex_P(const char *data)
{
char ch;
for (;;) {
ch = pgm_read_byte( data++ );
if ( !ch ) return;
Serial.print(ch, HEX);
}
}
void SPrintlnHex_P(const char *data)
{
printString(data);
Serial.println();
}

@ -0,0 +1,29 @@
#ifndef staticPrint_H
#define staticPrint_H
#ifndef nop
#define nop() asm volatile ("nop")
#endif
#ifndef SPrint
#define SPrint(str) SPrint_P(PSTR(str))
#endif
#ifndef SPrintln
#define SPrintln(str) SPrintln_P(PSTR(str))
#endif
#ifndef SPrintHex
#define SPrintHex(str) SPrintHex_P(PSTR(str))
#endif
#ifndef SPrint
#define SPrintlnHez(str) SPrintlnHex_P(PSTR(str))
#endif
void SPrint_P(const char *data);
void SPrintln_P(const char *data);
void SPrintHex_P(const char *data);
void SPrintlnHex_P(const char *data);
#endif

@ -0,0 +1,58 @@
#ifndef LCD_H
#define LCD_H
#define LCD_ROWS 2
#define LCD_COLUMNS 16
#define LCD_CURSOR_OFF 0x0C
#define LCD_CURSOR_OFF_BLINK 0x0D
#define LCD_CURSOR_NO_BLINK 0x0E
#define LCD_CURSOR_BLINK 0x0F
#define LCD_CLEAR 0x01
#define LCD_CLOSE_INIT 0x80
/**
* Entry modes
**/
#define LCD_ENTRY_AUTOINC 0x04
#define LCD_ENTRY_SHIFT 0x02
/**
* Shifting commands
**/
#define LCD_GO_HOME 0x02
#define LCD_SHIFT_RIGHT 0x1C
#define LCD_SHIFT_LEFT 0x18
/**
* Display off command
**/
#define LCD_TURN_OFF 0x0A
/**
* Character font
**/
#define LCD_CHARSET_0 0x00
#define LCD_CHARSET_1 0x04
/**
* Number of lines
**/
#define LCD_LINES_1 0x00
#define LCD_LINES_2 0x08
#define LCD_FUNCTION_MASK B00100000
// Choose the fonction modes here
#define LCD_FUNCTION_SET LCD_LINES_2 | LCD_CHARSET_0
// Choose the cursor mode here
#define LCD_CURSOR LCD_CURSOR_OFF
// Choose the entry mode here
#define LCD_ENTRY_MODE LCD_ENTRY_AUTOINC
// Uncomment this if you want clearScreen to call back a function named onClearScreen
//#define LCD_USE_CLRSCREEN_CALLBACK
#endif

@ -0,0 +1,42 @@
#ifndef RTC_CONFIG_H
#define RTC_CONFIG_H
/**
* Set this to your local GMT offset
* Comment to skip GMT offset calculations
**/
#define RTC_GMT_OFFSET -5
/**
* Select your DST type
* Comment all to skip DST calculation
**/
#define RTC_DST_TYPE 0 /* US */
//#define RTC_DST_TYPE 1 /* EU */
// Uncomment this only if you need to check DST prior to 2006
//#define RTC_CHECK_OLD_DST
#define RTC_DST_OLD_YEAR 2006
#define RTC_DOW_1 PSTR("Sun") /* First day of the week */
#define RTC_DOW_2 PSTR("Mon")
#define RTC_DOW_3 PSTR("Tue")
#define RTC_DOW_4 PSTR("Wed")
#define RTC_DOW_5 PSTR("Thu")
#define RTC_DOW_6 PSTR("Fri")
#define RTC_DOW_7 PSTR("Sat")
/* Wednesday is the first day of Epoch: This probably shouldn't change! */
#define RTC_DOW_0 RTC_DOW_4
/**
* Macros
**/
// Start (US/EU), Stop (EU)
#define DSTCALCULATION1(y) (31-((y * 5 / 4) + 1) % 7)
// Stop (US)
#define DSTCALCULATION2(y) (7 - ((1 + y * 5 / 4) % 7))
#endif

@ -0,0 +1,623 @@
extern "C" {
#include <Wire/Wire.h>
}
#include "../global.h"
#include "../configs/RTC/rtcConfig.h"
#include "ds1337.h"
// Internal macro for storing month days!
#ifndef GETMONTHDAYS
PROGMEM prog_uint16_t monthcount[] = {0, 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334, 365};
#define GETMONTHDAYS(index) (pgm_read_word_near(monthcount + index))
#endif
#ifndef CI
#define CI(reg,bit) (reg & ~(bit))
#endif
#ifndef SI
#define SI(reg,bit) (reg | bit)
#endif
DS1337::DS1337()
{
clockExists = false;
alarmId = false;
#ifdef WIRE_LIB_SCAN_MOD
/*if (!Wire.isStarted()) */Wire.begin();
#else
Wire.begin();
#endif
}
DS1337 RTC = DS1337();
#ifdef WIRE_LIB_SCAN_MOD
int8_t DS1337::Init(void)
{
// Account for the crystal power up!
delay(250);
// Check address and returns false is there is an error
if (Wire.checkAddress(DS1337_WADDR)) {
// Possibly set the default registers here
clockExists = true;
// Start the oscillator if need
if (getRegisterBit(DS1337_SP, DS1337_SP_EOSC))
{
if (getRegisterBit(DS1337_STATUS, DS1337_STATUS_OSF))
{
unsetRegister(DS1337_STATUS, DS1337_STATUS_OSF);
}
clockStart();
}
return DS1337_WADDR;
} else clockExists = false;
return -1;
}
#else
int8_t DS1337::Init(void)
{
// Account for the crystal power up!
delay(250);
clockExists = true;
// Start the oscillator if need
if (getRegisterBit(DS1337_SP, DS1337_SP_EOSC))
{
if (getRegisterBit(DS1337_STATUS, DS1337_STATUS_OSF))
{
unsetRegister(DS1337_STATUS, DS1337_STATUS_OSF);
}
clockStart();
return DS1337_WADDR;
}
return -1;
}
#endif
boolean DS1337::checkClock()
{
if (getRegisterBit(DS1337_STATUS, DS1337_STATUS_OSF))
{
return false;
}
return true;
}
void DS1337::setRegister(uint8_t registerNumber, uint8_t registerMask)
{
writeRegister(registerNumber, SI(getRegister(registerNumber), registerMask));
}
void DS1337::unsetRegister(uint8_t registerNumber, uint8_t registerMask)
{
writeRegister(registerNumber, CI(getRegister(registerNumber), registerMask));
}
void DS1337::writeRegister(uint8_t registerNumber, uint8_t registerValue)
{
if (!clockExists) return;
Wire.beginTransmission(DS1337_WADDR);
Wire.send(registerNumber);
Wire.send(registerValue);
Wire.endTransmission();
}
uint8_t DS1337::getRegister(uint8_t registerNumber)
{
if (!clockExists) return 0;
Wire.beginTransmission(DS1337_WADDR);
Wire.send(registerNumber);
Wire.endTransmission();
Wire.requestFrom(DS1337_WADDR, 1);
while (!Wire.available());
return Wire.receive();
}
void DS1337::clockRead(void)
{
if (!clockExists) return;
Wire.beginTransmission(DS1337_WADDR);
Wire.send(0x00);
Wire.endTransmission();
Wire.requestFrom(DS1337_WADDR, 7);
while (!Wire.available());
for(int i=0; i<7; i++)
{
if (Wire.available())
rtc_bcd[i] = Wire.receive();
}
}
void DS1337::clockSave(void)
{
if (!clockExists) return;
Wire.beginTransmission(DS1337_WADDR);
Wire.send(0x00);
for(int i=0; i<7; i++)
{
Wire.send(rtc_bcd[i]);
}
Wire.endTransmission();
delay(10);
}
void DS1337::clockGet(uint16_t *rtc)
{
clockRead();
for(int i=0;i<8;i++) // cycle through each component, create array of data
{
rtc[i]=clockGet(i, 0);
}
}
uint16_t DS1337::clockGet(uint8_t c, boolean refresh)
{
if(refresh) clockRead();
int timeValue=-1;
switch(c)
{
case DS1337_SEC:
timeValue = bcdToBin(DS1337_SEC, DS1337_HI_SEC);
break;
case DS1337_MIN:
timeValue = bcdToBin(DS1337_MIN, DS1337_HI_MIN);
break;
case DS1337_HR:
timeValue = bcdToBin(DS1337_HR, DS1337_HI_HR);
break;
case DS1337_DOW:
timeValue = rtc_bcd[DS1337_DOW] & DS1337_LO_DOW;
break;
case DS1337_DATE:
timeValue = bcdToBin(DS1337_DATE, DS1337_HI_DATE);
break;
case DS1337_MTH:
timeValue = CI(bcdToBin(DS1337_MTH, DS1337_HI_MTH), DS1337_LO_CNTY);
break;
case DS1337_YR:
timeValue = bcdToBin(DS1337_YR, DS1337_HI_YR)+(1900 + (rtc_bcd[DS1337_MTH] & DS1337_LO_CNTY ? 100 : 0));
break;
case DS1337_CNTY:
timeValue = rtc_bcd[DS1337_MTH] & DS1337_LO_CNTY>>7;
break;
} // end switch
return timeValue;
}
#ifdef DS1337_USE_BCD_CLOCKSET
void DS1337::clockSet(uint8_t timeSection, uint16_t timeValue)
{
switch(timeSection)
{
case DS1337_SEC:
if(timeValue<60)
{
rtc_bcd[DS1337_SEC] = binToBcd(timeValue);
}
break;
case DS1337_MIN:
if(timeValue<60)
{
rtc_bcd[DS1337_MIN] = binToBcd(timeValue);
}
break;
case DS1337_HR:
// TODO : AM/PM 12HR/24HR
if(timeValue<24)
{
rtc_bcd[DS1337_HR] = binToBcd(timeValue);
}
break;
case DS1337_DOW:
if(timeValue<8)
{
rtc_bcd[DS1337_DOW] = timeValue;
}
break;
case DS1337_DATE:
if(timeValue<31)
{
rtc_bcd[DS1337_DATE] = binToBcd(timeValue);
}
break;
case DS1337_MTH:
if(timeValue<13)
{
rtc_bcd[DS1337_MTH] = SI(CI(binToBcd(timeValue),DS1337_LO_CNTY), (rtc_bcd[DS1337_MTH] & DS1337_LO_CNTY));
}
break;
case DS1337_YR:
if(timeValue<1000)
{
rtc_bcd[DS1337_YR] = binToBcd(timeValue);
}
break;
case DS1337_CNTY:
if (timeValue > 0)
{
rtc_bcd[DS1337_MTH] = SI(rtc_bcd[DS1337_MTH], DS1337_LO_CNTY);
} else {
rtc_bcd[DS1337_MTH] = CI(rtc_bcd[DS1337_MTH], DS1337_LO_CNTY);
}
break;
} // end switch
clockSave();
}
#endif
#ifdef DS1337_USE_GET_UTS
uint32_t DS1337::calculateUTS(uint16_t year, uint8_t month, uint8_t day, uint8_t hour, uint8_t min, uint8_t sec)
{
// Number of days per month
// Compute days
tt = (year - 1970) * 365 + GETMONTHDAYS(month) + day - 1;
// Compute for leap year
for (month <= 2 ? year-- : 0; year >= 1970; year--)
if (ISLEAP(year))
tt++;
// Plus the time
tt = sec + 60 * (min + 60 * (tt * 24 + hour - RTC_GMT_OFFSET));
return tt;
}
#endif
#ifdef DS1337_USE_SET_UTS
void DS1337::clockSetWithUTS(uint32_t unixTimeStamp, boolean correctedTime)
{
int8_t ii;
uint16_t year;
uint16_t *yrPtr = &year;
uint16_t thisYear;
uint16_t *tyPtr = &thisYear;
#if defined(RTC_DST_TYPE)
uint8_t thisDate;
uint8_t *tdPtr = &thisDate;
#endif
// Serial.print((uint32_t)unixTimeStamp, DEC); delay(5); SPrint(" ");
/**
* Calculate GMT and DST
**/
#if defined(RTC_GMT_OFFSET)
if (!correctedTime) unixTimeStamp = (uint32_t)unixTimeStamp + (RTC_GMT_OFFSET * 3600);
#endif
// Years
tt = (uint32_t)unixTimeStamp / 3600 / 24 / 365;
year = tt + 1970;
thisYear = year;
// Set the century bit
if (tt > 30) {
rtc_bcd[DS1337_MTH] = SI(rtc_bcd[DS1337_MTH], DS1337_LO_CNTY);
tt-= 30;
} else {
rtc_bcd[DS1337_MTH] = CI(rtc_bcd[DS1337_MTH], DS1337_LO_CNTY);
}
// Set the year
rtc_bcd[DS1337_YR] = binToBcd(tt);
// Number of days left in the year
// Serial.print((uint32_t)unixTimeStamp, DEC); delay(5); SPrint(" "); delay(5);
// Serial.print((uint32_t)unixTimeStamp%31536000, DEC); delay(5); SPrint(" "); delay(5);
tt = ((uint32_t)(uint32_t)unixTimeStamp%31536000 / 3600 / 24) + 1;
// Serial.print(tt, DEC); delay(5); SPrint(" "); delay(5);
// leap year correction
for (year--; year > 1970; year--) {
if (ISLEAP(year))
{
tt--;
}
}
free(yrPtr);
// Serial.print(tt, DEC); SPrint(" ");
// Grab the number of previous days, account for leap years, and save the month
for (ii = 1; ii < 12; ii++)
{
if (( GETMONTHDAYS(ii+1) + ((ISLEAP(thisYear) && ii >= 2) ? 1 : 0) ) > tt)
{
rtc_bcd[DS1337_MTH] = SI(CI(binToBcd(ii), DS1337_LO_CNTY), (rtc_bcd[DS1337_MTH] & DS1337_LO_CNTY));
break;
}
}
// Serial.print(ii, DEC);
// SPrint(" ");
// Date
#if defined(RTC_DST_TYPE)
if (!correctedTime) {
thisDate = tt - (GETMONTHDAYS(ii) + ((ISLEAP(thisYear) && ii >= 2) ? 1 : 0));
}
#endif
// Date
rtc_bcd[DS1337_DATE] = binToBcd( tt - (GETMONTHDAYS(ii) + ((ISLEAP(thisYear) && ii >= 2) * 1)) );
// Serial.print( tt - (GETMONTHDAYS(ii) + ((ISLEAP(thisYear) && ii >= 2) * 1)) , DEC);
// SPrint(" ");
// Day of the week
rtc_bcd[DS1337_DOW] = ((tt)%7 + 1) & DS1337_LO_DOW;
// Serial.print(((tt)%7 + 1) & DS1337_LO_DOW, DEC);
// SPrint(" ");
// Hour
tt = (uint32_t)unixTimeStamp%86400 / 3600;
rtc_bcd[DS1337_HR] = binToBcd(tt);
// Serial.print(tt, DEC);
// SPrint(" ");
#if defined(RTC_DST_TYPE)
if (!correctedTime) {
uint8_t dstStartMo, dstStopMo, dstStart, dstStop;
uint8_t *dstStartMoPtr = &dstStartMo;
uint8_t *dstStopMoPtr = &dstStopMo;
uint8_t *dstStartPtr = &dstStart;
uint8_t *dstStopPtr = &dstStop;
#ifndef RTC_CHECK_OLD_DST
dstStart = DSTCALCULATION1(thisYear);
#if RTC_DST_TYPE == 1
dstStop = DSTCALCULATION1(thisYear); // EU DST
#else
dstStop = DSTCALCULATION2(thisYear); // US DST
#endif
dstStartMo = 3;
dstStopMo = 11;
#else
if (thisYear < RTC_DST_OLD_YEAR) {
dstStart = ((2+6 * thisYear - (thisYear / 4) ) % 7 + 1);
dstStop = (14 - ((1 + thisYear * 5 / 4) % 7));
dstStartMo = 4;
dstStopMo = 10;
} else {
dstStart = DSTCALCULATION1(thisYear)
#if RTC_DST_TYPE == 1
dstStop = DSTCALCULATION1(thisYear) // EU DST
#else
dstStop = DSTCALCULATION2(thisYear); // US DST
#endif
dstStartMo = 3;
dstStopMo = 11;
}
#endif
if (ii >= dstStartMo && ii <= dstStopMo)
{
if ( (ii < dstStopMo && (ii > dstStartMo || thisDate > dstStart || thisDate == dstStart && tt >= 2)) ||
(thisDate < dstStop || thisDate == dstStop && tt < 2) )
{
/**
* Free as much memory as possible before entering recursion
**/
free(tyPtr);
free(tdPtr);
free(dstStopPtr);
free(dstStartPtr);
free(dstStopMoPtr);
free(dstStartMoPtr);
clockSetWithUTS((uint32_t)unixTimeStamp + 3600, true);
return;
}
}
}
#endif
// Minutes
tt = (uint32_t)unixTimeStamp%3600 / 60;
rtc_bcd[DS1337_MIN] = binToBcd(tt);
// Serial.print(tt, DEC);
// SPrint(" ");
// Seconds
tt = ((uint32_t)unixTimeStamp%3600)%60;
rtc_bcd[DS1337_SEC] = binToBcd(tt);
// Serial.print(tt, DEC);
// SPrint(" ");
// Stop the clock
//clockStop(); // Uneeded with the ds1337
// Save buffer to the RTC
clockSave();
// Restart the oscillator
//clockStart(); // Uneeded with the ds1337
}
#endif
uint8_t DS1337::bcdToBin(uint8_t index, uint8_t hi)
{
return (10*((rtc_bcd[index] & hi)>>4))+(rtc_bcd[index] & DS1337_LO_BCD);
}
uint8_t DS1337::binToBcd(uint8_t val)
{
return ((((val)/10)<<4) + (val)%10);
}
/**
* Alarm support functions
**/
#ifdef DS1337_USE_ALARMS
void DS1337::alarmSelect(boolean alarm)
{
alarmId = alarm;
return;
}
void DS1337::alarmSet(uint8_t timeSection, uint8_t timeValue)
{
if (timeSection > DS1337_ALARM_DT) return;
if (alarmId == true) rtc_alarm[DS1337_SEC] = 0;
switch(timeSection)
{
case DS1337_SEC:
if(alarmId == false && timeValue<60)
{
rtc_alarm[DS1337_SEC] = binToBcd(timeValue) & ~DS1337_ALARM_MASK | (rtc_alarm[DS1337_SEC] & DS1337_ALARM_MASK);
}
break;
case DS1337_MIN:
if(timeValue < 60)
{
rtc_alarm[DS1337_MIN] = binToBcd(timeValue) & ~DS1337_ALARM_MASK | (rtc_alarm[DS1337_MIN] & DS1337_ALARM_MASK);
}
break;
case DS1337_HR:
if(timeValue < 24)
{
rtc_alarm[DS1337_HR] = binToBcd(timeValue) & ~DS1337_ALARM_MASK | (rtc_alarm[DS1337_HR] & DS1337_ALARM_MASK);
}
break;
case DS1337_DOW:
if(timeValue < 31)
{
rtc_alarm[DS1337_DOW] = binToBcd(timeValue) & ~DS1337_ALARM_MASK & ~DS1337_ALARM_DT_MASK | (rtc_alarm[DS1337_DOW] & DS1337_ALARM_MASK) | (rtc_alarm[DS1337_DOW] & DS1337_ALARM_DT_MASK);
}
break;
case DS1337_ALARM_MODE:
{
if (alarmId) {
timeValue = (timeValue>>1)<<1;
} else
rtc_alarm[DS1337_SEC] = (rtc_alarm[DS1337_SEC] & ~DS1337_ALARM_MASK) | DS1337_ALARM_MASK & timeValue<<7;
rtc_alarm[DS1337_MIN] = (rtc_alarm[DS1337_MIN] & ~DS1337_ALARM_MASK) | DS1337_ALARM_MASK & timeValue<<6;
rtc_alarm[DS1337_HR] = (rtc_alarm[DS1337_HR] & ~DS1337_ALARM_MASK) | DS1337_ALARM_MASK & timeValue<<5;
rtc_alarm[DS1337_DOW] = (rtc_alarm[DS1337_DOW] & ~DS1337_ALARM_MASK) | DS1337_ALARM_MASK & timeValue<<4;
if (timeValue == DS1337_ALARM_MCH_DOWHRMINSEC)
{
rtc_alarm[DS1337_DOW] = rtc_alarm[DS1337_DOW] & ~DS1337_ALARM_DT_MASK | DS1337_ALARM_DT_MASK;
}
}
break;
case DS1337_ALARM_DT:
{
rtc_alarm[DS1337_DOW] = rtc_alarm[DS1337_DOW] & ~DS1337_ALARM_DT_MASK | (timeValue == 1 ? DS1337_ALARM_DT_MASK : 0);
}
break;
} // end switch
alarmSave();
}
boolean DS1337::alarmCheck(boolean both)
{
if (!both) return alarmCheck();
bool res;
if (getRegisterBit(DS1337_STATUS, DS1337_STATUS_A2F))
{
res = true;
}
if (getRegisterBit(DS1337_STATUS, DS1337_STATUS_A1F))
{
unsetRegister(DS1337_STATUS, DS1337_STATUS_A1F);
unsetRegister(DS1337_STATUS, DS1337_STATUS_A2F);
res = true;
} else if (res) res = false;
return res;
}
boolean DS1337::alarmCheck(void)
{
if (getRegisterBit(DS1337_STATUS, (alarmId == false ? DS1337_STATUS_A1F : DS1337_STATUS_A2F)))
{
unsetRegister(DS1337_STATUS, (alarmId == false ? DS1337_STATUS_A1F : DS1337_STATUS_A2F));
return true;
}
return false;
}
void DS1337::alarmSave(void)
{
Wire.beginTransmission(DS1337_WADDR);
Wire.send((alarmId == false ? DS1337_ALARM1 : DS1337_ALARM2));
for(uint8_t i=(alarmId == false ? 0 : 1); i<4; i++)
{
Wire.send(rtc_alarm[i]);
}
Wire.endTransmission();
delay(5);
}
#endif
void DS1337::printRegisters(void)
{
for(int ii=0;ii<0x10;ii++)
{
SPrint("0x");
Serial.print(ii, HEX);
SPrint(" ");
Serial.println(getRegister(ii), BIN);
}
delay(200);
}

@ -0,0 +1,349 @@
/*
DS1337.h - library for DS1337 I2C Real Time Clock
*/
#ifndef DS1337_h
#define DS1337_h
// include types & constants of Wiring core API
#include <WConstants.h>
#include <inttypes.h>
// include types & constants of Wire ic2 lib
#include <Wire/Wire.h>
// Include global RTC configs
#include "../configs/RTC/rtcConfig.h"
// Ucomment this to enable setting the clock from a
// unix time stamp with gmt and dst correction
#define DS1337_USE_SET_UTS
// Uncomment this enable setting the clock using BCD
//#define DS1337_USE_BCD_CLOCKSET
// Uncomment this if you need to read back unix time stamp (without DTS correction)
//#define DS1337_USE_GET_UTS
// Uncomment this to support alarms
#define DS1337_USE_ALARMS
/**
* Define the position of the RTC buffer values
**/
#define DS1337_SEC 0
#define DS1337_MIN 1
#define DS1337_HR 2
#define DS1337_DOW 3
#define DS1337_DATE 4
#define DS1337_MTH 5
#define DS1337_YR 6
#define DS1337_CNTY 7
// For use externally
#define RTC_SEC DS1337_SEC
#define RTC_MIN DS1337_MIN
#define RTC_HR DS1337_HR
#define RTC_DOW DS1337_DOW
#define RTC_DATE DS1337_DATE
#define RTC_MTH DS1337_MTH
#define RTC_YR DS1337_YR
#define RTC_CNTY DS1337_CNTY
/**
* Define the DS1337 I2C addresses
**/
#define DS1337_WADDR 0x68
#define DS1337_RADDR DS1337_WADDR | 0x01
/**
* Define registers and bit masks
**/
#define DS1337_LO_BCD B00001111
#define DS1337_HI_BCD B01110000
#define DS1337_HI_SEC B01110000
#define DS1337_HI_MIN B01110000
#define DS1337_HI_HR B00110000
#define DS1337_LO_DOW B00000111
#define DS1337_HI_DATE B00110000
#define DS1337_HI_MTH B00010000
#define DS1337_LO_CNTY B10000000
#define DS1337_HI_YR B11110000
#define DS1337_ARLM1 0x07
#define DS1337_ARLM1_LO_SEC B00001111
#define DS1337_ARLM1_HI_SEC B01110000
#define DS1337_ARLM1_LO_MIN B01110000
#define DS1337_ARLM1_HI_MIN B00001111
#define DS1337_SP 0x0E
#define DS1337_SP_EOSC B10000000
#define DS1337_SP_RS2 B00010000
#define DS1337_SP_RS1 B00001000
#define DS1337_SP_INTCN B00000100
#define DS1337_SP_A2IE B00000010
#define DS1337_SP_A1IE B00000001
#define DS1337_STATUS 0x0F
#define DS1337_STATUS_OSF B10000000
#define DS1337_STATUS_A2F B00000010
#define DS1337_STATUS_A1F B00000001
// Alarm registers and masks
#define DS1337_ALARM1 0x07
#define DS1337_ALARM2 0x0B
#define DS1337_ALARM_DT_MASK B01000000
#define DS1337_ALARM_MASK B10000000
#define DS1337_ALARM_MODE 4
#define DS1337_ALARM_DT 5
#define DS1337_ALARM_DT_DOW true
#define DS1337_ALARM_DT_DATE false
#define DS1337_ALARM_PER_SEC B00001111
#define DS1337_ALARM_PER_MIN B00000111 /* Used for alarm 2 only*/
#define DS1337_ALARM_MCH_SEC B00001110 /* Used for alarm 1 only */
#define DS1337_ALARM_MCH_MINSEC B00001100
#define DS1337_ALARM_MCH_HRMINSEC B00001000 /* Used for alarm 1 only */
#define DS1337_ALARM_MCH_DATEHRMINSEC B00000000
#define DS1337_ALARM_MCH_DOWHRMINSEC B10000000
// Alarm mode masks
#define DS1337_ALARM2_MODE_MASK B00001000
#define DS1337_ALARM_M1 B00000001
#define DS1337_ALARM_M2 B00000010
#define DS1337_ALARM_M3 B00000100
#define DS1337_ALARM_M4 B00001000
/**
* Macros
**/
#define clockStart() unsetRegister(DS1337_SP, DS1337_SP_EOSC)
#define clockStop() setRegister(DS1337_SP, DS1337_SP_EOSC)
#define getRegisterSP() getRegisterSP(DS1337_SP)
#define getRegisterStatus() getRegisterStatus(DS1337_STATUS)
#define getRegisterBit(reg, bitMask) (getRegister(reg) & bitMask) && bitMask
#ifndef ISLEAP
#define ISLEAP(y) ((((y) % 4) == 0 && ((y) % 100) != 0) || ((y) % 400) == 0)
#endif
#ifndef BCDTOBIN
// This marco is for internal use only!
#define BCDTOBIN(index, hi) (10*((rtc_bcd[index] & hi)>>4))+(rtc_bcd[index] & DS1337_LO_BCD)
#endif
#ifndef BINTOBCD
#define BINTOBCD(val) ((((val)/10)<<4) + (val)%10)
#endif
/**
* getUTS: Macro for calculateUTS
* returns the time as a unix time stamp
* This function doesn't take into account having DST set or not!
**/
#ifdef DS1337_USE_GET_UTS
#define getUTS(refresh) calculateUTS( RTC.clockGet(DS1337_YR, true), RTC.clockGet(DS1337_MTH, false), \
RTC.clockGet(DS1337_DATE, false), RTC.clockGet(DS1337_HR, false), \
RTC.clockGet(DS1337_MIN, false), RTC.clockGet(DS1337_SEC, false) \
)
#endif
/**
* Use this macro to the time from a unix time stamp
**/
#if defined(DS1337_USE_SET_UTS)
#define clockSet(UTS) clockSetWithUTS(UTS, false)
#endif
/**
* Macros for getting time values without refreshing the RTC buffer
**/
#define clockGetSec() clockGet(DS1337_SEC, false)
#define clockGetMin() clockGet(DS1337_MIN, false)
#define clockGetHour() clockGet(DS1337_HR, false)
#define clockGetDate() clockGet(DS1337_DATE, false)
#define clockGetMonth() clockGet(DS1337_MTH, false)
#define clockGetDow() clockGet(DS1337_DOW, false)
/**
* Macros for getting time values refreshing the RTC buffer before each read.
**/
#define clockGetRSec() clockGet(DS1337_SEC, true)
#define clockGetRMin() clockGet(DS1337_MIN, true)
#define clockGetRHour() clockGet(DS1337_HR, true)
#define clockGetRDate() clockGet(DS1337_DATE, true)
#define clockGetRMonth() clockGet(DS1337_MTH, true)
#define clockGetRDow() clockGet(DS1337_DOW, true)
// library interface description
class DS1337
{
// user-accessible "public" interface
public:
/**
* clockExists: keeps track of the whether or not the RTC exists
**/
bool clockExists;
/**
* Class constructor
**/
DS1337();
/**
* Init: initializes the clock
* If the I2C scan mod is available, it'll verify the RTC is reachable
**/
int8_t Init(void);
/**
* checkClock: verifies the clock integrity
* Returns false when the integrity check fails
**/
boolean checkClock();
/**
* setRegister: sets a register bit fromt he register number and bitmask
**/
void setRegister(uint8_t, uint8_t);
/**
* unsetRegister: unsets a register bit fromt he register number and bitmask
**/
void unsetRegister(uint8_t, uint8_t);
/**
* getRegister: returns the specified register
**/
uint8_t getRegister(uint8_t);
/**
* clockGet: fills an array with the current time data
**/
void clockGet(uint16_t *);
/**
* clockGet: gets a specific item from the clock buffer
* use the second param to specify a buffer refresh
**/
uint16_t clockGet(uint8_t, boolean);
/**
* clockSet: Set the clock time using integer values
* Does not do any GMT or DST correction
**/
#ifdef DS1337_USE_BCD_CLOCKSET
void clockSet(uint8_t, uint16_t);
#endif
/**
* calculateUTS: returns the time as a unix time stamp
* This function doesn't take into account having DST set or not!
*
* Use the macro getUTS macro to access this function!
**/
#ifdef DS1337_USE_GET_UTS
uint32_t calculateUTS(uint16_t year, uint8_t month, uint8_t day, uint8_t hour, uint8_t min, uint8_t sec);
#endif
/**
* clockSetWithUTS: sets the date & time from a unix time stamp
* pass the second param as true to skip DTS and GMT calculation
*
* Use the clockSet macro to access this function!
**/
void clockSetWithUTS(uint32_t, boolean);
/**
* Prints all of the DS1337 registers
**/
void printRegisters(void);
#ifdef DS1337_USE_ALARMS
/**
* alarmSelect: allows selection of the DS1337 alarm 1 or 2
* false for alarm 1 and true for alarm 2
**/
void alarmSelect(boolean);
/**
* Allows setting an alarm's date and time using integers
**/
void alarmSet(uint8_t, uint8_t);
/**
* alarmCheck: checks if an alarm flag was set and reset the flag
* set param to true to check for both registers false (or void) to check for the selected alarm
**/
boolean alarmCheck(boolean);
boolean alarmCheck(void); // Same as above using false
#endif
private:
/**
* Hold a unix time stamp
**/
#if defined(DS1337_USE_SET_UTS) || defined(DS1337_USE_GET_UTS)
uint32_t tt;
#endif
/**
* Holds the RTC BCD time buffer
**/
uint8_t rtc_bcd[8];
/**
* Writes a value to a clock register
**/
void writeRegister(uint8_t, uint8_t);
/**
* Write the RTC BCD buffer to the clock
**/
void clockSave(void);
/**
* Read the RTC BCD buffer to the clock
**/
void clockRead(void);
/**
* Converts a BCD to a binary integer
**/
uint8_t bcdToBin(uint8_t, uint8_t);
/**
* Converts a binary integer to BCD
**/
uint8_t binToBcd(uint8_t);
#ifdef DS1337_USE_ALARMS
/**
* Hold the buffer for alarm manipulation
**/
uint8_t rtc_alarm[4];
/**
* alarmId: keeps track of which alarm we are working with
**/
boolean alarmId;
/**
* Writes the alarm buffer to the RTC
**/
void alarmSave(void);
#endif
};
/**
* Define the Object's name
**/
extern DS1337 RTC;
#endif

@ -0,0 +1,61 @@
extern "C" {
#include <Wire/Wire.h>
}
#include "../global.h"
#include "ds1624.h"
DS1624::DS1624()
{
#ifdef WIRE_LIB_SCAN_MOD
/*if (!Wire.isStarted())*/ Wire.begin();
#else
Wire.begin();
#endif
}
DS1624 TEMP = DS1624();
void DS1624::Init(void)
{
Wire.beginTransmission(DS1624_ADDR);
Wire.send(DS1624_CONFIG);
Wire.send(DS1624_CONFIGS);
Wire.endTransmission();
delay(10);
Wire.beginTransmission(DS1624_ADDR);
Wire.send(DS1624_CONFIG);
Wire.endTransmission();
Wire.requestFrom(DS1624_ADDR, 1);
Wire.beginTransmission(DS1624_ADDR);
Wire.send(DS1624_SMPL_START);
Wire.endTransmission();
#ifdef DS1624_HANDLE_BOOT_DELAY
delay(1500);
#endif
}
uint16_t DS1624::readTemp(void)
{
uint16_t res = 0;
Wire.beginTransmission(DS1624_ADDR);
Wire.send(DS1624_READ_TEMP);
Wire.endTransmission();
Wire.requestFrom(DS1624_ADDR, 2);
while (!Wire.available());
res = (uint8_t) (Wire.receive())<<8;
while (!Wire.available());
res |= (uint8_t) Wire.receive();
return res;
}

@ -0,0 +1,57 @@
#ifndef DS1624_H
#define DS1624_H
// include types & constants of Wiring core API
#include <WConstants.h>
#include <inttypes.h>
// include types & constants of Wire ic2 lib
#include <Wire/Wire.h>
/**
* Comment this out if you don't want the
* init function to account for the ~1S startup
* delay for the first temperature sample!
**/
#define DS1624_HANDLE_BOOT_DELAY
/**
* Address byte selection
* Select 0 for low and 1 for high
**/
#define DS1624_A0 0
#define DS1624_A1 0
#define DS1624_A2 0
#define DS1624_BASE_ADDR B01001000
#define DS1624_ADDR DS1624_BASE_ADDR | (DS1624_A0 * B00000001) | (DS1624_A1 * B00000010) | (DS1624_A2 * B00000100)
/**
* Registers and bit mask definition
**/
#define DS1624_CONFIG 0xAC
#define DS1624_CONFIG_DONE B10000000
#define DS1624_CONFIG_1SHOT B00000001
#define DS1624_CONFIG_CONT B00000000
// Select your config here!
#define DS1624_CONFIGS DS1624_CONFIG_CONT
#define DS1624_READ_TEMP 0xAA
#define DS1624_SMPL_START 0xEE
#define DS1624_SMPL_STOP 0x22
#define DS1624_ACCESS_MEM 0x17
class DS1624
{
public:
DS1624();
void Init(void);
uint16_t readTemp(void);
private:
};
extern DS1624 TEMP;
#endif

@ -0,0 +1,46 @@
extern "C" {
#include <Wire/Wire.h>
}
#include "../global.h"
#include "ds1803.h"
DS1803::DS1803()
{
#ifdef WIRE_LIB_SCAN_MOD
/*if (!Wire.isStarted())*/ Wire.begin();
#else
Wire.begin();
#endif
}
/**
* Instantiate the object
**/
DS1803 DPOT = DS1803();
void DS1803::setWiper(uint8_t value, uint8_t wiperAddr)
{
if (!Wire.checkAddress(DPOT_WADDR)) return;
Wire.beginTransmission(DPOT_WADDR);
Wire.send(wiperAddr); // Send the wiper address
Wire.send(value);
Wire.endTransmission();
}
/*
uint8_t DS1803::getValue()
{
if (!Wire.checkAddress(DPOT_WADDR)) return;
Wire.requestFrom(DPOT_RADDR, 2);
while (Wire.available()) {
Serial.println((uint8_t)Wire.receive(), DEC);
}
return 0;
}
*/

@ -0,0 +1,44 @@
#ifndef DS1803_H
#define DS1803_H
#include <inttypes.h>
#define DPOT_WADDR 0x28
#define DPOT_RADDR DPOT_WADDR | 0x01
/**
* The number of available potentiometer wipers
**/
#define DPOT_NBR_WIPERS 0x02
/**
* Digital pot selection commands
**/
#define DPOT_WIPERS B10101111
#define DPOT_WIPER_0 B10101001
#define DPOT_WIPER_1 B10101010
/**
* Macros
**/
#define setWiper1(value) setWiper(value, DPOT_WIPER_0)
#define setWiper2(value) setWiper(value, DPOT_WIPER_1)
#define setWipers(value) setWiper(value, DPOT_WIPERS)
/**
* DS1803 I2C Dual Digital Pot.
**/
class DS1803
{
public:
DS1803();
void setWiper(uint8_t, uint8_t);
//uint8_t getValue();
};
/**
* Define the object's name
**/
extern DS1803 DPOT;
#endif

@ -0,0 +1,45 @@
#ifndef GLOBAL_H
#define GLOBAL_H
extern "C" {
#include <avr/pgmspace.h>
#include <stdio.h>
#include <string.h>
#include <inttypes.h>
#include <stdlib.h>
#include "wiring.h"
#include "WConstants.h"
#include <HardwareSerial.h>
}
#include "staticPrint/staticPrint.h"
#ifndef BV
#define BV(bit) (1<<(bit))
#endif
#ifndef cbi
#define cbi(reg,bit) reg &= ~(BV(bit))
#endif
#ifndef sbi
#define sbi(reg,bit) reg |= (BV(bit))
#endif
#ifndef CI
#define CI(reg,bit) (reg & ~(bit))
#endif
#ifndef SI
#define SI(reg,bit) (reg | bit)
#endif
#ifndef cli
#define cli() __asm__ __volatile__ ("cli" ::)
#endif
#ifndef sei
#define sei() __asm__ __volatile__ ("sei" ::)
#endif
#endif

@ -0,0 +1,427 @@
extern "C" {
#include <Wire/Wire.h>
}
#include "../global.h"
#include "../configs/LCD/lcd.h"
#include "twiLCD.h"
#ifdef TWI_LCD_DPOT_CTRL
#include "../ds1803/ds1803.h"
#endif
twiLCD::twiLCD()
{
#if defined(__AVR_ATmega168__) && !defined(TWI_LCD_SMALL)
#if defined(TWI_LCD_CTRL) && !defined(TWI_LCD_BL_PWM)
backlightStatus = 0;
#endif
#ifdef TWI_LCD_BL_PWM
pinMode(TWI_LCD_BACKLIGHT, HIGH);
#endif
displayStatus = false;
#endif
#ifdef WIRE_LIB_SCAN_MOD
/*if (!Wire.isStarted())*/ Wire.begin();
#else
Wire.begin();
#endif
}
twiLCD LCD = twiLCD();
void twiLCD::Init() {
#ifdef TWI_LCD_CTRL
backlightOff();
#ifdef TWI_LCD_DPOT_CTRL
setBrightness(0);
#endif
#endif
delay(20);
/////////// 4 pin initialization
writeCommand(0x03); // function set: 4 pin initialization
delay(5);
writeCommand(0x03); // function set: 4 pin initialization
delay(1);
writeCommand(0x03); // function set: 4 pin initialization
delay(1);
writeCommand(0x02); // function set: 4 pin initialization
/////////// end of 4 pin initialization
writeCommand(LCD_FUNCTION_SET); // function set: 4-bit interface, 1 display lines, 5x7 font
writeCommand(LCD_ENTRY_MODE);
writeCommand(LCD_CURSOR);
clearScreen();
writeCommand(LCD_CLOSE_INIT);
#if defined(__AVR_ATmega168__) && !defined(TWI_LCD_SMALL)
#ifdef TWI_LCD_CTRL
#if defined(TWI_LCD_BL_PWM) || defined(TWI_LCD_DPOT_CTRL)
#ifdef TWI_LCD_DPOT_CTRL
setBrightness();
#endif
backlightOn(TWI_LCD_BL_LEVEL);
#else
backlightOn();
#endif
#endif
displayStatus = true;
#endif
}
boolean twiLCD::checkLCDBusy(void)
{
Wire.requestFrom(PCF8574_RADDR, 1);
while (!Wire.available());
return (Wire.receive() & TWI_LCD_BUSY ? true : false);
}
void twiLCD::writeCommand(uint8_t value)
{
int value1 = 0;
int control = 0; // stores RS and RW
#ifdef TWI_LCD_USE_TIMEOUT
previousMillis = millis();
#endif
control = value >> 8; // get the control signals RS and RW
control >>= 5; // shift the control signals to the left
Wire.beginTransmission(PCF8574_WADDR);
value1 = value;
cbi(value1, TWI_LCD_DATAL); // Turn off LByte
cbi(value1, TWI_LCD_RS);
cbi(value1, TWI_LCD_RW);
sendPulse(value1);
delay(1);
cbi(value, TWI_LCD_DATAH); // Turn off HByte
value <<= 4;
cbi(value, TWI_LCD_RS);
cbi(value, TWI_LCD_RW);
sendPulse(value);
Wire.endTransmission();
delay(1);
}
void twiLCD::writeData(uint8_t value)
{
int value1 = 0;
int control = 0; // stores RS and RW
// Wait for the LCD to be ready
#ifdef TWI_LCD_USE_TIMEOUT
previousMillis = millis();
#endif
control = value >> 8; // get the control signals RS and RW
control >>= 5; // shift the control signals to the left
value1 = value;
cbi(value1, TWI_LCD_DATAL); // Turn off LByte
sbi(value1, TWI_LCD_RS);
cbi(value1, TWI_LCD_RW);
while (checkLCDBusy());
Wire.beginTransmission(PCF8574_WADDR);
sendPulse(value1);
delay(1);
cbi(value, TWI_LCD_DATAH); // Turn off HByte
value <<= 4;
sbi(value, TWI_LCD_RS);
cbi(value, TWI_LCD_RW);
sendPulse(value);
Wire.endTransmission();
}
void twiLCD::sendPulse(int value)
{
cbi(value, TWI_LCD_ENABLE);
writeToPCF(value);
sbi(value, TWI_LCD_ENABLE);
writeToPCF(value);
cbi(value, TWI_LCD_ENABLE);
writeToPCF(value);
}
void twiLCD::writeToPCF(int value)
{
#if defined(TWI_LCD_CTRL) && !defined(TWI_LCD_BL_PWM)
if (backlightStatus)
sbi(value, TWI_LCD_BACKLIGHT);
else
cbi(value, TWI_LCD_BACKLIGHT);
Wire.send(value);
#else
Wire.send(value);
#endif
}
void twiLCD::clearScreen(void)
{
writeCommand(LCD_CLEAR);
delay(100);
#if defined(__AVR_ATmega168__) && !defined(TWI_LCD_SMALL)
currentLine = 1;
#endif
#ifdef LCD_USE_CLRSCREEN_CALLBACK
onClearScreen();
#endif
}
void twiLCD::printString_P(const char *data)
{
int ch;
for (;;) {
ch = pgm_read_byte( data++ );
if ( !ch ) return;
writeData(ch);
}
}
#if defined(__AVR_ATmega168__) && !defined(TWI_LCD_SMALL)
#ifdef TWI_LCD_USE_TIMEOUT
bool twiLCD::checkTimeout(void)
{
if (displayStatus && millis() - previousMillis > TWI_LCD_TIMEOUT) {
turnOff();
return true;
}
return false;
}
#endif
#ifdef TWI_LCD_CTRL
#ifdef TWI_LCD_BL_PWM
void twiLCD::backlightOn(void)
{
digitalWrite(TWI_LCD_BACKLIGHT, HIGH);
}
void twiLCD::backlightOn(uint8_t value)
{
analogWrite(TWI_LCD_BACKLIGHT, value);
}
void twiLCD::backlightOff(void)
{
digitalWrite(TWI_LCD_BACKLIGHT, LOW);
}
#else
#ifdef TWI_LCD_DPOT_CTRL
void twiLCD::backlightOn(void)
{
DPOT.setWiper2(TWI_LCD_BL_LEVEL);
}
void twiLCD::backlightOn(uint8_t value)
{
DPOT.setWiper2(value);
}
void twiLCD::backlightOff(void)
{
DPOT.setWiper2(0);
}
void twiLCD::setBrightness(void)
{
DPOT.setWiper1(TWI_LCD_DB_LEVEL);
}
void twiLCD::setBrightness(uint8_t value)
{
DPOT.setWiper1(value);
}
#else
void twiLCD::backlightOn(void)
{
int val = 0;
backlightStatus = 1;
sbi(val, TWI_LCD_BACKLIGHT);
Wire.beginTransmission(PCF8574_WADDR);
Wire.send(val);
Wire.endTransmission();
}
void twiLCD::backlightOff(void)
{
int val = 0;
backlightStatus = 0;
cbi(val, TWI_LCD_BACKLIGHT);
Wire.beginTransmission(PCF8574_WADDR);
Wire.send(val);
Wire.endTransmission();
}
#endif
#endif
#endif
void twiLCD::turnOff(void)
{
writeCommand(LCD_TURN_OFF);
#if defined(TWI_LCD_CTRL)
backlightOff();
#ifdef TWI_LCD_DPOT_CTRL
setBrightness(0);
#endif
#endif
displayStatus = false;
}
/**
* This function needs a rewrite
**/
void twiLCD::setCursor(int index)
{
//0-79, index for one line display, 8 bit mode
//0-39 and 64-103 for lines one and two of two line display, not implemented yet
int cmd = 128+index;
writeCommand(cmd);
}
/**
* This function needs a rewrite
**/
void twiLCD::moveToXY(uint8_t row, uint8_t column)
{
int position;
// Determine the new position
position = (row * 20) + column;
// Send the correct commands to the command register of the LCD
if(position < 20)
writeCommand(0x80 | position);
else if(position >= 20 && position < 40)
writeCommand(0x80 | (position % 20 + 0x40));
else if(position >= 41 && position < 60)
writeCommand(0x80 | (position % 40 + 0x14));
else if(position >= 20 && position < 40)
writeCommand(0x80 | (position % 60 + 0x54));
}
uint8_t twiLCD::getCurrentLine(void)
{
return currentLine;
}
void twiLCD::goToLine(uint8_t line)
{
if (line > LCD_ROWS) return;
moveToXY(line - 1, 0);
currentLine = line;
}
void twiLCD::goToNextLine(void)
{
if (currentLine+1 > LCD_ROWS) {
goToLine(1);
} else {
goToLine(currentLine+1);
}
}
void twiLCD::goHome(void)
{
writeCommand(LCD_GO_HOME); // set cursor position to zero
currentLine = 1;
}
void twiLCD::clearLine(void)
{
int ii;
moveToXY(currentLine-1, 0);
for (ii=0;ii<LCD_COLUMNS;ii++)
{
printString(" ");
}
moveToXY(currentLine-1, 0);
}
void twiLCD::shiftDisplayLeft(void)
{
writeCommand(LCD_SHIFT_LEFT);
}
void twiLCD::shiftDisplayRight(void)
{
writeCommand(LCD_SHIFT_RIGHT);
}
bool twiLCD::getCurrentStatus(void)
{
return displayStatus;
}
void twiLCD::printInteger(uint16_t integer, bool leadingZero)
{
uint8_t thousands = integer / 1000;
uint8_t hundreds = (integer - thousands*1000) / 100;
uint8_t tens = (integer - thousands*1000 - hundreds*100 ) / 10;
writeData(tens + 0x30);
uint8_t ones = (integer - thousands*1000 - hundreds*100 - tens*10);
writeData(ones + 0x30);
}
void twiLCD::printInteger(int16_t integer)
{
if (integer < 0) {
printString("-");
integer = 0 - integer;
}
// Break down the original number into the thousands, hundreds, tens,
// and ones places and then immediately write that value to the LCD
uint8_t thousands = integer / 1000;
if (thousands > 0) writeData(thousands + 0x30);
uint8_t hundreds = (integer - thousands*1000) / 100;
if (hundreds > 0 || thousands > 0)
writeData(hundreds + 0x30);
uint8_t tens = (integer - thousands*1000 - hundreds*100 ) / 10;
if (tens || hundreds > 0 || thousands > 0)
writeData(tens + 0x30);
uint8_t ones = (integer - thousands*1000 - hundreds*100 - tens*10);
writeData(ones + 0x30);
}
#endif

@ -0,0 +1,220 @@
#ifndef twiLCD_H
#define twiLCD_H
#include <inttypes.h>
#include "twiLCDConfig.h"
#define PCF8574_WADDR 0x20
#define PCF8574_RADDR PCF8574_WADDR | 0x01
#define TWI_LCD_RS 0 /* RS pin */
#define TWI_LCD_RW 1 /* RW pin */
#define TWI_LCD_ENABLE 2 /* Enable pin */
#ifdef TWI_LCD_CTRL
#ifdef TWI_LCD_BL_PWM
#define TWI_LCD_BACKLIGHT 9 /* This is an Arduino pin number! */
#else
#define TWI_LCD_BACKLIGHT 3 /* Backlight pin */
#endif
#endif
#define TWI_LCD_CONTROL B00000111 /* Mask for the 3 control bits (E, RS, RW) */
#define TWI_LCD_DATA B11110000 /* Mask for the 4 bit word */
#define TWI_LCD_DATAH B11110000
#define TWI_LCD_DATAL B00001111
#define TWI_LCD_BUSY B00001000
#ifndef printString
#define printString(str) printString_P(PSTR(str))
#endif
class twiLCD {
public:
/**
* Constructor: initializes this class
**/
twiLCD();
/**
* LCD Initilization method
**/
void Init();
/**
* writeData: write a byte of data to the LCD
* @param: value: the byte to write
**/
void writeData(uint8_t value);
/**
* clearScreen: clears the LCD and resets the cursor position to 0,0
**/
void clearScreen(void);
/**
* printString_P: prints a program string to the LCD
* To call this function, use the LCD.printString() macro!
**/
void printString_P(const char *data);
/**
* These function are only available on the mega168 for space reasons
**/
#if defined(__AVR_ATmega168__) && !defined(TWI_LCD_SMALL)
/**
* Methods for dealing with LCD timeout
* Returns true if the time is expired
**/
#ifdef TWI_LCD_USE_TIMEOUT
bool checkTimeout(void);
#endif
/**
* Backlight control functions
* Optionally enabled above
**/
#ifdef TWI_LCD_CTRL
/**
* backlightOn: Turn on the backlight at full brightness
**/
void backlightOn(void);
/**
* backlightOff: turn off the LCD backlight
**/
void backlightOff(void);
// PWM Backlight Control
#if defined(TWI_LCD_BL_PWM) || defined(TWI_LCD_DPOT_CTRL)
/**
* backlightOn: turns on the backlight with a specific brightness
**/
void backlightOn(uint8_t);
#endif
#ifdef TWI_LCD_DPOT_CTRL
/**
* setBrightness: sets the brightness level using a digital pot
* If no param is passed TWI_LCD_DB_LEVEL is used
**/
void setBrightness(void);
void setBrightness(uint8_t);
#endif
#endif
/**
* setCursor: set cursor a position "index"
**/
void setCursor(int);
/**
* moveToXY: moves the cursor to position (row,column)
**/
void moveToXY(uint8_t, uint8_t);
/**
* Turn off the LCD (will turn off the backlight if control is enabled)
**/
void turnOff(void);
/**
* goToLine: Allows to move at the beginning of a specific line
**/
void goToLine(uint8_t);
/**
* goToNextLine: goes to the next line, wraps arround at the end
**/
void goToNextLine(void);
/**
* goHome: goes to position (0,0)
**/
void goHome(void);
/**
* clearLine: clears the current line
**/
void clearLine(void);
/**
* shiftDisplayLeft: shift all lines of the display one position to the left
**/
void shiftDisplayLeft(void);
/**
* shiftDisplayRight: shift all lines of the display one position to the right
**/
void shiftDisplayRight(void);
/**
* getCurrentLine: returns the current line
**/
uint8_t getCurrentLine(void);
/**
* getCurrentStatus: returns whether the display is on or off
**/
bool getCurrentStatus(void);
/**
* printInteger: writes an interger as text on the lcd
* The second version is only good for intergers < 99 and will add a leading zero
**/
void printInteger(int16_t);
void printInteger(uint16_t integer, bool leadingZero);
#endif
private:
#if defined(__AVR_ATmega168__) && !defined(TWI_LCD_SMALL)
#ifdef TWI_LCD_USE_TIMEOUT
unsigned long previousMillis;
#endif
#if defined(TWI_LCD_CTRL) && !defined(TWI_LCD_BL_PWM)
/**
* backlightStatus: used to keep track of the backlight status
**/
uint8_t backlightStatus;
#endif
/**
* currentLine: keeps track of the current line
**/
uint8_t currentLine;
/**
* displayStatus: keeps track of whether the display is on or off
**/
bool displayStatus;
#endif
/**
* sendPulse: sends a byte of data with the appropiate Enable pulse
**/
void sendPulse(int);
/**
* writeToPCF: writes a new byte of data using twi
* This function is used to preserve some data through writes
* such as when bit3 of the expander is used to control the backlight
**/
void writeToPCF(int);
/**
* writeCommand: Writes an LCD command
* @param: value: the value to write
**/
void writeCommand(uint8_t value);
/**
* checkLCDBusy: reads the busy state bit from the LCD
**/
boolean checkLCDBusy(void);
};
/**
* Define the object's name
**/
extern twiLCD LCD;
#endif

@ -0,0 +1,42 @@
#ifndef TWI_LCD_CONF_H
#define TWI_LCD_CONF_H
// Uncomment this to use minimal mode (less functions, not as big)
// #define TWI_LCD_SMALL
#if defined(__AVR_ATmega168__) && !defined(TWI_LCD_SMALL)
// Uncomment this to enable use of a timeout after which the LCD turns off
#define TWI_LCD_USE_TIMEOUT
#ifdef TWI_LCD_USE_TIMEOUT
#define TWI_LCD_TIMEOUT 5000 /* In milliseconds (30 sec) */
#endif
// Uncomment this to enable control of the backlight on pin 3
#define TWI_LCD_CTRL
#ifdef TWI_LCD_CTRL
// Uncomment this to use PWM for backlight control.
//#define TWI_LCD_BL_PWM
#ifdef TWI_LCD_BL_PWM
// Set this to the default brightness for PWM controlled backlight
#define TWI_LCD_BL_LEVEL 255
#endif
#ifndef TWI_LCD_BL_PWM
// Uncomment this use the DS1803 digi-pot for display/backlight brightness
#define TWI_LCD_DPOT_CTRL
#ifdef TWI_LCD_DPOT_CTRL
// Set this to the default value of the backlight (0 to 254)
#define TWI_LCD_BL_LEVEL 254
// Set this to the default value of the display brightness (0 to 254)
#define TWI_LCD_DB_LEVEL 225
#endif
#endif
#endif
#endif
#endif
Loading…
Cancel
Save