Hola de nuevo, os cuento mi primera experiencia con la placa mbed ( mbed.org ), una placa ARM que tiene el entorno de desarrollo en la nube , lo que permite usar y compartir multitud de librerias super-utiles.
Y eso es lo que yo he hecho, usar la libreria Ethernet + TCP/IP( si, la placa soporta conexión de red) y una libreria de servidor Web disponible ( todo en C++) , de forma que hacer un mini-servidor web que atiende a comandos básicos , como enceder o apagar los leds de la placa via web, ha sido tan fácil como el código que os pongo abajo, bueno hay una pequeña trampa, como la complejidad del código en la placa es mínima, he tenido que meter un poco de Javascript en la página que devuelve el mini-servidor, pero tampoco ha sido complicado ... Lo he probado desde un portatil con Windows, un móvil android y un Iphone y los comandos remotos funcionan perfectamente en los tres casos.
Los comandos se activan desde código javascript de la página, porque mbed implementa un mecanismo de invocacion remota llamado RPC ( original
) que puede ejecutarse desde el mini-servidor web que ejecutamos en la placa, por ejemplo para encender el led1, se puede hacer con la siguiente URL:
http::/ip-del-mini-server/led1/write 1.
Ahora solo queda usar las salidas digitales de la placa para activar/desactivar por ejemplo reles, y estamos a un paso de un control web domotico, ah, RPC permite también acceder a ports de entrada, port analogicos o cosas más compejas como dispositivos I2C, USB, etc... todo se puede presentar como una sencilla URL
El código que hay que cargar en la placa es este , con tiempo os pondre el código de la pagina html...
Una pega importante, para poder compilar y acceder al entorno de desarrollo ( en la nube) hay que tener una placa mbed...
// Mini-servidor WEB en mbed
// para uso domotico.
//
// MBC (splasma) 2011
#include "mbed.h"
#include "TextLCD.h"
#include "EthernetNetIf.h"
#include "HTTPServer.h"
#include "RPCVariable.h"
EthernetNetIf eth;
HTTPServer svr;
TextLCD lcd(p21, p22, p23, p24, p25, p26,TextLCD::LCD16x2); // rs, e, d4-d7
DigitalOut led1(LED1, "led1");
DigitalOut led2(LED2, "led2");
DigitalOut led3(LED3, "led3");
DigitalOut led4(LED4, "led4");
LocalFileSystem fs("webfs");
int Ticks = 0;
//Attach variable to an RPCVariable Object
RPCVariable<int> rpc_i(&Ticks, "ticks");
int main() {
Base::add_rpc_class<DigitalOut>();
lcd.cls();
lcd.printf("Setting up...\n");
EthernetErr ethErr = eth.setup(10000);
if(ethErr)
{
lcd.printf("Error %d.\n", ethErr);
return -1;
}
lcd.printf("Setup OK\n");
IpAddr ethIp = eth.getIp();
lcd.printf("IP :%d.%d.%d.%d\n", ethIp[0], ethIp[1], ethIp[2], ethIp[3]);
const char* hwAddr = eth.getHwAddr();
//lcd.printf("MAC:%02x:%02x:%02x:%02x:%02x:%02x\n",
// hwAddr[0], hwAddr[1], hwAddr[2],
// hwAddr[3], hwAddr[4], hwAddr[5]);
FSHandler::mount("/webfs", "/files"); //Mount /webfs path on /files web path
FSHandler::mount("/webfs", "/"); //Mount /webfs path on web root path
svr.addHandler<SimpleHandler>("/hello");
svr.addHandler<RPCHandler>("/rpc");
svr.addHandler<FSHandler>("/files");
svr.addHandler<FSHandler>("/"); //Default handler
svr.bind(80);
Timer tm;
tm.start();
//Listen indefinitely
while(true)
{
Net::poll();
if(tm.read()>.5)
{
led1=!led1; //Show that we are alive
tm.start();
if (led1) Ticks++;
}
}
return 0;
}