Mit einem Schalter zwischen 2 loops wechseln

Hi,
ich habe mir mal ein kleines RPM Meter gebaut und die Drehzahlen von Lüftern etc. messen zu können. Ich habe mir einen Code aus dem Internet kopiert.

int ledPin = 13;                // IR LED connected to digital pin 13
volatile byte rpmcount;
unsigned int rpm;
unsigned long timeold;

// include the library code:
#include <LiquidCrystal.h>
// initialize the library with the numbers of the interface pins
LiquidCrystal lcd(7, 8, 9, 10, 11, 12);

void rpm_fun()
 {
   //Each rotation, this interrupt function is run twice, so take that into consideration for 
   //calculating RPM
   //Update count
      rpmcount++;
 }

void setup()
 {
   lcd.begin(16, 2);  // intialise the LCD

   //Interrupt 0 is digital pin 2, so that is where the IR detector is connected
   //Triggers on FALLING (change from HIGH to LOW)
   attachInterrupt(0, rpm_fun, FALLING);

   //Turn on IR LED
   pinMode(ledPin, OUTPUT);
   digitalWrite(ledPin, HIGH);

   rpmcount = 0;
   rpm = 0;
   timeold = 0;
 }

 void loop()
 {
   //Update RPM every second
   delay(1000);
   //Don't process interrupts during calculations
   detachInterrupt(0);
   //Note that this would be 60*1000/(millis() - timeold)*rpmcount if the interrupt
   //happened once per revolution instead of twice. Other multiples could be used
   //for multi-bladed propellers or fans
   rpm = 30*1000/(millis() - timeold)*rpmcount;
   timeold = millis();
   rpmcount = 0;

   //Print out result to lcd
   lcd.clear();
   lcd.print("RPM=");
   lcd.print(rpm);

   //Restart the interrupt processing
   attachInterrupt(0, rpm_fun, FALLING);
  }

Ich möchte jetzt zwischen meheren Modi wechseln. Einmal gibt es ja den Modus, wenn es 2 Unterbrechungen pro Umdrehung gibt: 30*1000/(millis() - timeold)*rpmcount;
und einmal den Modus, wenn es nur eine Unterbrechung pro Umdrehung gibt.

60*1000/(millis() - timeold)*rpmcount;

Meine Frage. Kann ich über einen taktilen Schalter zwischen meheren Modi wechseln. (Am besten 4). Was zusätzlich noch schön wäre, wenn auf dem Display noch der Modus angezeigt werden könnte.
Grüße,
Lukas

void setup(void) {
//...
}

void loop(void) {
switch(mode) {
case 1:
program1();
break;
case 2:
program2();
break;
case 3:
program3();
break;
case 4:
program4();
break;
default:
mode = 1;
break;
}

void program1() {
//...
}
void program2() {
//...
}
void program3() {
//...
}
void program4() {
//...
}

Wegen deiner Zeile

delay(1000);

müsstest du einen Taster (wenn du das mit "taktiler Schalter" meinst) bis zu eine Sekunde lang drücken, bis es gemerkt wird.
Aber sonst geht es natürlich.
Wenn statt 1 sec - delay nur ca. 2 bis 10 msec lang gewartet wird, kannst du damit das Prellen des Tasters abfangen.
Du musst dir merken, ob ein neuer Tastendruck vorliegt, und in welchem Modus du bist.
Ausserdem musst du dich bei Tastern zwischen Pullup und Pulldown entscheiden :wink:
Wenn der Taster zwischen GND und EingangsPin liegt, ist er LOW wenn gedrückt (verwirrend),
aber du brauchst keinen extra Pulldown-Widerstand:

void setup()
{
  pinMode ( 3, INPUT_PULLUP); // Pin 3 ist der Taster nach GND
  // ... andere Initialisierungen
}
boolean altTaster = HIGH;
int modus = 1; // wechselt zwischen 1,  2 , 3 
void loop()
{
   if (digitalRead(3) == LOW && altTaster == HIGH)
   {
      // neuer Tasterdruck
      delay(10); // prellen abwarten
      altTaster = LOW; // merken, dass erkannt
      modus ++;
      if (modus > 3) modus = 1;
   }
   else if (digitalRead(3) == HIGH && altTaster == LOW)
   {
       // jetzt wurde Taster losgelassen
       delay(10); // auch hier prellen abwarten
       altTaster = HIGH;
   } 
// ... weiter in loop

Den Sekundenzyklus ohne delay(1000) kriegst du hin durch:

 if ( millis() - timeold >= 1000)
 { // hier alles was nur einmal / sec passieren soll
    noInterrupts(); // detach is not required

    if ( modus == 1 )  rpm = 30*1000/(millis() - timeold)*rpmcount;
    // evtl. andere Modi , gerne auch mit Stefans switch ...

    rpmcount = 0;
    timeold = millis();
    interrupts(); //  Interrupts can be active again.
    // update LCD
    lcd.clear();
    lcd.print("Modus ");
    lcd.print(modus);
    lcd.print("   RPM=");
    lcd.print(rpm);
  } // Ende der Sekunden-Funktionen
}  // Ende Loop

edit: code Tags vergessen

Hallo,
das "TastenPrellen" solltest Du nicht unterschätzen. Es kann Dich in den
Wahnsinn treiben- glaube mir.
Wenn Du die vier Modi nicht "gleichzeitig" brauchst, dann ist "switch case"
eine feine und einfache Möglichkeit.
http://arduino.cc/de/Reference/SwitchCase
Gruß und Spaß
Andres