Shop OBEX P1 Docs P2 Docs Learn Events
Propeller Wireless Connectivity — Parallax Forums

Propeller Wireless Connectivity

PhilldapillPhilldapill Posts: 1,283
edited 2009-01-05 10:47 in Propeller 1
I'm in the robotics club at my university and we're designing a robot to fight other robots. We have a pretty cool "spinning" design that will turn other robots into mush. However, we would like to be able to record sensor data and other things going on internally in the robot. We've thought about using an SD card, but that's kind of a hassle when we are testing it because we would have to put the SD in the robot, do our tests, take the SD out, put it in the computer... etc. We are all lazy...

We already use one of those pre-made robot remote controls that IMO, are kind of crude. I figured that if we are already using some kind of wireless link between the robot and controller, why not make our data logging wireless as well? This way we could do our tests on the robot(different movements), and instantly see the results on the TV screen(via a propeller of course!)

This bring me to the XBee... Anyone have any experience with these?· How about other digital RF means? I'd like to get a discussion of various wireless communication going, involving the propeller as the processor since that's what we are using.

Comments

  • John AbshierJohn Abshier Posts: 1,116
    edited 2009-01-04 16:21
    I have used XBee as a wireless serial link to my PC from my robots. On the robot side I just use Full Duplex serial to send state information (x, y, speed, sensor readings, etc). On the PC side I just use a terminal program.

    John Abshier
  • LeonLeon Posts: 7,620
    edited 2009-01-04 17:12
    I like the new Nordic nRF24L01+. SFE has some modules using it that I've just tried with a PIC, they work very well. They have an SPI interface.

    Leon

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Amateur radio callsign: G1HSM
    Suzuki SV1000S motorcycle
  • jazzedjazzed Posts: 11,803
    edited 2009-01-04 17:59
    I've used SFE's bluetooth gold module successfully from my pc up to about 30ft with free line-of-sight with PST or Hyperterm.

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    --Steve
  • TJHJTJHJ Posts: 243
    edited 2009-01-04 19:27
    Transiver set from parallax?

    http://www.parallax.com/Store/Accessories/Communication/tabid/161/CategoryID/36/List/0/Level/a/ProductID/111/Default.aspx?SortField=ProductName%2cProductName

    or

    http://www.rfdigital.com/

    parallax used to sell a transiver made by them, but do not anymore I had a set and they work great, super simple. Not sure why.

    TJ
  • PhilldapillPhilldapill Posts: 1,283
    edited 2009-01-04 20:52
    Thanks everybody! I didn't know there were so many solutions out there...

    @Leon, I REALLY like those ones from NORDIC. How much are they? It says they come in a 4mmx4mm QFN? Only requires an external crystal? Can the propeller provide the 16Mhz? How much are they?
  • LeonLeon Posts: 7,620
    edited 2009-01-04 21:35
    They are quite cheap, about $2 each. They need a few other parts, mainly for matching the output to the antenna. I suppose the Propeller could supply the 16 MHz, if there isn't too much jitter. Most wireless mice and keyboards use the older nRF24L01. It's best to use the parts and PCB layout in the data sheet.

    I'm getting quite good range with the SFE modules - between the third and first floors where I live, although it depends on the orientation. The little ceramic antennas on the modules aren't very efficient. Inside a room the orientation doesn't matter. I'll check them outside tomorrow, and get some idea of the maximum range.

    Leon

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Amateur radio callsign: G1HSM
    Suzuki SV1000S motorcycle

    Post Edited (Leon) : 1/4/2009 9:48:52 PM GMT
  • SRLMSRLM Posts: 5,045
    edited 2009-01-05 03:08
    @TJHJ

    There're no longer sold because RF Digital stopped producing them... I had to ask too here.
  • PhilldapillPhilldapill Posts: 1,283
    edited 2009-01-05 05:39
    Just FYI, free chips and PCB's to anyone who will write code for that Nordic device. I am very interested in it, and would love to see some code made for the propeller!
  • LeonLeon Posts: 7,620
    edited 2009-01-05 10:47
    Here's the code for my test programs:

    /*
    ** Tx.c
    ** Transmit test program for PIC18F4520 and nRF24L01 or nRF24L01+
    ** Uses the Microchip C18 compiler
    ** Based on SFE code for the CC5X code in 24L01demo_V01.c
    */
    
    #include <p18cxxx.h>
    #include <spi.h>
    #include <timers.h>
    
    // Pragmas
    #pragma config OSC = INTIO67
    #pragma config PWRT = ON
    //#pragma config MCLRE = OFF
    #pragma config BOREN = OFF
    
    
    //function prototypes
    void init(void);
    void transmit_data(void);
    void configure_transmitter(void);
    unsigned char spi_Send_Read(unsigned char);
    unsigned char spi1_send_read_byte(unsigned char byte);
    void dly(unsigned int);
    
    
    // Defines
    #define SPI_SCK        LATCbits.LATC3        // Clock pin, PORTC pin 3 
    #define SPI_SO        LATCbits.LATC5        // Serial output pin, PORTC pin 5 
    #define SPI_SI        PORTCbits.RC4        // Serial input pin, PORTC pin 4 
    #define SPI_CSN        LATCbits.LATC2        // CSN output pin, PORTC pin 2
    #define SPI_CE        LATCbits.LATC1        // CE output pin, PORTC pin 1
    #define SPI_IRQ        PORTBbits.RB0        // IRQ input pin, PORTB pin 0
    #define SPI_SCALE    4                      // postscaling of signal 
    #define LED            LATAbits.LATA0
    #define PB            PORTAbits.RA1
    
    // Macros
    #define nop() _asm nop _endasm
    
    void main(void)
    {
        init();
        configure_transmitter();  
        while (1)  
        {
            transmit_data();
            LED = 1;
            dly(63973);            //200 ms delay
            LED = 0;           
            dly(40000);            //3.27 s delay 
            nop();          
        }
    }
    
    
    void init(void)
    {
        // run internal oscillator at 8 MHz
        OSCCON = OSCCON | 0x70;
        while (OSCCONbits.IOFS == 0)
            ;
        PORTA = 0x00;
        ADCON1 = 0x0F;        // set up PORTA to be digital I/Os
        TRISA = 0x02;        // PORTA<7.2,0> outputs PORTA<1> input
        TRISCbits.TRISC3 = 0;    // SDO output
        TRISCbits.TRISC5 = 0;   // SCK output
        TRISCbits.TRISC2 = 0;    // CSN output
        TRISCbits.TRISC1 = 0;    // CE output
        TRISBbits.TRISB0 = 1;    // IRQ input
        OpenSPI(SPI_FOSC_16, MODE_00, SMPMID); //open SPI1
        OpenTimer0( TIMER_INT_OFF &
                    T0_16BIT &
                    T0_SOURCE_INT &
                    T0_PS_1_256 );
    }
    
    void configure_transmitter(void)
    {
        unsigned char i, j, data, cmd;
    
        SPI_CE = 0;
        SPI_CSN = 0;
    
        // PTX, CRC enabled, mask a couple of ints    
         spi_Send_Read(0x20);
          spi_Send_Read(0x38);
        SPI_CSN = 1; 
        SPI_CSN = 0;
        
        //auto retransmit off
         spi_Send_Read(0x24);    
           spi_Send_Read(0x00);    
        SPI_CSN = 1;
        SPI_CSN = 0;
        
        //address width = 5
           spi_Send_Read(0x23);
         spi_Send_Read(0x03);    
        SPI_CSN = 1;
        SPI_CSN = 0;
        
        //data rate = 1MB
           spi_Send_Read(0x26);
         spi_Send_Read(0x07);
        SPI_CSN = 1; 
        SPI_CSN = 0;
        
        //set channel 2, this is default but we did it anyway...
           spi_Send_Read(0x25);
         spi_Send_Read(0x02);
        SPI_CSN = 1;
        
        //set address E7E7E7E7E7, also default...
           spi_Send_Read(0x30);    
        for (j = 0; j < 5; j++)
        {
            spi_Send_Read(0xE7);
        }  
        SPI_CSN = 1;
        SPI_CSN = 0;
        
        //disable auto-ack, RX mode
        //shouldn't have to do this, but it won't TX if you don't
           spi_Send_Read(0x21);
         spi_Send_Read(0x00);
        SPI_CSN = 1;
    }
    
    void transmit_data(void)
    {
        unsigned char i, data, cmd;   
        
        SPI_CSN = 0;
        
        //clear previous ints
          spi_Send_Read(0x27);
         spi_Send_Read(0x7E);
        SPI_CSN = 1;
        SPI_CSN = 0;
        
        //PWR_UP = 1
           spi_Send_Read(0x20);
         spi_Send_Read(0x3A);
        SPI_CSN = 1;
        SPI_CSN = 0;
        
        //clear TX fifo
        //the data sheet says that this is supposed to come up 0 after POR, but that doesn't seem to be the case
           spi_Send_Read(0xE1);
        SPI_CSN = 1;
        SPI_CSN = 0;
        
        //4 byte payload
           spi_Send_Read(0xA0);
           spi_Send_Read(0x34);
          spi_Send_Read(0x33);
           spi_Send_Read(0x32);
          spi_Send_Read(0x31);
        SPI_CSN = 1;
        
        //Pulse CE to start transmission
        SPI_CE = 1;
        dly(65000);            //delay 69 ms
        SPI_CE = 0;
    }
    
    
    unsigned char spi_Send_Read(unsigned char byte)
    {
        SSPBUF = byte;    
        while(!DataRdySPI())
            ;    
        return SSPBUF;
    }    
    
    void dly(unsigned int c)
    {
        INTCONbits.TMR0IF = 0;
        WriteTimer0(c);
        while (INTCONbits.TMR0IF == 0)
            ;
    }
    
    



    /*
    ** Rx.c
    ** Receive test program for PIC18F4520 and nRF24L01 or nRF24L01+
    ** Uses the Microchip C18 compiler
    ** Based on SFE code for the CC5X code in 24L01demo_V01.c
    **
    ** The LED is flashed five times when data are received.
    ** The received data in the buffer may be checked using the 
    ** debugger Watch window.*/
    
    #include <p18cxxx.h>
    #include <spi.h>
    #include <timers.h>
    
    // Pragmas
    #pragma config OSC = INTIO67
    #pragma config PWRT = ON
    #pragma config MCLRE = OFF
    #pragma config BOREN = OFF
    
    //function prototypes
    void init(void);
    void reset_RX(void);
    void configure_RX(void);
    unsigned char spi_Send_Read(unsigned char);
    void dly(unsigned int);
    
    // Defines
    #define SPI_SCK        LATCbits.LATC3        // Clock pin, PORTC pin 3 
    #define SPI_SO        LATCbits.LATC5        // Serial output pin, PORTC pin 5 
    #define SPI_SI        PORTCbits.RC4        // Serial input pin, PORTC pin 4 
    #define SPI_CSN        LATCbits.LATC2        // CSN output pin, PORTC pin 2
    #define SPI_CE        LATCbits.LATC1        // CE output pin, PORTC pin 1
    #define SPI_IRQ        PORTBbits.RB0        // IRQ input pin, PORTB pin 0
    #define SPI_SCALE    4                      // postscaling of signal 
    #define LED            LATAbits.LATA0
    #define PB            PORTAbits.RA1
    
    // Macros
    #define nop() _asm nop _endasm
    
    void main(void)
    {
        unsigned char i;
    
        init();
        configure_RX();
        while(1)
        {
               if (SPI_IRQ == 0)    //wait for anything
            {
                for (i = 0; i < 5; i++)  //flash LED 5 times if data received
                {
                    LED = 1;
                    dly(63973);        // 200 ms delay
                    LED = 0;
                    dly(63973);        // 196 ms
                }
                dly(63973);            // 196 ms
                reset_RX();            
            }
        }
    }
    
    // initialise 18F4520
    void init(void)
    {
        // run internal oscillator at 8 MHz
        OSCCON = OSCCON | 0x70;
        while (OSCCONbits.IOFS == 0)
            ;
    
        PORTA = 0x00;
        ADCON1 = 0x0F;        // set up PORTA to be digital I/Os
        TRISA = 0x02;        // PORTA<7.2,0> outputs PORTA<1> input
        TRISCbits.TRISC3 = 0;    // SDO output
        TRISCbits.TRISC5 = 0;   // SCK output
        TRISCbits.TRISC2 = 0;    // CSN output
        TRISCbits.TRISC1 = 0;    // CE output
        TRISBbits.TRISB0 = 1;    // IRQ input
        OpenSPI(SPI_FOSC_16, MODE_00, SMPMID); //open SPI1
        OpenTimer0( TIMER_INT_OFF &
                    T0_16BIT &
                    T0_SOURCE_INT &
                    T0_PS_1_256 );
    }
    
    //configure nRF24L01 for receive
    void configure_RX(void)
    {
        unsigned char i, j;
    
        SPI_CSN = 0;
        SPI_CE = 0;
        
        //PRX, CRC enabled
        spi_Send_Read(0x20);
        spi_Send_Read(0x39); 
        SPI_CSN = 1;   
        SPI_CSN = 0;
        
        //disable auto-ack for all channels      
        spi_Send_Read(0x21);
        spi_Send_Read(0x00);     
        SPI_CSN = 1;    
        SPI_CSN = 0;
        
        //address width = 5 bytes  
          spi_Send_Read(0x23);
        spi_Send_Read(0x03);    
        SPI_CSN = 1;    
        SPI_CSN = 0;
        
        //data rate = 1MB   
          spi_Send_Read(0x26);
        spi_Send_Read(0x07);    
        SPI_CSN = 1;
          SPI_CSN = 0;
    
        //4 byte payload  
         spi_Send_Read(0x31);
        spi_Send_Read(0x04);    
        SPI_CSN = 1;    
        SPI_CSN = 0;
    
        //set channel 2 
           spi_Send_Read(0x25);
        spi_Send_Read(0x02);    
        SPI_CSN = 1;     
        SPI_CSN = 0;
    
        //set address E7E7E7E7E7
        spi_Send_Read(0x30);
        for (j = 0; j < 5; j++)
             spi_Send_Read(0xE7); 
        SPI_CSN = 1;  
        SPI_CSN = 0;
        
        //PWR_UP = 1   
         spi_Send_Read(0x20);
        spi_Send_Read(0x3B);   
        SPI_CSN = 1;    
        SPI_CE = 1;     
    }
    
    void reset_RX(void)
    {
        unsigned char i, j;
        unsigned char buffer;    
        
        //Read RX payload   
        SPI_CSN = 0;    
           spi_Send_Read(0x61);    
        for (j = 0; j < 4; j++)
        {        
               buffer[noparse][[/noparse]j] = spi_Send_Read(0);        
        }    
        SPI_CSN = 1;    
        
        //Flush RX FIFO    
        SPI_CSN = 0;    
         spi_Send_Read(0xE2);    
        SPI_CSN = 1;
        SPI_CSN = 0;
     
        //reset int    
          spi_Send_Read(0x27);
        spi_Send_Read(0x40);    
        SPI_CSN = 1;
    }
    
    
    
    
    unsigned char spi_Send_Read(unsigned char byte)
    {
        SSPBUF = byte;    
        while(!DataRdySPI())
            ;    
        return SSPBUF;
    }    
    
    
    void dly(unsigned int c)
    {
        INTCONbits.TMR0IF = 0;
        WriteTimer0(c);
        while (INTCONbits.TMR0IF == 0)
            ;
    
    
    }
    
    



    It uses the C18 peripheral libraries. It should be quite easy to convert it into Spin.

    Leon

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Amateur radio callsign: G1HSM
    Suzuki SV1000S motorcycle

    Post Edited (Leon) : 1/5/2009 10:54:15 AM GMT
Sign In or Register to comment.