Grove-LCD + Led and NodeJS

Hello,

I’m a newbie with GrovePi and I’ve understood how to extend AnalogicSensor to use sound sensor. But it becomes more complicated (for me) with Grove LCD and Leds. Please do you know where I can find some samples ?

Regards
Philippe

Hey Phillippe,
We have examples for the Grove LCD and OLED on our github repo here: https://github.com/DexterInd/GrovePi/tree/master/Software/Python/grove_i2c_oled_128_64, https://github.com/DexterInd/GrovePi/tree/master/Software/Python/grove_oled and https://github.com/DexterInd/GrovePi/tree/master/Software/Python/grove_rgb_lcd . Do have a look and let us know if you have any questions.

-Karan

Hi Karan
Yes I’ve already used it, but now, I would like to do the same thing with NodeJS

Philippe

Hey Philippe, I don’t want to send you on a wild goose chase here, but I think the best way to try to suggest this is to go to our github repo for GrovePi.

The developer who’s been working on it is really responsive, really nice and helpful guy. I’m sure he’d be happy to talk to you about it.

Best, John

I’ve made the NodeJS/javascript version of the Python library to write data to the LCD screen through i2c and to change the background color. It requires the i2c-bus and sleep libraries.

var i2c = require('./node_modules/i2c-bus/i2c-bus');
var sleep = require('./node_modules/sleep/');
var GrovePi = require('node-grovepi').GrovePi

var Board = GrovePi.board

var DISPLAY_RGB_ADDR = 0x62;
var DISPLAY_TEXT_ADDR = 0x3e;

function setRGB(i2c1, r, g, b) {
  i2c1.writeByteSync(DISPLAY_RGB_ADDR,0,0)
  i2c1.writeByteSync(DISPLAY_RGB_ADDR,1,0)
  i2c1.writeByteSync(DISPLAY_RGB_ADDR,0x08,0xaa)
  i2c1.writeByteSync(DISPLAY_RGB_ADDR,4,r)
  i2c1.writeByteSync(DISPLAY_RGB_ADDR,3,g)
  i2c1.writeByteSync(DISPLAY_RGB_ADDR,2,b)
}

function textCommand(i2c1, cmd) {
  i2c1.writeByteSync(DISPLAY_TEXT_ADDR, 0x80, cmd);
}

function setText(i2c1, text) {
  textCommand(i2c1, 0x01) // clear display
  sleep.usleep(50000);
  textCommand(i2c1, 0x08 | 0x04) // display on, no cursor
  textCommand(i2c1, 0x28) // 2 lines
  sleep.usleep(50000);
  var count = 0;
  var row = 0;
  for(var i = 0, len = text.length; i < len; i++) {
    if(text[i] === '\n' || count === 16) {
      count = 0;
      row ++;
        if(row === 2)
          break;
      textCommand(i2c1, 0xc0)
      if(text[i] === '\n')
        continue;
    }
    count++;
    i2c1.writeByteSync(DISPLAY_TEXT_ADDR, 0x40, text[i].charCodeAt(0));
  }
}

var board = new Board({
    debug: true,
    onError: function(err) {
      console.log('Something wrong just happened')
      console.log(err)
    },
    onInit: function(res) {
      if (res) {
        console.log('GrovePi Version :: ' + board.version())

        var i2c1 = i2c.openSync(1);
        setText(i2c1, 'Memet is een\nEINDBAAS');
        setRGB(i2c1, 55, 55, 255);
        i2c1.closeSync();
      }
    }
  })
board.init();

Nice! I will test it quickly :slight_smile:

Hi there, some questions from me, I’m using Node.js

  • I worked with loudness and sound sensors today on a Raspberry with GrovePi+. Both of these sensors gave me ‘irregular’ results, i.e. either pretty low or pretty high values, not necessarily impacted by myself talking loudly or blowing into the microphone. Values I get range from 100 to 400 whereas if I reboot the Raspberry and start the app again I get values around 60.
    Loudness sensor is v0.9b whereas sound sensor is v1.6.
    Here is the code I’m using. Basically, I’m collecting a number of samples per second and when read() is called I return the average. What do you think of this code? How could I test sound and loudness sensors to make sure they are working correctly?

  • Moreover, here there is this Arduino code

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

void loop()
{
    analogRead(0);
    delay(10);
    val = analogRead(0);
    Serial.println(val);
    delay(200);
}

As you can see, it does a read and then waits for 10 miliseconds before getting the correct value. Should I do something like this with board.wait(10) or another method?

  • I also use the DHT sensor with the node-grovepi library, the temperature I’m getting is always x.5, e.g. 24.5, 25.5, 26.5. Any hints on why?

  • I also built this for the Rotary Angle Sensor, could I do a Pull Request? If yes, should the PR be made against the official Dexter Industries library or to this fork?

Hi @dgkanatsios,


There’s something we need to clarify before diving too far.

There’s a difference between a microphone and a sound level sensor.

  • The microphone outputs a signal that’s well within the kilohertz range.
    If you’d connect the microphone to an amplifier and then to a pair of headphones/speaker, you’ll be able to hear whatever the microphone records.
    This means there’s lots of information packed into that signal and with our GrovePi, we can only catch a glimpse of that signal. So this means, the signal can have any value between 0 and 1023 at any point in time.

  • The sound level sensor is basically a microphone with an additional circuit that quantifies lots of discrete values over a longer period of time. That quantified sum represents the actual level of the sound. Generally, DSPs are used for audio filtering and analysis - more specifically, for this task.

In our case, the Grove Sound Sensor is a microphone, whereas the Grove Loudness Sensor is a kind of sound level sensor (with nowhere near the capabilities of a dedicated analyzer).


In order to test the GrovePi's functionality, I’d read the sensor’s value with the GrovePi and with an Arduino at the same time in order to compare the values. It’s going to be tricky to get the sensor’s signal to your Arduino, but it’s doable.


Regarding the DHT sensor, I think that’s the sensor’s resolution - it just happens to increment with half of 1s.


About the PR for the Rotary Angle Sensor, I think I need to bring @JohnC on this one.


If there’s anything else you feel the need to talk about, please don’t hesitate to leave us a message.

Thank you!

Hi @RobertLucian, thanks for the response, much clearer now.

  • Thanks for the detailed explanation, so I’ll use the Loudness sensor. Is the approach I’m using on my code (i.e. gathering samples every X miliseconds and them outputting the average) the correct one or should I just use sensor.read()?

  • Regarding the RotaryAngle, I found out that it may emit some noise, i.e. in 30 samples one of them could be a random number. Of course, I’m not touching the sensor at all while this happens. Is this expected? I’ve done some filtering on my code and it seems to work

  • Regarding the PR, yes, please let me know, as I’ve done some more work (e.g. here I’ve implemented code for button press and longpress), may be useful to others.

Thanks!

Hi @dgkanatsios,


I think it’s okay to take samples over a longer period of time and then average them.

I recommend you to make 2-5 averages every second.
This means each average has between 200 ms and 500 ms of data samples.
It’s nowhere near the best “filtering” algorithm, but I think it should do the job.

Just pay attention that averaging values is just a sort of a low-pass filter, which means higher frequency sounds won’t get through - for instance stuff like a horn or hand clapping.


Regarding the RotaryAngle, I think you need to use filtering algorithms in order to remove unwanted frequencies / noise.


Thank you!

Thank you, just implemented code to get both average and maximum value over a period of time.
Also implemented a small class to filter out noise from the Rotary Angle sensor, my code seems to be working great.
Waiting on your guidance for a potential Pull Request for all of this. Should I open an issue on your repository to discuss there?

Hi @dgkanatsios,


I’m glad you did all these.
That’s really great to hear.


For creating a pull request, please head over to our github repo

And create a pull request to master branch.

Here are some general guidelines for creating this request. Add the following:

  1. A descriptive title for PR.
    Use square brackets [] for putting emphasis on an idea or for highlighting modules/scripts.

  2. A thorough description of the PR.
    Use bullet points, numbered lists, images when describing the work you’ve done.

  3. A description on how to install and run the software you’ve made.

  4. Comments inside your code so we can easily understand what you wrote there.

  5. A README because documenting code is the cornerstone of programming.

Again, these are general guidelines, so you can be flexible with what you do.
The point is, we need to understand the hows, whats and the whys, because otherwise, the code is just a black box.

If the code isn’t yet implemented or polished, then I suggest you open an issue on our repo and whenever you commit something, just use the ref DexterInd/GrovePi#issuenumber - description of commit format, where issuenumber is the assigned number of the issue on our repo.


Thank you a lot for your support :slight_smile:
People like you are the ones that make open-source communities thrive.

Thank you!

Thanks @RobertLucian, already did the fork, will submit the PR within the following days.

And I think we just merged this baby! Thanks so much @dgkanatsios, great work!

Thanks for the merge guys!
One more question for you, I’d like to connect a fourth analog sensor to my GrovePi. I suppose I have to get this sensor, is it easy then to connect to it and read data with Node.js via this class?

FYI, did another PR with a fix for the button (stupid mistake) and a fix for the dust sensor

@dgkanatsios thanks for the PR! You and @marcello-barile are doing an awesome job keeping the nodejs humming! Thanks!