不韋 呂 / UIT_WS2812B

Dependents:   Demo_WS2812B_SPI

ws2812B.cpp

Committer:
MikamiUitOpen
Date:
2016-09-26
Revision:
3:e09aafc9cabe
Parent:
2:2d4f2cc38f87
Child:
4:874beb47b375

File content as of revision 3:e09aafc9cabe:

//--------------------------------------------------------
//  SPI を使って WS2812B を点灯するためのクラス
//      サポートするボード: Nucleo-F401RE, Nucleo-F446RE
//
//  2016/09/26, Copyright (c) 2016 MIKAMI, Naoki
//--------------------------------------------------------

#include "ws2812B.hpp"

namespace Mikami
{
    WS2812B::WS2812B(PinName pin, bool inv)
        : SPI(pin, NC, NC), mySpi_((SPI_TypeDef *)_spi.spi)
    {
        format(8, 0);
        // クロックを 23 MHz 以下で最大の値に設定
        //      F401RE: 21.0 MHz
        //      F446RE: 22.5 MHz
        frequency(23000000);

        if (!inv) fp = &WS2812B::SendByteNorm;
        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::Write(uint32_t x, int k)
    {
        for (int n=0; n<k; n++) Write(x);
    }  

    void WS2812B::Clear(int k)
    {
        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::SendByteNorm(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;
    }
}