driver for WS2812B LED, modified for better compatibility with LPC812 and LPC1549

Dependencies:   BurstSPI

Dependents:   RGB-balls cylon

Fork of wsDrive by Andy A

Committer:
JojoS
Date:
Sat Dec 10 14:30:38 2016 +0000
Revision:
6:270a9728ee29
Parent:
4:c965e448d96b
support for STM32F4

Who changed what in which revision?

UserRevisionLine numberNew contents of line
AndyA 0:b3665f91bedc 1 #include "wsDrive.h"
AndyA 0:b3665f91bedc 2
AndyA 0:b3665f91bedc 3 wsDrive::wsDrive(PinName mosi, PinName miso, PinName clk) : BurstSPI(mosi,miso,clk)
AndyA 0:b3665f91bedc 4 {
JojoS 6:270a9728ee29 5 #if defined(TARGET_STM32F4)
JojoS 6:270a9728ee29 6 frequency(4000000);
JojoS 6:270a9728ee29 7 format(4*4, 1); // one WS bit -> four SPI bits
JojoS 6:270a9728ee29 8 #else
AndyA 0:b3665f91bedc 9 frequency(2400000);
JojoS 6:270a9728ee29 10 format(3*4, 1); // one WS bit -> three SPI bits
JojoS 6:270a9728ee29 11 #endif
JojoS 4:c965e448d96b 12
AndyA 0:b3665f91bedc 13 pixArray = NULL;
AndyA 3:3c48065d20ff 14 pixArray16 = NULL;
AndyA 0:b3665f91bedc 15 pixelLen = 0;
AndyA 0:b3665f91bedc 16 }
AndyA 0:b3665f91bedc 17
AndyA 0:b3665f91bedc 18 void wsDrive::setData(pixelInfo *dataStart, uint16_t dataLen)
AndyA 0:b3665f91bedc 19 {
AndyA 0:b3665f91bedc 20 pixArray = dataStart;
AndyA 0:b3665f91bedc 21 pixelLen = dataLen;
AndyA 3:3c48065d20ff 22 pixArray16 = NULL;
AndyA 3:3c48065d20ff 23 }
AndyA 3:3c48065d20ff 24
AndyA 3:3c48065d20ff 25 void wsDrive::setData(pixelInfo16 *dataStart, uint16_t dataLen)
AndyA 3:3c48065d20ff 26 {
AndyA 3:3c48065d20ff 27 pixArray16 = dataStart;
AndyA 3:3c48065d20ff 28 pixelLen = dataLen;
AndyA 3:3c48065d20ff 29 pixArray = NULL;
AndyA 0:b3665f91bedc 30 }
AndyA 0:b3665f91bedc 31
AndyA 0:b3665f91bedc 32 void wsDrive::sendData()
AndyA 0:b3665f91bedc 33 {
AndyA 0:b3665f91bedc 34 uint16_t pixIndex = 0;
AndyA 3:3c48065d20ff 35 if (pixArray) {
AndyA 3:3c48065d20ff 36 while (pixIndex < pixelLen) {
AndyA 3:3c48065d20ff 37 sendPixel(pixArray + pixIndex++);
AndyA 3:3c48065d20ff 38 }
AndyA 3:3c48065d20ff 39 } else if (pixArray16) {
AndyA 3:3c48065d20ff 40 while (pixIndex < pixelLen) {
AndyA 3:3c48065d20ff 41 sendPixel(pixArray16 + pixIndex++);
AndyA 3:3c48065d20ff 42 }
AndyA 3:3c48065d20ff 43 }
AndyA 0:b3665f91bedc 44 }
AndyA 0:b3665f91bedc 45
AndyA 0:b3665f91bedc 46 // each bytes sent as two 12 bit messages (3 bits of data per LED bit).
AndyA 0:b3665f91bedc 47 void wsDrive::sendByte(unsigned char value)
AndyA 0:b3665f91bedc 48 {
JojoS 6:270a9728ee29 49 uint16_t dataToSend = 0;
JojoS 6:270a9728ee29 50 uint8_t mask = 0x80;
AndyA 3:3c48065d20ff 51
JojoS 6:270a9728ee29 52 #if defined(TARGET_STM32F4)
JojoS 6:270a9728ee29 53 while (mask) {
JojoS 6:270a9728ee29 54 dataToSend += (value & mask)?0x0C:0x08; // 1000 for a 0 or 1100 for a 1
JojoS 6:270a9728ee29 55 if (mask & 0x11) { // trans
JojoS 6:270a9728ee29 56 fastWrite(dataToSend);
JojoS 6:270a9728ee29 57 dataToSend = 0;
JojoS 6:270a9728ee29 58 }
JojoS 6:270a9728ee29 59 dataToSend = dataToSend << 4;
JojoS 6:270a9728ee29 60 mask = mask >> 1;
JojoS 6:270a9728ee29 61 }
JojoS 6:270a9728ee29 62 #else
AndyA 0:b3665f91bedc 63 while (mask) {
AndyA 0:b3665f91bedc 64 dataToSend += (value & mask)?0x06:0x4; // 100 for a 0 or 110 for a 1
AndyA 0:b3665f91bedc 65 if (mask & 0x11) { // trans
AndyA 3:3c48065d20ff 66 fastWrite(dataToSend);
AndyA 3:3c48065d20ff 67 dataToSend = 0;
AndyA 0:b3665f91bedc 68 }
AndyA 0:b3665f91bedc 69 dataToSend = dataToSend << 3;
AndyA 0:b3665f91bedc 70 mask = mask >> 1;
AndyA 0:b3665f91bedc 71 }
JojoS 6:270a9728ee29 72 #endif
AndyA 0:b3665f91bedc 73 }
AndyA 0:b3665f91bedc 74
AndyA 0:b3665f91bedc 75 void wsDrive::sendPixel(pixelInfo *pixToSend)
AndyA 0:b3665f91bedc 76 {
AndyA 0:b3665f91bedc 77 sendByte(pixToSend->G);
AndyA 0:b3665f91bedc 78 sendByte(pixToSend->R);
AndyA 0:b3665f91bedc 79 sendByte(pixToSend->B);
AndyA 0:b3665f91bedc 80 }
AndyA 0:b3665f91bedc 81
AndyA 3:3c48065d20ff 82 void wsDrive::sendPixel(pixelInfo16 *pixToSend)
AndyA 3:3c48065d20ff 83 {
AndyA 3:3c48065d20ff 84 if (pixToSend->G > 0xff)
AndyA 3:3c48065d20ff 85 sendByte(0xff);
AndyA 3:3c48065d20ff 86 else if (pixToSend->G < 0)
AndyA 3:3c48065d20ff 87 sendByte(0xff);
AndyA 3:3c48065d20ff 88 else
AndyA 3:3c48065d20ff 89 sendByte((unsigned char)pixToSend->G);
AndyA 3:3c48065d20ff 90
AndyA 3:3c48065d20ff 91 if (pixToSend->R > 0xff)
AndyA 3:3c48065d20ff 92 sendByte(0xff);
AndyA 3:3c48065d20ff 93 else if (pixToSend->R < 0)
AndyA 3:3c48065d20ff 94 sendByte(0xff);
AndyA 3:3c48065d20ff 95 else
AndyA 3:3c48065d20ff 96 sendByte((unsigned char)pixToSend->R);
AndyA 3:3c48065d20ff 97
AndyA 3:3c48065d20ff 98 if (pixToSend->B > 0xff)
AndyA 3:3c48065d20ff 99 sendByte(0xff);
AndyA 3:3c48065d20ff 100 else if (pixToSend->B < 0)
AndyA 3:3c48065d20ff 101 sendByte(0xff);
AndyA 3:3c48065d20ff 102 else
AndyA 3:3c48065d20ff 103 sendByte((unsigned char)pixToSend->B);
AndyA 3:3c48065d20ff 104
AndyA 3:3c48065d20ff 105 }