OPEN SMART Rich Shield TWO für den Arduino UNO

In diesem Beitrag möchte ich dir Shield OPEN SMART Rich Shield TWO für den Arduino UNO vorstellen und zeigen, wie du die verschiedenen Sensoren & Aktoren in der Arduino IDE programmieren kannst.

OPEN SMART Rich Shield TWO für den Arduino UNO
OPEN SMART Rich Shield TWO für den Arduino UNO

Auf diesem Blog habe ich dir bereits einige solcher Module vorgestellt. Ich finde diese Shields besonders für Anfänger geeignet, da ein teils fehleranfälliges verkabeln der Sensoren & Aktoren entfällt. Du brauchst quasi nur einen Arduino UNO, ein Shield und ein USB Datenkabel und natürlich deinen Computer.

Der Preis dieser Shields ist gemessen an den verbauten Sensoren & Aktoren recht gut und somit kommt man meist damit günstiger weg als, wenn man alles einzeln kaufen würde.

Bezug

Das hier vorgestellte OPEN SMART Rich Shield TWO bekommst du auf zbsp. aliexpress.com für derzeit knapp 8 € zzgl. Versandkosten.

Aufbau des OPEN SMART Rich Shield TWO

Auf diesem Shield sind verbaut:

  • eine 16×8 LED Matrix,
  • ein Battery Display,
  • ein Rotary Decoder,
  • ein digitaler Temperatursensor DS18B20,
  • ein Geräuschdetektor,
  • ein analoger 2 Achsen Joystick,
  • ein Bewegungssensor / PIR,
  • ein Sockel für einen Ultraschallabstandssensor vom Typ HC-SR04

Anschluss der Sensoren & Aktoren

Auf dem Rich Shield TWO von OPEN SMART sind einige Sensoren & Aktoren verbaut, auf der Platine sind die Pins beschriftet und man kann ablesen wie diese mit dem Arduino UNO verbunden sind.

Für del Ultraschallabstandssensor vom Typ HC-SR04 ist ein Sockel verbaut, der Sensor liegt jedoch nicht dabei!

Sensor / AktorPinArduino UNO
Ultraschallabstandssensor HC-SR04
GND
ECHOD8
TRIGGERD7
5V
8×16 LED Matrix (I²C)
SDAanalog A4
SCLanalog A5
Battery Display (SPI)
CLKD10
DIOD11
4fach RGB LEDsA3
analoger 2 Achsen Joystick
XA0
YA1
Temperatursensor DS18B20D5
Bewegungssensor / PIR
D6
GeräuschdetektorA2
Rotary Encoder
SAD2
SBD3
SWD4

Hinweis

Dieses Shield ist für den Arduino UNO konzipiert, es passt auch auf einen Arduino Leonardo, jedoch hat dieser Mikrocontroller die I²C Pins SDA & SCL nicht an den analogen Pins A4 & A5. Somit wird die 8×16 LED Matrix nicht funktionieren.

Programmieren des OPEN SMART Richt Shield TWO in der Arduino IDE

Für einige der Sensoren / Aktoren benötigst du eine Bibliothek, wie man eine solche in der Arduino IDE installiert, habe ich dir bereits im Beitrag Arduino IDE, Einbinden einer Bibliothek ausführlich erläutert. An den entsprechenden Stellen werde ich dir einen Link zur ZIP-Datei liefern.

Vorbereiten des Arduino UNO zum Programmieren

Wenn du deinen Arduino UNO bereits für andere Projekte verwendet hast, ist es gut, wenn dieser auf eine Art „default“ Sketch gesetzt wird. Dieses hat den Vorteil, dass ggf. Pins welche zuvor auf HIGH gesetzt sind nicht aktiviert sind und somit dein Shield keinen Schaden nehmen kann.

In meinem Fall schreibe ich mir immer ein kleines Programm mit einer seriellen Ausgabe.

void setup() {
  Serial.begin(9600);

}

void loop() {
  Serial.println("Test");
  delay(500);
}

Den Rotary Decoder können wir nutzen, um die Segmente des Battery Display zu steuern.

Den Rotrary Decoder habe ich dir bereits im Beitrag Arduino Lektion 40: Drehregler KY-040 vorgestellt und gezeigt, wie dieser programmiert wird.

Für das Battery Display benötigen wir zusätzlich die Bibliothek TM1651, du findest diese zbsp. auf dem GitHub Repository von mworkfun / TM1651 als ZIP-Datei zum download.

Da jedoch der Rotary Decoder keinen fixen End- / Startpunkt hat, müssen wir hier die Schritte hinauf oder nach unten zählen und so die Segmente aktivieren / deaktivieren.

//Bibliothek zum ansteuern des Battery Displays
#include "TM1651.h"

//Pins des Displays definieren
#define BATTERY_DISPLAY_CLK 10
#define BATTERY_DISPLAY_DIO 11
//Instanz eines Objektes erzeugen
TM1651 batteryDisplay(BATTERY_DISPLAY_CLK, BATTERY_DISPLAY_DIO);

//Pins des Rotary Decoders definieren
#define ROTARY_DECODER_CLK 2
#define ROTARY_DECODER_DT 3

//Variablen zum merken der Positionen
int posCount = 0;
int lastPosition;
int currentPosition;

void setup() {
  pinMode (ROTARY_DECODER_CLK, INPUT);
  pinMode (ROTARY_DECODER_DT, INPUT);
  //initiales befüllen der Variable lastPosition
  lastPosition = digitalRead(ROTARY_DECODER_CLK);
}

void loop() {
  //lesen des aktuellen Wertes
  currentPosition = digitalRead(ROTARY_DECODER_CLK);
  //Wenn der aktuelle Wert ungleich des letzen ist dann mache...
  if (currentPosition != lastPosition) {
    //Wenn der Wert höher ist dann die Variable posCount um eines erhöhen,
    //andernfalls um eins verringern
    (digitalRead(ROTARY_DECODER_DT) != currentPosition) ? posCount ++ : posCount--;
    //Wenn der Wert in der Variable posCount sich zwischen 0 und 8 befindet
    //dann soll dieser auf dem Battery Display angezeigt werden.
    if (posCount >= 0 && posCount < 8) {
      batteryDisplay.displayLevel(posCount);
    }
  }
  //Überschreiben der letzen Position mit der aktuellen
  lastPosition = currentPosition;
}

analoger Joystick

Auf der Platine ist ein kleiner, analoger 2 Achsen Joystick verbaut.

Wie du einen analogen Joystick programmierst habe ich dir im Beitrag Arduino Lektion 38: Joystick gezeigt, jedoch hat dieser verbaute Joystick keinen zusätzlichen Taster.

Lesen wir zunächst die X & Y Position des Joysticks aus.

#define joystickX A0 //X Achse des Joysticks am analogen PIN A0.
#define joystickY A1 //Y Achse des Joysticks am analogen PIN A1.

void setup() {
  //begin der seriellen Kommunikation mit 9600 baud
  Serial.begin(9600);
}

void loop() {
  //auslesen der X Koordinate
  int x = analogRead(joystickX);
  //auslesen der Y Koordinate
  int y = analogRead(joystickY);

  //Ausgeben der Daten auf der seriellen Schnittstelle
  Serial.print("aktuelle Koordinaten des Joysticks (x,y): ");
  Serial.print(x);
  Serial.print(", ");
  Serial.println(y);
}

16×8 LED Matrix

Die 16×8 LED Matrix wird per I²C und dem Chip VK16K33 betrieben. Ein Datenblatt zu diesem Chip findest du unter https://cdn.sparkfun.com/assets/c/8/7/2/5/VK16K33Datasheet.pdf.

Zum Programmieren dieser Matrix nutze ich die Bibliothek LED Backpack, welche man als ZIP-Datei vom GitHub Repository adafruit / Adafruit_LED_Backpack laden kann.

Auf dem Display kannst du Smileys, Text und einfache geometrische Figuren zeichnen, dafür bietet dir die genannte Bibliothek jeweils Funktionen, somit musst du lediglich die einzelnen Funktionen aufrufen, ohne viel zu programmieren.

Die I²C Adresse der 16×8 LED Matrix ist 0x70!

Ausgeben von „Hello World!“ auf der LED Matrix

Geben wir zunächst die Zeile „Hello World!“ auf der LED Matrix aus.

//einbinden der benötigten Bibliotheken
#include <Wire.h>
#include <Adafruit_GFX.h>
#include "Adafruit_LEDBackpack.h"

//initialisieren eines Objektes
//vom Typ Adafruit_8x16matrix
Adafruit_8x16matrix matrix = Adafruit_8x16matrix();

void setup() {
  //begin der Kommunikation mit der LED Matrix
  //über die I²C Adresse 0x70
  matrix.begin(0x70);
}

void loop() {
  //setzen der Textgröße
  matrix.setTextSize(1);
  //deaktivieren des automatischen Umbruchs von langen Texten
  matrix.setTextWrap(false);
  //aktivieren der LEDs
  matrix.setTextColor(LED_ON);
  //drehen der LED Matrix
  matrix.setRotation(1);
  //eine Schleife von 7 bis -60
  for (int8_t x = 7; x >= -60; x--) {
    //leeren des Displays
    matrix.clear();
    //setzen des Cursors an die Position
    matrix.setCursor(x, 0);
    //schreiben der Textzeile "Hello World!"
    matrix.print("Hello World!");
    //ausgeben der Daten
    matrix.writeDisplay();
    //eine kleine Pause von 100 ms.
    delay(100);
  }
  
}

Ausgeben von Smileys auf der LED Matrix

Wie erwähnt kannst du neben Text auch Punkte, Linien etc. ausgeben, mit dieser Funktion kannst du dann auch Smileys ausgeben.

Für die Programmierung nutze ich wie erwähnt die Bibliothek von Adafruit, bei dieser liegen einige Beispiele für eine 16×8 LED Matrix bei. Aus einem dieser Beispiele habe ich mir die Smileys entnommen.

//einbinden der benötigten Bibliotheken
#include <Wire.h>
#include <Adafruit_GFX.h>
#include "Adafruit_LEDBackpack.h"

//initialisieren eines Objektes
//vom Typ Adafruit_8x16matrix
Adafruit_8x16matrix matrix = Adafruit_8x16matrix();

//definieren der Smileys
static const uint8_t PROGMEM
smile_bmp[] = { B00111100, B01000010, B10100101, B10000001, B10100101, B10011001, B01000010, B00111100},
neutral_bmp[] = { B00111100, B01000010, B10100101, B10000001, B10111101, B10000001, B01000010, B00111100},
frown_bmp[] = { B00111100, B01000010, B10100101, B10000001, B10011001, B10100101, B01000010, B00111100};

void setup() {
  //begin der Kommunikation mit der LED Matrix
  //über die I²C Adresse 0x70
  matrix.begin(0x70);
}

void loop() {
  //leeren der LED Matrix
  matrix.clear();
  //drehen der LED Matrix
  matrix.setRotation(1);
  //zeichnen eines Bitmaps in den zwischenspeicher
  matrix.drawBitmap(0, 0, smile_bmp, 8, 8, LED_ON);
  //schreiben der zwischenspeichers auf das Display
  matrix.writeDisplay();
  //eine kleine Pause von 500 ms.
  delay(500);
  matrix.clear();
  matrix.setRotation(1);
  matrix.drawBitmap(0, 0, neutral_bmp, 8, 8, LED_ON);
  matrix.writeDisplay();
  delay(500);
  matrix.clear();
  matrix.setRotation(1);
  matrix.drawBitmap(0, 0, frown_bmp, 8, 8, LED_ON);
  matrix.writeDisplay();
  delay(500);
}

Mit dem analogen Joystick und der 8×16 LED Matrix können wir einen kleinen Punkt auf der selbigen bewegen. Wenn man das ganze ausbauen würde, könnte man sogar das Spiel Snake nachprogrammieren.

Digitaler Temperatursensor DS18B20

Den Temperatursensor DS18B20 habe ich dir bereits in diversen Beiträgen auf meinem Blog vorgestellt.

Nachfolgend möchte ich dir zeigen, wie du die Temperatur auslesen und auf der zuvor gezeigten 16×8 LED Matrix anzeigen lassen kannst.

Zum Auslesen der Temperatur nutze ich die Bibliothek

//einbinden der benötigten Bibliotheken
#include <Wire.h>
#include <Adafruit_GFX.h>
#include "Adafruit_LEDBackpack.h"

#include <OneWire.h>
#include <DS18B20.h>

#define ONE_WIRE_BUS 5

OneWire oneWire(ONE_WIRE_BUS);
DS18B20 sensor(&oneWire);

//initialisieren eines Objektes
//vom Typ Adafruit_8x16matrix
Adafruit_8x16matrix matrix = Adafruit_8x16matrix();


//Pins des Rotary Decoders definieren
#define ROTARY_DECODER_CLK 2
#define ROTARY_DECODER_DT 3

//Variablen zum merken der Positionen
int posCount = 0;
int lastPosition;
int currentPosition;

void setup() {
  //begin der Kommunikation mit der LED Matrix
  //über die I²C Adresse 0x70
  matrix.begin(0x70);

  sensor.begin();

  pinMode (ROTARY_DECODER_CLK, INPUT);
  pinMode (ROTARY_DECODER_DT, INPUT);
  //initiales befüllen der Variable lastPosition
  lastPosition = digitalRead(ROTARY_DECODER_CLK);
}

void loop() {
  sensor.requestTemperatures();

  while (!sensor.isConversionComplete());

  String temp = "Temp:";
  temp += String(sensor.getTempC(), 2);
  temp += " C";

  //setzen der Textgröße
  matrix.setTextSize(1);
  //deaktivieren des automatischen Umbruchs von langen Texten
  matrix.setTextWrap(false);
  //aktivieren der LEDs
  matrix.setTextColor(LED_ON);
  //drehen der LED Matrix
  matrix.setRotation(1);
  //eine Schleife von 7 bis -60
  for (int8_t x = 7; x >= -60; x--) {
    //leeren des Displays
    matrix.clear();
    //setzen des Cursors an die Position
    matrix.setCursor(x, 0);
    //schreiben der Textzeile
    matrix.print(temp);
    //ausgeben der Daten
    matrix.writeDisplay();

    int pause = lastposition * 15;
    delay(pause);
    readRotaryDecoder();
  }

}

void readRotaryDecoder() {
  //lesen des aktuellen Wertes
  currentPosition = digitalRead(ROTARY_DECODER_CLK);
  //Wenn der aktuelle Wert ungleich des letzen ist dann mache...
  if (currentPosition != lastPosition) {
    //Wenn der Wert höher ist dann die Variable posCount um eines erhöhen,
    //andernfalls um eins verringern
    (digitalRead(ROTARY_DECODER_DT) != currentPosition) ? posCount ++ : posCount--;
    //Wenn der Wert in der Variable posCount sich zwischen 0 und 8 befindet
    //dann soll dieser auf dem Battery Display angezeigt werden.
    if (posCount >= 0 && posCount < 8) {
      batteryDisplay.displayLevel(posCount);
    }
  }
  //Überschreiben der letzen Position mit der aktuellen
  lastPosition = currentPosition;
  Serial.println(lastPosition);
}

Geräuschdetektor & 4fach NeoPixel

Einen Geräuschdetektor habe ich dir bereits in den nachfolgenden Beiträgen vorgestellt.

Der Sensor wird per analogen Anschluss ausgelesen und liefert Werte zwischen 0 und 1023. Diese Werte können wir recht einfach mit der Funktion map aus der Arduino Bibliothek auf die 4 vorhandenen NeoPixel anwenden.

In dem kleinen Beispiel aktiviere ich jeweils die NeoPixel nach Wert des Geräuschdetektors. D.h. um so lauter das Geräusch, desto mehr NeoPixel leuchten auf.

Wobei die ersten beiden NeoPixel in Grün, die dritte in Orange und die vierte in Rot aufleuchten.

#include <Adafruit_NeoPixel.h>

#define PIN            A3
#define NUMPIXELS      4

#define soundSensor A2 //Geräuschdetektor am analogen Pin A2

Adafruit_NeoPixel pixels = Adafruit_NeoPixel(NUMPIXELS, PIN, NEO_GRB + NEO_KHZ800);

int color_red[3] = {255, 0, 0};
int color_orange[3] = {255, 165, 0};
int color_green[3] = {0, 255, 0};

void setup() {
  Serial.begin(9600);
  //analogen Pin des Geräuschdetektor als Eingang definieren
  pinMode(soundSensor, INPUT);

  pixels.begin(); // initialisieren der NeoPixel Bibliothek
  pixels.setBrightness(50);
}

void loop() {
  //lesen des aktuellen Wertes des Geräuschdetektors
  int value = analogRead(soundSensor);
  //deaktivieren aller Pixel
  resetPixels();
  //ermitteln der NeoPixel welche aktiviert werden sollen
  int maxNumActivePixel = map(value, 0, 1023, 0, 4);

  //iteration von 0 bis zum Wert der zu aktivierenden NeoPixel
  for (int pixel = 0; pixel < maxNumActivePixel; pixel++) {
    //aktivieren des NeoPixel mit der Farbe x
    pixels.setPixelColor(pixel, findColorForPixel(pixel));
    //anzeigen der Farbe
    pixels.show();
  }
}

//Liefert einen Farbwert für einen Index eines NeoPixel
uint32_t findColorForPixel(int pixel) {
  int colorArray[3];

  if (pixel == 0 || pixel == 1) {
    //Pixel 1 & 2 sollen in grün angezeigt werden
    memcpy(colorArray, color_green, sizeof(color_green));
  } else if (pixel == 2) {
    //Pixel 3 soll in orange angezeigt werden
    memcpy(colorArray, color_orange, sizeof(color_orange));
  } else if (pixel == 3) {
    //Pixel 4 soll in rot angezeigt werden
    memcpy(colorArray, color_red, sizeof(color_red));
  }
  return pixels.Color(colorArray[0], colorArray[1], colorArray[2]);
}

//deaktiviert alle NeoPixel
void resetPixels() {
  for (int pixel = 0; pixel < NUMPIXELS; pixel++) {
    //setzen der Farbe schwarz an dem NeoPixel mit dem Index "pixel"
    pixels.setPixelColor(pixel, pixels.Color(0, 0, 0));
  }
}

Ultraschallabstandssensor HC-SR04 & Battery Display

Auf der Platine findest du einen Sockel für den Ultraschallabstandssensor HC-SR04 dieser Sensor liegt dem Shield nicht bei, kann aber recht günstig über zbsp. ebay.de für knapp 3 € zzgl. Versandkosten.

Ultraschallabstandssensor HC-SR04 auf OPEN SMART Rich Shield TWO
Ultraschallabstandssensor HC-SR04 auf OPEN SMART Rich Shield TWO

Den Sensor HC-SR04 habe ich bereits ebenfalls diverse Beiträge gewidmet.

Im nachfolgenden Beispiel möchte ich den Abstand am Battery Display anzeigen.

//Bibliothek zum ansteuern des Battery Displays
#include "TM1651.h"

#define TRIGGER 7
#define ECHO 8

//Pins des Displays definieren
#define BATTERY_DISPLAY_CLK 10
#define BATTERY_DISPLAY_DIO 11
//Instanz eines Objektes erzeugen
TM1651 batteryDisplay(BATTERY_DISPLAY_CLK, BATTERY_DISPLAY_DIO);

void setup() {
  Serial.begin(9600);
  //Den Trigger auf das Output Signal des Sainsmart setzen.
  pinMode(TRIGGER, OUTPUT);
  //Das Echo auf das Input Signal des Sainsmart setzen.
  pinMode(ECHO, INPUT);

  batteryDisplay.init();
  //Helligkeit des Battery Displays auf 2 setzen
  //min. 0 - max. 7
  batteryDisplay.set(2);
}

void loop() {
  //auslesen der Distanz in Zentimeter
  int distance = readUltrasonicSensor();
  //Ausgeben des Wertes auf der seriellen Schnittstelle
  Serial.println("distance: " + String(distance, DEC));
  //mappen des Wertes
  int activeLedIndex = map(distance, 0, 30, 8, 0);
  //ausgeben des Indexe auf der seriellen Schnittstelle
  Serial.println("activeLedIndex: " + String(activeLedIndex, DEC));
  //setzen des Index am Battery Display
  batteryDisplay.displayLevel(activeLedIndex);
  //eine kleine Pause von 250 ms.
  delay(250);
}

float readUltrasonicSensor() {
  //Trigger Signal ausschalten
  digitalWrite(TRIGGER, LOW);
  //2 ms warten
  delayMicroseconds(2);
  //Trigger Signal einschalten
  digitalWrite(TRIGGER, HIGH);
  //10ms warten
  delayMicroseconds(10);
  //Trigger Signal ausschalten
  digitalWrite(TRIGGER, LOW);
  //Das Empfangene Echo Signal in cm umrechnen
  float cm = pulseIn(ECHO, HIGH) / 58.0;
  //Da der Sensor mit einer Messgenauigkeit von 0,3cm arbeitet können wir das
  //Ergbnis auf 2 Nachkommastellen begrenzen
  return (int(cm * 100.0)) / 100.0;
}

Download

Die gezeigten Beispiele sowie die benötigten Bibliotheken findest du hier zum Download.

Kommentar hinterlassen

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert