diff --git a/midi2cv/drivers/ad57x4.cc b/midi2cv/drivers/ad57x4.cc index 42868e0..0295250 100644 --- a/midi2cv/drivers/ad57x4.cc +++ b/midi2cv/drivers/ad57x4.cc @@ -1,8 +1,8 @@ #include "ad57x4.h" #include "peripherals.h" #include "spi_mode.h" -#include "stm32f3xx_hal_gpio.h" #include +#include static const uint32_t kPinEnable = GPIO_PIN_5; @@ -18,6 +18,29 @@ void AD57X4::Init() HAL_GPIO_WritePin(GPIOB, kPinEnable, GPIO_PIN_SET); } +void AD57X4::WriteVoltage(uint8_t dac, float voltage) { + VoltageRange range = VOLTAGE_RANGE_FIVE_VOLTS; + if(fabs(voltage) > 5) range = VOLTAGE_RANGE_TEN_VOLTS; + if(fabs(voltage) > 10) range = VOLTAGE_RANGE_TEN_EIGHT_VOLTS; + + float multiplier = 2.0f; + if(range == VOLTAGE_RANGE_TEN_VOLTS) multiplier = 4.0f; + if(range == VOLTAGE_RANGE_TEN_EIGHT_VOLTS) multiplier = 4.32f; + float refin = 2.5f; + + if(voltage < 0) { + // convert to signed value + int16_t value = (voltage / (multiplier * refin)) * (65535.0f); + + this->WriteDacBipolar(dac, range, value); + } else { + // convert to unsigned value + uint16_t value = (voltage / (multiplier * refin)) * (65535.0f); + + this->WriteDacUnipolar(dac, range, value); + } +} + void AD57X4::EnableAndSetRange(uint8_t dac, VoltageRange range, bool bipolar) { if (!(this->dacPower & (1 << dac))) { diff --git a/midi2cv/drivers/ad57x4.h b/midi2cv/drivers/ad57x4.h index 121b065..1f2f32b 100644 --- a/midi2cv/drivers/ad57x4.h +++ b/midi2cv/drivers/ad57x4.h @@ -3,6 +3,7 @@ #include "stmlib/stmlib.h" enum VoltageRange { + VOLTAGE_RANGE_NONE = 4, VOLTAGE_RANGE_FIVE_VOLTS = 0, VOLTAGE_RANGE_TEN_VOLTS = 1, VOLTAGE_RANGE_TEN_EIGHT_VOLTS = 2 @@ -17,10 +18,16 @@ enum Register { class AD57X4 { public: - AD57X4() {}; + AD57X4() + { + for (size_t i = 0; i < 4; i++) + dacRange[i] = VOLTAGE_RANGE_NONE; + }; void Init(); + void WriteVoltage(uint8_t dac, float voltage); // smart range choosing! + void WriteDacBipolar(uint8_t dac, VoltageRange range, int16_t value); void WriteDacUnipolar(uint8_t dac, VoltageRange range, uint16_t value);