Bosch Sensortec Community

    cancel
    Showing results for 
    Search instead for 
    Did you mean: 

    BMI160 TAP DETECTION

    BMI160 TAP DETECTION

    HI,

    I need to detect the Double TAP during nRF52 Controller in sleep mode. and INT1 pin connect to the interrupt of the contrller. if the detection occurs, it need to capture and INT1 pin must chnge thier state to wakeup the controller. reset of the time sensor will be in normal mode. it send the data of Acc, Gyro.

    here what i need is how to config the DOUBLE TAP and / SINGLE TAP.

    how to enable and disable the interrupt pin(when i goto sleep mode i need to enable interrupt. and once a wake up i need to diasble it ).

    how the changes in ouput will occur in the INT1 pin.

    i have treied to code in my way.please verify and tell the changes.

    #include <stdio.h>
    #include "boards.h"
    #include "app_util_platform.h"
    #include "app_error.h"
    #include "nrf_drv_twi.h"
    #include "nrf_delay.h"
    
    
    #include "nrf_log.h"
    #include "nrf_log_ctrl.h"
    #include "nrf_log_default_backends.h"
    
    #include "bmi160.h"
    
    /* TWI instance ID. */
    #define TWI_INSTANCE_ID     0
    
    #define G_TO_LSB (16384.0f)
    
    #define DPS_TO_LSB (131.072f)
    
    
    /* Indicates if operation on TWI has ended. */
    static volatile bool m_xfer_done = false;
    
    /* TWI instance. */
    static const nrf_drv_twi_t m_twi = NRF_DRV_TWI_INSTANCE(TWI_INSTANCE_ID);
    
    struct bmi160_dev sensor;
    struct bmi160_sensor_data accel;
    struct bmi160_sensor_data gyro;
    struct bmi160_int_settg int_config;
    
    int8_t rslt = BMI160_OK;
    
    
    /*TWI initialization*/
    
    void twi_init (void)
    {
        ret_code_t err_code;
    
        const nrf_drv_twi_config_t twi_config = {
           .scl                = ARDUINO_SCL_PIN,
           .sda                = ARDUINO_SDA_PIN,
           .frequency          = NRF_DRV_TWI_FREQ_100K,
           .interrupt_priority = APP_IRQ_PRIORITY_HIGH,
           .clear_bus_init     = false
        };
    
        err_code = nrf_drv_twi_init(&m_twi, &twi_config, NULL, NULL);
        
        APP_ERROR_CHECK(err_code);
        if (NRF_SUCCESS == err_code)
    	{
    		nrf_drv_twi_enable(&m_twi);
    		NRF_LOG_INFO("TWI init success...");	
    	}
    }
    
    int8_t Acc_i2c_Write(uint8_t dev_id, uint8_t reg_addr, uint8_t *reg_data, uint16_t len)
    {
    
        //  NRF_LOG_INFO("WRITE: dev_id: %x reg_addr: %x reg_data: %x len: %i\n", dev_id, reg_addr, *reg_data, len);
    	int8_t rslt = 0;
    	uint8_t data[len + 1];
    	data[0] = reg_addr;
    	for (uint16_t i = 0; i < len; i++) {
    		data[i + 1] = reg_data[i];
    	}
    	
    	rslt = nrf_drv_twi_tx(&m_twi, dev_id, data, len + 1, false);
    	APP_ERROR_CHECK(rslt);
            return rslt;
      
    }
    
    
    int8_t Acc_i2c_Read(uint8_t dev_id, uint8_t reg_addr, uint8_t *reg_data, uint16_t len)
    {
    	int8_t rslt = 0;
       //     NRF_LOG_INFO("READ: dev_id: %x reg_addr: %x len: %i\n", dev_id, reg_addr, len);
    	rslt = nrf_drv_twi_tx(&m_twi, dev_id, &reg_addr, 1, false);
            APP_ERROR_CHECK(rslt);
    
    	if (rslt == 0)
    	{
    		rslt = nrf_drv_twi_rx(&m_twi, dev_id, reg_data, len);
    	}
        //    NRF_LOG_INFO("READ: %x",*reg_data);
    	return rslt;
    }
    
    void Acc_delay_ms(uint32_t period)
    { 
    	
    /*if (period==NULL){
    period = 1;
    }// delay time*/
    	
      nrf_delay_ms( period ) ;
    }
    
    void BMI160_init (void)
    {
        sensor.id = BMI160_I2C_ADDR;         //0x69
        sensor.interface = BMI160_I2C_INTF;  //0x00
        sensor.read = &Acc_i2c_Read;
        sensor.write = &Acc_i2c_Write;
        sensor.delay_ms = &Acc_delay_ms;
    
        rslt = bmi160_init(&sensor);
        APP_ERROR_CHECK(rslt);
    
        if(rslt == BMI160_OK){
        NRF_LOG_INFO("BMI160 Initialized...");
        } else {
        NRF_LOG_INFO("BMI160 not Initialized...");
        }NRF_LOG_FLUSH();
    
        sensor.accel_cfg.odr = BMI160_ACCEL_ODR_1600HZ;
        sensor.accel_cfg.range = BMI160_ACCEL_RANGE_2G;
        sensor.accel_cfg.bw = BMI160_ACCEL_BW_NORMAL_AVG4;
        sensor.accel_cfg.power = BMI160_ACCEL_LOWPOWER_MODE;
    
        sensor.gyro_cfg.odr = BMI160_GYRO_ODR_3200HZ;
        sensor.gyro_cfg.range = BMI160_GYRO_RANGE_2000_DPS;
        sensor.gyro_cfg.bw = BMI160_GYRO_BW_NORMAL_MODE;
        sensor.gyro_cfg.power = BMI160_GYRO_NORMAL_MODE;
    
        rslt = bmi160_set_sens_conf(&sensor);
        APP_ERROR_CHECK(rslt);
    
         if(rslt == BMI160_OK){
        NRF_LOG_INFO("sensor Configured...");
        } else {
        NRF_LOG_INFO("sensor not Configured...");
        }NRF_LOG_FLUSH();
    }
    
    void BMI160_IN_INT (void)
    {
      int_config.int_channel = BMI160_INT_CHANNEL_1;// Interrupt channel/pin 1
      /* Select the Interrupt type */
      int_config.int_type = BMI160_ACC_DOUBLE_TAP_INT;// Choosing Any motion interrupt
      /* Select the interrupt channel/pin settings */
      int_config.int_pin_settg.output_en = BMI160_ENABLE;// Enabling interrupt pins to act as output pin
      int_config.int_pin_settg.output_mode = BMI160_DISABLE;// Choosing push-pull mode for interrupt pin
      int_config.int_pin_settg.output_type = BMI160_DISABLE;// Choosing active low output
      int_config.int_pin_settg.edge_ctrl = BMI160_ENABLE;// Choosing edge triggered output
      int_config.int_pin_settg.input_en = BMI160_DISABLE;// Disabling interrupt pin to act as input
      int_config.int_pin_settg.latch_dur = BMI160_LATCH_DUR_NONE;// non-latched output
    
      /* Select the DOUBLE_TAP interrupt parameters */
      int_config.int_type_cfg.acc_tap_int.tap_thr = 3;
      int_config.int_type_cfg.acc_tap_int.tap_shock = BMI160_ENABLE;
      int_config.int_type_cfg.acc_tap_int.tap_quiet = BMI160_ENABLE;
      int_config.int_type_cfg.acc_tap_int.tap_dur = 3;
      int_config.int_type_cfg.acc_tap_int.tap_data_src=BMI160_ENABLE;
      int_config.int_type_cfg.acc_tap_int.tap_en = BMI160_ENABLE;
      
      /* Set the DOUBLE_TAP interrupt */
      bmi160_set_int_config(&int_config, &sensor); /* sensor is an instance of the structure bmi160_dev  */
    }
    
    static void read_sensor_data()
    {
          m_xfer_done = false;
          bmi160_get_sensor_data((BMI160_ACCEL_SEL | BMI160_GYRO_SEL | BMI160_TIME_SEL), &accel, &gyro, &sensor);
          /*NRF_LOG_INFO("DataX:%d", accel.x);
          NRF_LOG_INFO("DataY:%d", accel.y);
          NRF_LOG_INFO("DataZ:%d", accel.z);
          NRF_LOG_INFO("GyroX:%d", gyro.x);
          NRF_LOG_INFO("GyroY:%d", gyro.y);
          NRF_LOG_INFO("GyroZ:%d", gyro.z);*/
    
          /* need the calculation to study  */
          float accelX = ((((float)accel.x) / G_TO_LSB) * 9.80655); // in m/s^2
          float gyrX = ((((float)gyro.x) / DPS_TO_LSB) * 0.0174532925); // in rad/sec
          NRF_LOG_INFO("DataX in m/s^2   : " NRF_LOG_FLOAT_MARKER, 
          NRF_LOG_FLOAT( accelX));
          NRF_LOG_INFO("DataY in rad/sec : " NRF_LOG_FLOAT_MARKER, 
          NRF_LOG_FLOAT(gyrX));
          NRF_LOG_FLUSH();
    }
    
    
    /**
     * @brief Function for main application entry.
     */
    int main(void)
    {
        bsp_board_init(BSP_INIT_LEDS);
        APP_ERROR_CHECK(NRF_LOG_INIT(NULL));
        NRF_LOG_DEFAULT_BACKENDS_INIT();
    
        NRF_LOG_INFO("BMI160 get started.\n");
        NRF_LOG_FLUSH();
        Acc_delay_ms(100);
    
        twi_init();
        Acc_delay_ms(50);
    
        BMI160_init();
        Acc_delay_ms(100);
        uint8_t reg_addr = BMI160_CHIP_ID_ADDR;
        uint8_t data;
        uint16_t len = 1;
        Acc_delay_ms(1000);
        rslt = bmi160_get_regs(reg_addr, &data, len, &sensor);
        NRF_LOG_INFO("Data:%x", data);
    
        /*uint8_t reg_addr = BMI160_INT_MOTION_1_ADDR;
        uint8_t data = 20;
        uint16_t len = 1;
        rslt = bmi160_set_regs(reg_addr, &data, len, &sensor);*/
        BMI160_IN_INT();
        NRF_LOG_FLUSH();
        Acc_delay_ms(3000);
        while (true)
        {
            //nrf_delay_ms(250);
    
           __WFE();
            
            
           /* union bmi160_int_status interrupt;
            enum bmi160_int_status_sel int_status_sel;
    
            
            int_status_sel = BMI160_INT_STATUS_ALL;
            rslt = bmi160_get_int_status(int_status_sel, &interrupt, &sensor);
            if (interrupt.bit.d_tap)
            {NRF_LOG_INFO("BMI160 get started.\n");
                printf("Step detector interrupt occured\n");}
                else
                printf("not detected\n");
            //read_sensor_data();
            NRF_LOG_FLUSH();*/
        }
    }
    
    /** @} */

    and also is there the fuction to use both INT pin at the time.

     

    Tags (2)
    5 REPLIES 5
    New Poster

    Re: BMI160 TAP DETECTION

    Hi, i'm in the same problem, do you solve it?

    Community Moderator

    Re: BMI160 TAP DETECTION

    I don't find issue inside your code.

    Can you dump all your register map after finish your configuration?

    then also please use oscilloscope to monitor the pin change to see if HW interrupt are generated or not.

    INT1 and INT2 of BMI160 can work separated and enable both. 

    Re: BMI160 TAP DETECTION

    Hi Vincent,

    I have dumped the register after the configuration..

    but same problem occur.

    is there any related code for TAP DETECTION that you have worked. please share to us.

    We are not sitll getting this

     

    Re: BMI160 TAP DETECTION

    Hi Florin,

    Did you find the solution.

    Please share you experience with us. we are in same struggle.

    Icon--AD-black-48x48Icon--address-consumer-data-black-48x48Icon--appointment-black-48x48Icon--back-left-black-48x48Icon--calendar-black-48x48Icon--center-alignedIcon--Checkbox-checkIcon--clock-black-48x48Icon--close-black-48x48Icon--compare-black-48x48Icon--confirmation-black-48x48Icon--dealer-details-black-48x48Icon--delete-black-48x48Icon--delivery-black-48x48Icon--down-black-48x48Icon--download-black-48x48Ic-OverlayAlertIcon--externallink-black-48x48Icon-Filledforward-right_adjustedIcon--grid-view-black-48x48IC_gd_Check-Circle170821_Icons_Community170823_Bosch_Icons170823_Bosch_Icons170821_Icons_CommunityIC-logout170821_Icons_Community170825_Bosch_Icons170821_Icons_CommunityIC-shopping-cart2170821_Icons_CommunityIC-upIC_UserIcon--imageIcon--info-i-black-48x48Icon--left-alignedIcon--Less-minimize-black-48x48Icon-FilledIcon--List-Check-grennIcon--List-Check-blackIcon--List-Cross-blackIcon--list-view-mobile-black-48x48Icon--list-view-black-48x48Icon--More-Maximize-black-48x48Icon--my-product-black-48x48Icon--newsletter-black-48x48Icon--payment-black-48x48Icon--print-black-48x48Icon--promotion-black-48x48Icon--registration-black-48x48Icon--Reset-black-48x48Icon--right-alignedshare-circle1Icon--share-black-48x48Icon--shopping-bag-black-48x48Icon-shopping-cartIcon--start-play-black-48x48Icon--store-locator-black-48x48Ic-OverlayAlertIcon--summary-black-48x48tumblrIcon-FilledvineIc-OverlayAlertwhishlist