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.
IQS5xx.cpp
00001 /* IQS572.cpp 00002 * Tested with mbed board: LPC1768 00003 * Author: skydarc 00004 * skydarc@gmail.com 00005 */ 00006 00007 #include "mbed.h" 00008 #include "IQS5xx.h" 00009 #include <new> 00010 00011 00012 IQS5xx::IQS5xx (PinName sda, PinName scl, PinName rdy) : i2c_(*reinterpret_cast<I2C*>(i2cRaw)), _readyPin(rdy) { 00013 00014 // Placement new to avoid additional heap memory allocation. 00015 new(i2cRaw) I2C(sda, scl); 00016 00017 //_readyPin.input(); 00018 } 00019 00020 //***************************************************************************** 00021 // 00022 //! Acknowledge the reset flag 00023 //! 00024 //! This function simply sets the ACK_RESET bit found in the SYSTEM_CONTROL_0 00025 //! register. By setting this bit the SHOW_RESET flag is cleared in the 00026 //! SYSTEM_INFO_0 register. During normal operation, the SHOW_RESET bit can be 00027 //! monitored and if it becomes set, then an unexpected reset has occurred. 00028 //! If any device configuration is needed, it must then be repeated. 00029 //! 00030 //! \param None 00031 //! 00032 //! \return None 00033 // 00034 //***************************************************************************** 00035 void IQS5xx::AcknowledgeReset(void) { 00036 static uint8_t System_ctrl_0 = ACK_RESET; 00037 00038 I2C_Write(SystemControl0_adr, &System_ctrl_0, 1); 00039 } 00040 00041 void IQS5xx::checkVersion(void) { 00042 00043 uint8_t ui8DataBuffer[15]; // defaut size : 6 00044 // 00045 // Dont wait for RDY here, since the device could be in EventMode, and then 00046 // there will be no communication window to complete this. Rather do a 00047 // forced communication, where clock stretching will be done on the IQS5xx 00048 // until an appropriate time to complete the i2c. 00049 // 00050 I2C_Read(ProductNumber_adr, &ui8DataBuffer[0] ,6); 00051 00052 printf("Product %d ", (ui8DataBuffer[0]<<8) + ui8DataBuffer[1]); 00053 printf("Project %d ", (ui8DataBuffer[2]<<8) + ui8DataBuffer[3]); 00054 printf("Version %d.%d\n", ui8DataBuffer[4], ui8DataBuffer[5]); 00055 00056 //////////////////////// 00057 // check other address : 00058 //////////////////////// 00059 00060 // System Config 1 00061 ui8DataBuffer[0] = 3; 00062 I2C_Write(SystemConfig1_adr, &ui8DataBuffer[0] ,1); 00063 I2C_Read(SystemConfig1_adr, &ui8DataBuffer[0] ,1); 00064 printf("System Config : %d\n", ui8DataBuffer[0]); 00065 00066 // swipe initial distance 00067 ui8DataBuffer[1] = 150; ui8DataBuffer[0] = 0; 00068 I2C_Write(SwipeInitDistance_adr, &ui8DataBuffer[0] ,2); 00069 I2C_Read(SwipeInitDistance_adr, &ui8DataBuffer[0] ,2); 00070 printf("Swp init dist. : %d\n", (ui8DataBuffer[0]<<8) + ui8DataBuffer[1]); 00071 00072 // X resolution 00073 ui8DataBuffer[1] = 0; ui8DataBuffer[0] = 8; 00074 I2C_Write(XResolution_adr, &ui8DataBuffer[0] ,2); 00075 I2C_Read(XResolution_adr, &ui8DataBuffer[0] ,2); 00076 printf("X resolution : %d\n", (ui8DataBuffer[0]<<8) + ui8DataBuffer[1]); 00077 00078 // Yresolution 00079 ui8DataBuffer[1] = 0; ui8DataBuffer[0] = 8; 00080 I2C_Write(YResolution_adr, &ui8DataBuffer[0] ,2); 00081 I2C_Read(YResolution_adr, &ui8DataBuffer[0] ,2); 00082 printf("Y resolution : %d\n", (ui8DataBuffer[0]<<8) + ui8DataBuffer[1]); 00083 00084 // Rx mapping 00085 I2C_Read(RxMapping_adr, &ui8DataBuffer[0] ,10); 00086 printf("mapping Rx :"); 00087 printf(" %d,", ui8DataBuffer[0]); 00088 printf(" %d,", ui8DataBuffer[1]); 00089 printf(" %d,", ui8DataBuffer[2]); 00090 printf(" %d,", ui8DataBuffer[3]); 00091 printf(" %d,", ui8DataBuffer[4]); 00092 printf(" %d,", ui8DataBuffer[5]); 00093 printf(" %d,", ui8DataBuffer[6]); 00094 printf(" %d\n", ui8DataBuffer[7]); 00095 00096 // Tx mapping 00097 I2C_Read(TxMapping_adr, &ui8DataBuffer[0] ,10); 00098 printf("mapping Tx :"); 00099 printf(" %d,", ui8DataBuffer[0]); 00100 printf(" %d,", ui8DataBuffer[1]); 00101 printf(" %d,", ui8DataBuffer[2]); 00102 printf(" %d,", ui8DataBuffer[3]); 00103 printf(" %d,", ui8DataBuffer[4]); 00104 printf(" %d,", ui8DataBuffer[5]); 00105 printf(" %d,", ui8DataBuffer[6]); 00106 printf(" %d\n", ui8DataBuffer[7]); 00107 00108 // total chanel Rx 00109 ui8DataBuffer[0] = 3; 00110 I2C_Write(TotalRx_adr, &ui8DataBuffer[0] ,1); 00111 I2C_Read(TotalRx_adr, &ui8DataBuffer[0] ,1); 00112 printf("nombre cannaux Rx : %d\n", ui8DataBuffer[0]); 00113 00114 // total chanel Tx 00115 ui8DataBuffer[0] = 4; 00116 I2C_Write(TotalTx_adr, &ui8DataBuffer[0] ,1); 00117 I2C_Read(TotalTx_adr, &ui8DataBuffer[0] ,1); 00118 printf("nombre cannaux Tx : %d\n", ui8DataBuffer[0]); 00119 } 00120 00121 //***************************************************************************** 00122 // 00123 //! Display a snap state change 00124 //! 00125 //! If the state of any snap output has changed, then this function can be used 00126 //! to display which Rx/Tx channel has changed status. 00127 //! 00128 //! \param None 00129 //! 00130 //! \return None 00131 // 00132 //***************************************************************************** 00133 void IQS5xx::DisplaySnap(void) 00134 { 00135 uint8_t ui8Tx, ui8Rx; 00136 uint16_t ui16ToggledBits; 00137 00138 for(ui8Tx = 0; ui8Tx < 15; ui8Tx++) 00139 { 00140 ui16ToggledBits = ui16PrevSnap[ui8Tx] ^ ui16SnapStatus[ui8Tx]; 00141 00142 for(ui8Rx = 0; ui8Rx < 10; ui8Rx++) 00143 { 00144 if(BitIsSet(ui16ToggledBits, ui8Rx)) 00145 { 00146 if(BitIsSet(ui16SnapStatus[ui8Tx], ui8Rx)) 00147 { 00148 printf("Snap set on Rx:"); 00149 } 00150 else 00151 { 00152 printf("Snap released on Rx:"); 00153 } 00154 printf(" %d / Tx: %d channel \n", ui8Rx, ui8Tx); 00155 } 00156 } 00157 } 00158 } 00159 00160 //***************************************************************************** 00161 // 00162 //! Process the data received 00163 //! 00164 //! This function sorts the read bytes from the IQS5xx and prints relevant data 00165 //! on serial port. 00166 //! REL_X[n]: Relative X Position of the finger n; n is from (1 to 5) 00167 //! REL_Y[n]: Relative X Position of the finger n; n is from (1 to 5) 00168 //! ABS_X[n]: Absolute X Position of the finger n; n is from (1 to 5) 00169 //! ABS_Y[n]: Absolute Y Position of the finger n; n is from (1 to 5) 00170 //! ui16TouchStrength[n] : Touch strength of finger n; n is from (1 to 5) 00171 //! ui8Area[n] : Touch area of finger n; this is number of channels under touch 00172 //! for a particular finger; 00173 //! Where 'n' is from (1 to 5) 00174 //! 00175 //! \param None 00176 //! 00177 //! \return None 00178 // 00179 //***************************************************************************** 00180 void IQS5xx::Process_XY(void) 00181 { 00182 uint8_t i; 00183 static uint8_t ui8FirstTouch = 0; 00184 uint8_t ui8NoOfFingers; 00185 uint8_t ui8SystemFlags[2]; 00186 int16_t i16RelX[6]; 00187 int16_t i16RelY[6]; 00188 uint16_t ui16AbsX[6]; 00189 uint16_t ui16AbsY[6]; 00190 uint16_t ui16TouchStrength[6]; 00191 uint8_t ui8Area[6]; 00192 00193 ui8SystemFlags[0] = Data_Buff[2]; 00194 ui8SystemFlags[1] = Data_Buff[3]; 00195 ui8NoOfFingers = Data_Buff[4]; 00196 // 00197 // Re-initialize the device if unexpected RESET detected 00198 // 00199 if((ui8SystemFlags[0] & SHOW_RESET) != 0) 00200 { 00201 printf("RESET DETECTED\n"); 00202 AcknowledgeReset(); 00203 return; 00204 } 00205 00206 if((ui8SystemFlags[1] & SNAP_TOGGLE) != 0) 00207 { 00208 // A snap state has changed, thus indicate which channel 00209 // 00210 DisplaySnap(); 00211 return; 00212 } 00213 00214 if((Data_Buff[0]) == SINGLE_TAP) 00215 { 00216 printf("Single Tap \n"); 00217 } 00218 else if((Data_Buff[1]) == TWO_FINGER_TAP) 00219 { 00220 printf("2 Finger Tap\n"); 00221 } 00222 00223 if(ui8NoOfFingers != 0) 00224 { 00225 if (!(ui8FirstTouch)) 00226 { 00227 printf("Gestures: \n"); 00228 //printf(" RelX: "); 00229 //printf("RelY: "); 00230 //printf("Fig: "); 00231 //printf("X1: "); printf("Y1: "); printf("TS1: "); printf("TA1: "); 00232 //printf("X2: "); printf("Y2: "); printf("TS2: "); printf("TA2:\n"); 00233 //printf("X3: "); printf("Y3: "); printf("TS3: "); printf("TA3: "); 00234 //printf("X4: "); printf("Y4: "); printf("TS4: "); printf("TA4: "); 00235 //printf("X5: "); printf("Y5: "); printf("TS5: "); printf("TA5: \n"); 00236 ui8FirstTouch = 1; 00237 } 00238 00239 switch (Data_Buff[0]) 00240 { 00241 case SINGLE_TAP : printf("Single Tap \n"); 00242 break; 00243 case TAP_AND_HOLD : printf("Tap & Hold \n"); 00244 break; 00245 case SWIPE_X_NEG : printf("Swipe X- \n"); 00246 break; 00247 case SWIPE_X_POS : printf("Swipe X+ \n"); 00248 break; 00249 case SWIPE_Y_POS : printf("Swipe Y+ \n"); 00250 break; 00251 case SWIPE_Y_NEG : printf("Swipe Y- \n"); 00252 break; 00253 } 00254 00255 switch (Data_Buff[1]) 00256 { 00257 case TWO_FINGER_TAP : printf("2 Finger Tap\n"); 00258 break; 00259 case SCROLL : printf("Scroll \n"); 00260 break; 00261 case ZOOM : printf("Zoom \n"); 00262 break; 00263 } 00264 if((Data_Buff[0] | Data_Buff[1]) == 0) 00265 { 00266 //printf(" "); 00267 } 00268 00269 /*i16RelX[1] = ((Data_Buff[5] << 8) | (Data_Buff[6])); 00270 i16RelY[1] = ((Data_Buff[7] << 8) | (Data_Buff[8])); 00271 00272 Print_signed(i16RelX[1]); 00273 Print_signed(i16RelY[1]); 00274 Print_unsigned(ui8NoOfFingers); 00275 00276 for (i = 0; i < 2; i++) 00277 { 00278 ui16AbsX[i+1] = ((Data_Buff[(7*i)+9] << 8) | (Data_Buff[(7*i)+10])); //9-16-23-30-37//10-17-24-31-38 00279 ui16AbsY[i+1] = ((Data_Buff[(7*i)+11] << 8) | (Data_Buff[(7*i)+12])); //11-18-25-32-39//12-19-26-33-40 00280 ui16TouchStrength[i+1] = ((Data_Buff[(7*i)+13] << 8) | (Data_Buff[(7*i)+14])); //13-20-27-34-11/14-21-28-35-42 00281 ui8Area[i+1] = (Data_Buff[7*i+15]); //15-22-29-36-43 00282 00283 Print_unsigned(ui16AbsX[i+1]); 00284 Print_unsigned(ui16AbsY[i+1]); 00285 Print_unsigned(ui16TouchStrength[i+1]); 00286 Print_unsigned(ui8Area[i+1]); 00287 } 00288 printf("");*/ 00289 } 00290 else 00291 { 00292 ui8FirstTouch = 0; 00293 } 00294 } 00295 00296 //***************************************************************************** 00297 // 00298 //! Terminate communication window 00299 //! 00300 //! The IQS5xx B000 does not close the communication window on the reception of 00301 //! the STOP bit; therefore this function sends the END COMMUNICATION WINDOW 00302 //! COMMAND (Please see datasheet for more information). RDY will go low after 00303 //! receiving any write to 0xEEEE followed by a STOP. 00304 //! 00305 //! \param None 00306 //! 00307 //! \return None 00308 // 00309 //***************************************************************************** 00310 void IQS5xx::Close_Comms() 00311 { 00312 uint8_t ui8DataBuffer[1]; 00313 00314 I2C_Write(END_WINDOW, &ui8DataBuffer[0], 1); 00315 } 00316 00317 //***************************************************************************** 00318 // 00319 //! I2C write function 00320 //! 00321 //! This function writes the provided data to the address specified. If 00322 //! anything in the write process is not successful, then it will be repeated 00323 //! up till four more times. If still not successful, it will write an error 00324 //! message on the serial terminal. 00325 //! 00326 //! \param ui16RegisterAddress is the 16-bit memory map address on the IQS5xx 00327 //! \param pData is a pointer to the first byte of a block of data to write 00328 //! \param ui8NoOfBytes indicates how many bytes of data to write 00329 //! 00330 //! \return Boolean indicating success/fail of write attempt 00331 // 00332 //***************************************************************************** 00333 uint8_t IQS5xx::I2C_Write(uint16_t ui16RegisterAddress, uint8_t *pData, uint8_t ui8NoOfBytes) { 00334 00335 uint8_t ui8Retry = 4; 00336 00337 ui8Success = I2C_Write2(ui16RegisterAddress, pData, ui8NoOfBytes); 00338 00339 // 00340 // If comms was not successful, retry 4 more times 00341 // 00342 while((!ui8Success) && (ui8Retry != 0)) 00343 { 00344 wait_ms(5); 00345 ui8Success = I2C_Write2(ui16RegisterAddress, pData, ui8NoOfBytes); 00346 ui8Retry--; 00347 } 00348 00349 if(ui8Success) return(true); 00350 else { 00351 printf("Comms write error\n"); 00352 return(false); 00353 } 00354 } 00355 00356 //***************************************************************************** 00357 // 00358 //! I2C read function 00359 //! 00360 //! This function reads data from the address specified and stores this data 00361 //! in the area provided by the pointer. If anything in the read process is 00362 //! not successful, then it will be repeated up till four more times. 00363 //! If still not successful, it will write an error message on the serial 00364 //! terminal. 00365 //! 00366 //! \param ui16RegisterAddress is the 16-bit memory map address on the IQS5xx 00367 //! \param pData is a pointer to where the read data must be stored 00368 //! \param ui8NoOfBytes indicates how many bytes of data to read 00369 //! 00370 //! \return Boolean indicating success/fail of read attempt 00371 // 00372 //***************************************************************************** 00373 uint8_t IQS5xx::I2C_Read(uint16_t ui16RegisterAddress, uint8_t *pData, uint8_t ui8NoOfBytes) { 00374 00375 uint8_t ui8Retry = 4; 00376 00377 ui8Success = I2C_Read2(ui16RegisterAddress, pData, ui8NoOfBytes); 00378 00379 // 00380 // If comms was not successful, retry 4 more times 00381 // 00382 while((!ui8Success) && (ui8Retry != 0)) { 00383 wait_ms(5); 00384 ui8Success = I2C_Read2(ui16RegisterAddress, pData, ui8NoOfBytes); 00385 ui8Retry--; 00386 } 00387 00388 if(ui8Success) return(true); 00389 else { 00390 printf("Comms read error\n"); 00391 return(false); 00392 } 00393 } 00394 00395 uint8_t IQS5xx::I2C_Write2(uint16_t ui16RegisterAddress, uint8_t *pData, uint8_t ui8NoOfBytes) 00396 { 00397 uint8_t i; 00398 00399 i2c_.start(); 00400 00401 if(i2c_.write(IQS5xx_ADDR<<1) == false) return(false); 00402 00403 if(i2c_.write((uint8_t)(ui16RegisterAddress>>8)) == false) return(false); 00404 if(i2c_.write((uint8_t)ui16RegisterAddress) == false) return(false); 00405 00406 for(i = 0; i < ui8NoOfBytes; i++) { 00407 if(i2c_.write(*pData) == false) return(false); 00408 pData++; 00409 } 00410 00411 i2c_.stop(); 00412 00413 return(true); 00414 } 00415 00416 uint8_t IQS5xx::I2C_Read2(uint16_t ui16RegisterAddress, uint8_t *pData, uint8_t ui8NoOfBytes) { 00417 00418 uint8_t i; 00419 00420 if(ui8NoOfBytes == 0) ui8NoOfBytes++; 00421 00422 i2c_.start(); 00423 00424 if(i2c_.write(IQS5xx_ADDR<<1) == false) return(false); 00425 00426 if(i2c_.write((uint8_t)(ui16RegisterAddress>>8)) == false) return(false); 00427 if(i2c_.write((uint8_t)ui16RegisterAddress) == false) return(false); 00428 00429 i2c_.start(); 00430 00431 if(i2c_.write((IQS5xx_ADDR<<1) + 0x01) == false) return(false); 00432 00433 for(i = 0; i < ui8NoOfBytes; i++) 00434 { 00435 if(i == (ui8NoOfBytes - 1)) { 00436 *pData = i2c_.read(0); 00437 } 00438 else { 00439 *pData = i2c_.read(1); 00440 } 00441 pData++; 00442 } 00443 00444 i2c_.stop(); 00445 00446 return(true); 00447 } 00448 00449 //***************************************************************************** 00450 // 00451 //! Print a signed value on serial display 00452 //! 00453 //! Print the signed integer on the serial port with adjusted tabs 00454 //! on serial port for easy column reading. 00455 //! 00456 //! \param None 00457 //! 00458 //! \return None 00459 // 00460 //***************************************************************************** 00461 void IQS5xx::Print_signed(int16_t i16Num) 00462 { 00463 if(i16Num < (-99)) 00464 { 00465 printf(" "); 00466 } 00467 else if(i16Num < (-9)) 00468 { 00469 printf(" "); 00470 } 00471 else if(i16Num < 0) 00472 { 00473 printf(" "); 00474 } 00475 else if(i16Num < 10) 00476 { 00477 printf(" "); 00478 } 00479 else if(i16Num < 100) 00480 { 00481 printf(" "); 00482 } 00483 else if(i16Num < 1000) 00484 { 00485 printf(" "); 00486 } 00487 printf("%d", i16Num); 00488 } 00489 00490 //***************************************************************************** 00491 // 00492 //! Print an unsigned value on serial display 00493 //! 00494 //! Print the unsigned integer on the serial port with adjusted tabs 00495 //! on serial port for easy column reading. 00496 //! 00497 //! \param None 00498 //! 00499 //! \return None 00500 // 00501 //***************************************************************************** 00502 void IQS5xx::Print_unsigned(uint16_t ui16Num) 00503 { 00504 if(ui16Num < 10) 00505 { 00506 printf(" "); 00507 } 00508 else if(ui16Num < 100) 00509 { 00510 printf(" "); 00511 } 00512 else if(ui16Num < 1000) 00513 { 00514 printf(" "); 00515 } 00516 else if(ui16Num < 10000) 00517 { 00518 printf(" "); 00519 } 00520 00521 if(ui16Num > 10000) 00522 { 00523 printf(" xxx"); 00524 } 00525 else 00526 { 00527 printf("%d", ui16Num); 00528 } 00529 }
Generated on Wed Jul 20 2022 16:15:23 by
1.7.2