Priliminary
Dependencies: DS1307 MAX17048 MODSERIAL SSD1308_128x64_I2C mbed-rpc mbed
Fork of ECGAFE_copy by
Revision 0:ee0649a9025a, committed 2015-09-30
- Comitter:
- zainulcharbiwala
- Date:
- Wed Sep 30 11:30:56 2015 +0000
- Commit message:
- Priliminary
Changed in this revision
diff -r 000000000000 -r ee0649a9025a ADS1298.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/ADS1298.cpp Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,250 @@ +#include "ADS1298.h" + + +ADS1298::ADS1298(PinName mosi, + PinName miso, + PinName sck, + PinName csn, + PinName reset, + PinName drdy, + PinName start) : spi_(mosi, miso, sck), cs_(csn), reset_(reset), drdy_(drdy), start_(start) { +} + +void ADS1298::sendCommand(uint8_t cmd) +{ + // Select the device by seting chip select low + cs_ = 0; + wait_us(TCSSC); + + // Send SDATAC, as device comes up in RDATAC + spi_.write(cmd); + wait_us(TCMD); + + // Deselect the device + wait_us(TSCCS); + cs_ = 1; + // Wait between commands + wait_us(TCSH); +} + +void ADS1298::writeRegister(uint8_t reg, uint8_t val) +{ + // Select the device by seting chip select low + cs_ = 0; + wait_us(TCSSC); + + // Write register address + spi_.write(WREG|reg); + wait_us(TCMD); + + // Writing one register + spi_.write(0x00); + wait_us(TCMD); + + // Write the value + spi_.write(val); + wait_us(TCMD); + + // Deselect the device + wait_us(TSCCS); + cs_ = 1; + + // Wait between commands + wait_us(TCSH); +} + +uint8_t ADS1298::readRegister(uint8_t reg) +{ + uint8_t res; + // Select the device by seting chip select low + cs_ = 0; + wait_us(TCSSC); + + // Write register address + spi_.write(RREG|reg); + wait_us(TCMD); + + // Reading one register + spi_.write(0x00); + wait_us(TCMD); + + // Write a dummy value to read the register + res = spi_.write(0x00); + wait_us(TCMD); + + // Deselect the device + wait_us(TSCCS); + cs_ = 1; + + // Wait between commands + wait_us(TCSH); + return res; +} + +void ADS1298::readData(uint8_t *data) +{ + // Select the device by seting chip select low + cs_ = 0; + wait_us(TCSSC); + + for (int i=0; i<27; i++) { + // Write a dummy value to read the register + *(data+i) = spi_.write(0x00); + } + wait_us(TCMD); + + // Deselect the device + wait_us(TSCCS); + cs_ = 1; + + // Wait between commands + wait_us(TCSH); +} + +void ADS1298::initialize(void (*dataReady)(void)) +{ + // Initialize signals + cs_ = 1; + start_ = 0; + reset_ = 1; + drdy_.fall(dataReady); + + // Set up SPI + spi_.format(8,1); + // Choosing 1MHz arbitrarily for now + spi_.frequency(1000000); + + + // Power on reset + wait_us(TPOR); + + // Reset the device + reset_ = 0; + wait_us(TRST); + reset_ = 1; + wait_us(TRST2); + + // Send SDATAC, as device comes up in RDATAC + sendCommand(SDATAC); + + //pc.printf("ID = 0x%02X\r\n", readRegister(ID)); + //pc.printf("CONFIG1 = 0x%02X\r\n", readRegister(CONFIG1)); + //pc.printf("CONFIG2 = 0x%02X\r\n", readRegister(CONFIG2)); + //pc.printf("CONFIG3 = 0x%02X\r\n", readRegister(CONFIG3)); + + // Turn on internal reference and wait for it to settle + writeRegister(CONFIG3, CONFIG3_DEFAULT | CONFIG3_PD_REFBUF); + wait_us(TINTREF); + //pc.printf("CONFIG3 = 0x%02X\r\n", readRegister(CONFIG3)); + + /* + // Set up device + writeRegister(CONFIG1, CONFIG1_HR | CONFIG1_DR2 | CONFIG1_DR1); + pc.printf("CONFIG1 = 0x%02X\r\n", readRegister(CONFIG1)); + writeRegister(CONFIG2, CONFIG2_DEFAULT); + pc.printf("CONFIG2 = 0x%02X\r\n", readRegister(CONFIG2)); + + // Input short on all channels + writeRegister(CH1SET, CHNSET_MUXN0); + writeRegister(CH2SET, CHNSET_MUXN0); + writeRegister(CH3SET, CHNSET_MUXN0); + writeRegister(CH4SET, CHNSET_MUXN0); + writeRegister(CH5SET, CHNSET_MUXN0); + writeRegister(CH6SET, CHNSET_MUXN0); + writeRegister(CH7SET, CHNSET_MUXN0); + writeRegister(CH8SET, CHNSET_MUXN0); + pc.printf("CH1SET = 0x%02X\r\n", readRegister(CH1SET)); + pc.printf("CH2SET = 0x%02X\r\n", readRegister(CH2SET)); + pc.printf("CH3SET = 0x%02X\r\n", readRegister(CH3SET)); + pc.printf("CH4SET = 0x%02X\r\n", readRegister(CH4SET)); + pc.printf("CH5SET = 0x%02X\r\n", readRegister(CH5SET)); + pc.printf("CH6SET = 0x%02X\r\n", readRegister(CH6SET)); + pc.printf("CH7SET = 0x%02X\r\n", readRegister(CH7SET)); + pc.printf("CH8SET = 0x%02X\r\n", readRegister(CH8SET)); + */ + + /* + // Set up device + writeRegister(CONFIG1, CONFIG1_HR | CONFIG1_DR2 | CONFIG1_DR1); + writeRegister(CONFIG2, CONFIG2_DEFAULT | CONFIG2_INTTEST); + + // Input test on all channels + writeRegister(CH1SET, CHNSET_MUXN2 | CHNSET_MUXN0); + writeRegister(CH2SET, CHNSET_MUXN2 | CHNSET_MUXN0); + writeRegister(CH3SET, CHNSET_MUXN2 | CHNSET_MUXN0); + writeRegister(CH4SET, CHNSET_MUXN2 | CHNSET_MUXN0); + writeRegister(CH5SET, CHNSET_MUXN2 | CHNSET_MUXN0); + writeRegister(CH6SET, CHNSET_MUXN2 | CHNSET_MUXN0); + writeRegister(CH7SET, CHNSET_MUXN2 | CHNSET_MUXN0); + writeRegister(CH8SET, CHNSET_MUXN2 | CHNSET_MUXN0); + */ + + // Set up device + writeRegister(CONFIG1, CONFIG1_HR | CONFIG1_DR2 | CONFIG1_DR1); + writeRegister(CONFIG2, CONFIG2_DEFAULT); + writeRegister(CONFIG3, CONFIG3_DEFAULT | CONFIG3_PD_REFBUF | + CONFIG3_RLDREF_INT | CONFIG3_PD_RLD); + writeRegister(CONFIG4, CONFIG4_PD_LOFF_COMP); + writeRegister(LOFF, LOFF_VLEAD_OFF_EN | LOFF_FLEAD_OFF1 | LOFF_FLEAD_OFF0); + writeRegister(LOFF_SENSP, 0xFF); // for V6, LA, LL, V2, V3, V4, V5, V1 + writeRegister(LOFF_SENSN, 0x02); // for RA only + writeRegister(RLD_SENSP, 0x06); // for LA, LL + writeRegister(RLD_SENSN, 0x02); // for RA + writeRegister(WCT1, WCT1_PD_WCTA | WCT1_WCTA1); // WCTA to CH2P = LA + writeRegister(WCT2, WCT2_PD_WCTC | WCT2_PD_WCTB | + WCT2_WCTB2 | WCT2_WCTC1 | + WCT2_WCTC0); // WCTB to CH3P = LL, WCTC to CH2N = RA + + // Input test on all channels + writeRegister(CH1SET, CHNSET_DEFAULT); + writeRegister(CH2SET, CHNSET_DEFAULT); + writeRegister(CH3SET, CHNSET_DEFAULT); + writeRegister(CH4SET, CHNSET_DEFAULT); + writeRegister(CH5SET, CHNSET_DEFAULT); + writeRegister(CH6SET, CHNSET_DEFAULT); + writeRegister(CH7SET, CHNSET_DEFAULT); + writeRegister(CH8SET, CHNSET_DEFAULT); + +} + +void ADS1298::startCapture() { + //Start conversion + start_ = 1; + + // Send RDATAC to start data collection + sendCommand(RDATAC); +} + +void ADS1298::stopCapture() { + //Stop conversion + start_ = 0; + + // Send SDATAC to stop data collection + sendCommand(SDATAC); +} + +int ADS1298::updateLeadOff(uint8_t *buf) { + + // Buffer contains 9 fields of 24 bits each + // First field contains an identifier and the status bits + // First nibble of first byte is always 0b1100 + // Second nibble of third byte is always 0x00 because GPIO are not used + if ((buf[0] & 0xf0) != 0xc0 || (buf[2] & 0x0f) != 0x00) + return -1; + + // Second nibble of first byte has IN8P_OFF (V1), IN7P_OFF (V5), IN6P_OFF (V4), IN5P_OFF (V3) + lOff_ = 0; + lOff_ |= (buf[0] & 0x08) ? (1 << LOFFV1) : 0; + lOff_ |= (buf[0] & 0x04) ? (1 << LOFFV5) : 0; + lOff_ |= (buf[0] & 0x02) ? (1 << LOFFV4) : 0; + lOff_ |= (buf[0] & 0x01) ? (1 << LOFFV3) : 0; + // First nibble of second byte has IN4P_OFF (V2), IN3P_OFF (LL), IN2P_OFF (LA), IN1P_OFF (V6) + lOff_ |= (buf[1] & 0x80) ? (1 << LOFFV2) : 0; + lOff_ |= (buf[1] & 0x40) ? (1 << LOFFLL) : 0; + lOff_ |= (buf[1] & 0x20) ? (1 << LOFFLA) : 0; + lOff_ |= (buf[1] & 0x10) ? (1 << LOFFV6) : 0; + // First nibble of third byte has IN2N_OFF (RA) + lOff_ |= (buf[2] & 0x20) ? (1 << LOFFRA) : 0; + + return 0; +} \ No newline at end of file
diff -r 000000000000 -r ee0649a9025a ADS1298.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/ADS1298.h Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,221 @@ +// Copyright 2013, Zainul Charbiwala + +#ifndef _ADS1298_h_ +#define _ADS1298_h_ + +#include "mbed.h" + +#define TCSSC 1 // 6 ns +#define TSCCS 2 // 4 TCLKs +#define TPOR 32768 // 2^16 TCLKs +#define TRST 1 // 2 TCLKs +#define TRST2 9 // 18 TCLKs +#define TINTREF 150000 // 150ms +#define TCMD 2 // 4 TCLKs +#define TCSH 1 // 2 TCLKs + +#define RDATA 0x12 +#define RDATAC 0x10 +#define SDATAC 0x11 +#define WREG 0x40 +#define RREG 0x20 + +#define ID 0x00 +#define CONFIG1 0x01 +#define CONFIG2 0x02 +#define CONFIG3 0x03 +#define LOFF 0x04 +#define CH1SET 0x05 +#define CH2SET 0x06 +#define CH3SET 0x07 +#define CH4SET 0x08 +#define CH5SET 0x09 +#define CH6SET 0x0A +#define CH7SET 0x0B +#define CH8SET 0x0C +#define RLD_SENSP 0x0D +#define RLD_SENSN 0x0E +#define LOFF_SENSP 0x0F +#define LOFF_SENSN 0x10 +#define LOFF_FLIP 0x11 +#define LOFF_STATP 0x12 +#define LOFF_STATN 0x13 +#define GPIO 0x14 +#define PACE 0x15 +#define RESP 0x16 +#define CONFIG4 0x17 +#define WCT1 0x18 +#define WCT2 0x19 + + +#define CONFIG1_HR 0x80 +#define CONFIG1_DAISYEN 0x40 +#define CONFIG1_CLKEN 0x20 +#define CONFIG1_DR2 0x04 +#define CONFIG1_DR1 0x02 +#define CONFIG1_DR0 0x01 + +#define CONFIG2_WCTCHOP 0x20 +#define CONFIG2_INTTEST 0x10 +#define CONFIG2_TESTAMP 0x04 +#define CONFIG2_TESTFREQ1 0x02 +#define CONFIG2_TESTFREQ0 0x01 +#define CONFIG2_DEFAULT 0x00 + +#define CONFIG3_PD_REFBUF 0x80 +#define CONFIG3_VREF_4V 0x20 +#define CONFIG3_RLD_MEAS 0x10 +#define CONFIG3_RLDREF_INT 0x08 +#define CONFIG3_PD_RLD 0x04 +#define CONFIG3_RLD_LOFF_SENS 0x02 +#define CONFIG3_RLD_STAT 0x01 +#define CONFIG3_DEFAULT 0x40 + +#define LOFF_COMP_TH2 0x80 +#define LOFF_COMP_TH1 0x40 +#define LOFF_COMP_TH0 0x20 +#define LOFF_VLEAD_OFF_EN 0x10 +#define LOFF_ILEAD_OFF1 0x08 +#define LOFF_ILEAD_OFF0 0x04 +#define LOFF_FLEAD_OFF1 0x02 +#define LOFF_FLEAD_OFF0 0x01 + +#define CHNSET_PD 0x80 +#define CHNSET_GAIN2 0x40 +#define CHNSET_GAIN1 0x20 +#define CHNSET_GAIN0 0x10 +#define CHNSET_MUXN2 0x04 +#define CHNSET_MUXN1 0x02 +#define CHNSET_MUXN0 0x01 +#define CHNSET_DEFAULT 0x00 + +#define GPIO_GPIOD4 0x80 +#define GPIO_GPIOD3 0x40 +#define GPIO_GPIOD2 0x20 +#define GPIO_GPIOD1 0x10 +#define GPIO_GPIOC4 0x08 +#define GPIO_GPIOC3 0x04 +#define GPIO_GPIOC2 0x02 +#define GPIO_GPIOC1 0x01 + +#define PACE_PACEE1 0x10 +#define PACE_PACEE0 0x08 +#define PACE_PACEO1 0x04 +#define PACE_PACEO0 0x02 +#define PACE_PD_PACE 0x01 + +#define RESP_DEMOD_EN1 0x80 +#define RESP_MOD_EN1 0x40 +#define RESP_DEFAULT 0x20 +#define RESP_PH2 0x10 +#define RESP_PH1 0x08 +#define RESP_PH0 0x04 +#define RESP_CTRL1 0x02 +#define RESP_CTRL0 0x01 + +#define CONFIG4_RESP_FREQ2 0x80 +#define CONFIG4_RESP_FREQ1 0x40 +#define CONFIG4_RESP_FREQ0 0x20 +#define CONFIG4_SINGLE_SHOT 0x08 +#define CONFIG4_WCT_TO_RLD 0x04 +#define CONFIG4_PD_LOFF_COMP 0x02 + +#define WCT1_AVF_CH6 0x80 +#define WCT1_AVL_CH5 0x40 +#define WCT1_AVR_CH7 0x20 +#define WCT1_AVR_CH4 0x10 +#define WCT1_PD_WCTA 0x08 +#define WCT1_WCTA2 0x04 +#define WCT1_WCTA1 0x02 +#define WCT1_WCTA0 0x01 + +#define WCT2_PD_WCTC 0x80 +#define WCT2_PD_WCTB 0x40 +#define WCT2_WCTB2 0x20 +#define WCT2_WCTB1 0x10 +#define WCT2_WCTB0 0x08 +#define WCT2_WCTC2 0x04 +#define WCT2_WCTC1 0x02 +#define WCT2_WCTC0 0x01 + +// Bit positions of the lead off status bits +#define LOFFRA 15 +#define LOFFLA 14 +#define LOFFLL 13 +#define LOFFRL 12 +#define LOFFV1 11 +#define LOFFV2 10 +#define LOFFV3 9 +#define LOFFV4 8 +#define LOFFV5 7 +#define LOFFV6 6 + +/** Class to control an ADS1298 AFE + * + * Example: + * @code + * + * @endcode + */ +class ADS1298 { + public: + + /** + * @brief Constructor + * @param mosi mbed pin to use for MOSI line of SPI interface. + * @param miso mbed pin to use for MISO line of SPI interface. + * @param sck mbed pin to use for SCK line of SPI interface. + * @param csn mbed pin to use for not chip select line of SPI interface. + * @param reset mbed pin to use for the reset line. + * @param drdy mbed pin to use for the data ready line. + * @param start mbed pin to use for the start conversion line. + */ + ADS1298(PinName mosi, PinName miso, PinName sck, PinName csn, PinName reset, PinName drdy, PinName start); + + +// High Level methods + + /** + * @brief High level Init, most settings remain at Power-On reset value + */ + void initialize(void (*dataready)(void)); + + /** + * @brief Start capturing data + */ + void startCapture(); + + /** + * @brief Stop capturing data + */ + void stopCapture(); + + /** + * @brief Read data from the ADS1298 + */ + void readData(uint8_t *buf); + + /** + * @brief Update the lead off status + */ + int updateLeadOff(uint8_t *buf); + + private: + + SPI spi_; // mosi, miso, sclk + DigitalOut cs_; + DigitalOut reset_; + InterruptIn drdy_; + DigitalOut start_; + uint16_t lOff_; + +// Low Level methods + void sendCommand(uint8_t cmd); + void writeRegister(uint8_t reg, uint8_t val); + uint8_t readRegister(uint8_t reg); + +}; + + + +#endif \ No newline at end of file
diff -r 000000000000 -r ee0649a9025a DS1307.lib --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/DS1307.lib Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/harrypowers/code/DS1307/#c3e4da8feb10
diff -r 000000000000 -r ee0649a9025a DebouncedIn.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/DebouncedIn.cpp Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,96 @@ +#include "DebouncedIn.h" +#include "mbed.h" + +/* + * Constructor + */ +DebouncedIn::DebouncedIn(PinName in) + : _in(in) { + + // reset all the flags and counters + _samples = 0; + _output = 0; + _output_last = 0; + _releasing_flag = 0; + _pressing_flag = 0; + _press_counter = 0; + + // Switch is assumed to go to ground + _in.mode(PullUp); + + // Attach ticker + _ticker.attach(this, &DebouncedIn::_sample, 0.005); +} + +void DebouncedIn::_sample() { + + // take a sample + _samples = _samples >> 1; // shift left + + if (_in) { + _samples |= 0x80; + } + + // examine the sample window, look for steady state + if (_samples == 0x00) { + _output = 0; + } + else if (_samples == 0xFF) { + _output = 1; + } + + + // Release detection + if ((_output == 1) && (_output_last == 0)) { + _releasing_flag++; + } + + // Press detection + else if ((_output == 0) && (_output_last == 1)) { + _pressing_flag++; + _press_counter = 0; + } + + // pressed state + else if (_output == 0) { + _press_counter++; + } + + // update the output + _output_last = _output; + + //printf("%d %d\n", _press_counter, _releasing_flag); +} + + + +// return number of releasing events +int DebouncedIn::releasing(void) { + int return_value = _releasing_flag; + _releasing_flag = 0; + return(return_value); +} + +// return number of pressing events +int DebouncedIn::pressing(void) { + int return_value = _pressing_flag; + _pressing_flag = 0; + return(return_value); +} + +// return number of ticks we've bene steady for +int DebouncedIn::pressed(void) { +return(_press_counter); +} + +// return the debounced status +int DebouncedIn::read(void) { + return(_output); +} + +// shorthand for read() +DebouncedIn::operator int() { + return read(); +} + +
diff -r 000000000000 -r ee0649a9025a DebouncedIn.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/DebouncedIn.h Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,31 @@ +#include "mbed.h" + + class DebouncedIn { + public: + DebouncedIn(PinName in); + + int read (void); + operator int(); + + int releasing(void); + int pressing(void); + int pressed(void); + + private : + // objects + DigitalIn _in; + Ticker _ticker; + + // function to take a sample, and update flags + void _sample(void); + + // counters and flags + int _samples; + int _output; + int _output_last; + int _releasing_flag; + int _pressing_flag; + int _press_counter; + + }; + \ No newline at end of file
diff -r 000000000000 -r ee0649a9025a MAX17048.lib --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/MAX17048.lib Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/neilt6/code/MAX17048/#e61b2723d2cf
diff -r 000000000000 -r ee0649a9025a MODSERIAL.lib --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/MODSERIAL.lib Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/AjK/code/MODSERIAL/#ae0408ebdd68
diff -r 000000000000 -r ee0649a9025a SSD1308_128x64_I2C.lib --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/SSD1308_128x64_I2C.lib Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/wim/code/SSD1308_128x64_I2C/#fa18169dd7e6
diff -r 000000000000 -r ee0649a9025a WatchDog.lib --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/WatchDog.lib Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,1 @@ +https://mbed.org/users/Lerche/code/WatchDog/#a6661a79bf7b
diff -r 000000000000 -r ee0649a9025a main.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/main.cpp Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,306 @@ +// Copyright 2013, Zainul Charbiwala + +/* Includes */ +#include "mbed.h" +#include "ADS1298.h" +#include "SSD1308.h" +#include "ds1307.h" +#include "MAX17048.h" +#include "WatchDog.h" +#include "oledicons.h" +#include "mbed_rpc.h" +#include "DebouncedIn.h" +#include "MODSERIAL.h" + +/* mbed Objects */ +DigitalOut myled(LED1); +DigitalOut lWatchdog(LED4); +WatchDog_ms wdt(10000); +Ticker wdtTicker; +MODSERIAL pc(USBTX, USBRX); +Timer tt; +I2C i2c(p28, p27); // sda, scl +SSD1308 oled = SSD1308(i2c, SSD1308_SA0); +ADS1298 ads = ADS1298(p5, p6, p7, p24, p23, p22, p21); //mosi, miso, sclk, cs, reset, drdy, start +DS1307 rtc(p28,p27); // start DS1307 class and give it pins for connections of the DS1307 device +MAX17048 gauge(p28, p27); +DigitalIn battChging(p14); +DebouncedIn button(p20); + +/* Constants */ +#define OLEDPAGEMAX 14 +// Page 0 for general use +// Page 1-12 for signals +// Page 13 for network status +// Page 14 for something else + +/* Global Variables */ +uint8_t buf[27]; +char rpcInBuf[256], rpcOutBuf[256]; +int vCapturing; + +static char oledstr[16]; +static int vOledPage; + +/* External Functions */ + +/* Local Functions */ +static void dataReady(void); +static void wdtKicker(); +static void oledBattery(uint8_t percentage, uint8_t charging); +static void oledNetwork(uint8_t percentage, const char *mode); +static void oledTime(); +static void fCaptureStart(Arguments *arg, Reply *r); +static void fCaptureStop(Arguments *arg, Reply *r); +static void fButtonLongPress(); +static void fButtonShortPress(); +static void fOledPage0(); +static void fOledPageSignal(); +static void fOledPageNetwork(); +static void fOledPageSomethingElse(); + + +/* RPC Variables */ +RPCVariable<int> rpc_vCapturing(&vCapturing, "vCapturing"); + +/* RPC Functions */ +RPCFunction rpc_fCaptureStart(&fCaptureStart, "fCaptureStart"); +RPCFunction rpc_fCaptureStop(&fCaptureStop, "fCaptureStop"); + + +static void wdtKicker() { + wdt.feed(); +} + +static void fCaptureStart(Arguments *arg, Reply *r){ + vCapturing = 1; + ads.startCapture(); + oled.writeString(7, 0, "Capture started."); +} + +static void fCaptureStop(Arguments *arg, Reply *r){ + vCapturing = 0; + ads.stopCapture(); + oled.writeString(7, 0, "Capture stopped."); +} + +static void fOledPage0() { + oled.writeString(5, 0, " HR: xxx bpm "); + oled.writeString(6, 0, " LO: "); + + sprintf(oledstr, "Display Page: %02d", vOledPage); + oled.writeString(7, 0, oledstr); + +} + +static void fOledPageSignal() { + sprintf(oledstr, "Display Page: %02d", vOledPage); + oled.writeString(7, 0, oledstr); + +} + +static void fOledPageNetwork() { + sprintf(oledstr, "Display Page: %02d", vOledPage); + oled.writeString(7, 0, oledstr); + +} + +static void fOledPageSomethingElse() { + sprintf(oledstr, "Display Page: %02d", vOledPage); + oled.writeString(7, 0, oledstr); + +} + +static void fButtonShortPress() +{ + // Scroll to the next page of the oled display + vOledPage++; + if (vOledPage > OLEDPAGEMAX) { + vOledPage = 0; + } + if (vOledPage == 0) { + fOledPage0(); + } + if (vOledPage >= 1 && vOledPage <= 12) { + fOledPageSignal(); + } + if (vOledPage == 13) { + fOledPageNetwork(); + } + if (vOledPage == 0) { + fOledPageSomethingElse(); + } +} + +static void fButtonLongPress() +{ + // If in capture mode, stop capture + // If not in capture mode, start capture + if (vCapturing) { + oled.writeString(7, 0, "Capture Stopping"); + fCaptureStop(NULL, NULL); + } else { + oled.writeString(7, 0, "Capture Starting"); + fCaptureStart(NULL, NULL); + } +} + + +static void oledBattery(uint8_t percentage, uint8_t charging) +{ + // Hardcoded a 24 column, 1 page high battery meter icon + // It has 18 columns that can be set + uint8_t battimg[24]; + uint8_t i; + percentage=(percentage>100?100:percentage); + memcpy((uint8_t *)battimg, (uint8_t *)iconBattery, 24); + for (i=2; i<2+(18*percentage)/100; i++) { + battimg[i] |= 0x3C; + } + + if (charging) { + for (i=0; i<20; i++) { + battimg[i+2] ^= iconBattChg[i]; + } + } + oled.writeBitmap((uint8_t*) battimg, 0, 0, 104, 127); +} + +static void oledNetwork(uint8_t percentage, const char *mode) +{ + // Hardcoded a 16 column, 1 page high network meter icon + // It has 6 columns that can be set + uint8_t netwimg[16]; + percentage=(percentage>100?100:percentage); + memcpy((uint8_t *)netwimg, (uint8_t *)iconNetwork, 16); + + if (percentage > 0) + netwimg[1] = 0xF0; + if (percentage > 16) + netwimg[2] = 0xF0; + if (percentage > 33) + netwimg[6] = 0xFC; + if (percentage > 49) + netwimg[7] = 0xFC; + if (percentage > 66) + netwimg[11] = 0xFF; + if (percentage > 83) + netwimg[12] = 0xFF; + + oled.writeBitmap((uint8_t*) netwimg, 0, 0, 0, 15); + oled.writeString(0, 2, mode); +} + +static void oledTime() +{ + int sec = 0, min = 0, hours = 0; + int day = 0, date = 0, month = 0, year = 0; + int ret = 0; + + char timestr[7]; + ret = rtc.gettime( &sec, &min, &hours, &day, &date, &month, &year); + if (ret == 0) { + if (hours == 0) { + sprintf(timestr, "%02d:%02da", hours+12, min); + } else if (hours == 12) { + sprintf(timestr, "%02d:%02dp", hours, min); + } else if (hours>12) { + sprintf(timestr, "%02d:%02dp", hours-12, min); + } else { + sprintf(timestr, "%02d:%02da", hours, min); + } + oled.writeString(0, 5, timestr); + } else { + oled.writeString(0, 5, "00:00!"); + } + +} + +static void fSetTime() +{ +} + +void dataReady() +{ + ads.readData(buf); + ads.updateLeadOff(buf); + + if (vCapturing) { + // Send it to the serial port + // How much time does this take ? + // We have 2ms until the next interrupt comes + //pc.printf("\r\n%d", tt.read_ms()); + for (int i=0; i<27; i++) { + //if (!(i%3)) pc.printf(" "); + //pc.printf("%02x", buf[i]); + pc.putc(buf[i]); + } + } + myled = !myled; +} + + + +int main() { + uint8_t lev=0; + char ch; + + vOledPage = 0; + vCapturing = 0; + i2c.frequency(400000); // according to the spec the max bitrate for the SSD1308 is 400 kbit/s + battChging.mode(PullUp); + pc.baud(921600); + pc.printf("starting\r\n"); + + wdtTicker.attach(&wdtKicker, 5); + + myled=1; + oled.setDisplayOn(); + oled.writeString(7, 0, "Initializing... "); + ads.initialize(&dataReady); + if (!gauge.open()) { + oled.writeString(7, 0, "Gauge Error !!!"); + wait(5); + } + + fCaptureStart(NULL, NULL); + + while(1) { + wait(0.1); + + // Check if there's a command over RPC + if (pc.readable()) { + pc.gets(rpcInBuf, 256); + RPC::call(rpcInBuf, rpcOutBuf); + //pc.printf("%s", rpcOutBuf); + } + + // Check if there's a user event + if (button.releasing()) { + // Short press + if (button.pressed() < 50) { + fButtonShortPress(); + } + // Long press + if (button.pressed() > 100) { + fButtonLongPress(); + } + } + + // Update battery status icon + oledBattery(gauge.socInt(), !battChging); + // Update time + oledTime(); + // Update network + if (++lev > 100) lev = 0; + oledNetwork(lev, "H"); + + //Print the current state of charge + sprintf(oledstr, "VCell = %.2fV\n", gauge.vcell()); + oled.writeString(3, 0, oledstr); + + //myled = !myled; + } + + +}
diff -r 000000000000 -r ee0649a9025a mbed-rpc.lib --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/mbed-rpc.lib Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/mbed_official/code/mbed-rpc/#4490a0d9cb2a
diff -r 000000000000 -r ee0649a9025a mbed.bld --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/mbed.bld Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/mbed_official/code/mbed/builds/f37f3b9c9f0b \ No newline at end of file
diff -r 000000000000 -r ee0649a9025a oledicons.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/oledicons.h Wed Sep 30 11:30:56 2015 +0000 @@ -0,0 +1,26 @@ +#ifndef _oledicons_h_ +#define _oledicons_h_ + +const uint8_t iconNetwork[] = { + 0xF0, 0x90, 0x90, 0xF0, + 0x00, 0xFC, 0x84, 0x84, + 0xFC, 0x00, 0xFF, 0x81, + 0x81, 0xFF, 0x00, 0x00 +}; +const uint8_t iconBattery[] = { + 0x7E, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, + 0x81, 0x7E, 0x3C, 0x3C +}; +const uint8_t iconBattChg[] = { + 0x00, 0x00, 0x00, 0x00, + 0x00, 0x08, 0x10, 0x10, + 0x20, 0x30, 0x0C, 0x04, + 0x04, 0x08, 0x08, 0x00, + 0x00, 0x00, 0x00, 0x00 +}; + +#endif \ No newline at end of file