Hi Leute,
Ich bin gerade dabei an meinem Jeep Wrangler TJ zu schrauben und kam jetzt auf die Idee, die alte Temperatursteuerung für die Heizung, durch eine automatisierte Variante mittels Arduino zu ersetzen.
Das Projekt beinhaltet einen Arduino Nano, 3 DS18B20 Temperatursensoren, einen 20kg Servomotor und ein OLED-Display.
Aktuell wird die Temperatur mit einem Schieberegler gesteuert, der über einen Seilzug mit einer Klappe verbunden ist, die sich in einem Bereich von ca. 90° bewegt. An diesem "Drehpunkt" will ich einen kleinen Servomotor anbringen, der das manuelle Umstellen automatisieren soll.
Ich habe aktuell schon ein bisschen was an Code geschrieben, der soweit auch schon einigermaßen gut funktioniert, allerdings komme ich mittlerweile so langsam an's Ende meiner Programmierfähigkeiten ![]()
Ziel ist es, den Servomotor schrittweise in Richtung Kalt (135°), bzw. Warm (45°) zu bewegen, bis die Temperatur im Innenraum (in_temp) mit der gesetzten Temperatur (set_temp) übereinstimmt.
(Der Sensor für den Außenbereich dient nur zur Anzeige und ist für die Regelung nicht relevant)
Dabei hätte ich gerne einen gewissen Toleranzbereich (ca. +- 1°C), damit der Servomotor nicht dauerhaft Nachregeln muss.
Außerdem sollte es zwischen den Versuchen die Temperatur anzupassen, eine gewisse Verzögerung geben, da ich ein ständiges Voll-AUF/Voll-ZU der Klappe vermeiden möchte ![]()
Delays würde ich gerne vermeiden und auf millis() zurückgreifen, allerdings weiß ich gerade nicht so genau wie ich das am besten angehen sollte...
Ich hoffe Ihr könnt mir weiterhelfen!
Für Verbesserungsvorschläge am vorhandenen Code bin ich immer offen ![]()
#include <Servo.h>
#include <OneWire.h>
#include <DallasTemperature.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#include <SPI.h>
#include <Wire.h>
#define ONE_WIRE_BUS_OUT 2 // Pins für Temperatursensoren definieren
#define ONE_WIRE_BUS_IN_L 3
#define ONE_WIRE_BUS_IN_R 4
const int servopin = 8; //Pin für Servomotor
const int btn_minus = 6; // Pins für die Taster zur Temperatureinstellung (- / +)
const int btn_plus = 7;
int out_temp; //Festlegen der Variablen für die Temperaturwerte
int inl_temp;
int inr_temp;
int in_temp;
int set_temp = 24;
unsigned long startMillis;
unsigned long currentMillis;
const unsigned long period = 2000;
int angle = 90; // Startwinkel für Servo (Mitte)
int state_minus;
int state_plus;
int val_minus;
int val_plus;
#define OLED_RESET 4
Adafruit_SSD1306 display(OLED_RESET);
Servo servo; // Namen für Servomotor definieren
OneWire temp_outside(ONE_WIRE_BUS_OUT);
OneWire temp_inside_left(ONE_WIRE_BUS_IN_L);
OneWire temp_inside_right(ONE_WIRE_BUS_IN_R);
DallasTemperature temp_out(&temp_outside);
DallasTemperature temp_in_l(&temp_inside_left);
DallasTemperature temp_in_r(&temp_inside_right);
void setup()
{
servo.attach(servopin); // Initialisierung Servomotor
Serial.begin(115200);
temp_out.begin();
temp_in_l.begin();
temp_in_r.begin();
display.begin(SSD1306_SWITCHCAPVCC, 0x3C); // Initialisierung OLED-Display
display.clearDisplay();
display.setTextColor(WHITE);
display.setTextSize(2);
display.setCursor(1, 0);
display.println("TEMP-Test");
display.display();
delay(2000);
display.clearDisplay();
display.display();
pinMode(btn_minus, INPUT_PULLUP); // Taster als Eingänge definieren
pinMode(btn_plus, INPUT_PULLUP);
state_minus = digitalRead(btn_minus); // Startzustand der Taster auslesen
state_plus = digitalRead(btn_plus);
}
void loop() {
currentMillis = millis(); // Start des millis-Timers
val_minus = digitalRead(btn_minus);
val_plus = digitalRead(btn_plus);
if (val_minus != state_minus) {
if (val_minus == LOW) {
set_temp--; // Bei Tastendruck -> Temperatur um 1 verringern
}
}
state_minus = val_minus;
if (val_plus != state_plus) {
if (val_plus == LOW) {
set_temp++; // Bei Tastendruck -> Temperatur um 1 erhöhen
}
}
state_plus = val_plus;
if (currentMillis - startMillis >= period) {
temp_out.requestTemperatures(); // Abfrage der Temperatursensoren
temp_in_l.requestTemperatures();
temp_in_r.requestTemperatures();
display.clearDisplay();
display.setTextColor(WHITE);
display.setTextSize(0.5);
display.setCursor(1, 0);
out_temp = temp_out.getTempCByIndex(0); // Speichern der Temperaturen in Variablen ohne Nachkommastellen
inl_temp = temp_in_l.getTempCByIndex(0);
inr_temp = temp_in_r.getTempCByIndex(0);
in_temp = ((inl_temp + inr_temp) / 2); // Mittelwert der beiden Temperatursensoren für den Innenbereich
display.print("Out: "); // Ausgabe der Werte auf dem OLED-Display
display.print(out_temp);
display.print(" IN: ");
display.println(in_temp);
display.print("In-L: ");
display.print(inl_temp);
display.print(" SET: ");
display.println(set_temp);
display.print("In-R: ");
display.println(inr_temp);
display.print("Angle: "); // Aktueller Servo-Winkel
display.println(angle);
display.display();
startMillis = millis(); // millis-Timer zurücksetzen
}
if (in_temp > set_temp && angle < 135) { // Anpassen des Servowinkels bei Temperaturabweichung (135° = Kalt)
angle++;
servo.write(angle);
delay(200);
}
if (in_temp < set_temp && angle > 45) { // Anpassen des Servowinkels bei Temperaturabweichung (45° = Warm)
angle--;
servo.write(angle);
delay(200);
}
if (angle < 45) { // Servo-Winkel begrenzen
angle = 45;
}
if (angle > 135) {
angle = 135;
}
}