SD-Card Daten speichern

Hallo Leute,

Ich versuche für ein Messtechnikprojekt zwei Winkel zu messen und anschließend die Werte alle 10ms auf einer SD-Karte zu speichern.
Das Problem: Die Datei wird nicht auf der SD-Karte erstellt.

Verwende ich ein Beispielprogramm funktioniert das Speichern und auch das beschreiben der erstellten Datei. Gehe ich allerdings dann in meinem Programm nach dem gleichen Prinzip vor, wird nichtmal die gewünschte Datei erstellt. Bin Anfänger und verstehe leider das Problem nicht.
Für jeden Rat bin ich dankbar.
Codes füg ich ein.

//MEINCODE
#include <Wire.h>
#include <SPI.h>
#include <SD.h>
#define MPU6050_ADRESS1 0x68
#define MPU6050_ADRESS2 0x69

const int ACCEL_OFFSET   = 200;
long timer=0;
long timeout=10;
int accValue1[3], accAngle1[3], accValue2[3],accAngle2[3] ,accCorr2, accCorr1;

File data;
void setup()
{
  pinMode(3,INPUT);
  pinMode(10,OUTPUT);
  SD.begin();
  if(!SD.begin(10))
  {
    Serial.print("Fehler SD-Karte");
    return;
  }
  data=SD.open("Messdaten.txt", FILE_WRITE);
  data.print("Linker SKI: ");
  data.print("rechter SKI: ");
  data.close();
  Wire.begin();
  Wire.beginTransmission(MPU6050_ADRESS1); // Begins a transmission to the I2C slave 
  Wire.write(0x6B); // PWR_MGMT_1 register
  Wire.write(0); // set to zero (wakes up the MPU-6050)
  Wire.endTransmission(true);
  Wire.beginTransmission(MPU6050_ADRESS2); // Begins a transmission to the I2C slave 
  Wire.write(0x6B); // PWR_MGMT_1 register
  Wire.write(0); // set to zero (wakes up the MPU-6050)
  Wire.endTransmission(true);
  Serial.begin(9600);
  Serial.flush();
  
}
void loop()
{
  if(millis()> timer+timeout)
  {
    timer=millis();
  if(digitalRead(3)==1)
  {
  Wire.beginTransmission(MPU6050_ADRESS1);
  Wire.write(0x3B); // starting with register 0x3B (ACCEL_XOUT_H) [MPU-6000 and MPU-6050 Register Map and Descriptions Revision 4.2, p.40]
  Wire.endTransmission(false); // the parameter indicates that the Arduino will send a restart. As a result, the connection is kept active.
  Wire.requestFrom(MPU6050_ADRESS1, 3*2, true); // request a total of 7*2=14 registers

  // "Wire.read()<<8 | Wire.read();" means two registers are read and stored in the same variable
  for(byte i=0; i<3; i++) {
    accValue1[i] = Wire.read()<<8 | Wire.read(); // reading registers: ACCEL_XOUT, ACCEL_YOUT, ACCEL_ZOUT
  }
Serial.print("Linker Ski: ");
 for(byte i=0;i<3;i++)
  {
  
    accCorr1 = accValue1[0]- ACCEL_OFFSET;
    accCorr1 = map(accCorr1, -16800, 16800, -90, 90);
    accAngle1[0] = constrain(accCorr1, -90, 90);
   // Serial.print(accAngle1[i]);
  //  Serial.print("\t");
  }
  Serial.print(accAngle1[0]);
  Wire.beginTransmission(MPU6050_ADRESS2);
  Wire.write(0x3B); // starting with register 0x3B (ACCEL_XOUT_H) [MPU-6000 and MPU-6050 Register Map and Descriptions Revision 4.2, p.40]
  Wire.endTransmission(false); // the parameter indicates that the Arduino will send a restart. As a result, the connection is kept active.
  Wire.requestFrom(MPU6050_ADRESS2, 3*2, true); // request a total of 3*2=14 registers

  // "Wire.read()<<8 | Wire.read();" means two registers are read and stored in the same variable
  for(byte i=0; i<3; i++) {
    accValue2[i] = Wire.read()<<8 | Wire.read(); // reading registers: ACCEL_XOUT, ACCEL_YOUT, ACCEL_ZOUT
  }

    Serial.print("| Rechter Ski: \t");
    for(byte i=0;i<3;i++)
    {
    accCorr2=accValue2[0]- ACCEL_OFFSET;
    accCorr2= map(accCorr2,-16800,16800,-90,90);
    accAngle2[0] = constrain(accCorr2,-90,90);
    //Serial.print(accAngle2[i]);
   // Serial.print("\t");
    }
 Serial.print(accAngle2[0]);
  Serial.println(" ");
  }
  }
  else
  {
    //data1.close();
    Serial.print("Messung beendet");

  }
 
}
//Beispielcode funktioniert
#include <SPI.h>
#include <SD.h>

File Datei;

void setup() {
  pinMode(10,OUTPUT);
  Serial.begin(9600);
  SD.begin();
  while(!Serial)
  {
    ;
  }
  if(!SD.begin(10))
  {
    Serial.println("Verbindung zur SD Karte fehlgeschlagen");
    return;
  }
    

  Datei = SD.open("daten.txt", FILE_WRITE);
  Datei.print("SERVUS");
  Datei.print("ARDUINO");
  Datei.close();
  Serial.println("Fertig");
}


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

}

Im englischen Teil des Forum müssen die Beiträge und Diskussionen in englischer Sprache verfasst werden. Deswegen wurde diese Diskussion in den deutschen Teil des Forums verschoben.

mfg ein Moderator.

1 Like

Das ist falsch!
Niemals vorwärts rechnen!

Dein Problem:

Das führst Du nur einmal aus.
Das setup() wird nach dem ersten Durchlauf nie mehr erreicht.
Darum heisst es setup() :wink:

Und gib Deinen Pins Namen! Du suchst Dich später dumm und dämlich mit den Nummern...

//MEINCODE
#include <Wire.h>
#include <SPI.h>
#include <SD.h>
#define MPU6050_ADRESS1 0x68
#define MPU6050_ADRESS2 0x69

const int ACCEL_OFFSET   = 200;
long timer = 0;
long timeout = 10;
int accValue1[3], accAngle1[3], accValue2[3], accAngle2[3], accCorr2, accCorr1;

File data;
void setup()
{
  pinMode(3, INPUT);
  pinMode(10, OUTPUT);
  SD.begin();
  if (!SD.begin(10))
  {
    Serial.print("Fehler SD-Karte");
    return;
  }
  Wire.begin();
  Wire.beginTransmission(MPU6050_ADRESS1); // Begins a transmission to the I2C slave
  Wire.write(0x6B); // PWR_MGMT_1 register
  Wire.write(0); // set to zero (wakes up the MPU-6050)
  Wire.endTransmission(true);
  Wire.beginTransmission(MPU6050_ADRESS2); // Begins a transmission to the I2C slave
  Wire.write(0x6B); // PWR_MGMT_1 register
  Wire.write(0); // set to zero (wakes up the MPU-6050)
  Wire.endTransmission(true);
  Serial.begin(9600);
  Serial.flush();
}
void loop()
{
  if (millis() - timer > timeout)
  {
    timer = millis();
    if (digitalRead(3) == 1)
    {
      Wire.beginTransmission(MPU6050_ADRESS1);
      Wire.write(0x3B); // starting with register 0x3B (ACCEL_XOUT_H) [MPU-6000 and MPU-6050 Register Map and Descriptions Revision 4.2, p.40]
      Wire.endTransmission(false); // the parameter indicates that the Arduino will send a restart. As a result, the connection is kept active.
      Wire.requestFrom(MPU6050_ADRESS1, 3 * 2, true); // request a total of 7*2=14 registers
      // "Wire.read()<<8 | Wire.read();" means two registers are read and stored in the same variable
      for (byte i = 0; i < 3; i++)
      {
        accValue1[i] = Wire.read() << 8 | Wire.read(); // reading registers: ACCEL_XOUT, ACCEL_YOUT, ACCEL_ZOUT
      }
      Serial.print("Linker Ski: ");
      for (byte i = 0; i < 3; i++)
      {
        accCorr1 = accValue1[0] - ACCEL_OFFSET;
        accCorr1 = map(accCorr1, -16800, 16800, -90, 90);
        accAngle1[0] = constrain(accCorr1, -90, 90);
        // Serial.print(accAngle1[i]);
        //  Serial.print("\t");
      }
      Serial.print(accAngle1[0]);
      Wire.beginTransmission(MPU6050_ADRESS2);
      Wire.write(0x3B); // starting with register 0x3B (ACCEL_XOUT_H) [MPU-6000 and MPU-6050 Register Map and Descriptions Revision 4.2, p.40]
      Wire.endTransmission(false); // the parameter indicates that the Arduino will send a restart. As a result, the connection is kept active.
      Wire.requestFrom(MPU6050_ADRESS2, 3 * 2, true); // request a total of 3*2=14 registers
      // "Wire.read()<<8 | Wire.read();" means two registers are read and stored in the same variable
      for (byte i = 0; i < 3; i++)
      {
        accValue2[i] = Wire.read() << 8 | Wire.read(); // reading registers: ACCEL_XOUT, ACCEL_YOUT, ACCEL_ZOUT
      }
      Serial.print("| Rechter Ski: \t");
      for (byte i = 0; i < 3; i++)
      {
        accCorr2 = accValue2[0] - ACCEL_OFFSET;
        accCorr2 = map(accCorr2, -16800, 16800, -90, 90);
        accAngle2[0] = constrain(accCorr2, -90, 90);
        //Serial.print(accAngle2[i]);
        // Serial.print("\t");
      }
      Serial.print(accAngle2[0]);
      Serial.println(" ");
      data = SD.open("Messdaten.txt", FILE_WRITE);
      data.print("Linker SKI: ");
      data.print(accAngle1[0]);  // what ever....
      data.print("rechter SKI: ");
      data.print(accAngle2[0]);
      data.close();
    }
  }
  else
  {
    //data1.close();
    Serial.print("Messung beendet");
  }
}
1 Like

Alles klar danke. Timer ändere ich sofort.

Ja, das mit dem Setup ist mir klar. Hier hab ich versucht, ob eine Datei erstellt wird, das sollte ja auch passieren, wenn ich das im Setup mache oder?
Aber die Datei wird irgendwie nicht erstellt.

Danke schonmal

Hallo,
dann schaue Dir das Beispiel noch mal genau an. Da gibt es einen Anschnitt bei dem auf die SD Karte geschrieben wird.

Diesen Abschnitt vermisse ich in Deinem ersten Sketch völlig. Kann es sein das Du ein Problem damit hast aus den beiden Programen eines zu machen ?
Ob das allerdings in 10ms dann geht weiß ich nicht. Das SD Filesystem ist nicht das schnellste. bei 100 ms hätte ich erst mal keine Bedenken. Schau Dir auch noch mal die Sache mit millis() an . An Deiner Abfrage wirst Du nicht lange Freude haben.

if(millis()> timer+timeout)

zudem sollte timer eine Variable vom Typ "unsigned long oder "uint32_t" sein. Dazu noch mal das Beispiel "blinkWithoutDelay" studieren.

if (millis() - vorhin >= zyklus)

verhindert einen Fehler bei einem Überlauf von millis()

Fang mit 1s an und taste dich dann runter ansonsten ballerst Du dir die SD Karte voll und kannst es schlecht testen. Zudem würde ich einen Zeitstempel mit auf die Karte schreiben. Das könnte der millis() wert der Messung sein.

Heinz

1 Like

Ist zu lang, max ist 8.3, kürze das 'Messdaten.txt'

2 Likes

... und setz das Serial.begin an den Anfang von Setup - sonst siehst die Fehlermeldungen von deinem SD Start nicht. Es ist fast 2023 ... 9600 ist aus den 70ern.

Danke für die schnelle Hilfe! Hab jetzt das delay raus. Das Hauptproblem war anscheinend, dass der Dateiname zu lang war. Den gekürzt, zack ist die Datei auf der SD-Karte. Hab dann die Befehle zum beschreiben der SD-Karte in den loop rein und geht. Vielen Dank nochmals allen.

VG

Lukas

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