---
title: "Reading Bluetooth cadence sensor data on iOS"
language: en
topics: ["AI", "apple", "bike", "creating", "data", "design", "gran fondo", "health", "heart", "minimal", "programming", "running", "sensors", "sport", "watch"]
full_article_url: https://willem.com/en/2024-05-11_developing-a-native-ios-app/
---
# Reading Bluetooth cadence sensor data on iOS

*The sensor sends raw bits, not a cadence number.*

> A Bluetooth cadence sensor does not send you a cadence number. It identifies as a combined speed and cadence sensor, sends flag-driven raw packets, and only gives a cumulative revolution count with a timestamp, from which you calculate RPM yourself.

Connecting a sensor takes many steps: scan for devices, connect, discover the device's characteristics, subscribe to the right characteristic, then decode raw bits, and every vendor encodes data its own way.
A cadence sensor uses the combined Cycling Speed and Cadence profile, so it always identifies as both a speed and a cadence sensor and you discover its actual capabilities on the fly. Packet contents depend on what the sensor detected, so you interpret each packet bit for bit by checking flags that say what the next bits represent.
ChatGPT's sample code did not work with my sensor. The Bluetooth debugging app Bluefy showed me what the sensor actually transmitted, and a piece of Java code on the official Bluetooth blog explained the decoding. I adapted it for different sensor profiles, translated it to Swift, and had a working prototype.
