Zahlenschloss

Arduino Zahlenschloss

Das Zahlenschloss war eins der ersten „Projekte“ bei denen ich einige Bauteile kombiniert habe. Über die vier Potis werden die vier Ziffern des Schlosses eingestellt. Ist eine bestimmte Kombination erreicht, dreht sich das Servo zum öffnen. Wird eine Ziffer geändert, schließt das Servo wieder.

Lochraster Layout

 7segment_lr1 7segment_lr2

Quelltext

    #include <Servo.h>
     
    //////// Einstellungen ////////
    int servoOff = 90;             // Stellung des Servos bei falscher PIN
    int servoOn = 120;             // Stellung des Servos bei korrekter PIN
    const int pin[4] = {2,4,6,8};  // PIN
     
    //////// Aus- und Eingaenge ////////
    const int latchPin = 2;        // ST_CP Pin des 74HC595 (Schieberegister)
    const int clockPin = 3;        // SH_CP Pin des 74HC595 (Schieberegister)
    const int dataPin = 4;         // DS Pin des 74HC595 (Schieberegister)
    const int servo = 9;           // SteuerPIN des Servos (PWM)
    const int green = 6;           // Gruene LED
    const int red = 7;             // Rote LED
    const int potis[4] = {0,1,2,3};// Die vier Potis (analoge Ports)
     
    //////// Hilfsvariablen ////////
    Servo myservo;
    long lastTime = 0;
    int ledLastState = 0;
    int last[4] = {0,0,0,0};
     
    const uint8_t num[10] = {      // Binaere Codierung der Ziffern 0-9 der 7-Segmentanzeigen
      0b10000010,
      0b11011011,
      0b00000111,
      0b00010011,
      0b01011010,
      0b00110010,
      0b00100000,
      0b10011011,
      0b00000010,
      0b00010000
    };
     
    const uint8_t init_num[17] = { // Bitfolgen fuer die "Initialisierung"
      0b10111111,
      0b10011111,
      0b10011011,
      0b10010011,
      0b10000011,
      0b10000010,
      0b00000010,
      0b00000000,
      0b11111111,
      0b00000000,
      0b11111111,
      0b00000000,
      0b11111111,
      0b00000000,
      0b11111111,
      0b11111111,
      0b11111111
    };
     
    //////////////////////////////////////////////////////////////////////////////
    // Die setup-Funktion wird beim Booten einmal ausgefuehrt
    void setup(){
      // Schieberegister
      pinMode(latchPin, OUTPUT);
      pinMode(clockPin, OUTPUT);
      pinMode(dataPin, OUTPUT);
     
      // LEDs
      pinMode(green, OUTPUT);
      pinMode(red, OUTPUT);
     
      // Servo
      myservo.attach(servo);
      myservo.write(servoOff);
     
      // "Initialisierung"
      for(int i=0; i<17; i++){
        // Wechselblinken der zwei LEDs
        digitalWrite(green,0);
        digitalWrite(red,1);
     
        // Schreibe jeweils 8 Bit hintereinander um die vier Schieberegister zu fuellen
        digitalWrite(latchPin, LOW);
        shiftOut(dataPin, clockPin, MSBFIRST, init_num[i]);
        shiftOut(dataPin, clockPin, MSBFIRST, init_num[i]);
        shiftOut(dataPin, clockPin, MSBFIRST, init_num[i]);
        shiftOut(dataPin, clockPin, MSBFIRST, init_num[i]);
        digitalWrite(latchPin, HIGH);
     
        delay(200);
     
        // Wechselblinken der zwei LEDs
        digitalWrite(green,1);
        digitalWrite(red,0);
     
        delay(200);
      }
    }
     
    // Die loop-Funktion wird nach durchlauf immer wieder neu gestartet - "Endlosschleife"
    void loop() {
      // Auslesen der Poti-Werte (0-1023) und umrechnen in Werte 0-9
      int a = analogRead(potis[0])/103;
      int b = analogRead(potis[1])/103;
      int c = analogRead(potis[2])/103;
      int d = analogRead(potis[3])/103;
     
      // Wenn die Potiwerte sich geandert haben ...
      if(a != last[0] || b != last[1] || c != last[2] || d != last[3]){
        // Schreibe neue Werte in die Schieberegister
        digitalWrite(latchPin, LOW);
        shiftOut(dataPin, clockPin, MSBFIRST, num[a]);
        shiftOut(dataPin, clockPin, MSBFIRST, num[b]);
        shiftOut(dataPin, clockPin, MSBFIRST, num[c]);
        shiftOut(dataPin, clockPin, MSBFIRST, num[d]);
        digitalWrite(latchPin, HIGH);
     
        last[0] = a;
        last[1] = b;
        last[2] = c;
        last[3] = d;
      }
     
      // Wenn aktuelle PIN die wunsch-PIN ist ...
      if(a == pin[0] && b == pin[1] && c == pin[2] && d == pin[3]){
        if(millis()-lastTime > 500){ // Ein "delay" von 500ms ohne den Code anzuhalten
          lastTime = millis();
     
          // Blinken der gruenen LED
          if(ledLastState == 1) ledLastState = 0;
          else ledLastState = 1;
          digitalWrite(green,ledLastState);
     
          // Servo verstellen
          myservo.write(servoOn);
        }
     
        // Ausschalten der roten LED
        digitalWrite(red,1);
      }else{ // PIN ist nicht korrekt ...
        // Servo verstellen
        myservo.write(servoOff);
     
        // Gruene LED aus, rote LED an
        digitalWrite(green,1);
        digitalWrite(red,0);
      }
    }