From 7551a06cf4b800b51b284bbf42afbbc92d9015fd Mon Sep 17 00:00:00 2001 From: tociek Date: Thu, 12 Nov 2015 00:22:11 +0100 Subject: [PATCH] Corrected APA102 USB (adalight) led device I have removed the 'hack' that allowed to use APA102 with original version of adalight. I have modified adalight code and placed it into dependencies folder. This change is not backward compatible, so it won't work with original adalight code. The reason for the change is that last leds were not acting as they should (last led red). Additionally with this change and new arduino code, performance is lot better and lights change much smoother. I have also changed switchOff method that requires different data sent to apa102 to turn all leds off. Enjoy :) Jacek Former-commit-id: 624fe6c429aee896b150d23289f0be19e040474d --- dependencies/LightberryHDUSBAPA1021.1.zip | Bin 0 -> 4443 bytes libsrc/leddevice/LedDeviceAdalightApa102.cpp | 35 ++++++++++++++----- libsrc/leddevice/LedDeviceAdalightApa102.h | 8 +++-- 3 files changed, 32 insertions(+), 11 deletions(-) create mode 100644 dependencies/LightberryHDUSBAPA1021.1.zip diff --git a/dependencies/LightberryHDUSBAPA1021.1.zip b/dependencies/LightberryHDUSBAPA1021.1.zip new file mode 100644 index 0000000000000000000000000000000000000000..13c743a080b77d837e04beb6a62e7e210ae984bc GIT binary patch literal 4443 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 PdnNi~9{quczdrXr;VLB$ literal 0 HcmV?d00001 diff --git a/libsrc/leddevice/LedDeviceAdalightApa102.cpp b/libsrc/leddevice/LedDeviceAdalightApa102.cpp index 07732080..5f5cc42e 100644 --- a/libsrc/leddevice/LedDeviceAdalightApa102.cpp +++ b/libsrc/leddevice/LedDeviceAdalightApa102.cpp @@ -3,7 +3,6 @@ #include #include #include -#include // Linux includes #include @@ -18,24 +17,23 @@ LedDeviceAdalightApa102::LedDeviceAdalightApa102(const std::string& outputDevice _timer() { } -//comparing to ws2801 adalight, the following changes were needed: -// 1- differnt data frame (4 bytes instead of 3) -// 2 - in order to accomodate point 1 above, number of leds sent to adalight is increased by 1/3rd +// see dependencies folder for arduino sketch for APA102 int LedDeviceAdalightApa102::write(const std::vector & ledValues) { + ledCount = ledValues.size(); const unsigned int startFrameSize = 4; const unsigned int endFrameSize = std::max(((ledValues.size() + 15) / 16), 4); const unsigned int mLedCount = (ledValues.size() * 4) + startFrameSize + endFrameSize; - if(_ledBuffer.size() != mLedCount){ - _ledBuffer.resize(mLedCount, 0xFF); + if(_ledBuffer.size() != mLedCount+6){ + _ledBuffer.resize(mLedCount+6, 0x00); _ledBuffer[0] = 'A'; _ledBuffer[1] = 'd'; _ledBuffer[2] = 'a'; - _ledBuffer[3] = (((unsigned int)(ledValues.size() * 1.33) - 1) >> 8) & 0xFF; // LED count high byte - _ledBuffer[4] = ((unsigned int)(ledValues.size() * 1.33) - 1) & 0xFF; // LED count low byte + _ledBuffer[3] = (((unsigned int)(ledValues.size())) >> 8) & 0xFF; // LED count high byte + _ledBuffer[4] = ((unsigned int)(ledValues.size())) & 0xFF; // LED count low byte _ledBuffer[5] = _ledBuffer[3] ^ _ledBuffer[4] ^ 0x55; // Checksum } - + for (unsigned iLed=1; iLed<=ledValues.size(); iLed++) { const ColorRgb& rgb = ledValues[iLed-1]; _ledBuffer[iLed*4+6] = 0xFF; @@ -51,4 +49,23 @@ int LedDeviceAdalightApa102::write(const std::vector & ledValues) return writeBytes(_ledBuffer.size(), _ledBuffer.data()); } +int LedDeviceAdalightApa102::switchOff() +{ + for (unsigned iLed=1; iLed<=ledCount; iLed++) { + _ledBuffer[iLed*4+6] = 0xFF; + _ledBuffer[iLed*4+1+6] = 0x00; + _ledBuffer[iLed*4+2+6] = 0x00; + _ledBuffer[iLed*4+3+6] = 0x00; + } + // restart the timer + _timer.start(); + + // write data + return writeBytes(_ledBuffer.size(), _ledBuffer.data()); +} + +void LedDeviceAdalightApa102::rewriteLeds() +{ + writeBytes(_ledBuffer.size(), _ledBuffer.data()); +} diff --git a/libsrc/leddevice/LedDeviceAdalightApa102.h b/libsrc/leddevice/LedDeviceAdalightApa102.h index a0a7c89c..0c4b502a 100644 --- a/libsrc/leddevice/LedDeviceAdalightApa102.h +++ b/libsrc/leddevice/LedDeviceAdalightApa102.h @@ -32,13 +32,17 @@ public: /// @return Zero on succes else negative /// virtual int write(const std::vector & ledValues); + virtual int switchOff(); - +private slots: + /// Write the last data to the leds again + void rewriteLeds(); + private: /// The buffer containing the packed RGB values std::vector _ledBuffer; - + unsigned int ledCount; /// Timer object which makes sure that led data is written at a minimum rate /// The Adalight device will switch off when it does not receive data at least /// every 15 seconds