#include <Arduino_FreeRTOS.h>
#include <queue.h>
// LEDs
#define YellowLEDPin 8
#define GreenLEDPin 4
#define BlueLEDPin 7
// Botões
#define CH01Pin 2 // botão 1
#define CH02Pin 3 // botão 2
// Variáveis do debounce
volatile unsigned long lastInterruptTime = 0;
const unsigned long debounceDelay = 100;
// Variáveis de verificação se o botão foi apertado
volatile bool button1pressed = false;
volatile bool button2pressed = false;
// Variável para ver se a sequência está rodando
volatile bool started = false;
volatile bool isRunning = false;
// Variável para armazenar a sequência de comandos
char sequence[80] = ""; // Sequência inicial vazia
volatile int sequenceIndex = 0;
// Filas para comunicação entre a tarefa principal e as tarefas dos LEDs
QueueHandle_t ledQueue;
struct LEDCommand {
int pin;
int duration;
};
// Função para debounce e interrupção do botão 1
void pressButton1() {
Serial.print("Entrou no pressButton1()");
unsigned long interruptTime = millis();
if (interruptTime - lastInterruptTime > debounceDelay) {
Serial.print("Entrou no if do pressButton1()");
delay(10);
if (digitalRead(CH01Pin) == LOW) {
Serial.print("Entrou no if do pressButton1().2");
lastInterruptTime = interruptTime;
button1pressed = true;
}
}
}
// Função para debounce e interrupção do botão 2
void pressButton2() {
Serial.print("Entrou no pressButton2()");
unsigned long interruptTime = millis();
if (interruptTime - lastInterruptTime > debounceDelay) {
Serial.print("Entrou no if do pressButton2()");
delay(10);
if (digitalRead(CH02Pin) == LOW) {
Serial.print("Entrou no if do pressButton2().2");
lastInterruptTime = interruptTime;
button2pressed = true;
}
}
}
// Função para processar a sequência de comandos
void processSequenceTask(void *pvParameters) {
Serial.println("Iniciando processSequenceTask");
while (1) {
if (isRunning) {
Serial.print("Processing command at index: ");
Serial.println(sequenceIndex);
if (sequence[sequenceIndex] == 'E') {
isRunning = false;
Serial.println("Fim da sequência");
digitalWrite(YellowLEDPin, LOW);
digitalWrite(GreenLEDPin, LOW);
digitalWrite(BlueLEDPin, LOW);
sequenceIndex = 0; // Reset sequence index
vTaskDelete(NULL); // Deleta a tarefa atual
return;
}
int durationIndex = sequenceIndex;
while (sequence[durationIndex] >= 'A' && sequence[durationIndex] <= 'Z') {
durationIndex++;
}
int duration = sequence[durationIndex] - '0'; // Convertendo char para int
Serial.print("Duration: ");
Serial.println(duration);
for (int i = sequenceIndex; i < durationIndex; i++) {
LEDCommand command;
command.duration = duration * 1000; // Convertendo para milissegundos
switch (sequence[i]) {
case 'Y':
command.pin = YellowLEDPin;
break;
case 'G':
command.pin = GreenLEDPin;
break;
case 'B':
command.pin = BlueLEDPin;
break;
}
Serial.print("Sending command to pin: ");
Serial.println(command.pin);
xQueueSend(ledQueue, &command, portMAX_DELAY);
}
vTaskDelay(pdMS_TO_TICKS(duration * 1000)); // Espera pelo tempo especificado
for (int i = sequenceIndex; i < durationIndex; i++) {
switch (sequence[i]) {
case 'Y':
digitalWrite(YellowLEDPin, LOW);
break;
case 'G':
digitalWrite(GreenLEDPin, LOW);
break;
case 'B':
digitalWrite(BlueLEDPin, LOW);
break;
}
}
sequenceIndex = durationIndex + 1; // Avança para o próximo comando
} else {
vTaskDelay(pdMS_TO_TICKS(100)); // Aguarda até que a execução seja retomada
}
}
}
// Função para controlar o LED específico
void ledTask(void *pvParameters) {
Serial.println("Iniciando ledTask");
LEDCommand command;
while (1) {
if (xQueueReceive(ledQueue, &command, portMAX_DELAY) == pdPASS) {
Serial.print("Received command for pin: ");
Serial.print(command.pin);
Serial.print(" with duration: ");
Serial.println(command.duration);
digitalWrite(command.pin, HIGH);
vTaskDelay(pdMS_TO_TICKS(command.duration));
digitalWrite(command.pin, LOW);
Serial.print("Finished command for pin: ");
Serial.println(command.pin);
}
}
}
// Função para gerenciar a leitura dos botões
void buttonTask(void *pvParameters) {
Serial.println("Iniciando buttonTask");
while (1) {
Serial.println("Entrou no while da buttonTask()");
if (button1pressed) {
button1pressed = false;
Serial.println("Button 1 pressed");
if (!started) {
// Começa a execução
Serial.println("começa a execução");
started = true;
isRunning = true;
sequenceIndex = 0;
xTaskCreate(processSequenceTask, "ProcessSequenceTask", 128, NULL, 1, NULL);
} else if (isRunning) {
// Pausa execução
Serial.println("pausa execução");
isRunning = false;
} else {
// Continua a execução
Serial.println("continua a execução");
isRunning = true;
}
}
if (button2pressed) {
button2pressed = false;
Serial.println("Button 2 pressed");
Serial.print("Digite a sequência: ");
int index = 0;
while (true) {
if (Serial.available() > 0) {
char c = Serial.read();
if (c == '\n' || c == '\r') {
break;
}
sequence[index++] = c;
}
vTaskDelay(pdMS_TO_TICKS(100));
}
sequence[index] = '\0'; // Termina a string
Serial.print("Sequência recebida: ");
Serial.println(sequence);
sequenceIndex = 0;
isRunning = false; // Pausa execução para que a nova sequência possa ser iniciada
started = false; // Permite iniciar a execução com o botão 1
}
vTaskDelay(pdMS_TO_TICKS(100));
}
}
void setup() {
Serial.begin(9600);
Serial.println("Setup iniciado");
pinMode(CH01Pin, INPUT_PULLUP);
pinMode(CH02Pin, INPUT_PULLUP);
Serial.println("Botões setados");
pinMode(YellowLEDPin, OUTPUT);
Serial.println("LED amarelo setado");
pinMode(GreenLEDPin, OUTPUT);
Serial.println("LED verde setado");
pinMode(BlueLEDPin, OUTPUT);
Serial.println("LED azul setado");
attachInterrupt(digitalPinToInterrupt(CH02Pin), pressButton2, FALLING);
Serial.println("Interrupção do botão 2 setada");
attachInterrupt(digitalPinToInterrupt(CH01Pin), pressButton1, FALLING);
Serial.println("Interrupção do botão 1 setada");
ledQueue = xQueueCreate(10, sizeof(LEDCommand));
Serial.println("Filas criadas");
xTaskCreate(ledTask, "YellowTask", 128, NULL, 2, NULL);
xTaskCreate(ledTask, "GreenTask", 128, NULL, 2, NULL);
xTaskCreate(ledTask, "BlueTask", 128, NULL, 2, NULL);
xTaskCreate(buttonTask, "ButtonTask", 128, NULL, 3, NULL);
Serial.println("Tarefas criadas");
}
void loop() {
// O loop está vazio porque usamos FreeRTOS
}