Loop Durchgang sehr langsam durch Schleifen?! (Graph mit SPI OLED Display)

Also
ich habe jetzt einfach mal alle float's auf int geändert - ohne die 1000er Anpassung etc.
Die Geschwindigkeit ist leider nach wie vor (im Haupt-Code) langsam. :o

Ich werde wohl den Code neu erstellen müssen da ja der Test-Code richtig gut läuft. Vielleicht finde ich dann den Fehler oder die Stelle, wo es langsam wird.

Recht komisch wie ich finde. Irgendwo ist da der Wurm drin.

Das einzige was halt dazukommen würde wäre der Kalibrierungs-Teil, wo der Mittelwert nach einer gewissen Zeit neu gebildet wird und dann nur eine Hand voll Grafischer Verschönerungen - hier mal nen Rahmen und da mal nen gefülltes Rechteck - und dann noch 4 ausgegebene Zahlen bzw. Textpassagen auf dem Display.

Hallo,

Also mich hat das jetzt auch mal interessiert was da so machbar ist.

Messung einer analogen Spannung , alternativ Simulation mit random(). Messrate 100ms. Die Function zur Verwaltung des Arrays und die Ausgabe auf die Anzeige hat eine Laufzeit von ca 70ms. Wenn man da ein richtiges Schieberegister (Zeiger) einsetzen würde können noch ein paar ms drin sein. Die Grafik sieht "fliessend" aus kein Flackern zu sehen.

Die Verarbeitung der Messwerte für die Grafik erfolgt als Integer , skaliert für das Display (map) . Zur numerischen Ausgabe des Messwertes in Volt wird der Messwert als Float verarbeitet.

Interessant ist die Tatsasche das wenn man im Beispiel die ranom(-500,500) ändert auf random(50,50) die Laufzeit nur noch 40ms ist. Ursache dürfte die kleinere Anzahl der zu übertragenden Punkte sein.

Heinz

/*Test zeitlicher Verlauf einer Analogspannnung darstellen
   Hardware UNO, Display 128x64 i2c Bus.

*/
#include <SPI.h>
#include <Wire.h>
#include <Adafruit_SSD1306.h>
#define SCREEN_WIDTH 128 // DISP display width, in pixels
#define SCREEN_HEIGHT 64 // DISP display height, in pixels
#define DISP_RESET -1

Adafruit_SSD1306 DISP(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, DISP_RESET);

int messwert[SCREEN_WIDTH];
int wert;
float wert_real;
uint32_t altzeit;

void setup() {
  // put your setup code here, to run once:

  Serial.begin(115200);
  DISP.begin(SSD1306_SWITCHCAPVCC, 0x3C);
  DISP.clearDisplay();
  DISP.setTextWrap(false);
  DISP.setTextSize(2);
  DISP.setTextColor(WHITE);
  DISP.setCursor(10, 10); DISP.print(F("Graf"));
  DISP.setTextSize(2);
  DISP.display();
  delay(3000);
}

void loop() {
  // put your main code here, to run repeatedly:

  if (millis() - altzeit >= 100) {
    altzeit = millis();
    //int w=analogRead(A0);
    int w = 500 + random(-500, 500); // zum testen
    wert = map(w, 0, 1023, 0, SCREEN_HEIGHT - 1); // scale für Grafik
    wert_real = w / 1023.0 * 5.0; // scale für reale Werte
    //Serial.print(wert_real); Serial.println("Volt");
    anzeige();
  }
}

void anzeige() {
  // Laufzeit ca. 70 ms
  static uint32_t startzeit;
  startzeit = millis();
  // Datenspeicher schieben
  for (byte x = 0; x < SCREEN_WIDTH - 1; x++) {
    messwert[x] = messwert[x + 1];
  }
  messwert[SCREEN_WIDTH - 1] = wert; // am ende eintragen
  DISP.clearDisplay();

  // Grafik ausgeben
  for (int x = 0; x < SCREEN_WIDTH - 1 ; x++) {
    DISP.drawLine(x, SCREEN_HEIGHT - messwert[x], x + 1, SCREEN_HEIGHT - messwert[x + 1], WHITE);
  }
  DISP.display();
  int dif = millis() - startzeit;
  Serial.println(dif);// Ausgabe Laufzeit
}

ALSO, jetzt habe ich mal den Code Stück für Stück zusammengepackt und ich habe den Fehler gefunden.

Was ich nicht erwähnt hatte war, dass ich auch noch eine Temperatur messe. Das passiert mit einem DS18B20 Sensor.
Ich hätte nie gedacht, dass dieser Sensor das Problem ist, darum kam er auch nicht zur Sprache.

Sobald ich

sensors.requestTemperatures();

in den Code einbringe, bricht die Geschwindigkeit ein also von 6ms auf 500ms :o

Ich habe Ihn wie im Beispiel eingebunden, also

#include <OneWire.h> 
#include <DallasTemperature.h>

#define ONE_WIRE_BUS 4 

OneWire oneWire(ONE_WIRE_BUS); 


DallasTemperature sensors(&oneWire);

Das einzige was geändert wurde ist dass der One Wire Pin 4 und nicht 2 ist.
Im Loop kommt dann

sensors.requestTemperatures();

und einlesen mache ich es bezogen auf die Bibliothek so

u8g2.print(sensors.getTempCByIndex(0),1);

Kann es an One Wire liegen?
Ich habe nur den Sensor von Dallas und ich meine einen NTC Widerstand.

WAMBO:
Kann es an One Wire liegen?

Nö, an Dir.

Lesen der Lib und des Datenblattes bringt Erkenntnisse.

Es gibt einen NoBlockingMode.
Da stößt Du die Messung mit requestTemperatures an und holst je nach Auflösung 500 bis 750 ms später den Messwert ab. In der Zwischenzeit kannst Du anderes machen.

Gruß Tommy

Hallo,
dann schau Dir mal das Beispiel waitForConversation aus der Dalles Lib an. Es geht auch ohne Wartezeit

Auszug aus dem Beispiel

 // Request temperature conversion - non-blocking / async
  Serial.println("Before NON-blocking/async requestForConversion");
  start = millis();       
  sensors.setWaitForConversion(false);  // makes it async
  sensors.requestTemperatures();
  sensors.setWaitForConversion(true);
  stop = millis();
  Serial.println("After NON-blocking/async requestForConversion");
  Serial.print("Time used: ");
  Serial.println(stop - start);

Heinz

Das anschließende sensors.setWaitForConversion(true); ist eher kontraproduktiv.
Einfach nach Ablauf der Wartezeit lesen.

Gruß Tommy

Hey, vielen Dank für die Hilfe

This topic was automatically closed 120 days after the last reply. New replies are no longer allowed.