Added first implementation of WS2811

Former-commit-id: e4fbe7a7f33c28e1f430b5159e6a5cf8c4fc4f9a
This commit is contained in:
T. van der Zwan 2013-12-10 18:59:49 +00:00
parent f65f546c61
commit 2b4adce2d4
4 changed files with 139 additions and 0 deletions

View File

@ -46,6 +46,7 @@ SET(Hyperion_HEADERS
${CURRENT_SOURCE_DIR}/device/LedDeviceTest.h
${CURRENT_SOURCE_DIR}/device/LedDeviceSedu.h
${CURRENT_SOURCE_DIR}/device/LedDeviceWs2801.h
${CURRENT_SOURCE_DIR}/device/LedDeviceWs2811.h
${CURRENT_SOURCE_DIR}/device/LedDeviceLpd6803.h
${CURRENT_SOURCE_DIR}/device/LedDeviceLpd8806.h
${CURRENT_SOURCE_DIR}/device/LedDeviceLightpack.h
@ -70,6 +71,7 @@ SET(Hyperion_SOURCES
${CURRENT_SOURCE_DIR}/device/LedDeviceSedu.cpp
${CURRENT_SOURCE_DIR}/device/LedDeviceTest.cpp
${CURRENT_SOURCE_DIR}/device/LedDeviceWs2801.cpp
${CURRENT_SOURCE_DIR}/device/LedDeviceWs2811.cpp
${CURRENT_SOURCE_DIR}/device/LedDeviceLpd6803.cpp
${CURRENT_SOURCE_DIR}/device/LedDeviceLpd8806.cpp
${CURRENT_SOURCE_DIR}/device/LedDeviceAdalight.cpp

View File

@ -21,6 +21,7 @@
#include "device/LedDeviceSedu.h"
#include "device/LedDeviceTest.h"
#include "device/LedDeviceWs2801.h"
#include "device/LedDeviceWs2811.h"
#include "device/LedDeviceAdalight.h"
#include "device/LedDeviceLightpack.h"
#include "device/LedDeviceMultiLightpack.h"
@ -46,6 +47,16 @@ LedDevice* Hyperion::createDevice(const Json::Value& deviceConfig)
device = deviceWs2801;
}
else if (type == "ws2811")
{
const std::string output = deviceConfig["output"].asString();
const bool rate = deviceConfig["fast"].asBool();
LedDeviceWs2811 * deviceWs2811 = new LedDeviceWs2811(output, rate);
deviceWs2811->open();
device = deviceWs2811;
}
else if (type == "lpd6803" || type == "ldp6803")
{
const std::string output = deviceConfig["output"].asString();

View File

@ -0,0 +1,88 @@
// Local hyperion includes
#include "LedDeviceWs2811.h"
LedDeviceWs2811::LedDeviceWs2811(const std::string & deviceName, const bool fastDevice) :
LedRs232Device(deviceName, fastDevice?4000000:2000000)
{
fillEncodeTable();
}
int LedDeviceWs2811::write(const std::vector<ColorRgb> & ledValues)
{
if (_ledBuffer.size() != ledValues.size() * 3)
{
_ledBuffer.resize(ledValues.size() * 3);
}
auto bufIt = _ledBuffer.begin();
for (const ColorRgb & color : ledValues)
{
*bufIt = _byteToSignalTable[color.red ];
++bufIt;
*bufIt = _byteToSignalTable[color.green];
++bufIt;
*bufIt = _byteToSignalTable[color.blue ];
++bufIt;
}
writeBytes(_ledBuffer.size() * 3, reinterpret_cast<uint8_t *>(_ledBuffer.data()));
return 0;
}
int LedDeviceWs2811::switchOff()
{
write(std::vector<ColorRgb>(_ledBuffer.size()/3, ColorRgb::BLACK));
return 0;
}
void LedDeviceWs2811::fillEncodeTable()
{
for (unsigned byteValue=0; byteValue<256; ++byteValue)
{
char byteSignal[4];
for (unsigned iBit=0; iBit<8; iBit=2)
{
// Isolate two bits
char bitVal = (byteValue >> (6-iBit)) & 0x03;
switch (bitVal)
{
case 0:
// _ _
// | | _ _ _ _| |_ _ _ _|
// <----bits----->
byteSignal[iBit/2] = 0x08;
break;
case 1:
// _ _ _
// | | _ _ _ _| |_ _ _|
// <----bits----->
byteSignal[iBit/2] = 0x0C;;
break;
case 2:
// _ _ _
// | |_ _ _| |_ _ _ _|
// <----bits----->
byteSignal[iBit/2] = 0x88;
break;
case 3:
// _ _ _ _
// | |_ _ _| |_ _ _|
// <----bits----->
byteSignal[iBit/2] = 0x8C;
break;
default:
// Should not happen
std::cerr << "two bits evaluated to other value: " << bitVal << std::endl;
}
}
const unsigned byteSignalVal =
(byteSignal[0] & 0x00ff) << 0 |
(byteSignal[1] & 0x00ff) << 8 |
(byteSignal[2] & 0x00ff) << 16 |
(byteSignal[3] & 0x00ff) << 24;
_byteToSignalTable.push_back(byteSignalVal);
}
}

View File

@ -0,0 +1,38 @@
#pragma once
// Local hyperion includes
#include "LedRs232Device.h"
class LedDeviceWs2811 : public LedRs232Device
{
public:
///
/// Constructs the LedDevice with Ws2811 attached via a serial port
///
/// @param outputDevice The name of the output device (eg '/dev/ttyS0')
/// @param fastDevice The used baudrate for writing to the output device
///
LedDeviceWs2811(const std::string& outputDevice, const bool fastDevice);
///
/// Writes the led color values to the led-device
///
/// @param ledValues The color-value per led
/// @return Zero on succes else negative
///
virtual int write(const std::vector<ColorRgb> & ledValues);
/// Switch the leds off
virtual int switchOff();
private:
void fillEncodeTable();
/** Translation table of byte to signal */
std::vector<unsigned> _byteToSignalTable;
/// The buffer containing the packed RGB values
std::vector<unsigned> _ledBuffer;
};