Adafruit_AS5600/Adafruit_AS5600.cpp
ladyada f182def47d Apply clang-format to all source files for consistent code formatting
Format C/C++ files according to project style guidelines for improved readability and maintainability.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-06-11 13:17:37 -04:00

423 lines
No EOL
13 KiB
C++

/*!
* @file Adafruit_AS5600.cpp
*
* @mainpage Adafruit AS5600 12-bit contactless position sensor library
*
* @section intro_sec Introduction
*
* This is the documentation for Adafruit's AS5600 driver for the
* Arduino platform. It is designed specifically to work with the
* Adafruit AS5600 breakout:
*
* These sensors use I2C to communicate, 2 pins are required to interface.
*
* Adafruit invests time and resources providing this open source code,
* please support Adafruit and open-source hardware by purchasing products
* from Adafruit!
*
* @section author Author
*
* Written by Limor Fried for Adafruit Industries.
*
* @section license License
*
* MIT license, all text above must be included in any redistribution
*/
#include "Adafruit_AS5600.h"
/*!
* @brief Instantiates a new AS5600 class
*/
Adafruit_AS5600::Adafruit_AS5600() {}
/*!
* @brief Destructor for AS5600 class
*/
Adafruit_AS5600::~Adafruit_AS5600() {
if (i2c_dev) {
delete i2c_dev;
}
}
/*!
* @brief Initializes the sensor
* @param i2c_addr The I2C address to use (default AS5600_DEFAULT_ADDR)
* @param wire The Wire object to use for I2C communication
* @return true if initialization was successful, false otherwise
*/
bool Adafruit_AS5600::begin(uint8_t i2c_addr, TwoWire* wire) {
i2c_dev = new Adafruit_I2CDevice(i2c_addr, wire);
if (!i2c_dev->begin()) {
return false;
}
return true;
}
/*!
* @brief Get the ZMCO count - number of times ZPOS and MPOS have been burned
* @return Number of times ZPOS/MPOS have been permanently written (0-3)
*/
uint8_t Adafruit_AS5600::getZMCount() {
Adafruit_BusIO_Register zmco_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_ZMCO, 1);
uint8_t zmco_value = zmco_reg.read();
return zmco_value & 0x03; // Only bits 1:0 are used
}
/*!
* @brief Get the zero position (start position) - 12-bit value
* @return Zero position value (0-4095)
*/
uint16_t Adafruit_AS5600::getZPosition() {
Adafruit_BusIO_Register zpos_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_ZPOS_H, 2, MSBFIRST);
uint16_t zpos_value = zpos_reg.read();
return zpos_value & 0x0FFF; // Only 12 bits are used
}
/*!
* @brief Set the zero position (start position) - 12-bit value
* @param position Zero position value (0-4095)
* @return true if write was successful, false otherwise
*/
bool Adafruit_AS5600::setZPosition(uint16_t position) {
position &= 0x0FFF; // Ensure only 12 bits are used
Adafruit_BusIO_Register zpos_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_ZPOS_H, 2, MSBFIRST);
return zpos_reg.write(position);
}
/*!
* @brief Get the maximum position (stop position) - 12-bit value
* @return Maximum position value (0-4095)
*/
uint16_t Adafruit_AS5600::getMPosition() {
Adafruit_BusIO_Register mpos_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_MPOS_H, 2, MSBFIRST);
uint16_t mpos_value = mpos_reg.read();
return mpos_value & 0x0FFF; // Only 12 bits are used
}
/*!
* @brief Set the maximum position (stop position) - 12-bit value
* @param position Maximum position value (0-4095)
* @return true if write was successful, false otherwise
*/
bool Adafruit_AS5600::setMPosition(uint16_t position) {
position &= 0x0FFF; // Ensure only 12 bits are used
Adafruit_BusIO_Register mpos_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_MPOS_H, 2, MSBFIRST);
return mpos_reg.write(position);
}
/*!
* @brief Get the maximum angle range - 12-bit value
* @return Maximum angle value (0-4095, representing 0-360 degrees)
*/
uint16_t Adafruit_AS5600::getMaxAngle() {
Adafruit_BusIO_Register mang_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_MANG_H, 2, MSBFIRST);
uint16_t mang_value = mang_reg.read();
return mang_value & 0x0FFF; // Only 12 bits are used
}
/*!
* @brief Set the maximum angle range - 12-bit value
* @param angle Maximum angle value (0-4095, representing 0-360 degrees)
* @return true if write was successful, false otherwise
*/
bool Adafruit_AS5600::setMaxAngle(uint16_t angle) {
angle &= 0x0FFF; // Ensure only 12 bits are used
Adafruit_BusIO_Register mang_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_MANG_H, 2, MSBFIRST);
return mang_reg.write(angle);
}
/*!
* @brief Get the raw angle reading - 12-bit value (unscaled/unmodified)
* @return Raw angle value (0-4095)
*/
uint16_t Adafruit_AS5600::getRawAngle() {
Adafruit_BusIO_Register rawangle_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_RAWANGLE_H, 2, MSBFIRST);
uint16_t rawangle_value = rawangle_reg.read();
return rawangle_value & 0x0FFF; // Only 12 bits are used
}
/*!
* @brief Get the scaled angle reading - 12-bit value
* @return Angle value (0-4095, scaled according to ZPOS/MPOS/MANG settings)
*/
uint16_t Adafruit_AS5600::getAngle() {
Adafruit_BusIO_Register angle_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_ANGLE_H, 2, MSBFIRST);
uint16_t angle_value = angle_reg.read();
return angle_value & 0x0FFF; // Only 12 bits are used
}
/*!
* @brief Check if AGC minimum gain overflow occurred (magnet too strong)
* @return true if MH bit is set (magnet too strong), false otherwise
*/
bool Adafruit_AS5600::isAGCminGainOverflow() {
Adafruit_BusIO_Register status_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_STATUS, 1);
Adafruit_BusIO_RegisterBits mh_bit =
Adafruit_BusIO_RegisterBits(&status_reg, 1, 3);
return mh_bit.read();
}
/*!
* @brief Check if AGC maximum gain overflow occurred (magnet too weak)
* @return true if ML bit is set (magnet too weak), false otherwise
*/
bool Adafruit_AS5600::isAGCmaxGainOverflow() {
Adafruit_BusIO_Register status_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_STATUS, 1);
Adafruit_BusIO_RegisterBits ml_bit =
Adafruit_BusIO_RegisterBits(&status_reg, 1, 4);
return ml_bit.read();
}
/*!
* @brief Check if magnet is detected
* @return true if MD bit is set (magnet detected), false otherwise
*/
bool Adafruit_AS5600::isMagnetDetected() {
Adafruit_BusIO_Register status_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_STATUS, 1);
Adafruit_BusIO_RegisterBits md_bit =
Adafruit_BusIO_RegisterBits(&status_reg, 1, 5);
return md_bit.read();
}
/*!
* @brief Get the AGC (Automatic Gain Control) value
* @return AGC value (0-255 in 5V mode, 0-128 in 3.3V mode)
*/
uint8_t Adafruit_AS5600::getAGC() {
Adafruit_BusIO_Register agc_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_AGC, 1);
return agc_reg.read();
}
/*!
* @brief Get the magnitude value from the CORDIC processor
* @return Magnitude value (0-4095)
*/
uint16_t Adafruit_AS5600::getMagnitude() {
Adafruit_BusIO_Register magnitude_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_MAGNITUDE_H, 2, MSBFIRST);
uint16_t magnitude_value = magnitude_reg.read();
return magnitude_value & 0x0FFF; // Only 12 bits are used
}
/*!
* @brief Enable or disable watchdog timer
* @param enable true to enable watchdog, false to disable
* @return true if write was successful, false otherwise
*/
bool Adafruit_AS5600::enableWatchdog(bool enable) {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_H, 2, MSBFIRST);
Adafruit_BusIO_RegisterBits wd_bit =
Adafruit_BusIO_RegisterBits(&conf_reg, 1, 13);
return wd_bit.write(enable ? 1 : 0);
}
/*!
* @brief Get watchdog timer status
* @return true if watchdog is enabled, false otherwise
*/
bool Adafruit_AS5600::getWatchdog() {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_H, 2, MSBFIRST);
Adafruit_BusIO_RegisterBits wd_bit =
Adafruit_BusIO_RegisterBits(&conf_reg, 1, 13);
return wd_bit.read();
}
/*!
* @brief Set power mode
* @param mode Power mode to set (AS5600_POWER_MODE_NOM, LPM1, LPM2, LPM3)
* @return true if write was successful, false otherwise
*/
bool Adafruit_AS5600::setPowerMode(as5600_power_mode_t mode) {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_L, 1);
Adafruit_BusIO_RegisterBits pm_bits =
Adafruit_BusIO_RegisterBits(&conf_reg, 2, 0);
return pm_bits.write((uint8_t)mode);
}
/*!
* @brief Get current power mode
* @return Current power mode setting
*/
as5600_power_mode_t Adafruit_AS5600::getPowerMode() {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_L, 1);
Adafruit_BusIO_RegisterBits pm_bits =
Adafruit_BusIO_RegisterBits(&conf_reg, 2, 0);
return (as5600_power_mode_t)pm_bits.read();
}
/*!
* @brief Set hysteresis setting
* @param hysteresis Hysteresis to set (AS5600_HYSTERESIS_OFF, 1LSB, 2LSB, 3LSB)
* @return true if write was successful, false otherwise
*/
bool Adafruit_AS5600::setHysteresis(as5600_hysteresis_t hysteresis) {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_L, 1);
Adafruit_BusIO_RegisterBits hyst_bits =
Adafruit_BusIO_RegisterBits(&conf_reg, 2, 2);
return hyst_bits.write((uint8_t)hysteresis);
}
/*!
* @brief Get current hysteresis setting
* @return Current hysteresis setting
*/
as5600_hysteresis_t Adafruit_AS5600::getHysteresis() {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_L, 1);
Adafruit_BusIO_RegisterBits hyst_bits =
Adafruit_BusIO_RegisterBits(&conf_reg, 2, 2);
return (as5600_hysteresis_t)hyst_bits.read();
}
/*!
* @brief Set output stage configuration
* @param output Output stage to set (ANALOG_FULL, ANALOG_REDUCED, DIGITAL_PWM,
* RESERVED)
* @return true if write was successful, false otherwise
*/
bool Adafruit_AS5600::setOutputStage(as5600_output_stage_t output) {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_L, 1);
Adafruit_BusIO_RegisterBits outs_bits =
Adafruit_BusIO_RegisterBits(&conf_reg, 2, 4);
return outs_bits.write((uint8_t)output);
}
/*!
* @brief Get current output stage configuration
* @return Current output stage setting
*/
as5600_output_stage_t Adafruit_AS5600::getOutputStage() {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_L, 1);
Adafruit_BusIO_RegisterBits outs_bits =
Adafruit_BusIO_RegisterBits(&conf_reg, 2, 4);
return (as5600_output_stage_t)outs_bits.read();
}
/*!
* @brief Set PWM frequency
* @param freq PWM frequency to set (115Hz, 230Hz, 460Hz, 920Hz)
* @return true if write was successful, false otherwise
*/
bool Adafruit_AS5600::setPWMFreq(as5600_pwm_freq_t freq) {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_L, 1);
Adafruit_BusIO_RegisterBits pwmf_bits =
Adafruit_BusIO_RegisterBits(&conf_reg, 2, 6);
return pwmf_bits.write((uint8_t)freq);
}
/*!
* @brief Get current PWM frequency setting
* @return Current PWM frequency setting
*/
as5600_pwm_freq_t Adafruit_AS5600::getPWMFreq() {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_L, 1);
Adafruit_BusIO_RegisterBits pwmf_bits =
Adafruit_BusIO_RegisterBits(&conf_reg, 2, 6);
return (as5600_pwm_freq_t)pwmf_bits.read();
}
/*!
* @brief Set slow filter setting
* @param filter Slow filter to set (16x, 8x, 4x, 2x)
* @return true if write was successful, false otherwise
*/
bool Adafruit_AS5600::setSlowFilter(as5600_slow_filter_t filter) {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_H, 1);
Adafruit_BusIO_RegisterBits sf_bits =
Adafruit_BusIO_RegisterBits(&conf_reg, 2, 0);
return sf_bits.write((uint8_t)filter);
}
/*!
* @brief Get current slow filter setting
* @return Current slow filter setting
*/
as5600_slow_filter_t Adafruit_AS5600::getSlowFilter() {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_H, 1);
Adafruit_BusIO_RegisterBits sf_bits =
Adafruit_BusIO_RegisterBits(&conf_reg, 2, 0);
return (as5600_slow_filter_t)sf_bits.read();
}
/*!
* @brief Set fast filter threshold
* @param thresh Fast filter threshold to set
* @return true if write was successful, false otherwise
*/
bool Adafruit_AS5600::setFastFilterThresh(as5600_fast_filter_thresh_t thresh) {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_H, 1);
Adafruit_BusIO_RegisterBits fth_bits =
Adafruit_BusIO_RegisterBits(&conf_reg, 3, 2);
return fth_bits.write((uint8_t)thresh);
}
/*!
* @brief Get current fast filter threshold setting
* @return Current fast filter threshold setting
*/
as5600_fast_filter_thresh_t Adafruit_AS5600::getFastFilterThresh() {
Adafruit_BusIO_Register conf_reg =
Adafruit_BusIO_Register(i2c_dev, AS5600_REG_CONF_H, 1);
Adafruit_BusIO_RegisterBits fth_bits =
Adafruit_BusIO_RegisterBits(&conf_reg, 3, 2);
return (as5600_fast_filter_thresh_t)fth_bits.read();
}