Skip to content

Lightweight MicroPython driver for the Bosch BMI160 IMU (accelerometer + gyroscope) with clean APIs, interrupts, and calibration.

DanielBustillos/bmi160-micropython-driver

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

2 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

BMI160 MicroPython Driver

Lightweight MicroPython driver for the Bosch BMI160 IMU (accelerometer + gyroscope). Includes clean configuration APIs, data reads (raw and scaled), interrupts, and built‑in calibration (FOC) support.

Features

  • Simple initialization and power-up sequence
  • Flexible accelerometer/gyroscope range and output data rate (ODR) configuration
  • Motion and tap/double-tap interrupt support (any-motion, single/double tap)
  • Fast Offset Calibration (FOC) and manual offset adjustment
  • Read raw and scaled acceleration (g) and gyro (°/s) values
  • I2C interface, compatible with ESP32 and other MicroPython boards

Wiring

BMI160 Pin ESP32 Example Notes
VCC 3V3 1.71–3.6 V typical
GND GND Common ground
SCL 16 Any I2C SCL‑capable
SDA 4 Any I2C SDA‑capable
INT1 5 (optional) For motion/tap IRQs

bmi160 photo

Usage & Examples

Quick Start

from machine import I2C, Pin
from bmi160 import BMI160

i2c = I2C(0, sda=Pin(4), scl=Pin(16), freq=400_000)

imu = BMI160(i2c, addr=0x68)
imu.initialize()

# Configure
imu.set_accel_range(2)   # ±2 g
imu.set_accel_rate(100)  # 100 Hz
imu.set_gyro_range(250)  # ±250 °/s
imu.set_gyro_rate(100)   # 100 Hz

# Read scaled values
ax, ay, az = imu.read_accel()  # g
gx, gy, gz = imu.read_gyro()   # °/s
print(ax, ay, az, gx, gy, gz)

Read acceleration and gyro in a loop

imu.set_accel_range(2); imu.set_accel_rate(100)
imu.set_gyro_range(250); imu.set_gyro_rate(100)
while True:
  ax, ay, az = imu.read_accel()
  gx, gy, gz = imu.read_gyro()
  print("Accel (g):", ax, ay, az, "Gyro (°/s):", gx, gy, gz)

Calibration (FOC)

Note: Keep the board completely still. For accel FOC, place it flat (Z+ up) to target X=0 g, Y=0 g, Z=+1 g.

# Enable offset compensation, then run FOC
imu.set_accel_offset_enabled(True)
imu.set_gyro_offset_enabled(True)

imu.auto_calibrate_x_accel_offset(0)  # X -> 0 g
imu.auto_calibrate_y_accel_offset(0)  # Y -> 0 g
imu.auto_calibrate_z_accel_offset(1)  # Z -> +1 g
imu.auto_calibrate_gyro_offset()      # Gyro -> zero-rate

print("Accel offsets:", imu.get_x_accel_offset(), imu.get_y_accel_offset(), imu.get_z_accel_offset())
print("Gyro offsets:", imu.get_x_gyro_offset(), imu.get_y_gyro_offset(), imu.get_z_gyro_offset())

Gyro only

imu.initialize()
imu.set_gyro_range(250)
while True:
  gx, gy, gz = imu.read_gyro()
  print("g:\t{:.2f}\t{:.2f}\t{:.2f}".format(gx, gy, gz))

ESP32 deep sleep + wake on any-motion

imu = BMI160(i2c, addr=0x68)
imu.initialize()
imu.set_accel_range(2)
imu.set_accel_rate(100)
imu.set_motion_threshold_mg(200.0)
imu.set_motion_duration_s(0.03)
imu.set_int_output(active_low=False, open_drain=False, enable=True)
imu.set_int_latch('320_MS')
imu.enable_any_motion(True)
# Configure wakeup with esp32.wake_on_ext0/ext1 on the INT pin, then deepsleep

Troubleshooting

  • No response on I2C: verify wiring, address (0x68 vs 0x69), and pull‑ups.
  • FOC has no effect: ensure offsets are enabled before FOC and the sensor is completely still.
  • Motion interrupt not firing: verify INT pin polarity/latch config and threshold/duration settings.

Contributing

  • Issues and PRs welcome. Please keep code lightweight and portable across MicroPython boards.

License

  • Specify your preferred license here (e.g., MIT). If this folder is shared standalone, add a LICENSE file.

About

Lightweight MicroPython driver for the Bosch BMI160 IMU (accelerometer + gyroscope) with clean APIs, interrupts, and calibration.

Topics

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages