MAX44008 RGB Color, Infrared, and Temperature Sensor
Dependents: test_MAX44008 testSensor
MAX44008.cpp
- Committer:
- Rhyme
- Date:
- 2016-12-07
- Revision:
- 2:e4631b2273f8
- Parent:
- 1:45b23a5fff8e
File content as of revision 2:e4631b2273f8:
/** * MAX44008 RGB Color, Infrared, * and Temperature Sensor * I2C 7bit address: 0x40 (A0 = 1) 0x41 (A0 = 0) */ #include "mbed.h" #include "MAX44008.h" /* STATUS */ #define REG_INT_STATUS 0x00 /* CONFIGURATION */ #define REG_MAIN_CONFIG 0x01 #define REG_AMB_CONFIG 0x02 /* AMBIENT READING */ #define REG_AMB_CLR_MSB 0x04 #define REG_AMB_CLR_LSB 0x05 #define REG_AMB_RED_MSB 0x06 #define REG_AMB_RED_LSB 0x07 #define REG_AMB_GRN_MSB 0x08 #define REG_AMB_GRN_LSB 0x09 #define REG_AMB_BLU_MSB 0x0A #define REG_AMB_BLU_LSB 0x0B #define REG_AMB_IR_MSB 0x0C #define REG_AMB_IR_LSB 0x0D #define REG_AMB_IRCMP_MSB 0x0E #define REG_AMB_IRCMP_LSB 0x0F #define REG_TMP_MSB 0x12 #define REG_TMP_LSB 0x13 /* Interrupt Thresholds */ #define REG_AMB_UPTHR_MSB 0x14 #define REG_AMB_UPTHR_LSB 0x15 #define REG_AMB_LOTHR_MSB 0x16 #define REG_AMB_LOTHR_LSB 0x17 #define REG_AMB_PST 0x18 /* Ambient ADC Gains */ #define REG_TRIM_GAIN_CLR 0x1D #define REG_TRIM_GAIN_RED 0x1E #define REG_TRIM_GAIN_GRN 0x1F #define REG_TRIM_GAIN_BLU 0x20 #define REG_TRIM_GAIN_IR 0x21 #if 0 /* Operation Mode */ #define MODE_CLEAR 0x00 #define MODE_CLEAR_IR 0x01 #define MODE_CLEAR_RGB_IR 0x02 /* Ambient Interrupt Select */ #define AMB_INT_CLEAR 0x00 #define AMB_INT_GREEN 0x01 #define AMB_INT_IR 0x02 #define AMB_INT_TEMP 0x03 #endif MAX44008::MAX44008(PinName sda, PinName scl, int addr) : m_i2c(sda, scl), m_addr(addr<<1) { // activate the peripheral } MAX44008::~MAX44008() { } void MAX44008::readRegs(int addr, uint8_t *data, int len) { int i ; char t[1] = {addr} ; for (i = 0 ; i < len ; i++) { t[0] = addr + i ; m_i2c.write(m_addr, t, 1, true) ; m_i2c.read(m_addr, (char *)(&data[i]), 1) ; } } void MAX44008::writeRegs(uint8_t *data, int len) { m_i2c.write(m_addr, (char *)data, len) ; } /** * REGISTER: Interrupt Status * Bit7: - * Bit6: - * Bit5: - * Bit4: RESET : Reset Control * 0 : The part is in normal operation. * 1 : The part undergoes a forced POR sequence. * All configuration, threshold, and data registers are * reset to a power-on state by writing a 1 to this bit, * and an internal hardware reset pulse is generated. * This bit then automatically becomes 0 after the RESET sequence is completed. * After resettign, the PWRON interrupt is triggered. * Bit3: SHDN : Shutdown Control * 0 : The part is in normal operatin. * When the part returns from shutdown, note that the value in data registers * is not current until the first conversion cycle is completed. * 1 : The part can be put into a power-save mode by writing a 1 to this bit. * Supply current is reduced to approximately 0.5uA with no I2C clock activity. * While all registers remain accessible and retain data, ADC conversion data * contained in them may not be current. Writeable registers also remain * accessible in shutdown. All interrupts are cleared. * Bit2: PWRON : Power-On INTERRUPT STATUS Flag * 0 : Normal operating mode. * 1 : The part went through a power-up event, either because the part was turned on, * or because there was a power-supply voltage glitch. * All interrupt threshold settings in the registers have been reset to power-on * default states, and should be examined if nccessary. The /INT pin is also pulled low. * Once this bit is set, the only way to clear this bit is to read this register. * Bit1: - * Bit0: AMBINTS : Ambient INTERRUPT STATUS Flag * 0 : No interrupt trigger ever has occurred. * 1 : The ambient light has exceeded the designated window limits defined * by the threshold registers for longer than persist timer count AMBPST[1:0]. * It also causes the /INT pin to be pulled low. Once set, * the only way to clear this bit is to read this register. * This bit is always set to 0 if AMBINTE bit is set to 0. */ uint8_t MAX44008::getIntStatus(void) { uint8_t value = 0 ; readRegs(REG_INT_STATUS, &value, 1) ; return( value ) ; } void MAX44008::setIntStatus(uint8_t newValue) { uint8_t val[2] ; val[0] = REG_INT_STATUS ; val[1] = newValue ; writeRegs(val, 2) ; } /** * REGISTER: Main Configuration * Bit7: - * Bit6: - * Bit5: MODE[1] * Bit4: MODE[0] * 00 : Clear : CLEAR + TEMP(*) channels active * 01 : Clear + IR : CLEAR + TEMP(*) + IR channels active * 10 : Clear + RGB + IR : CLEAR + TEMP(*) + RGB + IR channels active * (*) When TEMPEN set to 1. * Bit3: AMBSEL[1] : Ambient Interrupt Select * Bit2: AMBSEL[0] : Ambient Interrupt Select * 00 : CLEAR channel data is used to compare with ambient interrupt thresholds and ambient timer settings. 01 : GREEN channel data is used to compare with ambinet interrupt thresholds and ambient timer settings. 10 : IR channel data is used to compare with ambient interrupt thresholds and ambient timer settings. 11 : TEMP channel data is used to compare with ambinet interrupt thresholds and ambinet timer settings. * Bit1: - * Bit0: AMBINTE : Ambient Interrupt Enable * 0 : The AMBINTS bit and /INT pin remain unasserted even if an ambient interrupt event has occurred. * The AMBINTS bit is set to 0 if previously set to 1. * 1 : Detection of ambient interrupt is enabled (see the AMBINTS bit for more details). * An ambient interrupt can trigger a hardware interrupt (/INT pin pullued low) * and set AMBINTS bit (register 0x00, BIT0) */ uint8_t MAX44008::getMainConfig(void) { uint8_t value = 0 ; readRegs(REG_MAIN_CONFIG, &value, 1) ; return( value ) ; } void MAX44008::setMainConfig(uint8_t newConfig) { uint8_t val[2] ; val[0] = REG_MAIN_CONFIG ; val[1] = newConfig ; writeRegs(val, 2) ; } /** * REGISTER: Ambient Configuration * Bit7: TRIM * 0 : Use factory-programmed gains for all the channels. * Ignore any bytes written to TRIM_GAIN_GREEN[6:0], * TRIM_GAIN_RED[6:0], TRIM_GAIN_BLUE[6:0], TRIM_GAIN_CLEAR[6:0], * and TRIM_GAIN_IR[6:0] registers. * 1 : Use bytes written to TRIM_GAIN_GREEN[6:0], TRIM_GAIN_RED[6:0], * TRIM_GAIN_BLUE[6:0], TRIM_GAIN_CLEAR[6:0], * and TRIM_GAIN_IR[6:0] registers to set the gain for each channel. * Bit6: COMPEN * 0 : Disables IR compensation. * 1 : Enables IR compensation. * Only for MODE[1:0] = 00 Mode. * The integration time of compensation channel is controlled by the AMB mode settings. * The compensation is enabled only when the clear channel is on. * When COMPEN = 1, the CLEAR data is automatically compensated * for stray IR leakeds and temperature variations. * When COMPEN = 0, the IR compensation is disabled, * but the output of the IR compensation data exits. * Bit5: TEMPEN * 0 : Disables temperature sensor. * 1 : Enables temperature sensor. * The integration time of temperature sensor is controlled by the ambient mode settings. * The temperature sensor is enabled only if the clear channel is on. * Bit4: AMBTIM[2] * Bit3: AMBTIM[1] * Bit2: AMBTIM[0] * | Integration Time | Full-scale ADC | Bit Resolution | Relative LSB Size | * | (ms) | (counts) | | for fixed AMPGA[1:0] | * 000 : 100 | 16,384 | 14 | 1x | * 001 : 25 | 4,096 | 12 | 4x | * 010 : 6.25 | 1,024 | 10 | 16x | * 011 : 1.5625 | 256 | 8 | 64x | * 100 : 400 | 16,384 | 14 | 1/4x | * 101 : Reserved | Not applicable | Not applicable | Not applicable | * 110 : Reserved | Not applicable | Not applicable | Not applicable | * 111 : Reserved | Not applicable | Not applicable | Not applicable | * Bit1: AMBPGA[1] * Bit0: AMBPGA[0] * In AMBTIM[2:0] = 000 Mode (100ms integraation time) * | CLEAR/RED/GREEN/IR | BLUE | * | nW/cm^2 per LSB | Full-scale (nW/cm^2) | nW/cm^2 per LSB | Full-scale (nW/cm^2) | * 00 : 2 | 32.768 | 4 | 65.536 | * 01 : 8 | 131.072 | 16 | 262.144 | * 10 : 32 | 524.288 | 64 | 1048.573 | * 11 : 512 | 8388.61 | 1024 | 16777.2 | * In AMBTIM[2:0] = 100 Mode (400ms integration time) * | CLEAR/RED/GREEN/IR | BLUE | * | nW/cm^2 per LSB | Full-scale (nW/cm^2) | nW/cm^2 per LSB | Full-scale (nW/cm^2) | * 00 : 0.5 | 8.192 | 1 | 16.384 | * 01 : 2 | 32.768 | 4 | 65.536 | * 10 : 8 | 131.072 | 16 | 262.1433 | * 11 : 128 | 2097.153 | 256 | 4194.3 | */ uint8_t MAX44008::getAMB_Config(void) { uint8_t value = 0 ; readRegs(REG_AMB_CONFIG, &value, 1) ; return( value ) ; } void MAX44008::setAMB_Config(uint8_t newConfig) { uint8_t val[2] ; val[0] = REG_AMB_CONFIG ; val[1] = newConfig ; writeRegs(val, 2) ; } int16_t MAX44008::getAMB_CLEAR(void) { int16_t value; uint8_t res[2]; readRegs(REG_AMB_CLR_MSB, res, 2) ; value = (res[0] << 8)+res[1] ; return( value ) ; } int16_t MAX44008::getAMB_RED(void) { int16_t value; uint8_t res[2]; readRegs(REG_AMB_RED_MSB, res, 2) ; value = (res[0] << 8)+res[1] ; return( value ) ; } int16_t MAX44008::getAMB_GREEN(void) { int16_t value; uint8_t res[2]; readRegs(REG_AMB_GRN_MSB, res, 2) ; value = (res[0] << 8)+res[1] ; return( value ) ; } int16_t MAX44008::getAMB_BLUE(void) { int16_t value; uint8_t res[2]; readRegs(REG_AMB_BLU_MSB, res, 2) ; value = (res[0] << 8)+res[1] ; return( value ) ; } int16_t MAX44008::getIR(void) { int16_t value; uint8_t res[2]; readRegs(REG_AMB_IR_MSB, res, 2) ; value = (res[0] << 8)+res[1] ; return( value ) ; } int16_t MAX44008::getIRCOMP(void) { int16_t value; uint8_t res[2]; readRegs(REG_AMB_IRCMP_MSB, res, 2) ; value = (res[0] << 8)+res[1] ; return( value ) ; } int16_t MAX44008::getTEMP(void) { int16_t value; uint8_t res[2]; readRegs(REG_TMP_MSB, res, 2) ; value = (res[0] << 8)+res[1] ; return( value ) ; } int16_t MAX44008::getAMB_UPTHR(void) { uint16_t value ; uint8_t res[2] ; readRegs(REG_AMB_UPTHR_MSB, res, 2) ; value = (res[0] << 8) | res[1] ; return( value ) ; } void MAX44008::setAMB_UPTHR(int16_t newTHR) { uint8_t res[3] ; res[0] = REG_AMB_UPTHR_MSB ; res[1] = (newTHR >> 8) & 0x3F ; res[2] = newTHR & 0xFF ; writeRegs(res, 3) ; } int16_t MAX44008::getAMB_LOTHR(void) { uint16_t value ; uint8_t res[2] ; readRegs(REG_AMB_LOTHR_MSB, res, 2) ; value = (res[0] << 8) | res[1] ; return( value ) ; } void MAX44008::setAMB_LOTHR(int16_t newTHR) { uint8_t res[3] ; res[0] = REG_AMB_LOTHR_MSB ; res[1] = (newTHR >> 8) & 0x3F ; res[2] = newTHR & 0xFF ; writeRegs(res, 3) ; } uint8_t MAX44008::getAMB_PST(void) { uint8_t value ; readRegs(REG_AMB_PST, &value, 1) ; return( value ) ; } void MAX44008::setAMB_PST(uint8_t newValue) { uint8_t res[2] ; res[0] = REG_AMB_PST ; res[1] = newValue ; writeRegs(res, 2) ; } /* Ambient ADC Gains */ uint8_t MAX44008::getTRIM_GAIN_CLEAR(void) { uint8_t value ; readRegs(REG_TRIM_GAIN_CLR, &value, 1) ; return(value) ; } void MAX44008::setTRIM_GAIN_CLEAR(uint8_t newValue) { uint8_t res[2] ; res[0] = REG_TRIM_GAIN_CLR ; res[1] = newValue ; writeRegs(res, 2) ; } uint8_t MAX44008::getTRIM_GAIN_RED(void) { uint8_t value ; readRegs(REG_TRIM_GAIN_RED, &value, 1) ; return(value) ; } void MAX44008::setTRIM_GAIN_RED(uint8_t newValue) { uint8_t res[2] ; res[0] = REG_TRIM_GAIN_RED ; res[1] = newValue ; writeRegs(res, 2) ; } uint8_t MAX44008::getTRIM_GAIN_GREEN(void) { uint8_t value ; readRegs(REG_TRIM_GAIN_GRN, &value, 1) ; return(value) ; } void MAX44008::setTRIM_GAIN_GREEN(uint8_t newValue) { uint8_t res[2] ; res[0] = REG_TRIM_GAIN_GRN ; res[1] = newValue ; writeRegs(res, 2) ; } uint8_t MAX44008::getTRIM_GAIN_BLUE(void) { uint8_t value ; readRegs(REG_TRIM_GAIN_BLU, &value, 1) ; return(value) ; } void MAX44008::setTRIM_GAIN_BLUE(uint8_t newValue) { uint8_t res[2] ; res[0] = REG_TRIM_GAIN_BLU ; res[1] = newValue ; writeRegs(res, 2) ; } uint8_t MAX44008::getTRIM_GAIN_IR(void) { uint8_t value ; readRegs(REG_TRIM_GAIN_IR, &value, 1) ; return(value) ; } void MAX44008::setTRIM_GAIN_IR(uint8_t newValue) { uint8_t res[2] ; res[0] = REG_TRIM_GAIN_IR ; res[1] = newValue ; writeRegs(res, 2) ; } void MAX44008::enableTRIM(void) { uint8_t res[2] ; res[0] = REG_AMB_CONFIG ; readRegs(res[0], &res[1], 1) ; res[1] |= 0x80 ; /* BIT7 = TRIM */ writeRegs(res, 2) ; } void MAX44008::disableTRIM(void) { uint8_t res[2] ; res[0] = REG_AMB_CONFIG ; readRegs(res[0], &res[1], 1) ; res[1] &= (uint8_t)(0x7F) ; /* BIT7 = TRIM */ writeRegs(res, 2) ; } void MAX44008::enableCOMP(void) { uint8_t res[2] ; res[0] = REG_AMB_CONFIG ; readRegs(res[0], &res[1], 1) ; res[1] |= 0x40 ; /* BIT6 = COMPEN */ writeRegs(res, 2) ; } void MAX44008::disableCOMP(void) { uint8_t res[2] ; res[0] = REG_AMB_CONFIG ; readRegs(res[0], &res[1], 1) ; res[1] &= (uint8_t)(0xBF) ; /* BIT6 = COMPEN */ writeRegs(res, 2) ; } void MAX44008::enableTEMP(void) { uint8_t res[2] ; res[0] = REG_AMB_CONFIG ; readRegs(res[0], &res[1], 1) ; res[1] |= 0x20 ; /* BIT5 = TEMPEN */ writeRegs(res, 2) ; } void MAX44008::disableTEMP(void) { uint8_t res[2] ; res[0] = REG_AMB_CONFIG ; readRegs(res[0], &res[1], 1) ; res[1] &= (uint8_t)(0xDF) ; /* BIT5 = TEMPEN */ writeRegs(res, 2) ; } void MAX44008::enableAMBINT(void) { uint8_t res[2] ; res[0] = REG_MAIN_CONFIG ; readRegs(res[0], &res[1], 1) ; res[1] |= 0x01 ; /* BIT0 = AMBINTE */ writeRegs(res, 2) ; } void MAX44008::disableAMBINT(void) { uint8_t res[2] ; res[0] = REG_MAIN_CONFIG ; readRegs(res[0], &res[1], 1) ; res[1] &= (uint8_t)(0xFE) ; /* BIT0 = AMBINTE */ writeRegs(res, 2) ; } void MAX44008::selectAMBINT(uint8_t newChannel) { uint8_t res[2] ; res[0] = REG_MAIN_CONFIG ; readRegs(res[0], &res[1], 1) ; res[1] &= 0xF3 ; /* clear AMBSEL[1:0] */ res[1] |= ((newChannel & 0x03) << 2) ; writeRegs(res, 2) ; } void MAX44008::setRawMode(uint8_t newMode) { uint8_t res[2] ; res[0] = REG_MAIN_CONFIG ; res[1] = newMode ; writeRegs(res, 2) ; } void MAX44008::setMode(uint8_t newMode) { uint8_t res[2] ; res[0] = REG_MAIN_CONFIG ; readRegs(res[0], &res[1], 1) ; res[1] &= 0xCF ; /* clear MODE[1:0] */ res[1] |= ((newMode & 0x03) << 4) ; writeRegs(res, 2) ; }