Problema con envio de datos con decimales

Muy buenas , estoy utilizando estos codigos , para enviar la temperatura y humedad desde un TX y recibir en el RX:

Este es el emisor:

#include <SPI.h>
#include <Mirf.h>
#include <nRF24L01.h>
#include <MirfHardwareSpiDriver.h>
#include <dht.h>
// Pin donde va conectado los datos
#define dht_pin 2
#define DHT21PIN 2
#define DHTTYPE DHT21
 
//Sonda de temperatura
dht DHT;
 
//La última vez que envía datos a través de la NRF (en ms)
long lastSend = 0;
 
//El retardo entre cada envío (en ms)
  int sendDelay = 5*1000;//Aqui 5sec
 
//El identificador de cada sonda. Este identificador debe ser único a una sonda.
int probeId = 0;
 
void setup() 
{
  Serial.begin(9600);
  Serial.println("Inicio del sensor.");
  //dht.begin();
  Mirf.cePin = 9;
  Mirf.csnPin = 10;
  //Se incializa Mirf , para gestioner el rf24
  Mirf.spi = &MirfHardwareSpi;
  Mirf.init();
  Mirf.setRADDR((byte *)"prob1");//El nombre de la sonda del sensor
  Mirf.payload = 3;//La longitud del paquete que transitará
  Mirf.config();
  Mirf.setTADDR((byte*)"serv0");//El nombre del servidor al que transmite nuestros dato
 
  Serial.println( "nRF24L01+ inicializando!" );
  DHT.read21(dht_pin);
  Serial.println(DHT.temperature);
  Serial.println(DHT.humidity);  
}
 
void loop() 
{
  //Si, durante el tiempo entre las transferencias de datos
  if(lastSend+sendDelay <= millis())
  {
    Serial.println("Enviando...");
     
    //Si uno se está enviando, esperamos que se acabe
    while(Mirf.isSending()){
    }
     
    //Actualiza los valores de DHT21 (IMPORTANTE, poner en readdhtxx el que corresponda a tu sensor)
    DHT.read21(dht_pin);   
 
    //El paquete se crea con una longitud de tres bytes
    byte packet[3];
     
    //El ID del sensor
    packet[0] = probeId;
     
    //La temperatura
    packet[1] = DHT.temperature;
    //La humedad
    packet[2] = DHT.humidity;
    //Enviamos el paquete
    Mirf.send(packet);
     
    //Muestra los datos del paquete de depuración
    Serial.print("Temp:");
    Serial.println(packet[1]);
    Serial.print("Humi:");
    Serial.println(packet[2]);
    
     
    //Actualiza la "fecha" de la transmisión de datos reciente
    lastSend = millis();
  }
}

Y aqui el receptor:

#include <SPI.h>
#include <Mirf.h>
#include <nRF24L01.h>
#include <MirfHardwareSpiDriver.h>
#include <Ethernet.h>
 
//La direccion MAC del shield ethernet
byte mac[] = {0xAA, 0xBB, 0xCC, 0x18, 0x01, 0x95};
 
//Puerto de escucha xx
EthernetServer server(8081);
 
//Ip fija 
IPAddress ip(192,168,1,123);
//byte server[] = { 192,168,1,200 };
 
//Ultimos datos del sensor DHT21
int lastTemp = 0;
int lastHumi = 0;
 
//Los valores cambia desde los ultimos enviado desde el ethernet
boolean valuesHaveChanged = false;
 
void setup() 
{
  //Se inicia la conexion serial
  Serial.begin(9600);
  Serial.println("Inicio de la captura del sensor.");
 
  /*
   * Se inicia el nrf24L01
   */
  Mirf.cePin = 9;
  Mirf.csnPin = 8;
  Mirf.spi = &MirfHardwareSpi;
  Mirf.init();
  Mirf.setRADDR((byte *)"serv0");//El nombre del servidor/receptor nrf24l01
  Mirf.payload = 3;//Longitud del paquete en bytes
  Mirf.config();
 
  Serial.println( "nRF24L01+ inicializando!" );
   
  //Se inicia el servidor , dando una ip y la mac.
  Ethernet.begin(mac, ip);
  server.begin();
   
  //Muestra la Ip , para comprobar que todo este bien
  Serial.print("Direccion obtenida del servidor DHCP: ");
  Serial.println(Ethernet.localIP());
}
 
 
void loop() 
{
   
  //Recuperacio del servidor si entra un cliente
  EthernetClient client = server.available();
   
  //Si esta disponible los datos (nrf24L01+)
  if(Mirf.dataReady())
  {
    //Creamos la tabla que contendrá los datos
    byte datas[3];
     
    //Se recupera y coloca los datos en la tabla
    Mirf.getData(datas);
     
    //Se muestra los datos mediante el puerto serie para la depuración
    Serial.print("Temp:");
    Serial.println(datas[1]);
    Serial.print("Humi:");
    Serial.println(datas[2]);
     
    //Almacena los ultimos datos
    lastTemp = datas[1];
    lastHumi = datas[2];
     
    //Se le dice al programa que los valores han cambiado y por lo que hay cosas que se devuelvan
    valuesHaveChanged = true;
  }
   
  //Si un cliente entra, se recupera el servidor
  if (client) 
  {
    Serial.println("Nuevo cliente");
 
    boolean currentLineIsBlank = true;
     
    //Mientras el cliente está conectado
    while (client.connected()) 
    {
      //Hasta que haya terminado de leer su petición
      if (client.available()) 
      {
        //Lee la peticion del cliente , y muestra lo del serial
        char c = client.read();
        Serial.write(c);
         
        //Si nos encontramos con un salto de línea y la línea actual ya está vacía
        if (c == '\n' && currentLineIsBlank) 
        {
          //Responde a la petición con nuestros datos
          client.println("HTTP/1.1 200 OK");//Código 200 = Todo fue bien
          client.println("Content-Type: application/xml");//Especifica el MIME-TYPE que envía datos (XML)
          client.println("Connection: close");  
          client.println();
           
          client.println("<?xml version=\"1.0\"?>");//Cabecera del documento XML
           
          //El elemento raíz del documento XML
          client.println("<sensors>");
           
          
          for (int i = 0; i < 1; i++) 
          {
            //Se crea un elemento para cada sensor
            client.print("<sensor name=\"sns");
            client.print(i);//Id del sensor
            client.println("\">");
             
            //Se crea un elemento secundario que contiene los valores de temperatura
            client.print("<temperatura>");
            //Si los valores del sensor han cambiado, se envia
            if(valuesHaveChanged)
              client.print(lastTemp);
            //De lo contrario, devuelve una cadena no numérica
            else
              client.print("NaN");
            client.println("</temperatura>");
             
            //Se crea un elemento secundario que contiene valores de humedad
            client.print("<humedad>");
            //Si los valores del sensor han cambiado, se envia
            if(valuesHaveChanged)
              client.print(lastHumi);
            //De lo contrario, devuelve una cadena no numérica
            else
              client.print("NaN");
            client.println("</humedad>");
             
            client.println("</sensor>");   
          }
           
          //El elemento raíz sera cerrada
          client.println("</sensors>");
          break;
        }
         
        //Si se salta una línea
        if (c == '\n') 
        {
          //Es que comienza una nueva línea
          currentLineIsBlank = true;
        } 
        else if (c != '\r') 
        {
          //Un caracter en la linea actual , no esta vacia
          currentLineIsBlank = false;
        }
      }
    }
    //Se deja a la vez el navegador del cliente para recuperar datos
    delay(1);
     
    //Desconexión del cliente
    client.stop();
    Serial.println("cliente desconectado");
  }
}

En el codigo del emisor tengo estas lineas para la comprobacion correcta, de que lee bien el sensor antes de ser enviado:

  DHT.read21(dht_pin);
  Serial.println(DHT.temperature);
  Serial.println(DHT.humidity);

Si miro en el serial del TX , veo que la primera lectura es correcta con decimales, (22,40 y 54,30 por ejemplo) , pero luego me los envia en numero enteros , 22 y 54, al igual el RX los recibe como 22 y 54 .

Como puedo hacer que envie tambien los decimales correctamente al RX ??

Gracias y un saludo.

A mi se me ocurre que descompongas el número, y envíes primero la parte entera y luego la parte decimal, como dos números enteros. En el receptor, lo vuelves a componer como un número con decimales.

carmeloco:
A mi se me ocurre que descompongas el número, y envíes primero la parte entera y luego la parte decimal, como dos números enteros. En el receptor, lo vuelves a componer como un número con decimales.

Gracias por contestar , eso ya lo he leido , el problema es que no encuentro un ejemplo de como hacer eso que me dices.

Un saludo.

Por favor, se trata que lo programes tu.
a 54 lo que es la parte decimal lo divides por 100 y tienes 0.54 y lo sumas al entero 22 y tienes 22.54

Suponiendo una temperatura de 22.56 y una humedad de 54.31, con el siguiente código, separamos la parte entera del número y la parte decimal, en dos enteros y los imprimimos por puerto serie:

float temp = 22.56;
float hum = 54.31;
int tent, tdec, hent, hdec;
void setup() {
  tent = int(entero(temp));
  tdec = int(decimal(temp));
  hent = int(entero(hum));
  hdec = int(decimal(hum));
  Serial.begin (9600);
  Serial.print ("Temp: ");
  Serial.print (tent);
  Serial.print (",");
  Serial.println (tdec);

  Serial.print ("Humedad: ");
  Serial.print (hent);
  Serial.print (",");
  Serial.println (hdec);
}

void loop() {
}

float entero(float dato) {
  float a = abs(dato);
  return a;
}

float decimal (float dato) {
  int a = abs(dato);
  float b = (dato * 100) - (a * 100);
  return b;
}

O lo que es lo mismo, pero metiéndolo en el loop, para que no lleve a confusión, el haberlo hecho en el setup, para que solo se imprimiese una vez.

float temp = 22.56;
float hum = 54.31;
int tent, tdec, hent, hdec;

void setup() {
  Serial.begin (9600);
}

void loop() {
  tent = int(entero(temp));
  tdec = int(decimal(temp));
  hent = int(entero(hum));
  hdec = int(decimal(hum));
  Serial.print ("Temp: ");
  Serial.print (tent);
  Serial.print (",");
  Serial.print (tdec);
  Serial.print (" - ");
  Serial.print ("Humedad: ");
  Serial.print (hent);
  Serial.print (",");
  Serial.println (hdec);
}

float entero(float dato) {
  float a = abs(dato);
  return a;
}

float decimal (float dato) {
  int a = abs(dato);
  float b = (dato * 100) - (a * 100);
  return b;
}

Ok, tomo nota, porbare lo que me comentais , gracias a los dos.

Surbyte , creo que un foro es para ayudar, y se ayuda al que no sabe, si supiera hacerlo yo , para que iba a preguntar??

Saludos.

Y no te ayudé?
Yo leí que no sabías como hacerlo y te dije cómo

surbyte:
Y no te ayudé?
Yo leí que no sabías como hacerlo y te dije cómo

Si por supuesto y te lo agradezco , mi comentario es a lo primero que dices.

Saludos.

porqué no envias el dato como float en lugar de enteros?

Yo lo hago asi.

En esta parte del código definies byte packet[3];
Pudiste haber definido float packet[3];

void loop() 
{
  //Si, durante el tiempo entre las transferencias de datos
  if(lastSend+sendDelay <= millis())
  {
    Serial.println("Enviando...");
     
    //Si uno se está enviando, esperamos que se acabe
    while(Mirf.isSending()){
    }
     
    //Actualiza los valores de DHT21 (IMPORTANTE, poner en readdhtxx el que corresponda a tu sensor)
    DHT.read21(dht_pin);   
 
    //El paquete se crea con una longitud de tres bytes
    float packet[3];
     
    //El ID del sensor
    packet[0] = (float) probeId; // porque probeId es entera
     
    //La temperatura
    packet[1] = DHT.temperature;
    //La humedad
    packet[2] = DHT.humidity;
    //Enviamos el paquete
    Mirf.send(packet);
     
    //Muestra los datos del paquete de depuración
    Serial.print("Temp:");
    Serial.println(packet[1]);
    Serial.print("Humi:");
    Serial.println(packet[2]);
    
     
    //Actualiza la "fecha" de la transmisión de datos reciente
    lastSend = millis();
  }
}

en el receptor de nuevo cambias
byte datas[3]; por

float datas[3];

y tienes cuidado con el datas[0]

He probado con float, pero no como tu me dices , interesante , cuando pruebe comento resultados.

Muchas gracias surbyte.

Te das cuenta que ayudo... pero me gusta intentar que la gente aprenda.

surbyte:
Te das cuenta que ayudo... pero me gusta intentar que la gente aprenda.

Gracias surbyte, he tenido un dia muy ...... raro , me dieron una mala noticia de mi perro el veterinario :frowning: .

Espero poder mañana probar lo que me has puesto un poco mas atras y comentare que tal ido.

Gracias y un saludo.

Uhhh cuanto lo siento, yo tuve dos en solo 1 semana.. una por mi culpa, le di un hueso y se le trabó en la traquea y bueno la llevo a que la operen, sale aparentemente bien, pero el hueso habia lacerado su traquea y estómago aunque no fue ese el problema sino que un pedacito fue a dar a un pulmón que lo hizo colapsar, eso me devastó, porque yo se lo dí, ahora nunca mas reciben huesos por consejo del veterinario. Amaba esa cachorra que encima la llamé Nicoletta como el personaje de La Pantera Rosa, la francesa que amaba en silencio el Inspector Clouseau.

Por otro lado me entero luego de detectar unas protuberancias que otra cachorra Twity tiene cancer en una zona que cubre casi toda su panza. Como fue muy temprano ETAPA 1 y se pudo operar con buenas chances (95%). Aun estamos en su cuidado... y no sabremos nada hasta un buen tiempo.

Hay que ser paciente y tener fe que las cosas pueden ir bien y si no es asi el destino dirá.

Lo mejor para tu perro.

Bueno pues ya he probado como me comentas y aqui te expongo los errores:

error: no matching function for call to 'Nrf24l::send(float&)'

Esto es por la siguiente linea:Mirf.send(packet);

Seguire investigando el por que me da ese error , gracias.

puedes subir código y librerías, ponlas en el attachment porque será mucha información

Hola. Yo para temperaturas multiplicaría en origen por cien, lo enviaría como entero y en destino lo dividiría de nuevo por cien. Un pequeño cálculo, pero simplifica el proceso.

Bueno por fin ya lo he conseguido y tengo los datos con decimales subiendo a la web:

Temperatura y humedad

Al final lo que he hecho ha sido, añadir 2 packets mas:

El original:

byte packet[3];
     
    //El ID del sensor
    packet[0] = probeId;
     
    //La temperatura
    packet[1] = DHT.temperature;
    //La humedad
    packet[2] = DHT.humidity;

Modificado:

byte packet[5];
     
    //El ID del sensor
    packet[0] = probeId;
     
    //La temperatura
    packet[1] = DHT.temperature;
    packet[2] = (DHT.temperature-packet[1])*100;
    //La humedad
    packet[3] = DHT.humidity;
    packet[4] = (DHT.humidity-packet[3])*100;

Tambien tenemos que cambiar otra cosa y es el Mirf.payload = 3 , poner 5 .

Saludos.

Estoy siguiendo los vuestros adelantos....podrías publicar el código completo de emisor / receptor. Los que aprendemos nos va mejor para poder estudiarlo.
Muchas gracias.

francisco2v:
Estoy siguiendo los vuestros adelantos....podrías publicar el código completo de emisor / receptor. Los que aprendemos nos va mejor para poder estudiarlo.
Muchas gracias.

Los tienes en el primer post que puse, aun asi , si necesitas cualquier cosa mas , hazmelo saber.

Saludos.