不韋 呂 / UIT_WS2812B

Dependents:   Demo_WS2812B_SPI

Revision:
0:160ed7a225a4
Child:
1:2d0f84d78ca2
diff -r 000000000000 -r 160ed7a225a4 ws2812B.cpp
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/ws2812B.cpp	Sat Sep 24 05:52:29 2016 +0000
@@ -0,0 +1,95 @@
+//----------------------------------------------------
+//  SPI を使って WS2812B を点灯するためのクラス
+//
+//  2016/09/24, Copyright (c) 2016 MIKAMI, Naoki
+//----------------------------------------------------
+
+#include "ws2812B.hpp"
+
+namespace Mikami
+{
+    WS2812B::WS2812B(PinName pin, bool inv)
+        : mySpi_(NULL)
+    {
+        SPI mbedSpi_(pin, NC, NC);  // MOSI, MISO, SCK
+
+#ifdef STM32F401xE
+        spi123 const *f4xx = f401;
+#else
+        spi123 const *f4xx = f446;
+#endif
+        for (int n=0; n<8; n++)
+        {
+            if (f4xx[n].pin == D4)
+            {
+                mySpi_ = f4xx[n].spi;
+                break;
+            }
+            if  (f4xx[n].pin == NC) break;
+        }
+
+        mbedSpi_.format(8, 0);
+        // クロックを 23 MHz 以下で最大の値に設定
+        //      F401RE: 21.0 MHz
+        //      F446RE: 22.5 MHz
+        mbedSpi_.frequency(23000000);
+
+        if (!inv) fp = &WS2812B::SendByteNrm;
+        else      fp = &WS2812B::SendByteInv;
+    }
+
+    void WS2812B::Write(uint32_t x)
+    {
+        static const uint32_t bit23 = 0x800000;
+        for (int n=0; n<24; n++)
+        {
+            if ((x & bit23) == bit23) T1HL();
+            else                      T0HL();
+            x <<= 1;
+        }
+    }
+
+    void WS2812B::Reset()
+    {
+        Dummy();
+        wait_us(50);
+    }
+    
+    void WS2812B::Clear(int k)
+    {
+        Reset();
+        for (int n=0; n<k; n++) Write(0x000000);
+        Reset();
+    }
+
+    void WS2812B::Send3Bytes(uint8_t x0, uint8_t x1, uint8_t x2)
+    {
+        SendByte(x0);
+        SendByte(x1);
+        SendByte(x2);
+    }
+
+    void WS2812B::SendByteNrm(uint8_t x)
+    {
+        while ((mySpi_->SR & SPI_SR_TXE) != SPI_SR_TXE) {}
+        mySpi_->DR = x;
+    }
+
+    void WS2812B::SendByteInv(uint8_t x)
+    {
+        while ((mySpi_->SR & SPI_SR_TXE) != SPI_SR_TXE) {}
+        mySpi_->DR = ~x;
+    }
+
+// ピンと SPI 番号の関係
+#ifdef STM32F401xE
+    const WS2812B::spi123 WS2812B::f401[] =
+        {{   D4, SPI1}, {  D11, SPI1}, {PB_15, SPI2},
+         { PC_3, SPI2}, {PC_12, SPI3}, {   NC, NULL}};
+#else
+    const WS2812B::spi123 WS2812B::f446[] =
+        {{  D11, SPI1}, {   A4, SPI2}, {PB_15, SPI2},
+         { PC_3, SPI2}, {   A3, SPI3}, {   D4, SPI3},
+         {PC_12, SPI3}, {   NC, NULL}};
+#endif  // STM32F401xE
+}