Kionix KX123 accelerometer C++ driver. Can be used for some extend also with kx022, kx023, kx122, etc. when used features are present in sensor.

Dependents:   kionix-kx123-hello

Revision:
0:a3f43eb92f86
Child:
1:f328083fb80b
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/kx123.cpp	Thu Sep 29 15:05:08 2016 +0000
@@ -0,0 +1,157 @@
+/*   Copyright 2016 Rohm Semiconductor
+
+   Licensed under the Apache License, Version 2.0 (the "License");
+   you may not use this file except in compliance with the License.
+   You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+*/
+#include "RegisterWriter/RegisterWriter/rohm_hal2.h"
+#include "RegisterWriter/RegisterWriter/RegisterWriter.h"
+
+#include "kx123_registers.h"
+#include "kx123.h"
+
+/**
+* KX123 accelerometer driver
+*/
+/**
+* Create a KX123 instance which is connected to pre-instantiated I2C object.
+*
+* @param sad slave address of sensor.
+* @param wai who_am_i value (i.e. sensor type/model)
+*/
+KX123::KX123(RegisterWriter &i2c_obj, uint8_t newsad, uint8_t newwai) : i2c_rw(i2c_obj) {
+    sad = newsad;
+    wai = newwai;        
+}
+
+/**
+* KX123 destructor
+*/
+KX123::~KX123(){
+}
+
+/**
+* Check if sensor is connected, setup defaults to sensor and start measuring.
+* @return true on error, false on ok
+*/
+bool KX123::set_defaults()
+{
+    unsigned char buf;
+
+    DEBUG_print("\n\r");
+    DEBUG_print("KX123 init started\n\r");
+    i2c_rw.read_register(sad, KX122_WHO_AM_I, &buf, 1);
+    if (buf == KX123_WHO_AM_I_WAI_ID) {
+        DEBUG_print("KX123 found. (WAI %d) ", buf);
+    } else {
+        DEBUG_print("KX123 not found (WAI %d, not %d). ", buf, KX123_WHO_AM_I_WAI_ID);
+        switch(buf){        
+            case KX012_WHO_AM_I_WAI_ID:
+                DEBUG_print("Found KX012");
+                break;
+            case KX022_WHO_AM_I_WAI_ID:
+                DEBUG_print("Found KX022");
+                break;
+            case KX023_WHO_AM_I_WAI_ID:
+                DEBUG_print("Found KX023");
+                break;
+            case KX23H_WHO_AM_I_WAI_ID:
+                DEBUG_print("Found KX23H");
+                break;
+            case KX112_WHO_AM_I_WAI_ID:
+                DEBUG_print("Found KX112");
+                break;
+            case KX122_WHO_AM_I_WAI_ID:
+                DEBUG_print("Found KX122");
+                break;
+            case KX124_WHO_AM_I_WAI_ID:
+                DEBUG_print("Found KX124");
+                break;
+            case KX222_WHO_AM_I_WAI_ID:
+                DEBUG_print("Found KX222");
+                break;
+            case KX224_WHO_AM_I_WAI_ID:
+                DEBUG_print("Found KX224");
+                break;
+            default:
+                DEBUG_print("Not even other sensor found from same family.\n\r");
+                return true;
+            }
+            DEBUG_print(" though, trying to use that.\n\r");
+    }
+
+    //First set CNTL1 PC1-bit to stand-by mode, after that setup can be made
+    i2c_rw.write_register(sad, KX122_CNTL1, 0 );
+
+    //set_tilt_position_defaults();
+
+    //ODCNTL: Output Data Rate control (ODR) 
+    i2c_rw.write_register(sad, KX122_ODCNTL, KX122_ODCNTL_OSA_25600);
+    //Setup G-range and 8/16-bit resolution + set CNTL1 PC1-bit to operating mode (also WUF_EN, TP_EN and DT_EN)
+    i2c_rw.write_register(sad, KX122_CNTL1, ( KX122_CNTL1_PC1 | KX122_CNTL1_GSEL_8G | KX122_CNTL1_RES ) );
+
+    //resolution_divider = 32768/2;  //KX122_CNTL1_GSEL_2G
+    //resolution_divider = 32768/4;  //KX122_CNTL1_GSEL_4G
+    resolution_divider = 32768/8;  //KX122_CNTL1_GSEL_8G
+    
+    return false;
+}
+
+
+/**
+CNTL PC1-bit has to be set to stand-by before this command.
+return true on error
+**/
+void KX123::set_tilt_position_defaults(){
+    //CNTL3: Tilt position control, directional tap control and motion wakeup control
+    i2c_rw.write_register(sad, KX122_CNTL3, ( KX122_CNTL3_OTP_50 | KX122_CNTL3_OTDT_400 ) ); 
+    //TILT_TIMER: Setup tilt position timer (~=filter)
+    i2c_rw.write_register(sad, KX122_TILT_TIMER, 0x01);
+    return;
+}
+
+
+/**
+return read_error, true on error, false on read ok.
+**/
+bool KX123::getresults_raw(int16_t* buf){
+    #define RESULTS_LEN 6
+    uint8_t tmp[RESULTS_LEN];     //XYZ (lhlhlh)
+    uint8_t read_bytes;
+
+    read_bytes = i2c_rw.read_register(sad, KX122_XOUT_L, &tmp[0], sizeof(tmp));
+    if (read_bytes != RESULTS_LEN){
+        return true;
+        }
+    buf[0] = ( tmp[1] << 8 ) | tmp[0];  //X
+    buf[1] = ( tmp[3] << 8 ) | tmp[2];  //Y
+    buf[2] = ( tmp[5] << 8 ) | tmp[4];  //Z
+    return false;
+}
+
+
+bool KX123::getresults_g(float* buf){
+    int16_t raw[3];
+    int read_error;
+
+    read_error = getresults_raw(&raw[0]);
+    if (read_error){
+        return read_error;
+        }
+
+    //Scale raw values to G-scale
+    buf[0] = ((float)raw[0]) / resolution_divider;
+    buf[1] = ((float)raw[1]) / resolution_divider;
+    buf[2] = ((float)raw[2]) / resolution_divider;
+    return false;
+}
+
+