Saturday, 21 August 2021

DMX to control NeoPixels and an Isolated DMX Shield

I've been playing about with RS485 and DMX for some time now.  I am particularly interested in being able to control NeoPixels via DMX.  The amount of software and experience available for using DMX to control lights and LEDS in particular is vast.  YouTube is full of lighting shows and displays which range from humble but functional to truly epic and vast.  Here are a couple of videos which I thought were amazing:

Submergence - Squidsoup
  

Tom Betgeorge's Excellent 2020 Christmas Light Show

I must admit I watched all 35 minutes of that Christmas Show...It is incredible work.  Any way this is achieved is by controlling lots of LEDS in pre-programmed sequences using DMX control software and LED lights.  DMX is a lighting protocol based upon RS485.  Here is a brief primer on DMX:


Here is another which goes into more technical detail:


So basically lighting technicians control the lights in theatres, discos and concerts using the DMX protocol to control the brightness, colour and state (off/on) of a light or lighting fixture (many lights in one package).

DMX uses RS485 which is a differential serial protocol that electronic equipment has been using for communication since the standard was approved in 1998 and probably earlier than that.


I'm not going to go into too much detail on R485 or DMX for now other than to say it's very useful stuff for electronics and lighting fans to know about.

I have a confession to make: I'd like to be able to control lights...not just one or two but many.  If I had my way every light in my house would be sequenced and remote controlled.  Unfortunately not everyone I live with approves of this plan and as such most of my lights are still just regular lights....(boring!!!).

I have been asked in the past to assist with light shows and recently I have been asked to assist with the technical development of a light show using NeoPixels.

To that end I started to look at the DMX shields available for the Arduino and have a play.  I noticed that most of them have a flaw - they aren't isolated...that means that the electrical supply used to power  the lights is also connected via the return (or ground) to the controller.  In most cases this isn't an issue but it can be in very large lighting displays with lots of wiring and fixtures because of something referred to as a 'ground loop'.


Here are some of the DMX shields designed for use with the Arduino R3:



There is nothing functionally wrong with them and I bought two of the Concineptics variants to play with.  They arrived in good order and worked as described once I understood the code and the jumper settings.  

In order to actually use DMX properly with the software one needs a controller.  Something I was  aware of but not completely in understanding of at all.  I'd always used a hardware controller in the past.

So to really make use of DMX you will either need to make your own controller or buy one off Ebay or Amazon or wherever you might wish to.  I wanted to use an external computer and software to control my lights as I don't own or have access to a hardware DMX controller.

I bought a USB to RS485 dongle off Amazon which works perfectly...It didn't at first but that's because I cannot wire things up for love nor money sometimes.  I then bought a USB to DMX dongle and that worked straight out of the box without any issues whatsoever!  Don't tell anyone but I'm very disappointed in my engineering abilities sometimes...Not being able to wire up simple circuits competently is worrisome for somebody who works in electronic engineering!

Here are the two devices I bought which I heartily recommend:



Once you have a method of controlling DMX lights it's time to either buy some or make some...user's choice.  I was trying to make some so I got hold of some NeoPixel Tape and then connected everything up.

Before doing anything I tend to do some research...Planning is everything so they say....I watched several videos on YouTube and read some blogs on DMX and in particular this one stood out:

Gadget Reboot has an excellent channel and I recommend subscribing!

In it the narrator discusses exactly what I'm trying to achieve and provides all of the equipment required and some code.  The only issue I had was that it didn't work for me!  I didn't have the exact same setup and tried to rush things...never a good situation.  Their setup uses an Arduino mega and some potentiometers, an RS485 breakout module, Buttons and some wire for the connections - for the hardware controller.  For the receiver they use an Arduino uno and an RS485 breakout and some WS2812B LEDS.  I suspect armed with what I know now I could probably get this setup working... 

Here is my setup that worked for me:
 
A DMX to NeoPixel Receiver Setup!

The equipment needed:
1x Arduino R3 or suitable clone:  

1x RS485 breakout PCB:  
Suitable connection wire for making the connections between the arduino and the breakouts etc as well as some 4 core 120 Ohm signal cable for the RS485 communications.  For testing any wire would do but once something longer distance or more permanent is required get proper cable.  Belden 9842 is a pretty good option.  At a pinch some old ethernet cable would work...cut the R45 connectors off and use four of the cores...

The actual setup!


You will need to flash the following arduino code onto your Arduino R3:

// Target Hardware:  Arduino Uno

#include <DMXSerial.h>
#include "ws2812.h"                // a specific LED controller that disables interrupts to work better

#define NUM_LEDS 30                // number of RGB LEDs on strip - 3 LEDS in one W2182B9
#define DMXSTART 1                 // first DMX channel
#define DMXLENGTH (NUM_LEDS*3)     // number of DMX channels used (3*30 LEDs)

void setup () {

  DMXSerial.init(DMXProbe);        // initialize DMX bus in manual access mode
  DMXSerial.maxChannel(DMXLENGTH); // "onUpdate" will be called when all new ch data has arrived

  setupNeopixel();                 // setup the LED output hardcoded to pin 12 in ws2812.h

}


void loop() {
  // wait for an incomming DMX packet and write
  // the RGB data for 60 LEDs on the strip
  if (DMXSerial.receive()) {
    updateNeopixel(DMXSerial.getBuffer() + DMXSTART, NUM_LEDS);
  }

}

You will need to download a copy of the DMXSerial Library. It is available here:


Here is the source for ws2812.h - Cut and paste it into a text file called ws2812.h and store it in the same directory as your arduino sketch.

// neopixel.h


/*
  The Neopixel driving routines are taken from the article and sketch from bigjosh
  http://wp.josh.com/2014/05/13/ws2812-neopixels-are-not-so-finicky-once-you-get-to-know-them/
  where the interrupt cli() and sei() are included in the sendBit function.
  At the sources from his github this is not the case but it's important for the usage with DMXSerial library.
  (see https://github.com/bigjosh/SimpleNeoPixelDemo )
  These routines fit very good to the DMXSerial implementation because they switch on and off the
  Interrupt
  On DMX usual channels are used in the red then green then blue order.
  Neopixel wants colors in green then red then blue order so the 2 channels are switched.
*/

// ----- global defines from josh: -----

// These values are for the pin that connects to the Data Input pin on the LED strip. They correspond to...

#define PIXEL_PORT  PORTB  // Port of the pin the pixels are connected to
#define PIXEL_DDR   DDRB   // Port of the pin the pixels are connected to
#define PIXEL_BIT   4      // Bit of the pin the pixels are connected to

// This re3sults in the following Arduino Pins:
// Arduino Yun:     Digital Pin 8
// DueMilinove/UNO: Digital Pin 12
// Arduino Mega     PWM Pin 4

// You'll need to look up the port/bit combination for other boards.
// Note that you could also include the DigitalWriteFast header file to not need to to this lookup.

// These are the timing constraints taken mostly from the WS2812 datasheets
// These are chosen to be conservative and avoid problems rather than for maximum throughput

#define T1H  900    // Width of a 1 bit in ns
#define T1L  600    // Width of a 1 bit in ns

#define T0H  400    // Width of a 0 bit in ns
#define T0L  900    // Width of a 0 bit in ns

#define RES 6000    // Width of the low gap between bits to cause a frame to latch

// Here are some convience defines for using nanoseconds specs to generate actual CPU delays

#define NS_PER_SEC (1000000000L)          // Note that this has to be SIGNED since we want to be able to check for negative values of derivatives

#define CYCLES_PER_SEC (F_CPU)

#define NS_PER_CYCLE ( NS_PER_SEC / CYCLES_PER_SEC )

#define NS_TO_CYCLES(n) ( (n) / NS_PER_CYCLE )

#define DELAY_CYCLES(n) ( ((n)>0) ? __builtin_avr_delay_cycles( n ) :  __builtin_avr_delay_cycles( 0 ) )  // Make sure we never have a delay less than zero

// Low level function with mixed in assembler code.

// Actually send a bit to the string. We turn off optimizations to make sure the compile does
// not reorder things and make it so the delay happens in the wrong place.
inline void sendBit( bool bitVal )
{
  if (bitVal) {        // 0 bit
    asm volatile (
      "sbi %[port], %[bit] \n\t"        // Set the output bit
      ".rept %[onCycles] \n\t"                                // Execute NOPs to delay exactly the specified number of cycles
      "nop \n\t"
      ".endr \n\t"
      "cbi %[port], %[bit] \n\t"                              // Clear the output bit
      ".rept %[offCycles] \n\t"                               // Execute NOPs to delay exactly the specified number of cycles
      "nop \n\t"
      ".endr \n\t"
      ::
      [port]    "I" (_SFR_IO_ADDR(PIXEL_PORT)),
      [bit]   "I" (PIXEL_BIT),
      [onCycles]  "I" (NS_TO_CYCLES(T1H) - 2),    // 1-bit width less overhead  for the actual bit setting, note that this delay could be longer and everything would still work
      [offCycles]   "I" (NS_TO_CYCLES(T1L) - 2)     // Minimum interbit delay. Note that we probably don't need this at all since the loop overhead will be enough, but here for correctness
    );
  
  } else {          // 1 bit
    // **************************************************************************
    // This line is really the only tight goldilocks timing in the whole program!
    // **************************************************************************
    asm volatile (
      "sbi %[port], %[bit] \n\t"        // Set the output bit
      ".rept %[onCycles] \n\t"        // Now timing actually matters. The 0-bit must be long enough to be detected but not too long or it will be a 1-bit
      "nop \n\t"                                              // Execute NOPs to delay exactly the specified number of cycles
      ".endr \n\t"
      "cbi %[port], %[bit] \n\t"                              // Clear the output bit
      ".rept %[offCycles] \n\t"                               // Execute NOPs to delay exactly the specified number of cycles
      "nop \n\t"
      ".endr \n\t"
      ::
      [port]    "I" (_SFR_IO_ADDR(PIXEL_PORT)),
      [bit]   "I" (PIXEL_BIT),
      [onCycles]  "I" (NS_TO_CYCLES(T0H) - 2),
      [offCycles] "I" (NS_TO_CYCLES(T0L) - 2)
    );
  } // if
  
  // Note that the inter-bit gap can be as long as you want as long as it doesn't exceed the 5us reset timeout (which is A long time)
  // Here I have been generous and not tried to squeeze the gap tight but instead erred on the side of lots of extra time.
  // This has thenice side effect of avoid glitches on very long strings becuase
} // sendBit()

// Neopixel wants bit in highest-to-lowest order
// so send highest bit (bit #7 in an 8-bit byte since they start at 0)
inline void sendByte(uint8_t byte)
{
  for (uint8_t bit = 0; bit < 8; bit++) {
    sendBit(byte & 0x80);
    byte <<=
        1; // and then shift left so bit 6 moves into 7, 5 moves into 6, etc
  } // for
} // sendByte()

/*
  The following three functions are the public API:
  ledSetup() - set up the pin that is connected to the string. Call once at the begining of the program.
  sendPixel( r g , b ) - send a single pixel to the string. Call this once for each pixel in a frame.
  show() - show the recently sent pixel on the LEDs . Call once per frame.
*/

// Set the specified pin up as digital out

void sendPixel(uint8_t r, uint8_t g, uint8_t b)  {
  sendByte(g);          // Neopixel wants colors in green then red then blue order
  sendByte(r);
  sendByte(b);
} // sendPixel


// ----- defines and routines from josh - End -----

void setupNeopixel() {
  bitSet( PIXEL_DDR , PIXEL_BIT );
} // setupNeopixel()


// read data from the DMX buffer (RGB) and send it to the neopixels...
void updateNeopixel(uint8_t *ptr, uint8_t pixels) {
  uint8_t  r, g, b;

  // no interrupt is welcome.
  cli();

  for (int p = 0; p < pixels; p++ ) {
    r = *ptr++;
    g = *ptr++;
    b = *ptr++;
    // send to Neopixels
    // sendPixel(r, g , b);
    sendPixel(r >> 2, g >> 2, b >> 2);
  } // for

  // interrupt may come.
  sei();

  // Just wait long enough without sending any bots to cause the pixels to latch and display the last sent frame
  _delay_us((RES / 1000UL) + 1);
} // updateNeopixel()

// End

Once you have everything setup you will need to download some DMX software.  There is a great deal to choose from.  Some of it is very complicated and expensive and some are open source, still complicated but free for fair use.

I chose to use Q Light Controller Plus.  I have heard good things about Xlight and JinX.  

You can down load Q Light Controller Plus from here:


Once installed on the operating system of your choice, load up the software:

You will be presented with the following screen:


Click on the Inputs/Outputs button in the bottom middle of the screen.


Ensure that DMX USB is selected and that it relates to the USB Dongle.  It was already selected for me.

Next it is time to add a fixture.  Click on the fixtures icon in the bottom left corner.  You will be presented with the following screen:


Click on the green '+' Icon in the top left corner to add a DMX controlled lighting fixture.


I called mine 'LED_strip' but yours can be anything you wish.  I chose 90 channels as that is what was set in the code and I have 30 NeoPixels on my strip.  Each colour = one channel.  I noticed that Q Light Plus can only control 99 channels in one universe...Start from address 1 as there is only one fixture and therefore quantity = 1 and address gap = 0.

Anyway...Click OK and then Click on the Simple Desk button in the bottom middle of the screen.  The following window will be presented:


Now we are getting somewhere!  If you look at the display it looks quite like an audio mixing desk and in a way it is...just for lights...If you increase the slider on channel 1 you should see your first LED light up and it will be RED.  If you were to increase channel 2 It would light up up the GREEN LED in the first NeoPixel.  Channel 3 = BLUE LED etc.  The big red slider at the left hand side of the screen controls the master brightness.

Here is what I did to quickly test things:


It gives the following responses on the LED strip:


 That is about as much as I currently know on how to control Q Light Plus!  There are a million tutorials available however and a very active forum.  Go check them out!

I also had a quick play with JinX which can be downloaded from here:


I'm not going to go into how it works as the manual is OK but here is a quick video showing it in action:


That's all for now.  The next post will be about how I designed an isolated DMX shield and go into how the code works and probably a bit more on how to use DMX software.  I need to research more into the software and setting up scenes etc.

Take care everyone - Langster!

Sunday, 13 December 2020

How to design a simple LED Circuit

I am out of practice at many things it would seem at the moment...

I recently had to verify a colleague's design and honestly failed miserably.  Things that I consider basic in terms of electronics I didn't see and couldn't quickly do.  
To that end let us start from a simple area and attempt to cover as many aspects as possible...at least that way I will hopefully improve in my skills and prevent others from making similar mistakes.

I'm going to show a simple circuit that I was presented with...I'll be honest I struggle to visualise circuit operation from a schematic...it's probably why I struggle with the task of assessing designs. 

Simple LED Circuit

Lets try to analyze the circuit and explain how it works.  The circuit's function is to indicate which position the switch SW1 is in to the operator.  We have two different light emitting diodes (LEDS) connected via (SW1) a double pole single throw switch to a 5 Vdc supply with two 4k7 Ohm resistors and a 10 k Ohm Resistor.

When the switch (SW1) is in the position shown above LED D2 is supposed to be illuminated and a signal (at 5 Vdc) is also passed back to a microcontroller GPIO configured as an input (not shown here) via the node labelled SW1.  When the switch is in the alternative position the LED D1 is supposed to be illuminated and at the same time a signal or rather lack of signal (0 Vdc) is passed back to the microcontroller GPIO configured as an input. 

This method of connecting LEDS is known as reverse parallel - I'd actually not heard the term before...I had seen it before but not had it described that way...

So why is this circuit not particularly well designed?  There are a couple of reasons...which I'll be honest I did not pick up on during my assessment.  I made assumptions that the designer had performed calculations and checks to ensure the values selected were correct. 

The first reason is with respect to current.  In order to cause an LED to go into illumination normally at least 16 mA of current is required. How much current is flowing in the circuit with respect to D2?

Well the forward volt drop of the LED D2 is not stated so we don't actually know...lets fix that by supplying the datasheet:

C503B-BCS-CV0Z0461 Blue Light emitting diode datasheet

D2 is a 5 mm through hole LED with a wavelength of 470 nm.  It has a typical forward voltage (VF) of 3.2 Vdc when the forward current is at 20 mA.

We can now perform a simple calculation:

(Supply voltage - Diode forward voltage) / Resistor (R2) = Current flowing in LED D2 part of the circuit

(5 Volts - 3.2 Volts) / 4700 Ohms = 0.00038297872 A or 383 µA (micro-Amperes)

In order to get an LED to illuminate at normal brightness there should be milli-Amperes - I normally aim for 16 mA.  So in the circuit shown above with the switch in this position the LED D2 will not be illuminating brightly...I suspect it won't even be visible to the human eye.

The same issue is present with LED D1, here is the datasheet:

L-53SYD Yellow Light Emitting Diode Datasheet

D1 is a 5 mm through hole LED with a wavelength of  590 nm.  It has a typical forward voltage (VF)  of 2 Vdc when the forward current is at 20 mA.

(Supply voltage - Diode forward voltage) / Resistor (R1) = Current flowing in LED D1 part of the circuit

(5 Volts - 2 Volts) / 4700 Ohms = 0.00063829787 A or 638 µA (micro-Amperes) 

If again the aim was to illuminate the LED D1 (16 mA) then when the switch (SW1) is in the alternative positon the LED D1 will not be illuminated brightly at all...

So how do we resolve this issue?  We could try changing the resistor values (R1 and R2) for a lower value...

The standard formula for calculating the current limiting resistor for an LED is:

Current Limiting Resistor (Rlimit) (Ohms) = [Supply Voltage (VS) -  Diode Forward Voltage (VF)] /                                                                                                Diode Forward Current (IF)
Supply Voltage (VS) = 5 Vdc
Diode Forward Voltage (VF) = 3.2 Vdc (Blue LED)
Diode Forward Current (IF) = 16 * 10^-3 Amps or 16 mA

Therefore:

Current Limiting Resistor (Rlimit) (Ohms) in this case R2 = (5 Volts - 3.2 Volts) / 16 *10^-3 Amps

Current Limiting Resistor (Rlimit) (Ohms) = 112.5 Ohms for the Blue LED current limiting resistor.

For the current limiting resistor for D1 we have:

Current Limiting Resistor (Rlimit) (Ohms) in this case R1 = (5 Volts - 2 Volts) / 16 *10^-3 Amps

Current Limiting Resistor (Rlimit) (Ohms) = 187.5 Ohms for the Yellow LED current limiting resistor.

As 112.5 Ohms and 187.5 Ohms are not standard values for resistors one would probably use a 100 Ohm resistor and a 180 Ohm resistor.

The other calculation that should be made when designing circuits with resistors present is to ensure that the resistor power rating is suitable for the amount of power that will be present in the circuit.  Resistor life-time is reduced and unnecessary heat is generated when too much power is conducted through resistors.

The formula for calculating the power in a component is an application of Ohms Law:

Power (Watts) = Voltage (V) * Current (I) or

Power (Watts) = (Current * Current) * Resistance or

Power (Watts) = (Voltage * Voltage) / Resistance

We can apply any version of Ohms law to calculate the information required.  I have decided to use

Power (Watts) = (Current * Current) * Resistance

Power (Watts) in R1 =  (16*10^-3 * 16*10^-3) * 180 Ohms

Power (Watts) in R1 = 0.04608 Watts or 46.08 mW

Power (Watts) in R2 =  (16*10^-3 * 16*10^-3) * 100 Ohms

Power (Watts) in R2 = 0.0256 Watts or 25.6 mW

So to ensure that the power rating for the resistors is correct we should use 100 mW or quarter watt (250 mW) rated resistors.

There are still issues with the circuit as shown above however; The circuit is kind of wasteful...When the switch is in the position shown above there will always be current flowing in resistor R1 even though LED D1 is not illuminated.  With the switch in the opposite position the resistor R2 will still have current flowing through it even though LED D2 will not be illuminated.  Why have current flowing in a resistor for no purpose...It would be better to redraw the circuit in a different way but still achieve the same circuit function.

It would also (in my opinion) be better to redraw the circuit and do away with the reverse parallel LED connections...mostly because I find it hard to visualise the circuit...

Here is the circuit which was redesigned by my colleague having had some feedback (not from me):

Improved Circuit Design

The circuit's function is still to indicate which position the switch SW1 is in to the operator.  We have a 5 Vdc supply connected to a blue LED (D2) which in turn is connected to a 120 Ohm resistor (R1) and via (SW1) a double pole single throw switch, to ground completing the circuit.  With the switch SW1 in the alternative position we have the 5 Vdc supply connected to a yellow LED (D1) which is in turn connected to resistor (R2) and via switch SW1, to ground completing the circuit.

A signal is also passed back to a microcontroller GPIO configured as an input (not shown here) via the node labelled Controller SW1.  When the switch is in the first position the LED D2 is illuminated and at the same time a signal  (5 Vdc) through resistors R3 (10 k Ohms) and R58 (1 k Ohms) is passed back to the microcontroller GPIO input. 

When the switch (SW1) is in the second position LED D1 is illuminated and the signal passed back to the microcontroller is 0 Vdc as the  R3 (10 k Ohms) and R58 (1 k Ohms) are now connected to ground as well as the microcontroller GPIO input as the input impedance of a GPIO on a microcontroller is normally 100 k Ohms.  It is a standard method of reading the state of a switch position with a microcontroller.

The current limit on each of the LEDS can be calculated for completeness:

Current limit in LED D1 (Yellow LED) = (Supply voltage - Diode forward voltage) / Resistor (R2)

(5 Volts - 2 Volts) / 560 Ohms = 0.00535714286 A or 5.357 mA (milli-Amperes)

Current limit in LED D2 (Blue LED) = (Supply voltage - Diode forward voltage) / Resistor (R1)

(5 Volts - 3.2 Volts) / 120 Ohms = 0.015 A or 15 mA (milli-Amperes)

It seems a little odd to me that the value of R2 was chosen to be 560 Ohms...that seems a little high and will cause the yellow LED to be less visible when in operation...

The power rating for the resistors can also be recalculated:

Power (Watts) in R2 =  (5.357*10^-3 * 5.357*10^-3) * 560 Ohms

Power (Watts) in R2 = 0.01607057144 Watts or 16 mW (milli-Watts)

Power (Watts) in R1 =  (15*10^-3 * 15*10^-3) * 120 Ohms

Power (Watts) in R1 = 0.027 Watts or 27 mW (milli-Watts)

Therefore a 100 mW rated or 250 mW rated resistor would be ok to use in either position...

As the circuit has been redesigned there are no conditions where unnecessary current is flowing in any of the resistors and we still have the circuit function needed...When the circuit is constructed it should work perfectly.

When designing LED circuits from now on I will always try and do the following:

1. Obtain the datasheets for any and all components to be used.  For LEDS pay particular attention the electrical characteristics: Forward Voltage (VF), Forward Current (IF), maximum voltage (VMAX) and maximum power.

2. Calculate current limiting resistor needed for the appropriate brightness by reading the datasheet and obtaining a figure for the current at the appropriate brightness...it may be shown in a graph.  Use the formula:

Current Limiting Resistor (Rlimit) (Ohms) = [Supply Voltage (VS) -  Diode Forward Voltage (VF)] /                                                                                                Diode Forward Current (IF)

3. Calculate the power flowing through the current limiting resistor and select a suitably rated component.

4. Choose a suitable resistor tolerance...in this case a 5% resistor will probably be fine.

4. Get a friend or colleague to check your circuits <slight smile>.

5. It often helps to simulate circuits but only when the correct information is provided.  It is possibly better to perform the calculations on paper as it will enforce research into the requirements.

6.  Make sure the circuit meets the requirements...If the requirements aren't known then set them before attempting to perform the design...

In writing and researching this blog post I looked at the following website for inspiration:

https://www.ngineering.com/led_circuits.htm

Apologies for the long post - hope this was helpful - Langster! 

Tuesday, 28 July 2020

Product Review - Seeed Studio's new STEAM Grove Beginner Kit For Arduino

I was recently contacted by Seeed Studio to see if I would be happy to review their new Grove Beginner Kit for the Arduino.  I have been a customer of Seeed Studio in the past and I'm always happy to review kit.   

Seeed is the IoT hardware enabler providing services over 10 years that empower makers to realize their projects and products. Seeed offers a wide array of hardware platforms and sensor modules ready to be integrated with existing IoT platforms and one-stop PCB fabrication and PCB assembly service. Seeed Studio provides a wide selection of electronic parts including Arduino  Raspberry Pi and many different development board platforms  Especially the Grove System, which help engineers and makers to avoid jumper wire problems and connectivity issues. Seeed Studio has developed more than 280 Grove modules covering a wide range of applications that can fulfil a variety of needs. 

DISCLAIMER: I have not been paid to write this review, however I was sent the product free of charge.  My comments and opinions are my own, based upon my experience.  I am not affiliated or paid by Seeed Studio or anyone else to review products.

The Grove Beginner Kit For Arduino was sent to me via DHL in three days!  I was contacted to see if I would be happy to perform the review on Wednesday and placed my order Thursday and had the product in my hands the following Monday.  If nothing else, Seeed Studio's shipping department are excellent as are DHL!

First impressions of the packaging are excellent and as to be expected from Seeed.  I particularly liked to the code reference on the inside of the lid and the QR code to the tutorials page on the back.

The Top view of the Packaging

The inside of the box and the PCB itself.

The back of the box.

The Grove beginner kit and the external modules.

Lets power up the board and see what it does 😀

The board is powered from a microUSB connector on the arduino compatible PCB in the centre of the board.

As soon as the board is powered up the test sketch that is already present in the microcontroller drives the small OLED display connected via I2C in the middle left section of the board and reads the signal from the light sensor in the top right section of the board, connected to the A6 analogue input.  It gives confidence that the components are all working immediately.  In ambient light the display showed a value of 326 and when the sensor was covered the reading was 15.  Excellent visual feedback.

In a very unusual step for me I then went to find the instructions!  As an engineer I normally just like to connect everything up and start messing with things until I get stuck but in this case I went straight to Seeed's product page:


From reading the page quickly it has links to all of the information concerning the Grove beginner kit so I won't reproduce the information here.  If you need to know how one of the modules is connected or require the schematic diagram and technical information it's all on this page.

The page recommended new users to look at the Geppetto online editing environment which I'll be honest I had not heard about.  Here is the web address:


It looks like a way of configuring different Grove Sensor modules and helpfully there is a pre-made template for the Grove Beginner Kit.

I also found the wiki for the Grove Beginner Kit:


Having read through the Wiki it gives more information about the unboxing demo.  By pressing the button in the bottom left corner it is possible to see the LED in the top left corner light up.  By pressing and holding the button you can see the LED flash at different rates.

By pressing and holding the button for a long period of time the OLED display changes state and displays the current demonstration program.  By manipulating the potentiometer you can scroll through the various tests and see each device tested which is very useful.

The sound test didn't seem to do much although it did give an audible bleep from a long button press.  Having played with it a little further, the demonstration is taking input from the electret microphone and providing a volume level output on the OLED Display.  By tapping the microphone you can see the sound level change considerably.

The temperature and humidity test worked well and gave the current temperature and humidity on the OLED display.  Heating up the blue sensor did make the temperature change.

The pressure sensor test did give a readout although I think I need to calibrate mine as it gave a reading of 100830.00 Pa which would make my house somewhere on the side of a mountain which isn't true!

The accelerometer sensor test program worked and the animation on the OLED display was very cool.  Again I think calibration is in order but just getting a response straight away is very useful.

Demonstration programs are all very well and useful for proving function but what I always look for in a development board is how I can use it.  In particular I want to be able to learn how to use the sensors breakouts to my own requirements.

The wiki shows that the board can be used easily with the arduino IDE.  That's good as I have the IDE already installed and ready to go.  

I loaded up the Arduino IDE and selected the Arduino Uno as my board and selected the COM port which was already detected - I didn't need to install any drivers as Windows had already installed everything for me.  

Looking at the Wiki page I found the pre-written code for flashing the LED once a second.  I cut and paste the code straight into the IDE and pressed upload.  Within seconds the LED was flasing every second, as expected.


There are several other examples already written and ready to go.

Basically if I were looking to teach basic electronics and how to interface sensor breakout boards with an arduino uno compatible micro-controller I would purchase several of these boards.  The examples provided work perfectly and unlike separate modules and development boards nothing can be easily lost or removed.  One of the biggest complaints from teachers and students with teaching electronics is that parts go missing and get lost or broken or tidying up after the class takes as long as teaching the class.  With this system both of those problems are solved. The price of the board at $19.90 or £15.38 is incredibly reasonable.  I don't really have any negative comments to make about this product and that is incredibly unusual for me!

This is a bit of a change from my usual posts but hopefully someone will find this useful - take care everyone - Langster!


Sunday, 7 June 2020

More work with the Venturi Tube (Mark 4)

In order to test the latest venturi tube properly I have had to recalculate the areas of the different tube sections.  I performed several calculations to find out the areas of the first and second sections of the tube.

2D Cross Section of the Venturi Tube Design (Mark 4)

The blue shaded area is a cylinder.  The formula for calculating the cross sectional area of a cylinder is:

 

The area of the blue shaded section is therefore:



Which in metres is 0.0138590478.

The area of the red shaded section is a conical frustrum.  The formula for calculating the area of a conical frustrum is (really complicated!) :

 

I used an online calculator:


 

Which in metres is 0.00189862567

The red and blue shaded areas combined make up A1:

 


The grey shaded section is a cylinder. Its cross sectional area (A2) is therefore:



 

We can now apply the formula for the venturi tube:


We will of course just insert these values into the previously written arduino code.

One of the requirements for this project is to display real time graphs on a small graphical display.  The display I intend to develop with has not arrived yet. In preparation I thought it would be a good idea to look at using Python and matplotlib.

I have been playing with Python and installed Python 3.8.2 and got it added to my path (Windows 10).  I then installed the matplotlib (library for plotting graphs) and watched a few youtube videos and read some tutorials.

I need to create these graphs:


I have the data being delivered from the sensor so this should not be too difficult to achieve.  Helpfully the graphs have scales and axes...

Many people have been requesting access to the 3D print design files:


Well that is enough for now - Take care...Langster!

Saturday, 6 June 2020

Testing the new venturi tube (Mark 4)

After printing the new venturi tube with internal conical sections I have removed the support material and attempted to use it.  There are some design issues which need attention.  I made the pressure port pieces too small and have had to improvise with a couple of plastic M4 nuts glued on.  To be honest that seems to work quite well so I might do that again as its easier that printing connection pieces.

I have guessed at the new internal dimensions within the firmware code as I am unsure of how the formula applies to the conical sections and I cannot find any information as to how to proceed.  Rather than go through all the calculations again I have updated the firmware from my earlier post and performed a quick test.

For documentation purposes I have set the code with the internal dimensions:

A1 = 0.01455 m^3
A2 = 0.001145 m^3

Here are the results:

Raw Data from the ADC - Gain setting 1, positive = inhalation, negative = exhalation

Differential Pressure - much improved sensitivity

The results seem to be much better than the last attempt.  The graphs clearly show inhalation and exhalation and the sensitivity is much improved.  I suspect that with a calibrated pump the accuracy could be improved further. 

As I don't have a calibrated air pump my intention is to improvise with a balloon and a syringe body...

I have a 25 ml syringe body.  I wish I had a bigger volume one but they are very expensive for some reason.  I will fill a balloon with air from the syringe until I have a litre of air.  I will then release the balloon air through the tube and monitor the results on the volumetric flow graph.  If I get 1000 m/s I have a litre per second of air flow.  I would settle for something close.  Another method would be to obtain a calibrated air flow meter and use that to compare to what I have made...however I would still need a uniform volume of air to test and compare with.

The latest Venturi Tube design with face mask and tubing

If we compare the results from the previous venturi tube (Mark 3) we can see that some considerable improvement has been achieved:

  Venturi Mark 3
Venturi Mark 4
 Peak Raw Data Bits
850
 2900
 Peak Differential Pressure
103 Pa    
 342 Pa
 Peak Volumetric Flow
0.06 m^3/s
 0.03 m^3/s
 Peak Velocity of Flow
 7.1 m/s
 21 m/s

The tube's sensitivity has definitely improved.  We need to assess the volumetric flow measurement more closely hence the need for a calibrated air flow.  Once we have that I believe it will be possible to use this design of tube for accurate measurement of air flow.

Once that has been sorted I need to add the BME280 Temperature, pressure and humidity sensor which arrived recently. 

I have also just bought a 3.5 inch serial display...lets hope I can make it work well and it can be upscaled when necessary.


That's all for now - Langster!

Thursday, 4 June 2020

Design a better Venturi Tube!


I have looked at the previous post on designing a venturi tube and performed some more research.  It has come to my attention through testing experimentation and research that the venturi design I made is not fit for purpose.  It is unfortunately entirely my fault as to why that is the case.

I didn't do enough research and I didn't listen to my conscience.  I was rushing to get things done...this is what happens when one rushes things.

Rather than dwell on my mistakes I shall design a new and better and hopefully more correct venturi tube.  I wasn't aware of this but there is an ISO standard for venturi tubes.  It is based upon a British Standard:

BS 7405:1991

Unfortunately I cannot look at this standard as I do not have access to it and I cannot afford to buy it.  It costs £392 to non members and £196 to members of the British Standards Institute. 


It would be free for me to view at my local central library however I cannot access my nearest central library in lock down...

Helpfully a diagram has been reproduced which shows the pertinent mechanical details:

Classical Vetituri meter design. (From B. S. 7405 (1991) Fig. 3.1.4, with permission of B.S.I.)
Image Credit: http://thermopedia.com/content/1241/

So what does the diagram tell us:

1.  The high pressure portion of the venturi tube must be separated from the throat portion of the tube by a 21° sloping draft section.
2.  The exit section shall have a 15° draft section and shall be longer than the high pressure portion.
3.  The throad section shall have a specified width (d).
4.  The low pressure measurement port position (Throat) shall be fixed at half the dimension of the length of the section. (d/2)  
5.  The high pressure measurement port position shall be fixed at half the dimension of the length of the section. (D/2)
6.  The throat internal diamter shall be fixed and the same as the length of the section (d).
7.  The high pressure diameter shall be fixed and the same as the length of the section (D).

It is no surprise my design didn't work as well as expected...it was not designed properly...hey ho.  Lets mark up the diagram and then draw a new version of the venturi tube and get it 3D printed...

Here is the new design taking into account the information we now have:


Here is a render of how it might look when printed:


So...the plan is to print yet another tube and calculate it's response and then test it and hope that it's response will be good enough.  Iterating on designs is how improvements are made.  I should add that mechanical design of instrumentation is not my area of expertise and I'm applying what I have learned from research.  I have no real experience in designing venturi tubes!

I used the following sites to help me:





That's all for now!  Take care - Langster!