3 Replies Latest reply on Apr 15, 2015 6:25 AM by LeonY

    Driving WS2803 with Javascript on Galileo GEN2 (IOT)

    LeonY

      Im trying to see if its possible to write a function to drive the WS2803 LED Chips. They require the Arduino shiftOut() method to work. I have previously written one in Arduino code and have it working on both a GEN 1 and GEN 2. However i need to switch over to Node (for reasons) . I tried using the GPIO library rwaldron/galileo-io · GitHub but I'm just getting gibberish.

      Just as an example, i made a function to push out 144Bits all set to 1(that will drive 6 x RGB LEDs and set them all o FULL POWER) and then set them all to 0. When i run it, the WS2803 just gets garbage data.

      eg..

       

      var Galileo = require("../lib/galileo");
      var board = new Galileo();
      var bitCounter=0; 
      
      
      board.on("ready", function()
      {
      //Pin 2 is clock
      //Pin 3 is data
        //set the clock pin to low
        board.digitalWrite(2, 0);
      
        for(bitcounter=0; bitcounter<144; bitCounter++)
        {
        //send a 1 to data
        board.digitalWrite(3, 1);
        //set clock to high
        board.digitalWrite(2, 1);
        //set clock to low
        board.digitalWrite(2, 0);
        }    
         //need to wait 600us here but have no idea how to do that in js
      });
      
        • 1. Re: Driving WS2803 with Javascript on Galileo GEN2 (IOT)
          CMata_Intel

          Hi LeonY

           

          Have you tried to use MRAA there are some examples that may help you with this

          Checking your code it seems that what you are doing in the for-section is toggling the pin 2 144 times. Is this the behavior you need?

           

          Regards;

          CMata

          • 2. Re: Driving WS2803 with Javascript on Galileo GEN2 (IOT)
            LeonY

            I will try the MRAA functions and see if they are any better.

            Checking your code it seems that what you are doing in the for-section is toggling the pin 2 144 times. Is this the behavior you need?

            Yep thats correct. the function works like this:

             

            Repeat for 144 bits

                 Set Data pin 1

                 Latch Clock pin HIGH

                 Latch Clock pin LOW

             

            That is just an example to see if f i can get good data.

            • 3. Re: Driving WS2803 with Javascript on Galileo GEN2 (IOT)
              LeonY

              OK got it to work with the MRAA library and some tinkering!

              This code will drive a single WS2803 with 6 RGB LEDs attached:

               

              var m = require('mraa');
              console.log('MRAA Version: ' + m.getVersion());
              var clockPin = new m.Gpio(2);
              var dataPin = new m.Gpio(3);
              
              
              //led Vars
              var ledByteCount = 18; //6LED x 3Bytes(RGB)
              var ledMaxPower = 5; //Maximum dim level
              var ledBar = new Array(ledByteCount);
              
              
              init();
              run();
              
              
              function init()
              {
                  clockPin.dir(m.DIR_OUT);
                  dataPin.dir(m.DIR_OUT);
                  clockPin.write(0); 
                   //clear the LED data array and load nothing into the driver
                  for(var cnt=0; cnt<ledByteCount; cnt++)
                  {
                      ledBar[cnt]=0; 
                  }
                  loadWS2803();
                 
              }
              
              
              function run()
              {
                   
                  while(true)
                  {
                  var rcnt=0;
                    for(rcnt=0; rcnt<ledMaxPower; rcnt++)
                    {
                      ledBar[0]=rcnt;
                      ledBar[3]=rcnt;
                      ledBar[6]=rcnt;
                      ledBar[9]=rcnt;
                      ledBar[12]=rcnt;
                      ledBar[15]=rcnt;
                      loadWS2803();
                    }
                    for(rcnt=ledMaxPower; rcnt>-1; rcnt--)
                    {
                      ledBar[0]=rcnt;
                      ledBar[3]=rcnt;
                      ledBar[6]=rcnt;
                      ledBar[9]=rcnt;
                      ledBar[12]=rcnt;
                      ledBar[15]=rcnt;
                      loadWS2803();
                    }
                    for(rcnt=0; rcnt<ledMaxPower; rcnt++)
                    {
                      ledBar[1]=rcnt;
                      ledBar[4]=rcnt;
                      ledBar[7]=rcnt;
                      ledBar[10]=rcnt;
                      ledBar[13]=rcnt;
                      ledBar[16]=rcnt;
                      loadWS2803();
                    }
                    for(rcnt=ledMaxPower; rcnt>-1; rcnt--)
                    {
                      ledBar[1]=rcnt;
                      ledBar[4]=rcnt;
                      ledBar[7]=rcnt;
                      ledBar[10]=rcnt;
                      ledBar[13]=rcnt;
                      ledBar[16]=rcnt;
                      loadWS2803();
                    }
                    for(rcnt=0; rcnt<ledMaxPower; rcnt++)
                    {
                      ledBar[2]=rcnt;
                      ledBar[5]=rcnt;
                      ledBar[8]=rcnt;
                      ledBar[11]=rcnt;
                      ledBar[14]=rcnt;
                      ledBar[17]=rcnt;
                      loadWS2803();
                    }
                    for(rcnt=ledMaxPower; rcnt>-1; rcnt--)
                    {
                      ledBar[2]=rcnt;
                      ledBar[5]=rcnt;
                      ledBar[8]=rcnt;
                      ledBar[11]=rcnt;
                      ledBar[14]=rcnt;
                      ledBar[17]=rcnt;
                      loadWS2803();
                    }
                    //single step
                    for(var cnt=0; cnt<ledByteCount; cnt+=3)
                    {
                      //red
                      for(rcnt=0; rcnt<ledMaxPower; rcnt++)
                      {
                          ledBar[cnt]=rcnt;
                          loadWS2803();
                      } 
                      for(rcnt=ledMaxPower; rcnt>-1; rcnt--)
                      {
                          ledBar[cnt]=rcnt;
                          loadWS2803();
                      } 
                      //green
                      for(rcnt=0; rcnt<ledMaxPower; rcnt++)
                      {
                          ledBar[cnt+1]=rcnt;
                          loadWS2803();
                      } 
                      for(rcnt=ledMaxPower; rcnt>-1; rcnt--)
                      {
                          ledBar[cnt+1]=rcnt;
                          loadWS2803();
                      } 
                      //blue
                      for(rcnt=0; rcnt<ledMaxPower; rcnt++)
                      {
                          ledBar[cnt+2]=rcnt;
                          loadWS2803();
                      } 
                      for(rcnt=ledMaxPower; rcnt>-1; rcnt--)
                      {
                          ledBar[cnt+2]=rcnt;
                          loadWS2803();
                      }     
                    }
              
              
                  }
              
              
              }
              
              
              
              
              function delay(milliseconds)
              {
                  var start = new Date().getTime();
                  for (var i = 0; i < 1e7; i++) {
                      if ((new Date().getTime() - start) > milliseconds) {
                          break;
                      }
                  }
              }
              
              
              function loadWS2803()
              {
                  for(var wsOut=0; wsOut<ledByteCount; wsOut++)
                  {
                    shiftOut(ledBar[wsOut], true);
                  }
                  delay(2);
              }
              
              
              function shiftOut(dataToPush, mostSigFirst)
              {
                var mask=1, bitResult=0, cnt=0;
              
                if(mostSigFirst)
                {
                  //Set the mask to '10000000'
                  mask = mask << 7;
                  for(cnt=0; cnt<8; cnt++)
                  {
                    //AND the mask and the data value
                    bitResult = dataToPush & mask;
                    //Shift the result by the CNT to get 1 or 0
                    bitResult = bitResult >> (7-cnt);
                    //output result to data pin
                    dataPin.write(bitResult);
                    //set clock high
                    clockPin.write(1);
                    //set clock low
                    clockPin.write(0);
                    //Shift the bit of the mask RIGHT
                    mask = mask >> 1;
                  }
                }
                else
                {
                  for(cnt=7; cnt>=0; cnt--)
                  {
                    //The mask is preset to '00000001'
                    //AND the mask and the data value
                    bitResult = dataToPush & mask;
                    //Shift the result by the CNT to get 1 or 0
                    bitResult = bitResult >> (7-cnt);
                    //output result to data pin
                    dataPin.write(bitResult);
                    //set clock high
                    clockPin.write(1);
                    //set clock low
                    clockPin.write(0);
                    //Shift the bit of the mask left
                    mask = mask << 1;
                  }
                }
              }