rgbwifi/src/strip.cpp

119 lines
2.8 KiB
C++

/*
* ESP8266 RGBW controller
* Copyright 2020 (c) Mark van Renswoude
*
* https://git.x2software.net/pub/RGBWifi
*/
#include "./strip.h"
#include <Math.h>
#include <FS.h>
#include "./debug.h"
#include "./global.h"
NeoGamma<NeoGammaTableMethod> colorGamma;
RgbwColor clearColor(0);
void Strip::init(uint16_t ledCount)
{
mBus = new NeoPixelBus<NeoPixelBusFeature, NeoPixelBusMethod>(ledCount);
mBus->Begin();
setStatic(clearColor, 0);
}
void Strip::tick()
{
switch (mSetting)
{
case StripSetting::Static:
case StripSetting::Rainbow:
break;
case StripSetting::RainbowMoving:
tickRainbow();
break;
}
mAnimator->UpdateAnimations();
if (mBus->CanShow())
mBus->Show();
}
void Strip::setStatic(const RgbwColor color, uint16_t fadeTime)
{
_d("Strip :: setStatic, color = "); _d(color.R); _d(","); _d(color.G); _d(","); _d(color.B); _d(","); _dln(color.W);
RgbwColor corrected = colorGamma.Correct(color);
_d("Strip :: setStatic, gamma corrected = "); _d(corrected.R); _d(","); _d(corrected.G); _d(","); _d(corrected.B); _d(","); _dln(corrected.W);
if (mSetting == StripSetting::Static && fadeTime > 0)
{
// Make sure we use the current color as a start, which is corrected as well
RgbwColor startColor = mBus->GetPixelColor(0);
mAnimator->StartAnimation(0, fadeTime,
[this, startColor, corrected](AnimationParam param)
{
float progress = NeoEase::ExponentialInOut(param.progress);
RgbwColor color = RgbwColor::LinearBlend(startColor, corrected, progress);
mBus->ClearTo(color);
});
}
else
{
mSetting = StripSetting::Static;
mBus->ClearTo(corrected);
}
mStaticColor = color;
}
void Strip::setRainbow(uint16_t speed, uint8_t lightness)
{
if (mSetting != StripSetting::Rainbow && mSetting != StripSetting::RainbowMoving)
mRainbowShift = 0;
mSetting = speed > 0 ? StripSetting::RainbowMoving : StripSetting::Rainbow;
mRainbowSpeed = speed;
mRainbowLightness = lightness;
uint16_t ledCount = systemSettings->ledCount();
mDelay = speed > 0 ? (uint32_t)(1000.0F / (float)speed) : 0;
mLastTick = currentTime;
HslColor* color = new HslColor(0, 1, (float)lightness / 255.0F);
for (uint16_t ledIndex = 0; ledIndex < ledCount; ledIndex++)
{
color->H = (float)ledIndex / (float)ledCount;
mBus->SetPixelColor(ledIndex, *color);
}
delete color;
if (mRainbowShift > 0)
mBus->RotateLeft(mRainbowShift);
}
void Strip::tickRainbow()
{
if (currentTime - mLastTick < mDelay)
return;
// TODO for slower speeds it is quite noticable that the pixels simply
// shift. Figure out where the pivot point for that is, and switch to
// a smoother (but more calculation intensive) variant
mRainbowShift = (mRainbowShift + 1) % systemSettings->ledCount();
mLastTick = currentTime;
mBus->RotateLeft(1);
}