m

Fork of MAX30100 by Eduardo Avelar

Committer:
arturogasca
Date:
Sat Dec 03 11:43:35 2016 +0000
Revision:
1:e3b9aff8f221
Parent:
0:010b908e2187
max30100

Who changed what in which revision?

UserRevisionLine numberNew contents of line
AVELARDEV 0:010b908e2187 1 /*
AVELARDEV 0:010b908e2187 2 Arduino-MAX30100 oximetry / heart rate integrated sensor library
AVELARDEV 0:010b908e2187 3 Copyright (C) 2016 OXullo Intersecans <x@brainrapers.org>
AVELARDEV 0:010b908e2187 4 This program is free software: you can redistribute it and/or modify
AVELARDEV 0:010b908e2187 5 it under the terms of the GNU General Public License as published by
AVELARDEV 0:010b908e2187 6 the Free Software Foundation, either version 3 of the License, or
AVELARDEV 0:010b908e2187 7 (at your option) any later version.
AVELARDEV 0:010b908e2187 8 This program is distributed in the hope that it will be useful,
AVELARDEV 0:010b908e2187 9 but WITHOUT ANY WARRANTY; without even the implied warranty of
AVELARDEV 0:010b908e2187 10 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
AVELARDEV 0:010b908e2187 11 GNU General Public License for more details.
AVELARDEV 0:010b908e2187 12 You should have received a copy of the GNU General Public License
AVELARDEV 0:010b908e2187 13 along with this program. If not, see <http://www.gnu.org/licenses/>.
AVELARDEV 0:010b908e2187 14 */
AVELARDEV 0:010b908e2187 15
AVELARDEV 0:010b908e2187 16 #include "MAX30100.h"
arturogasca 1:e3b9aff8f221 17 #define I2C_SDA p7
arturogasca 1:e3b9aff8f221 18 #define I2C_SCL p6
arturogasca 1:e3b9aff8f221 19
AVELARDEV 0:010b908e2187 20
AVELARDEV 0:010b908e2187 21 I2C Wire(I2C_SDA , I2C_SCL );
arturogasca 1:e3b9aff8f221 22 //I2C Wire(P0_1, P0_2); //sda scl
AVELARDEV 0:010b908e2187 23
AVELARDEV 0:010b908e2187 24 MAX30100::MAX30100()
AVELARDEV 0:010b908e2187 25 {
AVELARDEV 0:010b908e2187 26
AVELARDEV 0:010b908e2187 27 }
AVELARDEV 0:010b908e2187 28
AVELARDEV 0:010b908e2187 29 bool MAX30100::begin()
AVELARDEV 0:010b908e2187 30 {
AVELARDEV 0:010b908e2187 31 // Wire.begin();
AVELARDEV 0:010b908e2187 32 // Wire.setClock(I2C_BUS_SPEED);
AVELARDEV 0:010b908e2187 33
AVELARDEV 0:010b908e2187 34 Wire.frequency(I2C_BUS_SPEED);
AVELARDEV 0:010b908e2187 35
AVELARDEV 0:010b908e2187 36 if(!setMode(DEFAULT_MODE))
AVELARDEV 0:010b908e2187 37 return false;
AVELARDEV 0:010b908e2187 38 if(!setLedsPulseWidth(DEFAULT_PULSE_WIDTH))
AVELARDEV 0:010b908e2187 39 return false;
AVELARDEV 0:010b908e2187 40 if(!setSamplingRate(DEFAULT_SAMPLING_RATE))
AVELARDEV 0:010b908e2187 41 return false;
AVELARDEV 0:010b908e2187 42 if(!setLedsCurrent(DEFAULT_IR_LED_CURRENT, DEFAULT_RED_LED_CURRENT))
AVELARDEV 0:010b908e2187 43 return false;
AVELARDEV 0:010b908e2187 44 if(!setHighresModeEnabled(true))
AVELARDEV 0:010b908e2187 45 return false;
AVELARDEV 0:010b908e2187 46
AVELARDEV 0:010b908e2187 47 return true;
AVELARDEV 0:010b908e2187 48 }
AVELARDEV 0:010b908e2187 49
AVELARDEV 0:010b908e2187 50 bool MAX30100::setMode(Mode mode)
AVELARDEV 0:010b908e2187 51 {
AVELARDEV 0:010b908e2187 52 if(!writeRegister(MAX30100_REG_MODE_CONFIGURATION, mode))
AVELARDEV 0:010b908e2187 53 return false;
AVELARDEV 0:010b908e2187 54 else
AVELARDEV 0:010b908e2187 55 return true;
AVELARDEV 0:010b908e2187 56 }
AVELARDEV 0:010b908e2187 57
AVELARDEV 0:010b908e2187 58 bool MAX30100::setLedsPulseWidth(LEDPulseWidth ledPulseWidth)
AVELARDEV 0:010b908e2187 59 {
AVELARDEV 0:010b908e2187 60 uint8_t previous;
AVELARDEV 0:010b908e2187 61 if(readRegister(MAX30100_REG_SPO2_CONFIGURATION, &previous))
AVELARDEV 0:010b908e2187 62 if(!writeRegister(MAX30100_REG_SPO2_CONFIGURATION, (previous & 0xfc) | ledPulseWidth))
AVELARDEV 0:010b908e2187 63 return false;
AVELARDEV 0:010b908e2187 64 else
AVELARDEV 0:010b908e2187 65 return true;
AVELARDEV 0:010b908e2187 66 else
AVELARDEV 0:010b908e2187 67 return false;
AVELARDEV 0:010b908e2187 68 }
AVELARDEV 0:010b908e2187 69
AVELARDEV 0:010b908e2187 70 bool MAX30100::setSamplingRate(SamplingRate samplingRate)
AVELARDEV 0:010b908e2187 71 {
AVELARDEV 0:010b908e2187 72 uint8_t previous;
AVELARDEV 0:010b908e2187 73 if(readRegister(MAX30100_REG_SPO2_CONFIGURATION, &previous))
AVELARDEV 0:010b908e2187 74 if(!writeRegister(MAX30100_REG_SPO2_CONFIGURATION, (previous & 0xe3) | (samplingRate << 2)))
AVELARDEV 0:010b908e2187 75 return false;
AVELARDEV 0:010b908e2187 76 else
AVELARDEV 0:010b908e2187 77 return true;
AVELARDEV 0:010b908e2187 78 else
AVELARDEV 0:010b908e2187 79 return false;
AVELARDEV 0:010b908e2187 80 }
AVELARDEV 0:010b908e2187 81
AVELARDEV 0:010b908e2187 82 bool MAX30100::setLedsCurrent(LEDCurrent irLedCurrent, LEDCurrent redLedCurrent)
AVELARDEV 0:010b908e2187 83 {
AVELARDEV 0:010b908e2187 84 if(!writeRegister(MAX30100_REG_LED_CONFIGURATION, redLedCurrent << 4 | irLedCurrent))
AVELARDEV 0:010b908e2187 85 return false;
AVELARDEV 0:010b908e2187 86 else
AVELARDEV 0:010b908e2187 87 return true;
AVELARDEV 0:010b908e2187 88 }
AVELARDEV 0:010b908e2187 89
AVELARDEV 0:010b908e2187 90 bool MAX30100::setHighresModeEnabled(bool enabled)
AVELARDEV 0:010b908e2187 91 {
AVELARDEV 0:010b908e2187 92 uint8_t previous;
AVELARDEV 0:010b908e2187 93 if(readRegister(MAX30100_REG_SPO2_CONFIGURATION, &previous))
AVELARDEV 0:010b908e2187 94 if (enabled) {
AVELARDEV 0:010b908e2187 95 if(!writeRegister(MAX30100_REG_SPO2_CONFIGURATION, previous | MAX30100_SPC_SPO2_HI_RES_EN))
AVELARDEV 0:010b908e2187 96 return false;
AVELARDEV 0:010b908e2187 97 else
AVELARDEV 0:010b908e2187 98 return true;
AVELARDEV 0:010b908e2187 99 } else {
AVELARDEV 0:010b908e2187 100 if(!writeRegister(MAX30100_REG_SPO2_CONFIGURATION, previous & ~MAX30100_SPC_SPO2_HI_RES_EN))
AVELARDEV 0:010b908e2187 101 return false;
AVELARDEV 0:010b908e2187 102 else
AVELARDEV 0:010b908e2187 103 return true;
AVELARDEV 0:010b908e2187 104 }
AVELARDEV 0:010b908e2187 105 else
AVELARDEV 0:010b908e2187 106 return false;
AVELARDEV 0:010b908e2187 107 }
AVELARDEV 0:010b908e2187 108
AVELARDEV 0:010b908e2187 109
AVELARDEV 0:010b908e2187 110 bool MAX30100::update()
AVELARDEV 0:010b908e2187 111 {
AVELARDEV 0:010b908e2187 112 if(!readFifoData())
AVELARDEV 0:010b908e2187 113 return false;
AVELARDEV 0:010b908e2187 114 else
AVELARDEV 0:010b908e2187 115 return true;
AVELARDEV 0:010b908e2187 116 }
AVELARDEV 0:010b908e2187 117
AVELARDEV 0:010b908e2187 118
AVELARDEV 0:010b908e2187 119 /*
AVELARDEV 0:010b908e2187 120 uint8_t MAX30100::readRegister(uint8_t address)
AVELARDEV 0:010b908e2187 121 {
AVELARDEV 0:010b908e2187 122 Wire.beginTransmission(MAX30100_I2C_ADDRESS);
AVELARDEV 0:010b908e2187 123 Wire.write(address);
AVELARDEV 0:010b908e2187 124 Wire.endTransmission(false);
AVELARDEV 0:010b908e2187 125 Wire.requestFrom(MAX30100_I2C_ADDRESS, 1);
AVELARDEV 0:010b908e2187 126
AVELARDEV 0:010b908e2187 127 return Wire.read();
AVELARDEV 0:010b908e2187 128 }
AVELARDEV 0:010b908e2187 129 */
AVELARDEV 0:010b908e2187 130
AVELARDEV 0:010b908e2187 131 bool MAX30100::readRegister(uint8_t uch_addr, uint8_t *puch_data)
AVELARDEV 0:010b908e2187 132 /**
AVELARDEV 0:010b908e2187 133 * \brief Read a MAX30102 register
AVELARDEV 0:010b908e2187 134 * \par Details
AVELARDEV 0:010b908e2187 135 * This function reads a MAX30102 register
AVELARDEV 0:010b908e2187 136 *
AVELARDEV 0:010b908e2187 137 * \param[in] uch_addr - register address
AVELARDEV 0:010b908e2187 138 * \param[out] puch_data - pointer that stores the register data
AVELARDEV 0:010b908e2187 139 *
AVELARDEV 0:010b908e2187 140 * \retval true on success
AVELARDEV 0:010b908e2187 141 */
AVELARDEV 0:010b908e2187 142 {
AVELARDEV 0:010b908e2187 143 char ch_i2c_data;
AVELARDEV 0:010b908e2187 144 ch_i2c_data=uch_addr;
AVELARDEV 0:010b908e2187 145 if(Wire.write(I2C_WRITE_ADDR, &ch_i2c_data, 1, true)!=0)
AVELARDEV 0:010b908e2187 146 return false;
AVELARDEV 0:010b908e2187 147 if(Wire.read(I2C_READ_ADDR, &ch_i2c_data, 1, false)==0)
AVELARDEV 0:010b908e2187 148 {
AVELARDEV 0:010b908e2187 149 *puch_data=(uint8_t) ch_i2c_data;
AVELARDEV 0:010b908e2187 150 return true;
AVELARDEV 0:010b908e2187 151 }
AVELARDEV 0:010b908e2187 152 else
AVELARDEV 0:010b908e2187 153 return false;
AVELARDEV 0:010b908e2187 154 }
AVELARDEV 0:010b908e2187 155
AVELARDEV 0:010b908e2187 156 /*
AVELARDEV 0:010b908e2187 157 void MAX30100::writeRegister(uint8_t address, uint8_t data)
AVELARDEV 0:010b908e2187 158 {
AVELARDEV 0:010b908e2187 159 Wire.beginTransmission(MAX30100_I2C_ADDRESS);
AVELARDEV 0:010b908e2187 160 Wire.write(address);
AVELARDEV 0:010b908e2187 161 Wire.write(data);
AVELARDEV 0:010b908e2187 162 Wire.endTransmission();
AVELARDEV 0:010b908e2187 163 }
AVELARDEV 0:010b908e2187 164 */
AVELARDEV 0:010b908e2187 165
AVELARDEV 0:010b908e2187 166 bool MAX30100::writeRegister(uint8_t uch_addr, uint8_t uch_data)
AVELARDEV 0:010b908e2187 167 /**
AVELARDEV 0:010b908e2187 168 * \brief Write a value to a MAX30102 register
AVELARDEV 0:010b908e2187 169 * \par Details
AVELARDEV 0:010b908e2187 170 * This function writes a value to a MAX30102 register
AVELARDEV 0:010b908e2187 171 *
AVELARDEV 0:010b908e2187 172 * \param[in] uch_addr - register address
AVELARDEV 0:010b908e2187 173 * \param[in] uch_data - register data
AVELARDEV 0:010b908e2187 174 *
AVELARDEV 0:010b908e2187 175 * \retval true on success
AVELARDEV 0:010b908e2187 176 */
AVELARDEV 0:010b908e2187 177 {
AVELARDEV 0:010b908e2187 178 char ach_i2c_data[2];
AVELARDEV 0:010b908e2187 179 ach_i2c_data[0]=uch_addr;
AVELARDEV 0:010b908e2187 180 ach_i2c_data[1]=uch_data;
AVELARDEV 0:010b908e2187 181
AVELARDEV 0:010b908e2187 182 if(Wire.write(I2C_WRITE_ADDR, ach_i2c_data, 2, false)==0)
AVELARDEV 0:010b908e2187 183 return true;
AVELARDEV 0:010b908e2187 184 else
AVELARDEV 0:010b908e2187 185 return false;
AVELARDEV 0:010b908e2187 186 }
AVELARDEV 0:010b908e2187 187
AVELARDEV 0:010b908e2187 188 bool MAX30100::readFifoData()
AVELARDEV 0:010b908e2187 189 {
AVELARDEV 0:010b908e2187 190 char ach_i2c_data[4];
AVELARDEV 0:010b908e2187 191
AVELARDEV 0:010b908e2187 192 ach_i2c_data[0]=MAX30100_REG_FIFO_DATA;
AVELARDEV 0:010b908e2187 193 if(Wire.write(I2C_WRITE_ADDR, ach_i2c_data, 1, true)!=0)
AVELARDEV 0:010b908e2187 194 return false;
AVELARDEV 0:010b908e2187 195 if(Wire.read(I2C_READ_ADDR, ach_i2c_data, 4, false)!=0)
AVELARDEV 0:010b908e2187 196 return false;
AVELARDEV 0:010b908e2187 197
AVELARDEV 0:010b908e2187 198 // Warning: the values are always left-aligned
AVELARDEV 0:010b908e2187 199 rawIRValue = (ach_i2c_data[0] << 8) | ach_i2c_data[1];
AVELARDEV 0:010b908e2187 200 rawRedValue = (ach_i2c_data[2] << 8) | ach_i2c_data[3];
AVELARDEV 0:010b908e2187 201
AVELARDEV 0:010b908e2187 202 return true;
AVELARDEV 0:010b908e2187 203 }