WS2812B Liblary this use SPI

Committer:
Suzutomo
Date:
Wed Jul 17 14:06:08 2019 +0000
Revision:
5:62b6ac21c199
Parent:
4:02e88df0ae2d
Child:
6:21a721b31a20
Perfect LED Light

Who changed what in which revision?

UserRevisionLine numberNew contents of line
Suzutomo 0:6a2dcf5cd545 1 //--------------------------------------------------------
Suzutomo 0:6a2dcf5cd545 2 // SPI を使って WS2812B を点灯するためのクラス
Suzutomo 0:6a2dcf5cd545 3 // サポートするボード: Nucleo-F401RE, Nucleo-F446RE
Suzutomo 0:6a2dcf5cd545 4 //
Suzutomo 0:6a2dcf5cd545 5 // 2016/11/21, Copyright (c) 2016 MIKAMI, Naoki
Suzutomo 0:6a2dcf5cd545 6 //--------------------------------------------------------
Suzutomo 0:6a2dcf5cd545 7
Suzutomo 0:6a2dcf5cd545 8 #include "WS2812B.h"
Suzutomo 0:6a2dcf5cd545 9 #include "PeripheralPins.h" // for pinmap_peripheral()
Suzutomo 0:6a2dcf5cd545 10
Suzutomo 3:c0a82b9775e6 11 WS2812B::WS2812B(PinName pin, int num, bool inv)
Suzutomo 0:6a2dcf5cd545 12 : spi_(pin, NC, NC),
Suzutomo 0:6a2dcf5cd545 13 mySpi_((SPI_TypeDef *)pinmap_peripheral(pin, PinMap_SPI_MOSI))
Suzutomo 0:6a2dcf5cd545 14 {
Suzutomo 5:62b6ac21c199 15 spi_.format(8, 0);
Suzutomo 0:6a2dcf5cd545 16 #if defined(STM32F446xx)
Suzutomo 1:c7bb475f0022 17 spi_.frequency(22500000);
Suzutomo 0:6a2dcf5cd545 18 #else
Suzutomo 0:6a2dcf5cd545 19 #error This code is not move this board.
Suzutomo 0:6a2dcf5cd545 20 #endif
Suzutomo 0:6a2dcf5cd545 21 if (!inv) fp = &WS2812B::SendByteNorm;
Suzutomo 0:6a2dcf5cd545 22 else fp = &WS2812B::SendByteInv;
Suzutomo 3:c0a82b9775e6 23
Suzutomo 5:62b6ac21c199 24
Suzutomo 3:c0a82b9775e6 25 colors = (uint32_t *)calloc(num,sizeof(uint32_t));
Suzutomo 3:c0a82b9775e6 26 if (colors == NULL) printf("can not reserve memory\n");
Suzutomo 3:c0a82b9775e6 27 bufferSize = num;
Suzutomo 3:c0a82b9775e6 28 bright = 1.0;
Suzutomo 3:c0a82b9775e6 29 }
Suzutomo 3:c0a82b9775e6 30
Suzutomo 3:c0a82b9775e6 31 uint32_t BrightAdjust(uint32_t x,double brightness)
Suzutomo 3:c0a82b9775e6 32 {
Suzutomo 3:c0a82b9775e6 33 uint8_t r = ((x >> 16) & 0xFF) * brightness;
Suzutomo 3:c0a82b9775e6 34 uint8_t g = ((x >> 8) & 0xFF) * brightness;
Suzutomo 3:c0a82b9775e6 35 uint8_t b = ((x >> 0) & 0xFF) * brightness;
Suzutomo 3:c0a82b9775e6 36 x = (r << 16) | (g << 8) | b;
Suzutomo 3:c0a82b9775e6 37 return x;
Suzutomo 3:c0a82b9775e6 38 }
Suzutomo 3:c0a82b9775e6 39
Suzutomo 3:c0a82b9775e6 40 void WS2812B::Write(int index,uint32_t x,double brightness)
Suzutomo 3:c0a82b9775e6 41 {
Suzutomo 3:c0a82b9775e6 42 if (index >= 0 && index < bufferSize) colors[index] = BrightAdjust(x,brightness);
Suzutomo 0:6a2dcf5cd545 43 }
Suzutomo 0:6a2dcf5cd545 44
Suzutomo 3:c0a82b9775e6 45 void WS2812B::Write(uint32_t x,double brightness)
Suzutomo 0:6a2dcf5cd545 46 {
Suzutomo 3:c0a82b9775e6 47 for (int i = 0; i < bufferSize; i++) colors[i] = BrightAdjust(x,brightness);
Suzutomo 0:6a2dcf5cd545 48 }
Suzutomo 0:6a2dcf5cd545 49
Suzutomo 3:c0a82b9775e6 50 void WS2812B::Send()
Suzutomo 0:6a2dcf5cd545 51 {
Suzutomo 3:c0a82b9775e6 52 uint32_t *colors_m;
Suzutomo 3:c0a82b9775e6 53 colors_m = (uint32_t *)calloc(bufferSize,sizeof(uint32_t));
Suzutomo 3:c0a82b9775e6 54 for (int i = 0; i < bufferSize; i++) {
Suzutomo 3:c0a82b9775e6 55 uint32_t x = colors[i];
Suzutomo 3:c0a82b9775e6 56 x = BrightAdjust(x,bright);
Suzutomo 3:c0a82b9775e6 57 colors_m[i] = 0;
Suzutomo 3:c0a82b9775e6 58 colors_m[i] |= ((x >> 8) & 0xFF00);
Suzutomo 3:c0a82b9775e6 59 colors_m[i] |= ((x << 8) & 0xFF0000);
Suzutomo 3:c0a82b9775e6 60 colors_m[i] |= (x & 0xFF);
Suzutomo 3:c0a82b9775e6 61 }
Suzutomo 3:c0a82b9775e6 62 static const uint32_t bit23 = 0x800000;
Suzutomo 5:62b6ac21c199 63 __disable_irq();
Suzutomo 3:c0a82b9775e6 64 for (int i = 0; i < bufferSize; i++) {
Suzutomo 3:c0a82b9775e6 65 for (int n=0; n<24; n++) {
Suzutomo 3:c0a82b9775e6 66 if ((colors_m[i] & bit23) == bit23) T1HL();
Suzutomo 3:c0a82b9775e6 67 else T0HL();
Suzutomo 3:c0a82b9775e6 68 colors_m[i] <<= 1;
Suzutomo 3:c0a82b9775e6 69 }
Suzutomo 3:c0a82b9775e6 70 }
Suzutomo 3:c0a82b9775e6 71 Reset();
Suzutomo 5:62b6ac21c199 72 __enable_irq();
Suzutomo 3:c0a82b9775e6 73 free(colors_m);
Suzutomo 3:c0a82b9775e6 74 }
Suzutomo 0:6a2dcf5cd545 75
Suzutomo 0:6a2dcf5cd545 76 void WS2812B::Clear(int k)
Suzutomo 0:6a2dcf5cd545 77 {
Suzutomo 3:c0a82b9775e6 78 for (int n=0; n<k; n++) colors[n] = 0;
Suzutomo 3:c0a82b9775e6 79 Send();
Suzutomo 0:6a2dcf5cd545 80 Reset();
Suzutomo 0:6a2dcf5cd545 81 }
Suzutomo 0:6a2dcf5cd545 82
Suzutomo 4:02e88df0ae2d 83 void WS2812B::Send3Bytes(uint16_t x0, uint16_t x1, uint16_t x2)
Suzutomo 0:6a2dcf5cd545 84 {
Suzutomo 0:6a2dcf5cd545 85 SendByte(x0);
Suzutomo 0:6a2dcf5cd545 86 SendByte(x1);
Suzutomo 0:6a2dcf5cd545 87 SendByte(x2);
Suzutomo 0:6a2dcf5cd545 88 }
Suzutomo 0:6a2dcf5cd545 89
Suzutomo 0:6a2dcf5cd545 90 void WS2812B::SendByteNorm(uint8_t x)
Suzutomo 0:6a2dcf5cd545 91 {
Suzutomo 0:6a2dcf5cd545 92 while ((mySpi_->SR & SPI_SR_TXE) != SPI_SR_TXE) {}
Suzutomo 0:6a2dcf5cd545 93 mySpi_->DR = x;
Suzutomo 0:6a2dcf5cd545 94 }
Suzutomo 0:6a2dcf5cd545 95
Suzutomo 0:6a2dcf5cd545 96 void WS2812B::SendByteInv(uint8_t x)
Suzutomo 0:6a2dcf5cd545 97 {
Suzutomo 0:6a2dcf5cd545 98 while ((mySpi_->SR & SPI_SR_TXE) != SPI_SR_TXE) {}
Suzutomo 0:6a2dcf5cd545 99 mySpi_->DR = ~x;
Suzutomo 0:6a2dcf5cd545 100 }
Suzutomo 0:6a2dcf5cd545 101
Suzutomo 3:c0a82b9775e6 102 void WS2812B::Brightness(double brightness)
Suzutomo 3:c0a82b9775e6 103 {
Suzutomo 3:c0a82b9775e6 104 bright = brightness;
Suzutomo 3:c0a82b9775e6 105 }
Suzutomo 3:c0a82b9775e6 106