2014-10-28 120 views
0

我正在尝试Arduino最终GPS突破,我想从GPS获取经度和纬度。然后我想通过射频发送这两个变量。像下面的图像中: enter image description hereC中的数据类型的问题

我使用名为panstamp所述RF模块库,以便能够从阿尔杜伊诺1发送的经度和纬度,以及接收它们的Arduino 2.像在下面的代码:

发射:

void send_data() { 
    CCPACKET data; 
    data.length=2; 

    float lon=26.533255; 
    float lat=27.533463; 


    data.data[0]=lon; 
    data.data[1]=lat; 
    if(cc1101.sendData(data)){ 
    Serial.println(data.data[0]); 
    Serial.println(data.data[1]); 

    Serial.println(" sent ok "); 
    return true; 
    }else{ 
    Serial.println("sent failed "); 
    return false; 
    } 

} 

接收:

void loop(){ 
     float j = 0; 
     lon = packet.data[j]; 
      Serial.print(lon); 
      Serial.print(" "); 
     float k = 1; 
     lat = packet.data[k]; 
      Serial.print(lat); 
      Serial.println("."); 
} 

发射时它完美和REC eiving :)

问题是,当我收到这两个变量我刚刚收到LON 26.00和LAT 27.00但不经度纬度26.533255 27.533463如我所料。

我假设的数据类型有一些错误。我调查了panstamp库以找到改变类型但没有成功的东西。

这里是CCPACKET头文件:

#ifndef _CCPACKET_H 
#define _CCPACKET_H 

#include "Arduino.h" 

/** 
* Buffer and data lengths 
*/ 
#define CC1101_BUFFER_LEN  64 
#define CC1101_DATA_LEN   CC1101_BUFFER_LEN - 3 

/** 
* Class: CCPACKET 
* 
* Description: 
* CC1101 data packet class 
*/ 
class CCPACKET 
{ 
    public: 
    /** 
    * Data length 
    */ 
    byte length; 

    /** 
    * Data buffer 
    */ 
    byte data[CC1101_DATA_LEN]; 

    /** 
    * CRC OK flag 
    */ 
    boolean crc_ok; 

    /** 
    * Received Strength Signal Indication 
    */ 
    byte rssi; 

    /** 
    * Link Quality Index 
    */ 
    byte lqi; 
}; 

#endif 

和发送数据的源代码/接收数据:

boolean CC1101::sendData(CCPACKET packet) 
{ 
    byte marcState; 
    bool res = false; 

    // Declare to be in Tx state. This will avoid receiving packets whilst 
    // transmitting 
    rfState = RFSTATE_TX; 

    // Enter RX state 
    setRxState(); 

    // Check that the RX state has been entered 
    while (((marcState = readStatusReg(CC1101_MARCSTATE)) & 0x1F) != 0x0D) 
    { 
    if (marcState == 0x11)  // RX_OVERFLOW 
     flushRxFifo();    // flush receive queue 
    } 

    delayMicroseconds(500); 

    // Set data length at the first position of the TX FIFO 
    writeReg(CC1101_TXFIFO, packet.length); 
    // Write data into the TX FIFO 
    writeBurstReg(CC1101_TXFIFO, packet.data, packet.length); 

    // CCA enabled: will enter TX state only if the channel is clear 
    setTxState(); 

    // Check that TX state is being entered (state = RXTX_SETTLING) 
    marcState = readStatusReg(CC1101_MARCSTATE) & 0x1F; 
    if((marcState != 0x13) && (marcState != 0x14) && (marcState != 0x15)) 
    { 
    setIdleState();  // Enter IDLE state 
    flushTxFifo();  // Flush Tx FIFO 
    setRxState();   // Back to RX state 

    // Declare to be in Rx state 
    rfState = RFSTATE_RX; 
    return false; 
    } 

    // Wait for the sync word to be transmitted 
    wait_GDO0_high(); 

    // Wait until the end of the packet transmission 
    wait_GDO0_low(); 

    // Check that the TX FIFO is empty 
    if((readStatusReg(CC1101_TXBYTES) & 0x7F) == 0) 
    res = true; 

    setIdleState();  // Enter IDLE state 
    flushTxFifo();  // Flush Tx FIFO 

    // Enter back into RX state 
    setRxState(); 

    // Declare to be in Rx state 
    rfState = RFSTATE_RX; 

    return res; 
} 


byte CC1101::receiveData(CCPACKET * packet) 
{ 
    byte val; 
    byte rxBytes = readStatusReg(CC1101_RXBYTES); 

    // Any byte waiting to be read and no overflow? 
    if (rxBytes & 0x7F && !(rxBytes & 0x80)) 
    { 
    // Read data length 
    packet->length = readConfigReg(CC1101_RXFIFO); 
    // If packet is too long 
    if (packet->length > CC1101_DATA_LEN) 
     packet->length = 0; // Discard packet 
    else 
    { 
     // Read data packet 
     readBurstReg(packet->data, CC1101_RXFIFO, packet->length); 
     // Read RSSI 
     packet->rssi = readConfigReg(CC1101_RXFIFO); 
     // Read LQI and CRC_OK 
     val = readConfigReg(CC1101_RXFIFO); 
     packet->lqi = val & 0x7F; 
     packet->crc_ok = bitRead(val, 7); 
    } 
    } 
    else 
    packet->length = 0; 

    setIdleState();  // Enter IDLE state 
    flushRxFifo();  // Flush Rx FIFO 
    //cmdStrobe(CC1101_SCAL); 

    // Back to RX state 
    setRxState(); 

    return packet->length; 
} 

请帮助我的人:)

的链接在Panstamp库:PanStamp Library

+0

为什么你不能收到双打?你正在失去精确度,这就是问题所在?此外,你已经指出,库代码可能有错误 – ha9u63ar 2014-10-28 11:12:41

+0

这是我失去了精度的问题。但我能做些什么来接收双打或浮标?这是我的问题。 – AdiT 2014-10-28 11:17:35

+0

可能是这个赋值工作不正常,data.data [0] = lon; data.data [1] = lat,在这里您将float转换为字节类型 – 2014-10-28 11:30:09

回答

1

据我看到它,你失去了你的presicion这里:

float lon=26.533255; 
float lat=27.533463; 
data.data[0]=lon; 
data.data[1]=lat; 

,因为数据是根据这样的一个字节数组:

/** 
* Data buffer 
*/ 
byte data[CC1101_DATA_LEN]; 

您需要正确bufferise数据。

+0

嗯,但如何正确地缓冲他们?正如我所说,我试过但没有成功。你有任何想法可以帮助我吗? – AdiT 2014-10-28 11:31:51

+0

@AdiT,看看这个:http://stackoverflow.com/questions/24420246/c-function-to-convert-float-to-byte-array – HighPredator 2014-10-28 11:34:04

0

float lon = 26.533255; 字节* P =(字节*)&lon;

对(INT I = 0;我<的sizeof(LON);我++){ data.data [I] = P [I]; }

做到这样,如果它的工作原理进行相同与纬度或作出这样floattobyte和使用功能。

+0

嗯,不幸的是它不工作,我只是随机接收数字。 – AdiT 2014-10-28 12:36:41

+0

我可以这样打印:Serial.println(data.data [i]) – AdiT 2014-10-28 17:01:12

+0

这是将float转换为字节....您需要处理字节以在接收器端浮动..... – 2014-10-30 10:35:57

0

HighPredator是对的!

从panstamp lib中我们看到,CCPACKET ::数据字段是一个uint8_t数组: https://github.com/panStamp/panstamp/wiki/CCPACKET#data

基本上当你写:

float lon=26.533255; 
float lat=27.533463; 
data.data[0]=lon; 
data.data[1]=lat; 

编译器基本上是这样做的:

data.data[0]=uint8_t(lon); // So 26.533255f just becomes 26 
data.data[1]=uint8_t(lat); // So 27.533463just becomes 27 

您需要了解float类型,长度为4个字节,因此您需要将数据包长度为8个字节并传输像这样的原始字节:

data.length = 8; 
data.data[0] = ((uint8_t*)(&lon))[0]; // Transfer first byte of the float 
data.data[1] = ((uint8_t*)(&lon))[1]; 
data.data[2] = ((uint8_t*)(&lon))[2]; 
data.data[3] = ((uint8_t*)(&lon))[3]; // Transfer last byte of the float 

data.data[4] = ((uint8_t*)(&lat))[0]; // Transfer first byte of the float 
data.data[5] = ((uint8_t*)(&lat))[1]; 
data.data[6] = ((uint8_t*)(&lat))[2]; 
data.data[7] = ((uint8_t*)(&lat))[3]; // Transfer last byte of the float 

在接收端,你可以重新构图彩车是这样的:

float lon, lat; 
((uint8_t*)(&lon))[0] = data.data[0]; // Place first byte 
((uint8_t*)(&lon))[1] = data.data[1]; 
((uint8_t*)(&lon))[2] = data.data[2]; 
((uint8_t*)(&lon))[3] = data.data[3]; // Place last byte 

((uint8_t*)(&lat))[0] = data.data[4]; // Place first byte 
((uint8_t*)(&lat))[1] = data.data[5]; 
((uint8_t*)(&lat))[2] = data.data[6]; 
((uint8_t*)(&lat))[3] = data.data[7]; // Place last byte 

希望有所帮助。