不韋 呂 / UIT_WS2812B

Dependents:   Demo_WS2812B_SPI

ws2812B.cpp

Committer:
MikamiUitOpen
Date:
2016-09-24
Revision:
0:160ed7a225a4
Child:
1:2d0f84d78ca2

File content as of revision 0:160ed7a225a4:

//----------------------------------------------------
//  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
}