Forum: Mikrocontroller und Digitale Elektronik Arduino Probleme mit SoftWire (SoftI2CMaster)


von Matthias S. (jadermatze)


Lesenswert?

Hallo,

ich möchte die SoftWire Bibliothek für ein Projekt verwenden aber hab 
hier irgendwie Probleme und gerade einen Knoten im Kopf 
(Verständnisproblem).

Ich möchte also die SoftWire.h verwenden anstatt der Wire.h von Arduino

   https://github.com/felias-fogg/SoftI2CMaster

Laut Dokumentation auf der Seite kann mann die SoftWire verwenden um die 
Wire.h zu "emulieren"
1
#define SDA_PORT ...
2
...
3
#include <SoftWire.h>
4
SoftWire Wire = SoftWire();
5
...
6
setup() {
7
    Wire.begin()
8
...
9
}

habe also ganz einfach folgenden Sketch:
1
#define SDA_PIN 3 
2
#define SDA_PORT PORTD
3
#define SCL_PIN 5
4
#define SCL_PORT PORTB
5
#define I2C_FASTMODE 1
6
#include "SoftWire.h"
7
8
SoftWire Wire = SoftWire();
9
10
void setup() 
11
{
12
    Wire.begin();    
13
}
14
15
void loop()
16
{
17
  //..
18
}

aber hier bekomme ich schon den Fehler:

  SoftI2CMaster.h:853: error: 'SDA_PIN' was not declared in this scope

Das kann ich lösen indem ich die #define Anweisungen einfach in die 
SoftWire.h geschrieben habe.

Jetzt aber das nächste und eigentliche Problem, ich verwende noch eine 
Andere Bibliothek die normalerweise auf die Wire.h zugreift sobald ich 
aber wie oben die SoftWire verwende bekomme ich nur angezeigt das er 
Wire nicht finden kann.

Irgendjemand eine Idee?

Gruß Matthias

von Dumpf Backe (Gast)


Lesenswert?

Matthias S. schrieb:
> Irgendjemand eine Idee?
1
#include <SoftI2CMaster.h>
statt
1
#include "SoftWire.h"

So tun es zumindest Beispiele zum Arduino.

von Dumpf Backe (Gast)


Lesenswert?

Dumpf  Backe schrieb:
> So tun es zumindest Beispiele zum Arduino.

Deine Softwire Bibliothek muss natürlich trotzdem vorhanden sein.

von Matthias S. (jadermatze)


Lesenswert?

Hier noch mal die ganzen files die ich verwende zum besseren 
Verständnis. Ich denke das ich hier einfach etwas falsch mache:

main.ino
1
#include "SoftWire.h"
2
3
SoftWire Wire = SoftWire();
4
5
void setup() 
6
{
7
    Wire.begin();    
8
}
9
10
.
11
.
12
.

SoftWire.h
1
#ifndef _SoftWire_h
2
#define _SoftWire_h
3
4
#define SDA_PIN 3 
5
#define SDA_PORT PORTD
6
#define SCL_PIN 5
7
#define SCL_PORT PORTB
8
#define I2C_FASTMODE 1
9
10
SoftWire Wire = SoftWire();
11
12
#include "SoftI2CMaster.h"
13
#include <inttypes.h>
14
#include "Stream.h"
15
16
.
17
.
18
.

I2Cdev.h
1
#ifndef _I2CDEV_H_
2
#define _I2CDEV_H_
3
4
#include "Arduino.h"
5
//#include <Wire.h>
6
#include "SoftWire.h"
7
8
.
9
.
10
.

I2Cdev.cpp
1
#include "I2Cdev.h"
2
/** Default constructor.
3
 */
4
5
I2Cdev::I2Cdev() 
6
{
7
    //..
8
}
9
.
10
.
11
.
12
int8_t I2Cdev::readBytes(uint8_t devAddr, uint8_t regAddr, uint8_t length, uint8_t *data, uint16_t timeout) 
13
{
14
    int8_t count = 0;
15
    uint32_t t1 = millis();
16
17
    for (uint8_t k = 0; k < length; k += min(length, BUFFER_LENGTH)) 
18
    {
19
        Wire.beginTransmission(devAddr);
20
        Wire.write(regAddr);
21
        Wire.endTransmission();
22
        Wire.beginTransmission(devAddr);
23
        Wire.requestFrom(devAddr, (uint8_t)min(length - k, BUFFER_LENGTH));
24
        
25
        for (; Wire.available() && (timeout == 0 || millis() - t1 < timeout); count++) 
26
        {
27
            data[count] = Wire.read();
28
            
29
            #ifdef I2CDEV_SERIAL_DEBUG
30
                Serial.print(data[count], HEX);
31
                if (count + 1 < length) Serial.print(" ");
32
            #endif
33
        }
34
    }
35
36
    // check for timeout
37
    if (timeout > 0 && millis() - t1 >= timeout && count < length) count = -1; // timeout
38
39
    #ifdef I2CDEV_SERIAL_DEBUG
40
        Serial.print(". Done (");
41
        Serial.print(count, DEC);
42
        Serial.println(" read).");
43
    #endif
44
45
    return count;
46
}
47
.
48
.
49
.

: Bearbeitet durch User
von Matthias S. (jadermatze)


Lesenswert?

Dumpf  Backe schrieb:
> Dumpf  Backe schrieb:
>> So tun es zumindest Beispiele zum Arduino.
>
> Deine Softwire Bibliothek muss natürlich trotzdem vorhanden sein.

Aber in der Doku steht ja:

Meanwhile, I have written a wrapper around SoftI2CMaster that emulates 
the Wire library (master mode only). It is another C++-header file 
called SoftWire.h, which you need to include instead of SoftI2CMaster.h. 
The ports and pins have to be specified as described above. After the 
include statement you need to create a SoftWire instance:

von Stefan F. (Gast)


Lesenswert?

Wofür gibt es eigentlich Konstruktor-Argumente?

von Matthias S. (jadermatze)


Lesenswert?

Stefan U. schrieb:
> Wofür gibt es eigentlich Konstruktor-Argumente?

Was genau willst du mir damit sagen? Ich muss zugeben dass ich aus dem 
ganzen C/C++ schon eine weile raus bin und erst wieder einsteige.

von Matthias S. (jadermatze)


Lesenswert?

Also wie gesagt bin schon ein bisschen raus aus der ganzen C/C++ 
Geschichte.

Vielleicht kann mir ja jemand einen ganz einfachen Tipp geben wo ich was 
einbinden muss damit die main.ino & I2Cdev.cpp die Instanz Wire vom Typ 
SoftWire kennen....

Gruß Matthias

von Stefan F. (Gast)


Lesenswert?

> Was genau willst du mir damit sagen?

Kritik an der "Library" üben.

Ich finde es ziemlich seltsam (um es nicht "falsch" zu nennen), dass ich 
ein Objekt durch konstante Definitionen konfigurieren muss. Wie soll man 
denn mehrere Instanzen von dem Objekt gleichzeitig verwenden, die 
unterschiedlich konfiguriert sind?

Normalerweise würde man schreiben:
1
SoftWire wire1(PORTD,3,PORTB,1);
2
SoftWire wire2(PORTD,4,PORTB,2);

Bzw. wenn man es konsequent im Arduino Style macht, würde man nur die 
(Arduino-)Pin-Nummern als Argumente angeben.

> Vielleicht kann mir ja jemand einen ganz einfachen Tipp geben

Wenn das jetzt nicht Arduino wäre, hätte ich Dir empfohlen, die 
Definitionen ins Makefile zu schreiben, damit sie dem Compiler als "-D" 
Parameter übergeben werden. So macht man das nämlich normalerweise. Aber 
das geht ja nicht, du hast kein Makefile.

Also sollte man es doch ordentlich mit Konstruktor-Argumenten 
programmieren, dafür müsstest du aber die Library umschreiben.

von Matthias S. (jadermatze)


Lesenswert?

Stefan U. schrieb:
> Normalerweise würde man schreiben:SoftWire wire1(PORTD,3,PORTB,1);
> SoftWire wire2(PORTD,4,PORTB,2);

Ok da stimme ich dir zu ist auch kein großes Problem hier einen 
entsprechenden Konstruktor einzubinden.

Das eigendliche Problem an dem ich leider immer noch hänge ist aber wie 
die "Wire" (SoftWire Wire = SoftWire()) in der I2Cdev.h & main.ino 
gleichermaßen nutzen kann. Wie gesagt ich glaube hab hier einfach gerade 
einen Denkfehler....

von Matthias S. (jadermatze)


Angehängte Dateien:

Lesenswert?

Hier mal das Beispiel Projekt

von Stefan F. (Gast)


Lesenswert?

Du kannst das Schlüsselwort "extern" benutzen, um auf globale Variablen 
zuzugreifen, die woanders "zu hause" sind. Beispiel:

Datei file1.ino:
1
int i=0;

Datei file2.ino:
1
extern int i;

Etwas sauberer wäre es, eine Getter-Funktion bereit zu stellen, die über 
eine Header-Datei eingebunden wird.

von Matthias S. (jadermatze)


Lesenswert?

Hilft leider auch nicht... :-(

von Matthias S. (jadermatze)


Lesenswert?

Ich schreie noch mal ganz leise nach Hilfe :-(

von Stefan F. (Gast)


Lesenswert?

Wobei brauchst du Hilfe? Du musst schon etwas konkreter werden oder 
jemanden zu Dir nach hause einladen, der sich dein Projekt mal vor Ort 
anschaut.

von Einer K. (Gast)


Lesenswert?

Matthias S. schrieb:
> Ich schreie noch mal ganz leise nach Hilfe :-(

Also, mich würde interessieren: Wozu SoftI2C?

von Joachim B. (jar)


Lesenswert?

Arduino F. schrieb:
> Also, mich würde interessieren: Wozu SoftI2C?

nun ja eine Idee hätte ich,

am ESP32 gibt es funktionierende I2C LIBs, die laufen genau wie auf 
meinem Arduino mit OLED und RTC 3231.

Dann habe ich ein Lora ESP32 mit aufgesetztem OLED gekauft und der I2C 
Scanner bleibt stumm, I2C RTC und I2C EEPROM wird nicht erkannt, da wird 
irgendeine andere selbstgebastelte I2C Lösung verwendet, da käme mir in 
den Sinn wieder die "normale" dafür zu nutzen.

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.