MicroPython Driver for ADXL335 Accelerometer

ADXL335 Driver Code for micro:bit

Download as zip file

'''
ADXL335 3-Axis Accelerometer
MicroPython driver for BBC micro:bit

AUTHOR: fredscave.com
DATE  : 2025/08
VERSION : 1.00

Acceleration is returned in g units.
'''

from microbit import *
from math import atan, sqrt, pi

# Sensitivity at 3.3V from datasheet = 340.3 mV/g.
# Converting to 10-bit ADC sensitivity
SENSITIVITY = 105.6

class ADXL335():
    def __init__(self, Xpin=pin0, Ypin=pin1, Zpin=pin2):
        self.Xpin = Xpin
        self.Ypin = Ypin
        self.Zpin = Zpin
        self.OSR = 1
        self.Xerror = 0
        self.Yerror = 0

    # Sets the oversampling rate.
    # A value between 1 and 8.
    # This is the number of samples
    # taken and then averaged for
    # the output acceleration.
    def SetOSR(self, osr=1):
        if osr not in range(1, 9):
            self.OSR = 1
        else:
            self.OSR = osr

    # Returns acceleration of all three
    # axis and returned as a tuple.
    @property
    def Reading(self):
        x = self.X
        y = self.Y
        z = self.Z
        return (x, y, z)

    # Returns the acceleration
    # in the X-axis.
    @property
    def X(self):
        sum = 0
        for __ in range(self.OSR):
            raw = self.Xpin.read_analog()
            sum += raw
        return (self._scale(sum/self.OSR))

    # Returns the acceleration
    # in the Y-axis.
    @property
    def Y(self):
        sum = 0
        for __ in range(self.OSR):
            raw = self.Ypin.read_analog()
            sum += raw
        return (self._scale(sum/self.OSR))

    # Returns the acceleration
    # in the Z-axis.
    @property
    def Z(self):
        sum = 0
        for __ in range(self.OSR):
            raw = self.Zpin.read_analog()
            sum += raw
        return (self._scale(sum/self.OSR))

    def _scale(self, raw):
        return (raw - 512) / SENSITIVITY

    # Returns inclination of X-axis from the
    # horizontal in degrees. Offsets are
    # subtracted if a calibration has been done.
    @property
    def Xangle(self):
        t = self.Reading
        X, Y, Z = t[0], t[1], t[2]
        p = atan(X / sqrt((Y*Y + Z*Z))) * 180 / pi
        return p - self.Xerror

    # Returns inclination of Y-axis from the
    # horizontal in degrees. Offsets are
    # subtracted if a calibration has been done.
    @property
    def Yangle(self):
        t = self.Reading
        X, Y, Z = t[0], t[1], t[2]
        p = atan(Y / sqrt((X*X + Z*Z))) * 180 / pi
        return p - self.Yerror

    # Returns the oversampling rate (OSR)
    # Value between 1 and 8
    @property
    def GetOSR(self):
        return self.OSR
          

Comparison of Angle Measurements

This project will measure a tilt angle in the X-axis and compare the results with that obtained from a commercial inclinometer. The inclinometer has a magnetic base which easily mounts on a breadboard.

The image below shows the setup used.


Code:

# This program measures a tilt angle (X-axis)
# using an ADXL335 accelerometer mounted on
# a breadboard.

# A commercial inclinometer can be mounted on
# the breadboard inline with the sensor as a
# check on the accuracy of the ADXL335's
# measurement.

from fc_adxl335 import *

sensor = ADXL335()
sensor.SetOSR(8)

# Endless loop:
# Pressing Button A on the micro:bit
# returns the X-axis angle.
while True:
    print('\nPress Button A to calculate the angle')
    while not button_a.was_pressed():
        sleep(100)
    print('Tilt in X-axis:', sensor.Xangle, 'degrees')

        
          
Typical Output:

Press Button A to calculate the angle
Tilt in X-axis: -22.05697 degrees

Press Button A to calculate the angle
Tilt in X-axis: -22.30622 degrees

Press Button A to calculate the angle
Tilt in X-axis: -21.74835 degrees
        
Inclinometer and ADXL335 accelerometer measuring X-axis angle.
Inclinometer and ADXL335 accelerometer measuring X-axis tilt angle

There is a difference of just less than 3° between the ADXL335 and the Shane inclinometer readings. The setup for this test is quite primitive with everything attached to a breadboard that's probably not exactly square. So, this isn't such a bad result!