La integración de hardware embebido con software de análisis de alto nivel es crucial para el prototipado rápido. Este artículo expone un sistema de monitoreo que emplea un microcontrolador ESP32 como servidor TCP local y la plataforma MATLAB App Designer para visualización y gestión de datos, evitando la necesidad de frameworks web o bases de datos externas.
Fundamentos de la Arquitectura del Sistema
El diseño se basa en roles claros: el ESP32 opera como un servidor de socket TCP que escucha en un puerto específico, mientras que la aplicación MATLAB actúa como un cliente que estiblece la conexión y consume los flujos de datos. La comunicación utiliza el protocolo TCP sobre Wi-Fi local, garantizando estabilidad y bajos latencias para transmisiones continuas.
Implementación del Firmware en el ESP32
El código del microcontrolador gestiona la red y la transmisión de datos. Primero, establece la conexión Wi-Fi y configura el servidor TCP. Es fundamental llamar explícitamente al método begin() en el objeto WiFiServer para iniciar la escucha.
#include <wifi.h>
const char* wifi_ssid = "NombreDeRed";
const char* wifi_password = "ClaveDeRed";
const uint16_t server_port = 9500;
WiFiServer tcp_server(server_port);
WiFiClient client_actual;
void setup() {
Serial.begin(115200);
WiFi.begin(wifi_ssid, wifi_password);
while (WiFi.status() != WL_CONNECTED) {
delay(1000);
Serial.println("Conectando a la red...");
}
Serial.print("Dirección IP asignada: ");
Serial.println(WiFi.localIP());
tcp_server.begin(); // Inicia la escucha en el puerto.
}
void loop() {
// Gestión de cliente no bloqueante.
if (!client_actual.connected()) {
client_actual = tcp_server.available();
return;
}
// Lógica de adquisición y envío periódico.
static unsigned long marca_tiempo = 0;
const unsigned long intervalo = 50; // Intervalo en ms (20 Hz).
if (millis() - marca_tiempo >= intervalo) {
float lectura_sensor = analogRead(34) * (3.3 / 4095.0);
// Estructura de datos con delimitador.
String payload = "{\"valor_adc\":" + String(lectura_sensor, 2) + "}\n";
if (client_actual.connected()) {
client_actual.print(payload);
}
marca_tiempo = millis();
}
}
</wifi.h>
Elementos de diseño críticos incluyen: el uso de un delimitador de mensaje (\n) para el framing de paquetes TCP, y la implementación de una gestión de conexión no bloqueante que verifica el estado del cliente antes de operar.
Desarrollo de la Aplicación en MATLAB App Designer
La interfaz gráfica se construye con componentes de App Designer, como ejes (UIAxes) y campos de texto. La lógica de comunicación se maneja mediante un temporizador que consulta periódicamente el socket TCP.
% Propiedades de la aplicación (en la clase App).
properties (Access = private)
SocketTCP tcpclient
Temporizador timer
DatosTiempo datetime
DatosVoltaje double
LineaAnimada animatedline
end
% Al presionar el botón 'Conectar'.
function BotonConectarPushed(app, ~)
try
app.SocketTCP = tcpclient('192.168.1.150', 9500, 'Timeout', 5);
app.Temporizador = timer('ExecutionMode', 'fixedRate', ...
'Period', 0.05, ...
'TimerFcn', @(~,~) adquirirDatos(app));
start(app.Temporizador);
app.EtiquetaEstado.Text = 'Conectado';
catch e
uialert(app.FigureUI, ['Error: ' e.message], 'Fallo de conexión');
end
end
function adquirirDatos(app)
try
if app.SocketTCP.NumBytesAvailable > 0
linea_cruda = readline(app.SocketTCP);
paquete = jsondecode(linea_cruda);
% Actualizar visualización
app.EtiquetaValor.Text = sprintf('%.3f V', paquete.valor_adc);
addpoints(app.LineaAnimada, datenum(datetime('now')), paquete.valor_adc);
drawnow limitrate
end
catch
stop(app.Temporizador);
app.EtiquetaEstado.Text = 'Desconectado';
end
end
Solución de Problemas y Optimización
Problemas Frecuentes
- Bloqueo por cortafuegos: Es necesario crear una regla de entrada en el firewall del sistema operativo para permitir el tráfico TCP en el puerto especificado (ej. 9500).
- IP Dinámica: Utilice el mDNS en el ESP32 (
#include <espmdns.h></espmdns.h>yMDNS.begin("dispositivo1")) para acceder mediante un nombre de dominio local (ej.dispositivo1.local) en lugar de una IP numérica. - Reconexión Automática: Implemente un bucle de reintento con un temporizador en MATLAB al detectar una desconexión, reutilizando el objeto
tcpclientsi es posible.
Optimización de Rendimiento
Para aplicaciones de larga duración, sustituya la función plot por animatedline. Este objeto actualiza gráficamente solo los nuevos puntos, reduciendo significativamente la carga de renderizado. Para el manejo de la memoria, considere implementar un buffer circular (estructura de tamaño fijo) en lugar de concatenar arrays en las propiedades de la aplicación.
Extensiones y Casos de Uso
La arquitectura es extensible. Puede modificar el payload JSON para incluir múltiples campos (ej. temperatura, humedad, estado digital) y actualizar la interfaz correspondientemente. Agregue funcionalidad de exportación mediante writetable() para guardar los datos en formato CSV con marcas de tiempo.
Este enfoque es idóneo para validación de algoritmos en entornos educativos, monitoreo rápido de prototipos en laboratorios, y construcción de paneles de supervisión para equipos de producción de baja complejidad, donde la rapidez de desarrollo es prioritaria sobre la escalabilidad.