Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependencies: TS_DISCO_F746NG LCD_DISCO_F746NG BSP_DISCO_F746NG BUTTON_GROUP
Adafruit_APDS9960.h
00001 /*! 00002 * @file Adafruit_APDS9960.h 00003 * 00004 * Software License Agreement (BSD License) 00005 * 00006 * Copyright (c) 2017, Adafruit Industries 00007 * All rights reserved. 00008 * 00009 * Redistribution and use in source and binary forms, with or without 00010 * modification, are permitted provided that the following conditions are met: 00011 * 1. Redistributions of source code must retain the above copyright 00012 * notice, this list of conditions and the following disclaimer. 00013 * 2. Redistributions in binary form must reproduce the above copyright 00014 * notice, this list of conditions and the following disclaimer in the 00015 * documentation and/or other materials provided with the distribution. 00016 * 3. Neither the name of the copyright holders nor the 00017 * names of its contributors may be used to endorse or promote products 00018 * derived from this software without specific prior written permission. 00019 * 00020 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ''AS IS'' AND ANY 00021 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 00022 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 00023 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY 00024 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 00025 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 00026 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 00027 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 00028 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 00029 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00030 */ 00031 #ifndef _APDS9960_H_ 00032 #define _APDS9960_H_ 00033 00034 #include "mbed.h" 00035 #include "Clock.h" 00036 00037 typedef bool boolean; 00038 typedef uint8_t byte; 00039 00040 #define APDS9960_ADDRESS (0x39<<1) /**< I2C Address */ 00041 00042 /** I2C Registers */ 00043 enum { 00044 APDS9960_RAM = 0x00, 00045 APDS9960_ENABLE = 0x80, 00046 APDS9960_ATIME = 0x81, 00047 APDS9960_WTIME = 0x83, 00048 APDS9960_AILTIL = 0x84, 00049 APDS9960_AILTH = 0x85, 00050 APDS9960_AIHTL = 0x86, 00051 APDS9960_AIHTH = 0x87, 00052 APDS9960_PILT = 0x89, 00053 APDS9960_PIHT = 0x8B, 00054 APDS9960_PERS = 0x8C, 00055 APDS9960_CONFIG1 = 0x8D, 00056 APDS9960_PPULSE = 0x8E, 00057 APDS9960_CONTROL = 0x8F, 00058 APDS9960_CONFIG2 = 0x90, 00059 APDS9960_ID = 0x92, 00060 APDS9960_STATUS = 0x93, 00061 APDS9960_CDATAL = 0x94, 00062 APDS9960_CDATAH = 0x95, 00063 APDS9960_RDATAL = 0x96, 00064 APDS9960_RDATAH = 0x97, 00065 APDS9960_GDATAL = 0x98, 00066 APDS9960_GDATAH = 0x99, 00067 APDS9960_BDATAL = 0x9A, 00068 APDS9960_BDATAH = 0x9B, 00069 APDS9960_PDATA = 0x9C, 00070 APDS9960_POFFSET_UR = 0x9D, 00071 APDS9960_POFFSET_DL = 0x9E, 00072 APDS9960_CONFIG3 = 0x9F, 00073 APDS9960_GPENTH = 0xA0, 00074 APDS9960_GEXTH = 0xA1, 00075 APDS9960_GCONF1 = 0xA2, 00076 APDS9960_GCONF2 = 0xA3, 00077 APDS9960_GOFFSET_U = 0xA4, 00078 APDS9960_GOFFSET_D = 0xA5, 00079 APDS9960_GOFFSET_L = 0xA7, 00080 APDS9960_GOFFSET_R = 0xA9, 00081 APDS9960_GPULSE = 0xA6, 00082 APDS9960_GCONF3 = 0xAA, 00083 APDS9960_GCONF4 = 0xAB, 00084 APDS9960_GFLVL = 0xAE, 00085 APDS9960_GSTATUS = 0xAF, 00086 APDS9960_IFORCE = 0xE4, 00087 APDS9960_PICLEAR = 0xE5, 00088 APDS9960_CICLEAR = 0xE6, 00089 APDS9960_AICLEAR = 0xE7, 00090 APDS9960_GFIFO_U = 0xFC, 00091 APDS9960_GFIFO_D = 0xFD, 00092 APDS9960_GFIFO_L = 0xFE, 00093 APDS9960_GFIFO_R = 0xFF, 00094 }; 00095 00096 /** ADC gain settings */ 00097 typedef enum { 00098 APDS9960_AGAIN_1X = 0x00, /**< No gain */ 00099 APDS9960_AGAIN_4X = 0x01, /**< 2x gain */ 00100 APDS9960_AGAIN_16X = 0x02, /**< 16x gain */ 00101 APDS9960_AGAIN_64X = 0x03 /**< 64x gain */ 00102 } apds9960AGain_t; 00103 00104 /** Proxmity gain settings */ 00105 typedef enum { 00106 APDS9960_PGAIN_1X = 0x00, /**< 1x gain */ 00107 APDS9960_PGAIN_2X = 0x04, /**< 2x gain */ 00108 APDS9960_PGAIN_4X = 0x08, /**< 4x gain */ 00109 APDS9960_PGAIN_8X = 0x0C /**< 8x gain */ 00110 } apds9960PGain_t; 00111 00112 /** Pulse length settings */ 00113 typedef enum { 00114 APDS9960_PPULSELEN_4US = 0x00, /**< 4uS */ 00115 APDS9960_PPULSELEN_8US = 0x40, /**< 8uS */ 00116 APDS9960_PPULSELEN_16US = 0x80, /**< 16uS */ 00117 APDS9960_PPULSELEN_32US = 0xC0 /**< 32uS */ 00118 } apds9960PPulseLen_t; 00119 00120 /** LED drive settings */ 00121 typedef enum { 00122 APDS9960_LEDDRIVE_100MA = 0x00, /**< 100mA */ 00123 APDS9960_LEDDRIVE_50MA = 0x40, /**< 50mA */ 00124 APDS9960_LEDDRIVE_25MA = 0x80, /**< 25mA */ 00125 APDS9960_LEDDRIVE_12MA = 0xC0 /**< 12.5mA */ 00126 } apds9960LedDrive_t; 00127 00128 /** LED boost settings */ 00129 typedef enum { 00130 APDS9960_LEDBOOST_100PCNT = 0x00, /**< 100% */ 00131 APDS9960_LEDBOOST_150PCNT = 0x10, /**< 150% */ 00132 APDS9960_LEDBOOST_200PCNT = 0x20, /**< 200% */ 00133 APDS9960_LEDBOOST_300PCNT = 0x30 /**< 300% */ 00134 } apds9960LedBoost_t; 00135 00136 /** Dimensions */ 00137 enum { 00138 APDS9960_DIMENSIONS_ALL = 0x00, // All dimensions 00139 APDS9960_DIMENSIONS_UP_DOWN = 0x01, // Up/Down dimensions 00140 APGS9960_DIMENSIONS_LEFT_RIGHT = 0x02, // Left/Right dimensions 00141 }; 00142 00143 /** FIFO Interrupts */ 00144 enum { 00145 APDS9960_GFIFO_1 = 0x00, // Generate interrupt after 1 dataset in FIFO 00146 APDS9960_GFIFO_4 = 0x01, // Generate interrupt after 2 datasets in FIFO 00147 APDS9960_GFIFO_8 = 0x02, // Generate interrupt after 3 datasets in FIFO 00148 APDS9960_GFIFO_16 = 0x03, // Generate interrupt after 4 datasets in FIFO 00149 }; 00150 00151 /** Gesture Gain */ 00152 enum { 00153 APDS9960_GGAIN_1 = 0x00, // Gain 1x 00154 APDS9960_GGAIN_2 = 0x01, // Gain 2x 00155 APDS9960_GGAIN_4 = 0x02, // Gain 4x 00156 APDS9960_GGAIN_8 = 0x03, // Gain 8x 00157 }; 00158 00159 /** Pulse Lenghts */ 00160 enum { 00161 APDS9960_GPULSE_4US = 0x00, // Pulse 4us 00162 APDS9960_GPULSE_8US = 0x01, // Pulse 8us 00163 APDS9960_GPULSE_16US = 0x02, // Pulse 16us 00164 APDS9960_GPULSE_32US = 0x03, // Pulse 32us 00165 }; 00166 00167 #define APDS9960_UP 0x01 /**< Gesture Up */ 00168 #define APDS9960_DOWN 0x02 /**< Gesture Down */ 00169 #define APDS9960_LEFT 0x03 /**< Gesture Left */ 00170 #define APDS9960_RIGHT 0x04 /**< Gesture Right */ 00171 00172 /*! 00173 * @brief Class that stores state and functions for interacting with 00174 * APDS9960 Sensor 00175 */ 00176 class Adafruit_APDS9960 { 00177 public: 00178 Adafruit_APDS9960(Serial *serial){_pc=serial;}; 00179 ~Adafruit_APDS9960(){}; 00180 00181 boolean begin(I2C *theWire, uint16_t iTimeMS = 10, apds9960AGain_t = APDS9960_AGAIN_4X, 00182 uint8_t addr = APDS9960_ADDRESS); 00183 void setADCIntegrationTime(uint16_t iTimeMS); 00184 float getADCIntegrationTime(); 00185 void setADCGain(apds9960AGain_t gain); 00186 apds9960AGain_t getADCGain(); 00187 void setLED(apds9960LedDrive_t drive, apds9960LedBoost_t boost); 00188 00189 // proximity 00190 void enableProximity(boolean en = true); 00191 void setProxGain(apds9960PGain_t gain); 00192 apds9960PGain_t getProxGain(); 00193 void setProxPulse(apds9960PPulseLen_t pLen, uint8_t pulses); 00194 void enableProximityInterrupt(); 00195 void disableProximityInterrupt(); 00196 uint8_t readProximity(); 00197 void setProximityInterruptThreshold(uint8_t low, uint8_t high, 00198 uint8_t persistance = 4); 00199 bool getProximityInterrupt(); 00200 00201 // gesture 00202 void enableGesture(boolean en = true); 00203 bool gestureValid(); 00204 void setGestureDimensions(uint8_t dims); 00205 void setGestureFIFOThreshold(uint8_t thresh); 00206 void setGestureGain(uint8_t gain); 00207 void setGestureProximityThreshold(uint8_t thresh); 00208 void setGestureOffset(uint8_t offset_up, uint8_t offset_down, 00209 uint8_t offset_left, uint8_t offset_right); 00210 uint8_t readGesture(); 00211 void resetCounts(); 00212 00213 // light & color 00214 void enableColor(boolean en = true); 00215 bool colorDataReady(); 00216 void getColorData(uint16_t *r, uint16_t *g, uint16_t *b, uint16_t *c); 00217 uint16_t calculateColorTemperature(uint16_t r, uint16_t g, uint16_t b); 00218 uint16_t calculateLux(uint16_t r, uint16_t g, uint16_t b); 00219 void enableColorInterrupt(); 00220 void disableColorInterrupt(); 00221 void clearInterrupt(); 00222 void setIntLimits(uint16_t l, uint16_t h); 00223 00224 // turn on/off elements 00225 void enable(boolean en = true); 00226 00227 private: 00228 uint8_t _i2caddr; 00229 I2C *_wire; 00230 Serial *_pc; 00231 00232 uint32_t read32(uint8_t reg); 00233 uint16_t read16(uint8_t reg); 00234 uint16_t read16R(uint8_t reg); 00235 00236 void write8(byte reg, byte value); 00237 uint8_t read8(byte reg); 00238 00239 uint8_t gestCnt; 00240 00241 uint8_t UCount; 00242 uint8_t DCount; 00243 00244 uint8_t LCount; 00245 uint8_t RCount; 00246 00247 uint8_t read(uint8_t reg, uint8_t *buf, uint8_t num); 00248 void write(uint8_t reg, uint8_t *buf, uint8_t num); 00249 void _i2c_init(); 00250 00251 struct enable { 00252 00253 // power on 00254 uint8_t PON : 1; 00255 00256 // ALS enable 00257 uint8_t AEN : 1; 00258 00259 // Proximity detect enable 00260 uint8_t PEN : 1; 00261 00262 // wait timer enable 00263 uint8_t WEN : 1; 00264 00265 // ALS interrupt enable 00266 uint8_t AIEN : 1; 00267 00268 // proximity interrupt enable 00269 uint8_t PIEN : 1; 00270 00271 // gesture enable 00272 uint8_t GEN : 1; 00273 00274 uint8_t get() { 00275 return (GEN << 6) | (PIEN << 5) | (AIEN << 4) | (WEN << 3) | (PEN << 2) | 00276 (AEN << 1) | PON; 00277 }; 00278 }; 00279 struct enable _enable; 00280 00281 struct pers { 00282 // ALS Interrupt Persistence. Controls rate of Clear channel interrupt to 00283 // the host processor 00284 uint8_t APERS : 4; 00285 00286 // proximity interrupt persistence, controls rate of prox interrupt to host 00287 // processor 00288 uint8_t PPERS : 4; 00289 00290 uint8_t get() { return (PPERS << 4) | APERS; }; 00291 }; 00292 pers _pers; 00293 00294 struct config1 { 00295 uint8_t WLONG : 1; 00296 00297 uint8_t get() { return WLONG << 1; }; 00298 }; 00299 config1 _config1; 00300 00301 struct ppulse { 00302 00303 /*Proximity Pulse Count. Specifies the number of proximity pulses to be 00304 generated on LDR. Number of pulses is set by PPULSE value plus 1. 00305 */ 00306 uint8_t PPULSE : 6; 00307 00308 // Proximity Pulse Length. Sets the LED-ON pulse width during a proximity 00309 // LDR pulse. 00310 uint8_t PPLEN : 2; 00311 00312 uint8_t get() { return (PPLEN << 6) | PPULSE; } 00313 }; 00314 ppulse _ppulse; 00315 00316 struct control { 00317 // ALS and Color gain control 00318 uint8_t AGAIN : 2; 00319 00320 // proximity gain control 00321 uint8_t PGAIN : 2; 00322 00323 // led drive strength 00324 uint8_t LDRIVE : 2; 00325 00326 uint8_t get() { return (LDRIVE << 6) | (PGAIN << 2) | AGAIN; } 00327 }; 00328 control _control; 00329 00330 struct config2 { 00331 /* Additional LDR current during proximity and gesture LED pulses. Current 00332 value, set by LDRIVE, is increased by the percentage of LED_BOOST. 00333 */ 00334 uint8_t LED_BOOST : 2; 00335 00336 // clear photodiode saturation int enable 00337 uint8_t CPSIEN : 1; 00338 00339 // proximity saturation interrupt enable 00340 uint8_t PSIEN : 1; 00341 00342 uint8_t get() { 00343 return (PSIEN << 7) | (CPSIEN << 6) | (LED_BOOST << 4) | 1; 00344 } 00345 }; 00346 config2 _config2; 00347 00348 struct status { 00349 /* ALS Valid. Indicates that an ALS cycle has completed since AEN was 00350 asserted or since a read from any of the ALS/Color data registers. 00351 */ 00352 uint8_t AVALID : 1; 00353 00354 /* Proximity Valid. Indicates that a proximity cycle has completed since PEN 00355 was asserted or since PDATA was last read. A read of PDATA automatically 00356 clears PVALID. 00357 */ 00358 uint8_t PVALID : 1; 00359 00360 /* Gesture Interrupt. GINT is asserted when GFVLV becomes greater than 00361 GFIFOTH or if GVALID has become asserted when GMODE transitioned to zero. 00362 The bit is reset when FIFO is completely emptied (read). 00363 */ 00364 uint8_t GINT : 1; 00365 00366 // ALS Interrupt. This bit triggers an interrupt if AIEN in ENABLE is set. 00367 uint8_t AINT : 1; 00368 00369 // Proximity Interrupt. This bit triggers an interrupt if PIEN in ENABLE is 00370 // set. 00371 uint8_t PINT : 1; 00372 00373 /* Indicates that an analog saturation event occurred during a previous 00374 proximity or gesture cycle. Once set, this bit remains set until cleared by 00375 clear proximity interrupt special function command (0xE5 PICLEAR) or by 00376 disabling Prox (PEN=0). This bit triggers an interrupt if PSIEN is set. 00377 */ 00378 uint8_t PGSAT : 1; 00379 00380 /* Clear Photodiode Saturation. When asserted, the analog sensor was at the 00381 upper end of its dynamic range. The bit can be de-asserted by sending a 00382 Clear channel interrupt command (0xE6 CICLEAR) or by disabling the ADC 00383 (AEN=0). This bit triggers an interrupt if CPSIEN is set. 00384 */ 00385 uint8_t CPSAT : 1; 00386 00387 void set(uint8_t data) { 00388 AVALID = data & 0x01; 00389 PVALID = (data >> 1) & 0x01; 00390 GINT = (data >> 2) & 0x01; 00391 AINT = (data >> 4) & 0x01; 00392 PINT = (data >> 5) & 0x01; 00393 PGSAT = (data >> 6) & 0x01; 00394 CPSAT = (data >> 7) & 0x01; 00395 } 00396 }; 00397 status _status; 00398 00399 struct config3 { 00400 // proximity mask 00401 uint8_t PMASK_R : 1; 00402 uint8_t PMASK_L : 1; 00403 uint8_t PMASK_D : 1; 00404 uint8_t PMASK_U : 1; 00405 00406 /* Sleep After Interrupt. When enabled, the device will automatically enter 00407 low power mode when the INT pin is asserted and the state machine has 00408 progressed to the SAI decision block. Normal operation is resumed when INT 00409 pin is cleared over I2C. 00410 */ 00411 uint8_t SAI : 1; 00412 00413 /* Proximity Gain Compensation Enable. This bit provides gain compensation 00414 when proximity photodiode signal is reduced as a result of sensor masking. 00415 If only one diode of the diode pair is contributing, then only half of the 00416 signal is available at the ADC; this results in a maximum ADC value of 127. 00417 Enabling PCMP enables an additional gain of 2X, resulting in a maximum ADC 00418 value of 255. 00419 */ 00420 uint8_t PCMP : 1; 00421 00422 uint8_t get() { 00423 return (PCMP << 5) | (SAI << 4) | (PMASK_U << 3) | (PMASK_D << 2) | 00424 (PMASK_L << 1) | PMASK_R; 00425 } 00426 }; 00427 config3 _config3; 00428 00429 struct gconf1 { 00430 /* Gesture Exit Persistence. When a number of consecutive gesture end 00431 occurrences become equal or greater to the GEPERS value, the Gesture state 00432 machine is exited. 00433 */ 00434 uint8_t GEXPERS : 2; 00435 00436 /* Gesture Exit Mask. Controls which of the gesture detector photodiodes 00437 (UDLR) will be included to determine a gesture end and subsequent exit 00438 of the gesture state machine. Unmasked UDLR data will be compared with the 00439 value in GTHR_OUT. Field value bits correspond to UDLR detectors. 00440 */ 00441 uint8_t GEXMSK : 4; 00442 00443 /* Gesture FIFO Threshold. This value is compared with the FIFO Level (i.e. 00444 the number of UDLR datasets) to generate an interrupt (if enabled). 00445 */ 00446 uint8_t GFIFOTH : 2; 00447 00448 uint8_t get() { return (GFIFOTH << 6) | (GEXMSK << 2) | GEXPERS; } 00449 }; 00450 gconf1 _gconf1; 00451 00452 struct gconf2 { 00453 /* Gesture Wait Time. The GWTIME controls the amount of time in a low power 00454 mode between gesture detection cycles. 00455 */ 00456 uint8_t GWTIME : 3; 00457 00458 // Gesture LED Drive Strength. Sets LED Drive Strength in gesture mode. 00459 uint8_t GLDRIVE : 2; 00460 00461 // Gesture Gain Control. Sets the gain of the proximity receiver in gesture 00462 // mode. 00463 uint8_t GGAIN : 2; 00464 00465 uint8_t get() { return (GGAIN << 5) | (GLDRIVE << 3) | GWTIME; } 00466 }; 00467 gconf2 _gconf2; 00468 00469 struct gpulse { 00470 /* Number of Gesture Pulses. Specifies the number of pulses to be generated 00471 on LDR. Number of pulses is set by GPULSE value plus 1. 00472 */ 00473 uint8_t GPULSE : 6; 00474 00475 // Gesture Pulse Length. Sets the LED_ON pulse width during a Gesture LDR 00476 // Pulse. 00477 uint8_t GPLEN : 2; 00478 00479 uint8_t get() { return (GPLEN << 6) | GPULSE; } 00480 }; 00481 gpulse _gpulse; 00482 00483 struct gconf3 { 00484 /* Gesture Dimension Select. Selects which gesture photodiode pairs are 00485 enabled to gather results during gesture. 00486 */ 00487 uint8_t GDIMS : 2; 00488 00489 uint8_t get() { return GDIMS; } 00490 }; 00491 gconf3 _gconf3; 00492 00493 struct gconf4 { 00494 /* Gesture Mode. Reading this bit reports if the gesture state machine is 00495 actively running, 1 = Gesture, 0= ALS, Proximity, Color. Writing a 1 to this 00496 bit causes immediate entry in to the gesture state machine (as if GPENTH had 00497 been exceeded). Writing a 0 to this bit causes exit of gesture when current 00498 analog conversion has finished (as if GEXTH had been exceeded). 00499 */ 00500 uint8_t GMODE : 1; 00501 00502 /* Gesture interrupt enable. Gesture Interrupt Enable. When asserted, all 00503 gesture related interrupts are unmasked. 00504 */ 00505 uint8_t GIEN : 2; 00506 00507 uint8_t get() { return (GIEN << 1) | GMODE; } 00508 void set(uint8_t data) { 00509 GIEN = (data >> 1) & 0x01; 00510 GMODE = data & 0x01; 00511 } 00512 }; 00513 gconf4 _gconf4; 00514 00515 struct gstatus { 00516 /* Gesture FIFO Data. GVALID bit is sent when GFLVL becomes greater than 00517 GFIFOTH (i.e. FIFO has enough data to set GINT). GFIFOD is reset when GMODE 00518 = 0 and the GFLVL=0 (i.e. All FIFO data has been read). 00519 */ 00520 uint8_t GVALID : 1; 00521 00522 /* Gesture FIFO Overflow. A setting of 1 indicates that the FIFO has filled 00523 to capacity and that new gesture detector data has been lost. 00524 */ 00525 uint8_t GFOV : 1; 00526 00527 void set(uint8_t data) { 00528 GFOV = (data >> 1) & 0x01; 00529 GVALID = data & 0x01; 00530 } 00531 }; 00532 gstatus _gstatus; 00533 }; 00534 00535 #endif
Generated on Fri Jul 22 2022 06:03:14 by
1.7.2