Moin,
ich habe mir einen Km/h Begrenzer gebastelt nach dem Prinzip:
Bei einer über ein Poti einstellbaren max Km/h schaltet ein Relais einen Stellmotor in meinem Fahrzeug welcher dann die Luftzufuhr drosselt und das Fahrzeug die Leistung/Geschwindigkeit reduziert.
Funktioniert auch soweit alles gut.
ABER: folgendes Problem
wenn ich an dem Relais ( 5v ) den Stellmotor anschließe ( wird über Masse geschaltet als Schließer, hat ca. 6A )
hängt sich der Arduino nach ein paar mal einwandfreier Funktion einfach "auf" . Auf dem LCD erscheinen komische Symbole oder er wird einfach blank ohne irgendwelche Symbole.
Die Funktion ist dann manchmal trotzdem noch da.
Manchmal friert auch das LCD ein und die Funktion ist weg.
Ich dachte schon das es evt. an einen "Spannungszusammenbruch" durch die höhere Stromaufnahme vom Stellmotor liegen könnte, aber das Relais schaltet doch nur einen Durchgang und ist bis 10A belastbar.
Auch habe ich den Arduino an eine seperate Stromquelle angeschlossen.
Kann es evt an meinem Code liegen: siehe (bin Ratlos, würde mich über Hilfe freuen)
Anlage: Bild der Verdrahtung
Code nur bis Arduino 1.5 !!!
//Anzahl Spalten des Display (16)
#define LCD_WIDTH 16
//Anzahl Zeilen des Display (2)
#define LCD_HEIGHT 2
// Pin fuer Reed-Kontakt, Digital-2 fuer Interrupt 0
#define REEDPIN 2
// Hardware-Interrupt fuer den Reed-Pin
#define REEDINTERRUPT 0
// Radumfang in mm
#define RADUMFANG 1900
#include <LiquidCrystal.h>
LiquidCrystal lcd(8, 9, 4, 5, 6, 7);
int Relais = 11; // Relais an Pin 11
int potiWert = 0;
// build 2-line digit font data array
// Digits are 3 characters wide.
byte bignums[10][2][3] = {
// Define which characters to use for each number. 255 is a solid block; 254 is a space
// The format is { {TopLeft, TopMiddle, TopRight}, {BottomLeft, BottomMiddle, BottomRight} }
{ {255, 0, 255}, {255, 1, 255} }, // data to display "0"
{ {0, 255, 254}, {1, 255, 1} }, // data to display "1"
{ {0, 5, 255}, {255, 1, 1} }, // data to display "2"
{ {0, 5, 255}, {1, 1, 255} }, // data to display "3"
{ {255, 1, 255}, {254, 254, 255} }, // data to display "4"
{ {255, 5, 5}, {1, 1, 255} }, // data to display "5"
{ {255, 5, 5}, {255, 1, 255} }, // data to display "6"
{ {0, 0, 255}, {254, 255, 254} }, // data to display "7"
{ {255, 5, 255}, {255, 1, 255} }, // data to display "8"
{ {255, 5, 255}, {254, 254, 255} } // data to display "9"
};
void loadchars() { // This subroutine programs the custom character data into the LCD
lcd.command(64);
// Custom character 0
lcd.write(byte(B11111));
lcd.write(byte(B11111));
lcd.write(byte(B11111));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
// Custom character 1
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B11111));
lcd.write(byte(B11111));
lcd.write(byte(B11111));
// Custom character 2
lcd.write(byte(B11111));
lcd.write(byte(B11111));
lcd.write(byte(B11111));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B11111));
lcd.write(byte(B11111));
lcd.write(byte(B11111));
// Custom character 3
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B01110));
lcd.write(byte(B01110));
lcd.write(byte(B01110));
// Custom character 4
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B01110));
lcd.write(byte(B01110));
lcd.write(byte(B01110));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
// Custom character 5
lcd.write(byte(B11111));
lcd.write(byte(B11111));
lcd.write(byte(B11111));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B11111));
lcd.write(byte(B11111));
// Custom character 6
lcd.write(byte(B11111));
lcd.write(byte(B11111));
lcd.write(byte(B11111));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B11110));
lcd.write(byte(B11111));
// Custom character 7
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.write(byte(B00000));
lcd.home();
}
void printbigchar(byte digit, byte col) { // This subroutine prints the big font characters on the LCD screen
if (digit > 9) return; // reject anything above 9
for (int i = 0; i < 2; i++) { // count i from 0 to 1
lcd.setCursor(col*4 , i); // set LCD cursor at correct point
for (int j = 0; j < 3; j++) { // count j from 0 to 2
lcd.write(bignums[digit][i][j]); // write proper block to LCD from array
}
lcd.write(254); // write an empty space
}
lcd.setCursor(col + 4, 0); // move the cursor to the top line, col + 4
}
void setup(){
Serial.begin(9600);
pinMode(Relais, OUTPUT); // Pin 11 Ausgang
pinMode(REEDPIN, INPUT_PULLUP); // Reedkontakt direkt und ohne Widerstand angeschlossen
lcd.begin(LCD_WIDTH, LCD_HEIGHT);
loadchars();
attachInterrupt(REEDINTERRUPT, reedISR, FALLING);
}
volatile byte reedCountSum;
volatile long reedMillisSum;
unsigned long lastReedMillis;
void reedISR()
{
if (millis()-lastReedMillis>=25) // 25ms entspricht max. 40 Radumdrehungen pro Sekunde
{
reedCountSum++; // eine Radumdrehung zaehlen
reedMillisSum+=millis()-lastReedMillis; // Zeit addieren
lastReedMillis=millis(); // Zeit merken
}
}
unsigned long gesamtUmdrehungen;
void tachoAnzeige()
{
byte umdrehungen;
unsigned long zeit;
float kph, kilometer;
int kphRounded;
char buffer[10];
noInterrupts(); // Interrupts sperren
umdrehungen=reedCountSum;// Zaehlvariable umkopieren
reedCountSum=0; // Zaehlvariable auf 0 zuruecksetzen
zeit=reedMillisSum; // Zeitzaehler umkopieren
reedMillisSum=0; // Zeitzaehler auf 0 zuruecksetzen
interrupts(); // Interrupts wieder zulassen
gesamtUmdrehungen+= umdrehungen; // Aufsummieren aller Radumdrehungen
kilometer=(float)gesamtUmdrehungen*(float)RADUMFANG/1000000.0; // Fahrtkilometerzaehler
if (umdrehungen>0)
kph=float(RADUMFANG)*(float)umdrehungen/(float)zeit*3.6;
else
kph=0.0;
if(kph>potiWert/7) digitalWrite(Relais, HIGH);
else digitalWrite(Relais, LOW);
lcd.setCursor(12, 0);
dtostrf(kilometer,3, 1, buffer);
if (potiWert/7<1000) lcd.print(' '); // loescht die ueberfuessigen Zeichen beim runterregeln
if (potiWert/7<100) lcd.print(' ');
if (potiWert/7<10) lcd.print(' ');
lcd.print(potiWert/7); // zeigt den PotiWert geteilt durch 7 also 1024 durch 7
/*
lcd.setCursor(0, 0);
dtostrf(kilometer,9,3,buffer);
lcd.print(buffer);
lcd.print(" km");
lcd.setCursor(0, 1);
lcd.print("KM/H ");
dtostrf(kph,5,1,buffer);
*/
kphRounded=int(kph+0.5); // auf ganze kph gerundet
// Ausgabe kph in grossen Ziffern
kphRounded = kphRounded % 1000; // drop any digits above 999
printbigchar(kphRounded / 100,0); // print the speed hundreds
kphRounded = kphRounded % 100; // drop any digits above 99
printbigchar(kphRounded/10,1); // print the speed tens
kphRounded = kphRounded % 10; // drop any digits above 9
printbigchar(kphRounded,2); // print the speed ones
lcd.setCursor(13, 1);
lcd.print("max");
}
unsigned long letzteSekunde=0;
void loop()
{
potiWert = analogRead(A0);
Serial.println(potiWert/7);
unsigned long dieseSekunde=millis()/500;
// Tachoanzeige wird genau einmal pro Sekunde aktualisiert
if (letzteSekunde != dieseSekunde)
{
tachoAnzeige();
letzteSekunde=dieseSekunde;
}
}