diff --git a/code/main/CMakeLists.txt b/code/main/CMakeLists.txt index 4970044..c8c9896 100644 --- a/code/main/CMakeLists.txt +++ b/code/main/CMakeLists.txt @@ -8,6 +8,7 @@ idf_component_register( "src/wifi.cpp" "src/logger.cpp" "src/led_strip_encoder.c" + "src/ledmatrix.cpp" INCLUDE_DIRS # optional, add here public include directories "inc" PRIV_INCLUDE_DIRS # optional, add here private include directories diff --git a/code/main/inc/ledmatrix.h b/code/main/inc/ledmatrix.h new file mode 100644 index 0000000..1834da6 --- /dev/null +++ b/code/main/inc/ledmatrix.h @@ -0,0 +1,122 @@ +// -------------------------------------------------------------------------------------------------------------------- +/// \file ledmatrix.h +/// \brief File description +// -------------------------------------------------------------------------------------------------------------------- +// +// vbchaos software design +// +// -------------------------------------------------------------------------------------------------------------------- +/// $Revision: $ +/// $Author: $ +/// $Date: $ +// (c) 2023 vbchaos +// -------------------------------------------------------------------------------------------------------------------- + + +#ifndef MAIN_INC_LEDMATRIX_H_ +#define MAIN_INC_LEDMATRIX_H_ + +/** + * ledmatrix implementation + * \defgroup ledmatrix + * \brief {group_description} + * \addtogroup {Layer} + * + * Detailed description + * @{ + */ + + + +// -------------------------------------------------------------------------------------------------------------------- +// Include files +// -------------------------------------------------------------------------------------------------------------------- + +// CompilerIncludes +// All include files that are provided by the compiler directly +#include + + +// ProjectIncludes +// All include files that are provided by the project +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "freertos/semphr.h" + +#include "driver/rmt_tx.h" + +// -------------------------------------------------------------------------------------------------------------------- +// Constant and macro definitions +// -------------------------------------------------------------------------------------------------------------------- + + +// -------------------------------------------------------------------------------------------------------------------- +// Type definitions. +// -------------------------------------------------------------------------------------------------------------------- + +typedef enum +{ + LEDMATRIX_ORIENTATION_ROW_LEFT_RIGHT, + LEDMATRIX_ORIENTATION_ROW_RIGHT_LEFT +} LEDMatrix_Orientation_Row_t; + +typedef enum +{ + LEDMATRIX_ORIENTATION_COLUM_UP_DOWN, + LEDMATRIX_ORIENTATION_COLUM_DOWN_UP +} LEDMatrix_Orientation_Colum_t; + +typedef enum +{ + LEDMATRIX_ORIENTATION_ROW, + LEDMATRIX_ORIENTATION_COLUM +}LEDMatrix_Orientation_t; + +typedef struct +{ + LEDMatrix_Orientation_Row_t rowOrientation; + LEDMatrix_Orientation_Colum_t columOrientation; + LEDMatrix_Orientation_t matrixOrientation; + unsigned int width; + unsigned int height; + // RMT objects for transmission + rmt_channel_handle_t* rmtChannel; + rmt_encoder_handle_t* rmtEncoder; + rmt_transmit_config_t* rmtConfig; +} LEDMatrix_Parameters_t; + +typedef struct +{ + bool on; + uint8_t red; + uint8_t green; + uint8_t blue; +} LEDMatrix_Pixel_t; + +// -------------------------------------------------------------------------------------------------------------------- +// Function declarations +// -------------------------------------------------------------------------------------------------------------------- + +class LEDMatrix +{ + public: + LEDMatrix(LEDMatrix_Parameters_t* parameters); + + void setPixelValue(unsigned int row, unsigned int colum, bool value); + + private: + LEDMatrix_Parameters_t parameters; + LEDMatrix_Pixel_t* matrix; + uint8_t* tx_matrix; + unsigned int numberOfPixels; + + static TaskHandle_t matrixTaskHandle; + static SemaphoreHandle_t taskSemaphore; + static void matrixTask(void* parameters); +}; + + + +/** @} */ + +#endif /* MAIN_INC_LEDMATRIX_H_ */ diff --git a/code/main/main.cpp b/code/main/main.cpp index f1d2911..4fef8bf 100644 --- a/code/main/main.cpp +++ b/code/main/main.cpp @@ -15,6 +15,7 @@ #include "inc/gpio.h" #include "inc/led_strip_encoder.h" +#include "inc/ledmatrix.h" #include "inc/logger.h" #include "inc/wifi.h" @@ -25,6 +26,10 @@ static GPIO gpio0(4, GPIO_DIRECTION_OUTPUT); static GPIO gpio1(18, GPIO_DIRECTION_OUTPUT); static time_t currentTime; +static rmt_channel_handle_t led_chan = NULL; +static rmt_transmit_config_t tx_config; +static rmt_encoder_handle_t led_encoder = NULL; + #define RMT_LED_STRIP_RESOLUTION_HZ 10000000 // 10MHz resolution, 1 tick = 0.1us (led strip needs a high resolution) #define RMT_LED_STRIP_GPIO_NUM 8 @@ -62,14 +67,13 @@ extern "C" void app_main(void) // Logger logger(10, uartPort); - LOGGER_DEBUG("YEAHAAA"); + LOGGER_DEBUG("Let's start the WORDCLOCK"); //-------------------------------------------- // RMT Channel // LOGGER_INFO("Create RMT TX channel"); - rmt_channel_handle_t led_chan = NULL; rmt_tx_channel_config_t tx_chan_config; memset(&tx_chan_config, 0, sizeof(tx_chan_config)); @@ -82,7 +86,6 @@ extern "C" void app_main(void) ESP_ERROR_CHECK(rmt_new_tx_channel(&tx_chan_config, &led_chan)); LOGGER_INFO("Install led strip encoder"); - rmt_encoder_handle_t led_encoder = NULL; led_strip_encoder_config_t encoder_config; memset(&encoder_config, 0, sizeof(encoder_config)); encoder_config.resolution = RMT_LED_STRIP_RESOLUTION_HZ; @@ -92,13 +95,23 @@ extern "C" void app_main(void) LOGGER_INFO("Enable RMT TX channel"); ESP_ERROR_CHECK(rmt_enable(led_chan)); - rmt_transmit_config_t tx_config; memset(&tx_config, 0, sizeof(tx_config)); tx_config.loop_count = 0; - - + //-------------------------------------------- + // LED Matrix + // + LEDMatrix_Parameters_t ledmatrix_parameters; + ledmatrix_parameters.columOrientation = LEDMATRIX_ORIENTATION_COLUM_DOWN_UP; + ledmatrix_parameters.height = 10; + ledmatrix_parameters.matrixOrientation = LEDMATRIX_ORIENTATION_COLUM; + ledmatrix_parameters.rmtChannel = &led_chan; + ledmatrix_parameters.rmtConfig = &tx_config; + ledmatrix_parameters.rmtEncoder = &led_encoder; + ledmatrix_parameters.rowOrientation = LEDMATRIX_ORIENTATION_ROW_LEFT_RIGHT; + ledmatrix_parameters.width = 11; + LEDMatrix LEDMatrix(&ledmatrix_parameters); // Create the development task @@ -118,33 +131,42 @@ extern "C" void app_main(void) sntp_init(); - uint8_t led_strip_pixels[111 * 3]; - int counter = 0; + unsigned int row = 0; + unsigned int colum = 0; + while (true) { - struct tm tm; - time(¤tTime); - localtime_r(¤tTime, &tm); +// struct tm tm; +// time(¤tTime); +// localtime_r(¤tTime, &tm); +// +// LOGGER_INFO("%lld\n\r", currentTime); +// LOGGER_INFO("%02i:%02i:%02i\n\r", tm.tm_hour, tm.tm_min, tm.tm_sec); +// +// vTaskDelay(300); - LOGGER_INFO("%lld\n\r", currentTime); - LOGGER_INFO("%i:%i:%i\n\r", tm.tm_hour, tm.tm_min, tm.tm_sec); - memset(&led_strip_pixels, 0, sizeof(led_strip_pixels)); - led_strip_pixels[counter * 3 + 0] = 0x3F; - led_strip_pixels[counter * 3 + 1] = 0x3F; - led_strip_pixels[counter * 3 + 2] = 0x3F; - - if (counter < 111) + LOGGER_DEBUG("Enable pixel (%i:%i)", row, colum); + LEDMatrix.setPixelValue(row, colum, true); + vTaskDelay(100); + LEDMatrix.setPixelValue(row, colum, false); + if (row<10) { - counter++; + row++; } else { - counter = 0; + row = 0; + if(colum < 2) + { + colum++; + } + else + { + colum = 0; + } } - rmt_transmit(led_chan, led_encoder, led_strip_pixels, sizeof(led_strip_pixels), &tx_config); - vTaskDelay(5); } } diff --git a/code/main/src/ledmatrix.cpp b/code/main/src/ledmatrix.cpp new file mode 100644 index 0000000..d9bfbc5 --- /dev/null +++ b/code/main/src/ledmatrix.cpp @@ -0,0 +1,160 @@ +// -------------------------------------------------------------------------------------------------------------------- +/// \file ledmatrix.cpp +/// \brief Description +// -------------------------------------------------------------------------------------------------------------------- +// +// vbchaos software design +// +// -------------------------------------------------------------------------------------------------------------------- +/// $Revision: $ +/// $Author: $ +/// $Date: $ +// (c) 2023 vbchaos +// -------------------------------------------------------------------------------------------------------------------- + + +// -------------------------------------------------------------------------------------------------------------------- +// Include files +// -------------------------------------------------------------------------------------------------------------------- + +#include "ledmatrix.h" +#include "logger.h" +#include "string.h" + +// -------------------------------------------------------------------------------------------------------------------- +// Constant and macro definitions +// -------------------------------------------------------------------------------------------------------------------- + + + +// -------------------------------------------------------------------------------------------------------------------- +// Type definitions +// -------------------------------------------------------------------------------------------------------------------- + + +// -------------------------------------------------------------------------------------------------------------------- +// File-scope variables +// -------------------------------------------------------------------------------------------------------------------- + + + +// -------------------------------------------------------------------------------------------------------------------- +// Function declarations +// -------------------------------------------------------------------------------------------------------------------- + + + +// -------------------------------------------------------------------------------------------------------------------- +// Function definitions +// -------------------------------------------------------------------------------------------------------------------- + +SemaphoreHandle_t LEDMatrix::taskSemaphore = 0; +TaskHandle_t LEDMatrix::matrixTaskHandle = NULL; + +LEDMatrix::LEDMatrix(LEDMatrix_Parameters_t* parameters) +{ + // Take the parameters + LEDMatrix::parameters = *parameters; + // Calculate the total number of pixels + LEDMatrix::numberOfPixels = parameters->width * parameters->height; + // Create the matrix storage + matrix = new LEDMatrix_Pixel_t[parameters->width * parameters->height]; + // Create the second matrix, that is actually transmitted to the periphery + + // Reset the matrix to all 0 (all LEDs off) +// memset(&matrix, 0, sizeof(matrix)); + + // Create the task Semaphore + vSemaphoreCreateBinary(LEDMatrix::taskSemaphore); + // Create the matrix task + xTaskCreate(matrixTask, (const char*)"matrixTask", 4096, this, 3, &LEDMatrix::matrixTaskHandle); + + for (int i = 0; i < numberOfPixels; i++) + { + matrix[i].on = false; + matrix[i].green = 0x1F; + } + + LOGGER_DEBUG("---- %i -----", matrix[0].green); + +} + +void LEDMatrix::setPixelValue(unsigned int row, unsigned int colum, bool value) +{ + unsigned int rowC = 0; + unsigned int colC = 0; + unsigned int pixelAddress = 0; + + // Determine the actual row coordinate based on the matrix orientation + if (parameters.columOrientation == LEDMATRIX_ORIENTATION_COLUM_UP_DOWN) + { + rowC = row; + } + else if (parameters.columOrientation == LEDMATRIX_ORIENTATION_COLUM_DOWN_UP) + { + rowC = parameters.height - row; + } + + // Determine the actual row coordinate based on the matrix orientation + if (parameters.rowOrientation == LEDMATRIX_ORIENTATION_ROW_LEFT_RIGHT) + { + colC = colum; + } + else if (parameters.rowOrientation == LEDMATRIX_ORIENTATION_ROW_RIGHT_LEFT) + { + colC = parameters.width - colum; + } + + // Calculate the pixel address in the pixel array based on the previous information + if (parameters.matrixOrientation == LEDMATRIX_ORIENTATION_COLUM) + { + pixelAddress = (rowC - 1) * (colC + 1); + } + + LOGGER_DEBUG("Calculated address: %i (%i:%i)", pixelAddress, rowC, colC); + // Update the pixel value + matrix[pixelAddress].on = value; + + + + // Release the semaphore to trigger an matrix update + xSemaphoreGive(LEDMatrix::taskSemaphore); +} + + + + +void LEDMatrix::matrixTask(void* parameters) +{ + LEDMatrix* ledmatrix = (LEDMatrix*)parameters; + + uint8_t matrix[ledmatrix->numberOfPixels * 3]; + memset(&matrix, 0, sizeof(matrix)); + + while(1) + { + xSemaphoreTake(ledmatrix->taskSemaphore, 1000); + for (int i = 0; i < ledmatrix->numberOfPixels; i++) + { + if (ledmatrix->matrix[i].on) + { + matrix[i * 3 + 0] = ledmatrix->matrix[i].red; + matrix[i * 3 + 1] = ledmatrix->matrix[i].green; + matrix[i * 3 + 2] = ledmatrix->matrix[i].blue; + } + else + { + matrix[i * 3 + 0] = 0; + matrix[i * 3 + 1] = 0; + matrix[i * 3 + 2] = 0; + } + + } + LOGGER_DEBUG("HERE AGAIN"); + // Re-draw the matrix every 10 seconds anyhow + rmt_transmit(*ledmatrix->parameters.rmtChannel, *ledmatrix->parameters.rmtEncoder, matrix, sizeof(matrix), ledmatrix->parameters.rmtConfig); + + } +} + +