China Post – 8-fach7-Segment, Taster und LED für Arduino

TM1638
TM1638 im Einsatz

TM1638 LED 7-Segmentanzeigen und Taster am Arduino

Im Artikel China Post – Arduino Multi Function Shield hatte ich bereits ein Arduino Shield mit LED-Anzeigen vorgestellt.
Eine weitere Möglichkeit am Arduino 7-Segment Anzeigen zu betreiben ist der IC TM1638.
Der TM1638 kann 10 Stellen 7-Segment Anzeige und  ein 3 x 8 Tastenfeld steuern. In der Praxis wird oft weniger umgesetzt. Die hier beschriebene Platine steuert 8x 7-Segment Anzeigen, 8x LED und 8x Taster an. Für die Ansteuerung sind nur 3 Digital Pins am Arduino erforderlich.Es ist kein Shield, welches für die Montage praktischer wäre. Mit 5 Kabeln ist aber auch die Verdrahtung kein Problem und die restlichen Pins sind ohne Einschränkung nutzbar.

Die Kommunikation ist nicht so trivial wie eine LED-Ansteuerung per Schieberegister. Daher greift man am einfachsten auf die TM1638 Bibliothek von Rjbatista zurück.
https://github.com/rjbatista/tm1638-library

Funktionen des Testprogramm tm1638_functions_example

  1. führende Nullen
  2. ohne führende Nullen, Dezimalpunk
  3. führende Nullen, hexadezimal
  4. ohne führende Nullen, hexadezimal
  5. binär
  6. Durchzählen der Digits
  7. 4 Digit Text + 4 Digit Ziffern
  8. wechselnder Text

Weitere Beispielprogramme zeigen die Anwendung von Lauftext und die Ansteuerung einzelner LED’s.
Es können auch Taster gleichzeitig gedrückt werden.

Es gibt neben dieser Platine noch weitere Ausführungen mit mehr Tastern , bzw. als kaskadierbare Anzeige.
Der Preis für Module mit dem TM1638 beginnt bei 5€.

[code language=”Arduino” title=”tm1638_functions_example”]
/*
Library examples for TM1638.

Copyright (C) 2011 Ricardo Batista <rjbatista at gmail dot com>

This program is free software: you can redistribute it and/or modify
it under the terms of the version 3 GNU General Public License as
published by the Free Software Foundation.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/

#include <TM1638.h>
#include <InvertedTM1638.h>

#define NO_MODULES 1

// define a regular module and a inverted module

// TM1638 module1(DIO, CLC, STB);

TM1638 module1(51, 52, 53);

TM1638* modules[NO_MODULES] = {
&module1,

};
byte modes[NO_MODULES];

unsigned long startTime;

void setup() {
startTime = millis();

for (int i = 0; i < NO_MODULES; i++) { modules[i]->setupDisplay(true, 7);
modes[i] = 0;
}
}

void update(TM1638* module, byte* mode) {
byte buttons = module->getButtons();
unsigned long runningSecs = (millis() – startTime) / 1000;

// button pressed – change mode
if (buttons != 0) {
*mode = buttons >> 1;
module->clearDisplay();
module->setLEDs(0);
}

switch (*mode) {
case 0:
module->setDisplayToDecNumber(runningSecs, 1 << 7); break; case 1: module->setDisplayToDecNumber(runningSecs, 1 << 6, false); break; case 2: module->setDisplayToHexNumber(runningSecs, 1 << 5); break; case 4: module->setDisplayToHexNumber(runningSecs, 1 << 4, false); break; case 8: module->setDisplayToBinNumber(runningSecs, 1 << 3); break; case 16: module->clearDisplayDigit((runningSecs – 1) % 8, 0);
module->setDisplayDigit(runningSecs % 8, runningSecs % 8, 0);
break;
case 32:
char s[8];
sprintf(s, "Secs %03d", runningSecs % 999);
module->setDisplayToString(s);
break;
case 64:
if (runningSecs % 2 == 0) {
module->setDisplayToString("TM1638 ");
} else {
module->setDisplayToString("LIBRARY ");
}

module->setLED(0, (runningSecs – 1) % 8);
module->setLED(1 + runningSecs % 3, runningSecs % 8);
break;
case 65:
module->setDisplayToError();
break;

}
}

void loop() {
for (int i = 0; i < NO_MODULES; i++) {
update(modules[i], &modes[i]);
}
}

[/code]



China Post – Arduino Multi Function Shield

Arduino Multi Function Shield
Arduino Multi Function Shield

Einfaches Test Shield für den Arduino

Es gibt leider nur wenige und meist recht teure Arduino Shields mit einer LED 7-Segmentanzeige. Bei diesem Multi Function Shield ist wenigsten eine kleine Anzeige dabei und teuer ist es auch nicht. Daneben bietet es noch weitere Features.
Eigentlich sind 7-Segmentanzeige günstig und in diversen Ausführungen enthalten. Das verdrahten einer mehrstelligen Anzeige macht aber nicht so richtig Spaß.
Das Shield bekommt man ab 5€ bei eBay. Da neben der Anzeige noch weitere Funktionen integriert sind bietet es die Möglichkeit viele Funktionen des Arduinos auszuprobieren, ohne das zusätzliche Bauteile oder Verdrahtungsaufwand erforderlich ist.

Funktionen des Arduino Multi Function Shield

  • 4 digit 7-segment LED Display mit 2x 74HC595 Schieberegister
  • 4x LED
  • 10K Potentiometer als analoger Eingang
  • 3 x Taster
  • Piezo Buzzer
  • Sockel für DS18B20 Temperature Sensor
  • Sockel für Infrarot Empfänger
  • Sockel für BT Modul



Anbei ein kleines Programm um einige Funktionen zu testen:

[code lang=”arduino” title=”Testprogramm Multi Function Shield”]
//*******************************************************************************
//*******************************************************************************/
// LED D1 … D4
#define LED1 10
#define LED2 11
#define LED3 12
#define LED4 13
int LEDS[] = {10,11,12,13};

// Taster
#define KEY1 A1
#define KEY2 A2
#define KEY3 A3
unsigned char KEYS[] = {A1, A2, A3};

// Potentiometer
#define Poti A0
int Spannung = 0;

// Schieberegister für 7-Segment
int latchPin = 4;
int clockPin = 7;
int dataPin = 8;

// Buzzer
#define Buz 3

// 7-Segment
unsigned char Dis_table[] = {0xC0,0xF9,0xA4,0xB0,0x99,0x92,0x82,0xF8,0X80,0X90}; // Ziffern 0 bis 7
unsigned char Dis_buf[] = {0xF1,0xF2,0xF4,0xF8}; // Schaltet die Segmente
unsigned char disbuff[] = {0, 0, 0, 0};

int SUM = 0;
int Flag_up = 1;
int Flag_up1 = 1;

void setup ()
{

// LED D1 … D4
for(int i=10; i<=13; i++)
{
pinMode(i, OUTPUT);
digitalWrite(i,HIGH);
}

// Taster A1 bis A3
for(int i=0; i<=2; i++)
{
pinMode(KEYS[i],INPUT);
//pinMode(KEYS[i],INPUT_PULLUP);
}

// Potentiometer
//pinMode(Poti,INPUT);

// Buzzer
pinMode(Buz,OUTPUT);
digitalWrite(Buz,HIGH);

// 7-Segment
pinMode(latchPin,OUTPUT);
pinMode(clockPin,OUTPUT);
pinMode(dataPin,OUTPUT);

// Anzeige ausschalten
for(char i=0; i<=3; i++)
{
digitalWrite(latchPin,LOW);
shiftOut(dataPin,clockPin,MSBFIRST,0xFF);
shiftOut(dataPin,clockPin,MSBFIRST,Dis_buf[i] );
digitalWrite(latchPin,HIGH);
delay(2);
}

Serial.begin(9600);

}

void led()
{
for(int i=0; i<=3; i++)
{
digitalWrite(LEDS[i],HIGH);
delay(1000);
digitalWrite(LEDS[i],LOW);
delay(1000);
}
}

void taster ()
{
for(int i=0; i<=2; i++)
{
if(digitalRead(KEYS[i]) == LOW)
{
delay(20);
if(digitalRead(KEYS[i]) == LOW)
{
digitalWrite(LEDS[i],LOW);
while(digitalRead(KEYS[i]) == LOW);
}
}
digitalWrite(LEDS[i],HIGH);
}
}

void analog()
{
Spannung = analogRead(Poti);
Spannung = map(Spannung, 0, 1023, 0, 5000);
Serial.print("Spannung = ");
Serial.println(Spannung);
delay(500);
}

void pwm ()
{
analogWrite(LED1,analogRead(Poti));
}

void buzzer ()
{
digitalWrite(Buz,LOW);
delay(10);
digitalWrite(Buz,HIGH);
delay(100);
}

void display1(void)
{
for(char i=0; i<=3; i++)
{
digitalWrite(latchPin,LOW);
shiftOut(dataPin,clockPin,MSBFIRST,Dis_table[disbuff[i]]);
shiftOut(dataPin,clockPin,MSBFIRST,Dis_buf[i] );
digitalWrite(latchPin,HIGH);
delay(2);
}
}

void display()

{
for(int i=0; i<=3; i++)

{
digitalWrite(latchPin,LOW);
shiftOut(dataPin,clockPin,MSBFIRST,Dis_table[disbuff[i]]);
shiftOut(dataPin,clockPin,MSBFIRST,Dis_buf[i] );
digitalWrite(latchPin,HIGH);
delay(2);
/*
Serial.print("Index Ziffer: ");
Serial.print("Dezimal= ");
Serial.print(Dis_buf[i]);
Serial.print("Binaer= ");
Serial.print(Dis_buf[i],BIN);
Serial.print(" Ziffer – dezimal: ");
Serial.print(Dis_table[disbuff[i]]);
Serial.print(" Binear: ");
Serial.println(Dis_table[disbuff[i]],BIN);
*/
}

}

void no_multiplex ()
{

for(char i=0; i<=3; i++)
digitalWrite(latchPin,LOW);
shiftOut(dataPin,clockPin,MSBFIRST,0b1111111);
shiftOut(dataPin,clockPin,MSBFIRST,0B11111111 );
digitalWrite(latchPin,HIGH);
delay(2);

delay(1000);
}

void counter ()
{
SUM++;
disbuff[0]=SUM/1000;
disbuff[1]=SUM%1000/100;
disbuff[2]=SUM%100/10;
disbuff[3]=SUM%10;
}

void loop()
{
//taster ();
//led();
//display();
//counter();
//analog();
//pwm();
//buzzer();
}
[/code]

I2C und fischertechnik – LED mit dem SAA1064 ansteuern

Der fischertechnik ROBO TX Controller bietet seit der letzten Firmware die Möglichkeit über den I2C-Bus mit diversen Bausteinen zu kommunizieren.

Anbei die Anschlussbelegung für den I2C Bus. Bitte beachten, das die interne 5 Volt Quelle des TX nur gering belastet werden kann. Vermutlich muss bei mehr als einer 7-Segmentanzeige eine externe Spannungsquelle gewählt werden.

TX Controller Draufsicht I2C

Einer Erweiterung des TX mit zusätzlicher Peripherie steht dem somit nichts entgegen. Besonders interessant ist den TX mit zusätzlichen Anzeigen auszustatten. In Form des IC SAA1064 von Philips ist dies besonders einfach möglich und soll hier kurz beschrieben werden.

 

I2C Ansteuerung mit fischertechnik ROBO TX Controller

Der SAA1064 kommuniziert per I2C Bus mit dem TX und kann bis zu 4 LED 7-Segmentanzeigen ansteuern. Über den Extern2 Anschluss am TX können die beiden I2C-Anschlüsse und die Betriebsspannung für den SAA1064 abgegriffen werden. An externen Bauelementen werden nur wenige Widerstände und Kondensatoren benötigt. Werden per Multiplex 4 Anzeigen angesteuert, werden noch 2 Transistoren benötigt.

SAA1064 Multiplexbetrieb

Bei mehreren 7-Segment Anzeigen reicht die interne 5Volt Quelle des TX nicht mehr. Die Anoden müssen dann an eine andere Spannungsquelle (<=+15V) geschaltet werden. Hier bietet sich die übliche fischertechnik Betriebsspannung von 9 Volt an.

 

Für die Ansteuerung des I2C Busses dient der Befehl I2C Schreiben.

Mit der Geräteadresse wird der gewünschte Empfänger angesprochen.

Die Unteradresse entspricht einem Befehlsbyte. Um die Kontroll-Bits zu setzen, wird hier eine Null gesetzt. Im Feld Datenwert erfolgt das Setzen der einzelnen Kontroll-Bits.

SAA1064 Befehl senden

Für das Schreiben von Daten wird die Unteradresse auf 1 für  Digit 1gesetzt. Analog dazu 2 für Digit 2 usw.. An das Datenfeld wird für jedes Segment welches leuchten soll eine 1 übergeben. Für eine 8 wäre diese der Wert „1111111“ in binärer Schreibweise (Dezimal 127).

SAA1064 Datenwert senden

Anbei ein Beispiel um den SAA1064 zu steuern und das erste Digit zu setzen. Für die komplette Ansteuerung kann man natürlich die ROBO Pro Bibliothek zum SAA1064 nehmen (ab Version 3.1.3).

SAA1064 Befehl senden mit ROBO Pro

SAA1064 Datenwert senden mit ROBO Pro

Dieses ROBO Pro Programm herunterladen

Versuchsaufbau mit einer 7-Segmentanzeige

Neben dem SAA1064 und der Anzeige mit gemeinsamer Anode wurden noch ein Kondensator benötigt. Die Anzeige wird über den +5Volt Anschluss des TX versorgt.

SAA1064 und TX Controller

Mehr zum SAA1064

Der SAA1064 ist ein I2C Treiberbaustein für die Ansteuerung von LEDs.

Werden die zwei Multiplexports genutzt können maximal 32 LEDs bzw. vier 7-Segmentanzeigen angesteuert werden.
Im Statikbetrieb sind es 16 LEDs bzw. zwei Anzeigen. Es kommen Anzeigen mit gemeinsamer Anode zum Einsatz. Da die Ausgänge Konstantstromsenken sind werden keine Vorwiderstände benötigt.

Über die Spannung am Pin1 können 4 I2C Adresse eingestellt werden. Somit lassen sich maximal 4 SAA1064 an einem I2C Bus betreiben.

 

Der LED-Strom lässt sich über die 3 Kontrol-Bits (C4…C6) per Software zwischen 0 und 21 mA steuern.

C4 = 1 plus 3 mA

C5 = 1 plus 6 mA

C6 = 1 plus 12 mA

 

Beschaltung im Statik Modus – 2 Anzeigen

Die gemeinsamen Anoden der Anzeigen kommen direkt auf die Betriebsspannung (max. +15V)

Digit1 an Port P1 bis P8 und Digit 2 an P9 bis P16.

Es sind keine zusätzlichen Bauteile notwendig.

 

Beschaltung im Multiplex Modus – 4 Anzeigen

Hier ist die Verlustleistung höher, so dass die Multiplexausgänge für die Anoden einen npn-Treibertransistor bekommen.

Die Segmentzuordnung sieht wie folgt aus.

Digit       Multiplexausgang                           Segment Port

1             MM1                                                    Port 1 – 8

2             MM2                                                    Port 9 – 16

3             MM1                                                    Port 1 – 8

4             MM2                                                    Port 9 – 16

Ansteuerung des SAA1064

Zuerst wird das Befehls Byte übertragen, welches bei einem Wert von 0 das nachfolgende Kontroll Byte zur Steuerung verwendet. Bei einem Wert zwischen 01 und 04 wird das entsprechende Digit mit dem Wert des folgenden Bytes angesteuert.

SC       SB       SA       SUB-ADDRESS            FUNCTION

0          0          0          00                                control register

0          0          1          01                                digit 1

0          1          0          02                                digit 2

0          1          1          03                                digit 3

1          0          0          04                                digit 4

1          0          1          05                                reserved, not used

1          1          0          06                                reserved, not used

1          1          1          07                                reserved, not used

 

Kontroll-Bits

C0 = 0 Statik Mode

C0 = 1 Dynamik Mode

C1 = 0/1  Digits 1 + 3 aus bzw. an

C2 = 0/1 Digits 2 + 4 aus bzw. an

C3 = Test, alle LEDs an.

C4 = 1  plus3 mA Ausgangsstrom

C5 = 1 plus 6 mA Ausgangsstrom

C6 = 1 plus 12 mA Ausgangsstrom

 

Die Zuordnung der Kontroll-Bits zu den Anzeigen ist wie folgt:

Bit: 7 6 5 4 3 2 1 0
Segment: p g f e d c b a

-a-
|f     |b
-g-
|e    |c
-d- .p

Damit ergibt sich folgende Kodierung für die einzelnen Ziffern.

0 = 0x3F = 63
1 = 0x06 = 6
2 = 0x5B = 91
3 = 0x4F = 79
4 = 0x66 = 102
5 = 0x6D = 109
6 = 0x7D = 125
7 = 0x07 = 7
8 = 0x7F = 127
9 = 0x6F = 111

 

Kosten

Den SAA1064 gibt es bei Reichelt für 2€, passende Anzeigen mit gemeinsamer Anode ab 0,50€ je nach Größe. Bei sehr großen LEDs beachten, dass dort mehrere LEDs intern in Reihe geschaltet sind. Mit einer 5 Volt Versorgungsspannung kommt man dann nicht mehr aus.
Für die ersten Versuche reicht ein kleines Steckbrett.
Fertige Module des SAA1064 sind ab ca. 30€ erhältlich.

TX Controller

Den verwendeten TX Controller gibt es sowohl einzeln als auch in Verbindung mit einem Bausatz. Momentan ist er bei Amazon mit 150€ relativ günstig zu bekommen.

fischertechnik ROBO TX Controller

Für Einsteiger ist es aber wesentlich praktischer den TX als Bestandteil einen Baukastens zu erwerben. Im ROBO TX Trainings Lab bekommt man noch 2 praktische Encodermotoren und einen Spurensosor für den Bau eines fahrenden Roboters dazu.