Skip to content

Commit de77dab

Browse files
committed
manually enable reports
1 parent 23bd06d commit de77dab

File tree

3 files changed

+83
-55
lines changed

3 files changed

+83
-55
lines changed

adafruit_bno080/__init__.py

Lines changed: 57 additions & 49 deletions
Original file line numberDiff line numberDiff line change
@@ -67,18 +67,18 @@
6767

6868

6969
# Calibrated Acceleration (m/s2)
70-
_BNO_REPORT_ACCELEROMETER = const(0x01)
70+
BNO_REPORT_ACCELEROMETER = const(0x01)
7171
# Calibrated gyroscope (rad/s).
72-
_BNO_REPORT_GYROSCOPE = const(0x02)
72+
BNO_REPORT_GYROSCOPE = const(0x02)
7373
# Magnetic field calibrated (in µTesla). The fully calibrated magnetic field measurement.
74-
_BNO_REPORT_MAGNETIC_FIELD = const(0x03)
74+
BNO_REPORT_MAGNETIC_FIELD = const(0x03)
7575
# Linear acceleration (m/s2). Acceleration of the device with gravity removed
76-
_BNO_REPORT_LINEAR_ACCELERATION = const(0x04)
76+
BNO_REPORT_LINEAR_ACCELERATION = const(0x04)
7777
# Rotation Vector
78-
_BNO_REPORT_ROTATION_VECTOR = const(0x05)
79-
_BNO_REPORT_GEOMAGNETIC_ROTATION_VECTOR = const(0x09)
80-
_BNO_REPORT_STEP_COUNTER = const(0x11)
81-
_BNO_REPORT_SHAKE_DETECTOR = const(0x19)
78+
BNO_REPORT_ROTATION_VECTOR = const(0x05)
79+
BNO_REPORT_GEOMAGNETIC_ROTATION_VECTOR = const(0x09)
80+
BNO_REPORT_STEP_COUNTER = const(0x11)
81+
BNO_REPORT_SHAKE_DETECTOR = const(0x19)
8282

8383

8484
_DEFAULT_REPORT_INTERVAL = const(50000) # in microseconds = 50ms
@@ -112,15 +112,15 @@
112112
_BNO_CMD_TIMESTAMP_REBASE: 5,
113113
}
114114
# length is probably deterministic, like axes * 2 +4
115-
_ENABLED_SENSOR_REPORTS = {
116-
_BNO_REPORT_ACCELEROMETER: (_Q_POINT_8_SCALAR, 3, 10),
117-
_BNO_REPORT_GYROSCOPE: (_Q_POINT_9_SCALAR, 3, 10),
118-
_BNO_REPORT_MAGNETIC_FIELD: (_Q_POINT_4_SCALAR, 3, 10),
119-
_BNO_REPORT_LINEAR_ACCELERATION: (_Q_POINT_8_SCALAR, 3, 10),
120-
_BNO_REPORT_ROTATION_VECTOR: (_Q_POINT_14_SCALAR, 4, 14,),
121-
_BNO_REPORT_GEOMAGNETIC_ROTATION_VECTOR: (_Q_POINT_12_SCALAR, 4, 14),
122-
_BNO_REPORT_STEP_COUNTER: (1, 1, 12),
123-
_BNO_REPORT_SHAKE_DETECTOR: (1, 1, 6),
115+
_AVAIL_SENSOR_REPORTS = {
116+
BNO_REPORT_ACCELEROMETER: (_Q_POINT_8_SCALAR, 3, 10),
117+
BNO_REPORT_GYROSCOPE: (_Q_POINT_9_SCALAR, 3, 10),
118+
BNO_REPORT_MAGNETIC_FIELD: (_Q_POINT_4_SCALAR, 3, 10),
119+
BNO_REPORT_LINEAR_ACCELERATION: (_Q_POINT_8_SCALAR, 3, 10),
120+
BNO_REPORT_ROTATION_VECTOR: (_Q_POINT_14_SCALAR, 4, 14,),
121+
BNO_REPORT_GEOMAGNETIC_ROTATION_VECTOR: (_Q_POINT_12_SCALAR, 4, 14),
122+
BNO_REPORT_STEP_COUNTER: (1, 1, 12),
123+
BNO_REPORT_SHAKE_DETECTOR: (1, 1, 6),
124124
}
125125

126126
DATA_BUFFER_SIZE = const(512) # data buffer size. obviously eats ram
@@ -158,7 +158,7 @@ def wrapper_timer(*args, **kwargs):
158158
def _parse_sensor_report_data(report_bytes):
159159
data_offset = 4 # this may not always be true
160160
report_id = report_bytes[0]
161-
scalar, count, _report_length = _ENABLED_SENSOR_REPORTS[report_id]
161+
scalar, count, _report_length = _AVAIL_SENSOR_REPORTS[report_id]
162162

163163
results = []
164164

@@ -204,7 +204,7 @@ def parse_sensor_id(buffer):
204204

205205
def _report_length(report_id):
206206
if report_id < 0xF0: # it's a sensor report
207-
return _ENABLED_SENSOR_REPORTS[report_id][2]
207+
return _AVAIL_SENSOR_REPORTS[report_id][2]
208208

209209
return _REPORT_LENGTHS[report_id]
210210

@@ -362,53 +362,62 @@ def initialize(self):
362362
self.soft_reset()
363363
if not self._check_id():
364364
raise RuntimeError("Could not read ID")
365-
for report_type in _ENABLED_SENSOR_REPORTS:
366-
self._enable_feature(report_type)
367365

368366
@property
369367
def magnetic(self):
370368
"""A tuple of the current magnetic field measurements on the X, Y, and Z axes"""
371369
self._process_available_packets() # decorator?
372-
return self._readings[_BNO_REPORT_MAGNETIC_FIELD]
373-
370+
try:
371+
return self._readings[BNO_REPORT_MAGNETIC_FIELD]
372+
except KeyError:
373+
raise RuntimeError("No magfield report found, is it enabled?") from None
374374
@property
375375
def quaternion(self):
376376
"""A quaternion representing the current rotation vector"""
377377
self._process_available_packets()
378-
return self._readings[_BNO_REPORT_ROTATION_VECTOR]
378+
return self._readings[BNO_REPORT_ROTATION_VECTOR]
379379

380380
@property
381381
def geomagnetic_quaternion(self):
382382
"""A quaternion representing the current geomagnetic rotation vector"""
383383
self._process_available_packets()
384-
return self._readings[_BNO_REPORT_GEOMAGNETIC_ROTATION_VECTOR]
384+
return self._readings[BNO_REPORT_GEOMAGNETIC_ROTATION_VECTOR]
385385

386386
@property
387387
def steps(self):
388388
"""The number of steps detected since the sensor was initialized"""
389389
self._process_available_packets()
390-
return self._readings[_BNO_REPORT_STEP_COUNTER]
390+
return self._readings[BNO_REPORT_STEP_COUNTER]
391391

392392
@property
393393
def linear_acceleration(self):
394394
"""A tuple representing the current linear acceleration values on the X, Y, and Z
395395
axes in meters per second squared"""
396396
self._process_available_packets()
397-
return self._readings[_BNO_REPORT_LINEAR_ACCELERATION]
397+
try:
398+
return self._readings[BNO_REPORT_LINEAR_ACCELERATION]
399+
except KeyError:
400+
raise RuntimeError("No lin. accel report found, is it enabled?") from None
398401

399402
@property
400403
def acceleration(self):
401404
"""A tuple representing the acceleration measurements on the X, Y, and Z
402405
axes in meters per second squared"""
403406
self._process_available_packets()
404-
return self._readings[_BNO_REPORT_ACCELEROMETER]
407+
try:
408+
return self._readings[BNO_REPORT_ACCELEROMETER]
409+
except KeyError:
410+
raise RuntimeError("No accel report found, is it enabled?") from None
405411

406412
@property
407413
def gyro(self):
408414
"""A tuple representing Gyro's rotation measurements on the X, Y, and Z
409415
axes in radians per second"""
410416
self._process_available_packets()
411-
return self._readings[_BNO_REPORT_GYROSCOPE]
417+
try:
418+
return self._readings[BNO_REPORT_GYROSCOPE]
419+
except KeyError:
420+
raise RuntimeError("No gyro report found, is it enabled?") from None
412421

413422
@property
414423
def shake(self):
@@ -419,20 +428,24 @@ def shake(self):
419428
this property is not guaranteed to reflect the shake state at the moment it is read
420429
"""
421430
self._process_available_packets()
422-
shake_detected = self._readings[_BNO_REPORT_SHAKE_DETECTOR]
431+
shake_detected = self._readings[BNO_REPORT_SHAKE_DETECTOR]
423432
# clear on read
424433
if shake_detected:
425-
self._readings[_BNO_REPORT_SHAKE_DETECTOR] = False
434+
self._readings[BNO_REPORT_SHAKE_DETECTOR] = False
426435

427436
# # decorator?
428437
def _process_available_packets(self):
429438
processed_count = 0
430439
while self._data_ready:
431-
new_packet = self._read_packet()
440+
print("reading a packet")
441+
try:
442+
new_packet = self._read_packet()
443+
except PacketError:
444+
continue
432445
self._handle_packet(new_packet)
433446
processed_count += 1
434447
self._dbg("")
435-
self._dbg("Processesd", processed_count, "packets")
448+
#print("Processed", processed_count, "packets")
436449
self._dbg("")
437450
# we'll probably need an exit here for fast sensor rates
438451
self._dbg("")
@@ -511,14 +524,14 @@ def _process_report(self, report_id, report_bytes):
511524
print(outstr)
512525
self._dbg("")
513526

514-
if report_id == _BNO_REPORT_STEP_COUNTER:
527+
if report_id == BNO_REPORT_STEP_COUNTER:
515528
self._readings[report_id] = _parse_step_couter_report(report_bytes)
516529
return
517-
if report_id == _BNO_REPORT_SHAKE_DETECTOR:
530+
if report_id == BNO_REPORT_SHAKE_DETECTOR:
518531
shake_detected = _parse_shake_report(report_bytes)
519532
# shake not previously detected - auto cleared by 'shake' property
520-
if not self._readings[_BNO_REPORT_SHAKE_DETECTOR]:
521-
self._readings[_BNO_REPORT_SHAKE_DETECTOR] = shake_detected
533+
if not self._readings[BNO_REPORT_SHAKE_DETECTOR]:
534+
self._readings[BNO_REPORT_SHAKE_DETECTOR] = shake_detected
522535
return
523536

524537
sensor_data = _parse_sensor_report_data(report_bytes)
@@ -541,10 +554,11 @@ def _get_feature_enable_report(
541554
pack_into("<I", set_feature_report, 5, report_interval)
542555
return set_feature_report
543556

544-
def _enable_feature(self, feature_id):
557+
def enable_feature(self, feature_id):
545558
self._dbg("\n********** Enabling feature id:", feature_id, "**********")
546559

547560
set_feature_report = self._get_feature_enable_report(feature_id)
561+
print("Enabling", feature_id)
548562
self._send_packet(_BNO_CHANNEL_CONTROL, set_feature_report)
549563
while True:
550564
packet = self._wait_for_packet_type(
@@ -553,15 +567,16 @@ def _enable_feature(self, feature_id):
553567

554568
if packet.data[1] == feature_id:
555569
if (
556-
feature_id == _BNO_REPORT_ROTATION_VECTOR
570+
feature_id == BNO_REPORT_ROTATION_VECTOR
557571
): # check for other vector types as well
558572
self._readings[feature_id] = (0.0, 0.0, 0.0, 0.0)
559573
else:
560574
self._readings[feature_id] = (0.0, 0.0, 0.0)
561-
self._dbg("Enabled")
562-
return True
575+
print("Enabled", feature_id)
576+
break
577+
else:
578+
raise RuntimeError("Was not able to enable feature", feature_id)
563579

564-
return False
565580

566581
def _check_id(self):
567582
self._dbg("\n********** READ ID **********")
@@ -613,13 +628,6 @@ def _get_data(self, index, fmt_string):
613628
data_index = index + 4
614629
return unpack_from(fmt_string, self._data_buffer, offset=data_index)[0]
615630

616-
def _read_header(self):
617-
"""Reads the first 4 bytes available as a header"""
618-
with self.bus_device_obj as bus_dev: # pylint:disable=no-member
619-
bus_dev.readinto(self._data_buffer, end=4)
620-
packet_header = Packet.header_from_buffer(self._data_buffer)
621-
self._dbg(packet_header)
622-
return packet_header
623631

624632
# pylint:disable=no-self-use
625633
@property

adafruit_bno080/i2c.py

Lines changed: 16 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -49,15 +49,27 @@ def _send_packet(self, channel, data):
4949
# returns true if available data was read
5050
# the sensor will always tell us how much there is, so no need to track it ourselves
5151

52+
def _read_header(self):
53+
"""Reads the first 4 bytes available as a header"""
54+
while True:
55+
with self.bus_device_obj as i2c:
56+
try:
57+
i2c.readinto(self._data_buffer, end=4) # this is expecting a header
58+
break
59+
except RuntimeError:
60+
time.sleep(0.1)
61+
pass
62+
packet_header = Packet.header_from_buffer(self._data_buffer)
63+
self._dbg(packet_header)
64+
return packet_header
65+
5266
def _read_packet(self):
5367
# TODO: MAGIC NUMBER?
54-
55-
time.sleep(0.001) #
5668
# TODO: this can be `_read_header` or know it's done by `_data_ready`
5769
with self.bus_device_obj as i2c:
5870
i2c.readinto(self._data_buffer, end=4) # this is expecting a header?
5971
self._dbg("")
60-
self._dbg("SHTP READ packet header: ", [hex(x) for x in self._data_buffer[0:4]])
72+
#print("SHTP READ packet header: ", [hex(x) for x in self._data_buffer[0:4]])
6173

6274
header = Packet.header_from_buffer(self._data_buffer)
6375
packet_byte_count = header.packet_byte_count
@@ -105,6 +117,7 @@ def _read(self, requested_read_length):
105117
@property
106118
def _data_ready(self):
107119
header = self._read_header()
120+
108121
if header.channel_number > 5:
109122
self._dbg("channel number out of range:", header.channel_number)
110123
# data_length, packet_byte_count)

examples/bno080_simpletest.py

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -4,21 +4,27 @@
44
import time
55
import board
66
import busio
7+
import adafruit_bno080
78
from adafruit_bno080.i2c import BNO080_I2C
89
from digitalio import DigitalInOut
910

10-
i2c = busio.I2C(board.SCL, board.SDA)
11+
i2c = busio.I2C(board.SCL, board.SDA, frequency=400000)
1112
reset_pin = DigitalInOut(board.G0)
1213
bno = BNO080_I2C(i2c, reset=reset_pin)
1314

15+
bno.enable_feature(adafruit_bno080.BNO_REPORT_ACCELEROMETER)
16+
#bno.enable_feature(adafruit_bno080.BNO_REPORT_GYROSCOPE)
17+
#bno.enable_feature(adafruit_bno080.BNO_REPORT_MAGNETIC_FIELD)
18+
1419
while True:
1520

16-
# print("Acceleration:")
21+
print("Acceleration:")
1722
accel_x, accel_y, accel_z = bno.acceleration # pylint:disable=no-member
1823
print("X: %0.6f Y: %0.6f Z: %0.6f m/s^2" % (accel_x, accel_y, accel_z))
1924
print("")
2025

21-
# print("Gyro:")
26+
"""
27+
print("Gyro:")
2228
gyro_x, gyro_y, gyro_z = bno.gyro # pylint:disable=no-member
2329
print("X: %0.6f Y: %0.6f Z: %0.6f rads/s" % (gyro_x, gyro_y, gyro_z))
2430
print("")
@@ -65,3 +71,4 @@
6571
print("")
6672
6773
sleep(0.5)
74+
"""

0 commit comments

Comments
 (0)