/*
 * Copyright 2025 NXP
 *
 * SPDX-License-Identifier: BSD-3-Clause
 */


#include "light_effect.h"
/*******************************************************************************
 * Definitions
 ******************************************************************************/
#define BIT(x) (1 << (x))
/*******************************************************************************
 * Prototypes
 ******************************************************************************/
void NeopixelSineWaveStep(uint8_t *rgb_buffer, uint8_t key_num);

/*******************************************************************************
 * Variables
 ******************************************************************************/

/*******************************************************************************
 * Code
 ******************************************************************************/
void __led_strip_spi_bit(uint8_t data, uint8_t *buf)
{
    // Each color of 1 bit is represented by 3 bits of SPI, low_level:100 ,high_level:110
    // So a color byte occupies 3 bytes of SPI.
    *(buf + 2) |= data & BIT(0) ? BIT(2) | BIT(1) : BIT(2);
    *(buf + 2) |= data & BIT(1) ? BIT(5) | BIT(4) : BIT(5);
    *(buf + 2) |= data & BIT(2) ? BIT(7) : 0x00;
    *(buf + 1) |= BIT(0);
    *(buf + 1) |= data & BIT(3) ? BIT(3) | BIT(2) : BIT(3);
    *(buf + 1) |= data & BIT(4) ? BIT(6) | BIT(5) : BIT(6);
    *(buf + 0) |= data & BIT(5) ? BIT(1) | BIT(0) : BIT(1);
    *(buf + 0) |= data & BIT(6) ? BIT(4) | BIT(3) : BIT(4);
    *(buf + 0) |= data & BIT(7) ? BIT(7) | BIT(6) : BIT(7);
}

void show_light_effects(uint8_t *rgbData, uint8_t keyNum, uint8_t index, uint8_t * spiData)
{
	uint8_t solid_rgb_buffer[3];
	switch(index){
		case kLIGHT_EFFECT_0:
			/* White, GRB */
			solid_rgb_buffer[0] = 77;
			solid_rgb_buffer[1] = 77;
			solid_rgb_buffer[2] = 77;
			light_solid_rendering(solid_rgb_buffer, keyNum, spiData);
			break;
		case kLIGHT_EFFECT_1:
			/* Ice Blue, GRB */
			solid_rgb_buffer[0] = 30;
			solid_rgb_buffer[1] = 0x00;
			solid_rgb_buffer[2] = 30;
			light_solid_rendering(solid_rgb_buffer, keyNum, spiData);
			break;
		case kLIGHT_EFFECT_2:
			/* Purple, GRB */
			solid_rgb_buffer[0] = 0;
			solid_rgb_buffer[1] = 38;
			solid_rgb_buffer[2] = 38;
			light_solid_rendering(solid_rgb_buffer, keyNum, spiData);
			break;
		case kLIGHT_EFFECT_3:
			/* Orange, GRB */
			solid_rgb_buffer[0] = 50;
			solid_rgb_buffer[1] = 77;
			solid_rgb_buffer[2] = 0;
			light_solid_rendering(solid_rgb_buffer, keyNum, spiData);
			break;
		case kLIGHT_EFFECT_DISABLE:
			 memset(rgbData, 0 , keyNum * 3);
			 light_rendering(rgbData, keyNum, spiData);
	}

	memset(&spiData[keyNum * 9], 0 , 125);

}

void light_rendering(uint8_t *rgbData, uint8_t keyNum, uint8_t * spiData)
{
	for (uint32_t i = 0; i < keyNum * 3; i = i + 3)
	{
		__led_strip_spi_bit(rgbData[i],&spiData[i * 3 + 0]);
		__led_strip_spi_bit(rgbData[i + 1],&spiData[i * 3 + 3]);
		__led_strip_spi_bit(rgbData[i + 2],&spiData[i * 3 + 6]);

	}
}

void light_solid_rendering(uint8_t *rgbData, uint8_t keyNum, uint8_t * spiData)
{
	for (uint32_t i = 0; i < keyNum * 3; i = i + 3)
	{
		__led_strip_spi_bit(rgbData[0],&spiData[i * 3 + 0]);
		__led_strip_spi_bit(rgbData[1],&spiData[i * 3 + 3]);
		__led_strip_spi_bit(rgbData[2],&spiData[i * 3 + 6]);

	}
}
