
// Эффект Пламя
// Пройтись по лампам
// Эффект Пламя и искры
void FireTick(uint8_t spark) {
    FOR_i(0, NUM_LAMP) ColorTickLamp(i,HUE_START);
    counter += 20;
    LedShow(spark);
}
//----------------------------

// Эффект Радужное Пламя и искры
// Пройтись по лампам
void RainbowTick(uint8_t spark) {
  static uint16_t MovedColor;
     FOR_i(0, NUM_LAMP) {
       ColorTickLamp(i,255/NUM_LAMP*i+MovedColor/8);
     }
    counter += 20;
    MovedColor++;
    LedShow(spark);
}
//----------------------------

// Эффект цвет и искры
void ColorTick(uint8_t HUE_C,uint8_t spark) {
    FOR_i(0,NUM_LEDS) { leds[i]=CHSV( HUE_C,255,255);}
    counter++;
    LedShow(spark);
}
//----------------------------

// Эффект Холодные искры
void ColdSparkTick() {
   FOR_i(0,NUM_LEDS) { leds[i]=CRGB(127, 127, 64);}
   LedShow(1);
} 
//----------------------------
// Эффект радуга и искры
void Rainbow(uint8_t spark) {
    FOR_i(0, NUM_LEDS) {
      leds[i] = CHSV(counter+i*5, 255,MAX_BRIGHT); 
    }
    counter ++;
    LedShow(spark);
}
//----------------------------
// Радуга из центра искры
void RainbowCenterTick(uint8_t spark) {
  static uint16_t MovedColor;
     FOR_i(0, NUM_LAMP/2) {
       ColorTickLamp(i,255/NUM_LAMP*i+MovedColor/8);
       ColorTickLamp(NUM_LAMP-i-1,255/NUM_LAMP*i+MovedColor/8);
     }
    counter += 20;
    MovedColor++;
    LedShow(spark);
}
//----------------------------
// ============= ЭФФЕКТ ДОЖДЬ ===============
void RainRoutine(uint8_t clr)
{
  static uint32_t rrr;
  FOR_x(0U,NUM_LAMP) {
    // заполняем случайно верхнюю строку
    CRGB thisColor = leds[XY(x, LAMP_LEDS - 1U)];
    if ((uint32_t)thisColor == 0U)
    {
      if (random8(0, (255-FIRE_STEP)/8) == 0U)
      {
        if (clr == 0) thisColor = CHSV(random(0, 9) * 28, 255U, 255U); // Радужный дождь
        else if (clr == 255) thisColor = 0xE0FFFF - 0x101010 * random(0, 4); // Снег
        else thisColor = CHSV(clr + random(0, 16), 255, 255);
        drawPixelXY(x, LAMP_LEDS - 1U, thisColor);
      }
    }
    else
     {
      leds[XY(x, LAMP_LEDS - 1U)] -= CHSV(0, 0, random(96, 128));
      leds[XY(x, LAMP_LEDS - 2U)] = leds[XY(x, LAMP_LEDS - 1U)];
     } 
  }
  // сдвигаем всё вниз
  if ((rrr++)%2==0)
   FOR_x(0U,NUM_LAMP) 
    for(uint8_t y=0;y<LAMP_LEDS - 3U;y+=2)
    {
     drawPixelXY(x, y, leds[XY(x, y+2U)]);
     drawPixelXY(x, y+1, leds[XY(x, y+3U)]);
    }
  FastLED.setBrightness(MAX_BRIGHT);
  FastLED.show();
}

//----------------------------
// Служебные
//----------------------------
// Устанавливает яркость и добавляет вспышки
void LedShow(uint8_t spark) {
    if (spark>0) Spark();
    FastLED.setBrightness(MAX_BRIGHT);
    FastLED.show();
}
// Вспышки
void Spark() {
  switch (random8(10)) {
   case 1: leds[random8(NUM_LEDS)]=CRGB(127, 127, 255); break;
   case 2: leds[random8(NUM_LEDS)]=CRGB(127, 255, 127); break;
   case 3: leds[random8(NUM_LEDS)]=CRGB(255, 127, 127); break;
   case 4: leds[random8(NUM_LEDS)]=CRGB(255, 255, 127); break;
   case 5: leds[random8(NUM_LEDS)]=CRGB(255, 127, 255); break;
   case 6: leds[random8(NUM_LEDS)]=CRGB(127, 255, 255); break;
   case 7: leds[random8(NUM_LEDS)]=CRGB(255, 255, 255); break;
  } 
}


// Заполнение одной лампы нужным цветом
void ColorTickLamp(int Lamp, uint8_t HUE_COLOR) {
  FOR_i(Lamp*LAMP_LEDS, Lamp*LAMP_LEDS+LAMP_LEDS) {
      leds[i] = getFireColor(inoise8(i * FIRE_STEP, counter),HUE_COLOR);
    }
}

// возвращает цвет огня для одного пикселя
CRGB getFireColor(int val, uint8_t HUE_COLOR) {
  // чем больше val, тем сильнее сдвигается цвет, падает насыщеность и растёт яркость
  return CHSV(
           HUE_COLOR + map(val, 0, 255, 0, HUE_GAP),                    // H
           constrain(map(val, 0, 255, MAX_SAT, MIN_SAT), 0, 255),       // S
           constrain(map(val, 0, 255, MIN_BRIGHT, 255), 0, 255)         // V
         );
}

void fadeBlink(CRGB color) {
  ColorTickLamp(0,color);
//  LEDS.showColor(color); 
  delay(100);
  LEDS.showColor(CRGB(0, 0, 0));
}
