#include <Arduino.h>
#include <WiFi.h>
#include <PubSubClient.h>
// Credenciales WiFi (las mismas del código original)
const char* ssid = "Wokwi-GUEST";
const char* password = "";
// Configuración MQTT (la misma del código original)
const char* mqtt_server = "broker.emqx.io";
const int mqtt_port = 1883;
// Tópicos MQTT (los mismos del código original)
const char* topicVoltaje = "medicion/voltaje";
const char* topicCorriente = "medicion/corriente";
const char* topicFrecuencia = "medicion/frecuencia";
const char* topicPotencia = "medicion/potencia";
const char* topicEstado = "medicion/estado";
const char* topicControlReset = "control/reset";
// LED para indicar estado de conexión
const int statusLedPin = 2;
// Variables para los valores aleatorios
float VAC = 110.0; // Voltaje inicial (90-150V)
float AmpAC = 5.0; // Corriente inicial (0-30A)
float Frequency = 60.0; // Frecuencia inicial (0-120Hz)
float Power = 0.0; // Se calculará con la fórmula P = V * I
// Límites para la generación de valores aleatorios
const float MIN_VOLTAGE = 90.0;
const float MAX_VOLTAGE = 150.0;
const float MIN_CURRENT = 0.0;
const float MAX_CURRENT = 30.0;
const float MIN_FREQUENCY = 45.0;
const float MAX_FREQUENCY = 120.0;
// Variación máxima entre mediciones
const float VOLTAGE_VARIATION = 5.0; // Variación de hasta 5V entre mediciones
const float CURRENT_VARIATION = 2.0; // Variación de hasta 2A entre mediciones
const float FREQUENCY_VARIATION = 1.0; // Variación de hasta 1Hz entre mediciones
// Tiempos de actualización
unsigned long lastUpdateTime = 0;
unsigned long lastMqttPublishTime = 0;
bool systemEnabled = true;
// Objetos para WiFi y MQTT
WiFiClient espClient;
PubSubClient client(espClient);
// Función para generar ID de cliente aleatorio
String generateRandomClientId() {
String clientId = "ESP32TestPublisher-";
clientId += String(random(0xffff), HEX);
return clientId;
}
// Función para generar un nuevo valor aleatorio dentro de un rango y con variación respecto al valor anterior
float generateRandomValue(float currentValue, float minValue, float maxValue, float maxVariation) {
float minNewValue = max(minValue, currentValue - maxVariation);
float maxNewValue = min(maxValue, currentValue + maxVariation);
return random(int(minNewValue * 100), int(maxNewValue * 100)) / 100.0;
}
// Configuración de la conexión WiFi
void setupWiFi() {
delay(10);
Serial.println();
Serial.print("Conectando a WiFi: ");
Serial.println(ssid);
WiFi.begin(ssid, password, 6);
// Parpadear LED durante la conexión
while (WiFi.status() != WL_CONNECTED) {
digitalWrite(statusLedPin, HIGH);
delay(250);
digitalWrite(statusLedPin, LOW);
delay(250);
Serial.print(".");
}
// LED estable cuando está conectado
digitalWrite(statusLedPin, HIGH);
Serial.println("");
Serial.println("WiFi conectado");
Serial.print("Dirección IP: ");
Serial.println(WiFi.localIP());
}
// Reconexión al servidor MQTT
void reconnectMQTT() {
while (!client.connected()) {
Serial.print("Conectando al servidor MQTT...");
// Generar un ID de cliente aleatorio
String clientId = generateRandomClientId();
Serial.print("ID de cliente: ");
Serial.print(clientId);
if (client.connect(clientId.c_str())) {
Serial.println(" - conectado");
// Suscribirse al tópico de control
client.subscribe(topicControlReset);
Serial.println("Suscrito al tópico de control/reset");
// Publicar que estamos online
client.publish(topicEstado, "TEST_PUBLISHER_ACTIVO");
} else {
Serial.print(" - falló, rc=");
Serial.print(client.state());
Serial.println(" intentando de nuevo en 5 segundos");
// Parpadear LED rápidamente cuando hay error de conexión MQTT
for (int i = 0; i < 10; i++) {
digitalWrite(statusLedPin, HIGH);
delay(100);
digitalWrite(statusLedPin, LOW);
delay(100);
}
delay(3000);
}
}
}
// Callback para procesar mensajes MQTT entrantes
void callback(char* topic, byte* payload, unsigned int length) {
Serial.print("Mensaje recibido en tópico: ");
Serial.println(topic);
// Convertir payload a string para comparar
char mensaje[length + 1];
for (unsigned int i = 0; i < length; i++) {
mensaje[i] = (char)payload[i];
}
mensaje[length] = '\0';
Serial.print("Mensaje: ");
Serial.println(mensaje);
// Procesar comando de reset
if (strcmp(topic, topicControlReset) == 0) {
if (strcmp(mensaje, "reset") == 0) {
Serial.println("🔄 Simulando reinicio del sistema por comando MQTT...");
systemEnabled = false;
client.publish(topicEstado, "REINICIANDO");
// Parpadear LED para indicar reinicio
for (int i = 0; i < 5; i++) {
digitalWrite(statusLedPin, HIGH);
delay(200);
digitalWrite(statusLedPin, LOW);
delay(200);
}
delay(2000);
systemEnabled = true;
client.publish(topicEstado, "ACTIVO");
digitalWrite(statusLedPin, HIGH);
}
}
}
// Generar nuevos valores aleatorios
void updateRandomValues() {
// Generar nuevos valores con variaciones graduales
VAC = generateRandomValue(VAC, MIN_VOLTAGE, MAX_VOLTAGE, VOLTAGE_VARIATION);
AmpAC = generateRandomValue(AmpAC, MIN_CURRENT, MAX_CURRENT, CURRENT_VARIATION);
Frequency = generateRandomValue(Frequency, MIN_FREQUENCY, MAX_FREQUENCY, FREQUENCY_VARIATION);
// Calcular potencia
Power = VAC * AmpAC;
}
// Mostrar datos en Serial
void displayData() {
Serial.println("------- DATOS DE PRUEBA -------");
Serial.print("Voltaje: "); Serial.print(VAC, 2); Serial.println(" V");
Serial.print("Corriente: "); Serial.print(AmpAC, 2); Serial.println(" A");
Serial.print("Potencia: "); Serial.print(Power, 2); Serial.println(" W");
Serial.print("Frecuencia: "); Serial.print(Frequency, 1); Serial.println(" Hz");
Serial.print("Estado: "); Serial.println(systemEnabled ? "ACTIVO" : "INACTIVO");
Serial.println("------------------------------");
}
// Publicar datos por MQTT
void publishMQTTData() {
char buffer[10];
// Publicar voltaje
dtostrf(VAC, 6, 2, buffer);
client.publish(topicVoltaje, buffer);
// Publicar corriente
dtostrf(AmpAC, 6, 2, buffer);
client.publish(topicCorriente, buffer);
// Publicar potencia
dtostrf(Power, 6, 2, buffer);
client.publish(topicPotencia, buffer);
// Publicar frecuencia
dtostrf(Frequency, 6, 2, buffer);
client.publish(topicFrecuencia, buffer);
// Publicar estado
client.publish(topicEstado, systemEnabled ? "ACTIVO" : "INACTIVO");
}
void setup() {
Serial.begin(115200);
Serial.println("\n--- ESP32 MQTT Test Publisher ---");
Serial.println("Generando valores aleatorios para mediciones eléctricas");
// Inicializar el generador de números aleatorios
randomSeed(analogRead(0));
// Configurar el pin del LED
pinMode(statusLedPin, OUTPUT);
digitalWrite(statusLedPin, LOW);
// Configurar WiFi
setupWiFi();
// Configurar MQTT
client.setServer(mqtt_server, mqtt_port);
client.setCallback(callback);
Serial.println("Sistema de prueba listo");
}
void loop() {
unsigned long currentMillis = millis();
// Verificar conexión MQTT
if (!client.connected()) {
digitalWrite(statusLedPin, LOW);
reconnectMQTT();
}
client.loop();
// Actualizar valores aleatorios cada 2 segundos
if (currentMillis - lastUpdateTime >= 2000) {
updateRandomValues();
displayData();
lastUpdateTime = currentMillis;
}
// Publicar datos MQTT cada segundo
if (currentMillis - lastMqttPublishTime >= 1000) {
if (systemEnabled) {
publishMQTTData();
}
lastMqttPublishTime = currentMillis;
}
delay(10);
}Loading
esp32-c6-devkitc-1
esp32-c6-devkitc-1
Voltage Sensor
Current Sensor
SSR Out
POWER ON/OFF
RESET