Forum: Projekte & Code SSD1306/1309 Library zum Darstellen von Text auf OLED Displays


von M. K. (sylaina)


Lesenswert?

Tuffi schrieb:
> Ich brauche
> am besten 2 weitere, eine die doppelt so groß ist und eine 4x so große.

Eine vier mal so große Schrift habe ich leider nicht. Aber es gibt eine 
Funktion, die die Schriftgröße verdoppelt. Die Funktion heißt 
lcd_charMode(uint8_t mode). Standard ist der Mode auf 1 eingestellt. 
Übergibst du der Funktion bei Aufruf eine 2 wird fortan die doppelte 
Schriftgröße verwendet. Hierzu gibt es zur Besseren Lesbarkeit auch zwei 
Makros, einmal NORMALSIZE (entspricht einer 1) und DOUBLESIZE 
(entspricht einer 2). Spiele damit ein wenig herum, nicht überall wird 
berücksichtigt welche Schriftgröße eingestellt ist, z.B. muss du bei 
einem Zeilenumbruch bei eingestellter doppelter Schriftgröße zwei Zeilen 
weiter springen statt nur eine.

Eigene Schriften lassen sich auch erstellen. Dafür gibts 
Schriftgeneratoren. Bedenke dabei aber, dass die Zeilengröße "nur" 8 
Pixel hoch ist, der Code berücksichtigt höhere Schriften nicht.

: Bearbeitet durch User
von Johannes S. (Gast)


Lesenswert?

Der Vorteil der Lib von M.K. ist die geringe Größe und wenig RAM Bedarf, 
aber die Fonts durch Pixel vervielfachen sehen dann entsprechend grob 
aus. Da gibt es schönere Fonts, die brauchen dann aber mehr Platz im 
Flash und es ist ein Framebuffer nötig, sonst flimmert es. Da hat die 
Adafruit Lib schöne Fonts drin und es gibt auch Generatoren um weitere 
zu erzeugen

https://youtu.be/Y0nxLMqq1Jk

von Tuffi (Gast)


Lesenswert?

Das mit der DOUBLESIZE wäre interessant, meine Lib hat die FUnktionen 
nicht? Wo bekomme ich die her?!

von M. K. (sylaina)


Lesenswert?

Zieh dir die Lib von github, da ist immer die aktuelle Version:

http://www.github.com/sylaina/oled-display/

: Bearbeitet durch User
von Was Costas (Gast)


Lesenswert?

Hat jemand eigentlich inzwischen mal ein zum restlichen Font passendes 
Omega-Zeichen designt und implementiert und würde es hier posten?

von M. K. (sylaina)


Lesenswert?

Was Costas schrieb:
> Hat jemand eigentlich inzwischen mal ein zum restlichen Font
> passendes
> Omega-Zeichen designt und implementiert und würde es hier posten?

Ich hab grad mal aus dem Stehgreif das Spezial-Char-Set erweitert um Ω 
und ω, meintest du das? Kannst du jetzt aus dem github herunterladen. 
Testen kann ich frühestens morgen.

von Was Costas (Gast)


Lesenswert?

Supi. Danke.

von M. K. (sylaina)


Angehängte Dateien:

Lesenswert?

So, konnte es mir jetzt auch noch mal anschauen und musste ein klein 
wenig nachbessern aber jetzt schauts gut aus (vgl. Anhang). Ich musste 
auch das Makefile anpassen da durch Ω und ω nun das charset UTF-8 nicht 
mehr funktioniert.

von Nano (Gast)


Lesenswert?

M. K. schrieb:
> konnte es mir jetzt auch noch mal anschauen

Hast Du dazu einen Beispielcode, den die Arduino-IDE verarbeiten mag?

von M. K. (sylaina)


Lesenswert?

Nano schrieb:
> M. K. schrieb:
>
>> konnte es mir jetzt auch noch mal anschauen
>
> Hast Du dazu einen Beispielcode, den die Arduino-IDE verarbeiten mag?

Die Library ist in C geschrieben aber auch zu C++ kompatibel, du kannst 
die Funktionen 1:1 auch in Arduino-Projekten verwenden. ;)

von Kinderschokolade (Gast)


Lesenswert?

ich hoffe es ist ok diesen Beitrag nach einigen Jahren wieder 
hervorzukramen. Eine super Bibliothek! Gibt es eine Möglichkeit die 
Anzeige um 180° zu drehen?

von Frank D. (Firma: Spezialeinheit) (feuerstein7)


Lesenswert?

Ich habe gerade keine Lust im Datenblatt zu suchen, aber ich glaube mich 
erinnern zu können, dass es dafür ein Befehl für das Display gibt. Also 
nur ein Bit setzen und fertig.

von Kinderschokolade (Gast)


Lesenswert?

Das dachte ich auch.
Im Datenblatt unter 10.1.14 Set COM Output Scan Direction müsste man es 
theoratisch mit (C0h/C8h) umschalten können. Habe diese Stelle 
angepasst.
Das Display zeigt nun tatsächlich um 180° gedreht, allerdings auch 
spiegelverkehrt :D
1
// Init Sequence of SSD Display
2
static const uint8_t init_sequence [] PROGMEM = {  // Initialization Sequence
3
LCD_DISP_OFF,      // Display OFF (sleep mode)
4
0x20, 0b00,    // Set Memory Addressing Mode
5
        // 00=Horizontal Addressing Mode; 01=Vertical Addressing Mode;
6
        // 10=Page Addressing Mode (RESET); 11=Invalid
7
0xB0,      // Set Page Start Address for Page Addressing Mode, 0-7
8
0xC0,                  // Set COM Output Scan Direction //Vorher: 0xC8 
9
0x00,      // --set low column address
10
0x10,      // --set high column address
11
0x40,      // --set start line address
12
0x81, 0x3F,    // Set contrast control register
13
0xA1,      // Set Segment Re-map. A0=address mapped; A1=address 127 mapped.
14
0xA6,      // Set display mode. A6=Normal; A7=Inverse
15
0xA8, DISPLAY_HEIGHT-1,    // Set multiplex ratio(1 to 64)
16
0xA4,      // Output RAM to Display
17
        // 0xA4=Output follows RAM content; 0xA5,Output ignores RAM content
18
0xD3, 0x00,    // Set display offset. 00 = no offset
19
0xD5,      // --set display clock divide ratio/oscillator frequency
20
0xF0,      // --set divide ratio
21
0xD9, 0x22,    // Set pre-charge period
22
0xDA, 0x12,    // Set com pins hardware configuration    
23
0xDB,      // --set vcomh
24
0x20,      // 0x20,0.77xVcc
25
0x8D, 0x14,    // Set DC-DC enable
26
};

von M. K. (sylaina)


Lesenswert?

Ja, man kann die Anzeige um 180° drehen. In meiner Library ist diese 
Funktionalität aber noch nicht implementiert da ich selbst diese 
Funktionalität noch nicht benötigt habe (ähnlich wie das Scrollen). Da 
werde ich mich am WE mal dran setzen und das integrieren.

von Kinderschokolade (Gast)


Lesenswert?

Das wäre ja super. Dafür vorab schonmal einen dicken Dank!

von J. S. (jojos)


Lesenswert?

ich habe das mal in eine ältere Version der Adafruit_GFX eingebaut, die 
codes waren:
1
void Adafruit_UC1601S::flipVertical(bool flip) {
2
  _flipVertical = flip;
3
  if (flip) {
4
    command(LCD_SET_MAPPING_CTRL | 0b000);// flip vertical / horizontal
5
    command(LCD_SET_RAM_ADDRESS_CTRL | 0b101);  //
6
    command(LCD_SET_COM_END);
7
    command(21);                // Rows - 1
8
  } else {
9
    command(LCD_SET_MAPPING_CTRL | 0b100);// flip vertical / horizontal
10
    command(LCD_SET_RAM_ADDRESS_CTRL | 0b001);  //
11
    command(LCD_SET_COM_END);
12
    command(21);                // Rows - 1
13
  }
14
}

von Stefan F. (Gast)


Lesenswert?

J. S. schrieb:
> UC1601S

Sind wir hier noch beim gleichen Display Controller? Nach meinem 
Kenntnisstand kann der SSD1306 das Bild nicht drehen.

von J. S. (jojos)


Lesenswert?

Stefan F. schrieb:
> Sind wir hier noch beim gleichen Display Controller?

du hast Recht, habe die Lib für beide Controller und bin im falschen 
gelandet.
1
    if (_flipVertical) {
2
        command(SSD1306_SEGREMAP | 0x0);
3
        command(SSD1306_COMSCANINC);
4
    } else {
5
        command(SSD1306_SEGREMAP | 0x1);
6
        command(SSD1306_COMSCANDEC);          // flip vertically
7
    }

ist schon länger her, aber müsste funktionieren.
ja, der Kommentar ist blöde, müsste eigentlich in den anderen Zweig. 
Lange her...

: Bearbeitet durch User
von Kinderschokolade (Gast)


Lesenswert?

habe mal einen Versuch gewagt und das hier direkt nach der Init-Sequenz 
aufgerufen:
1
void lcd_flip_vertical(){  //Neu hinzugefügte Funktion
2
   uint8_t SSD1306_SEGREMAP = 0xA0;
3
   uint8_t SSD1306_COMSCANINC = 0xC0;
4
   lcd_command(SSD1306_SEGREMAP | 0x0, sizeof(SSD1306_SEGREMAP));
5
   lcd_command(SSD1306_COMSCANINC, sizeof(SSD1306_COMSCANINC));
6
}
Das funktioniert leider nicht. Zeigt dann nur Müll an...

von J. S. (jojos)


Lesenswert?

Kann ich mir morgen nochmal ansehen, sitze ausnahmsweise mal nicht am 
PC.

von Kinderschokolade (Gast)


Lesenswert?

Danke euch für die schnellen Antworten.
Habe es nun dank der Tipps mit dieser Funktion hinbekommen:
1
void lcd_flip_vertical(){  //Neu hinzugefügte Funktion
2
   uint8_t SSD1306_SEGREMAP[2] = {0x80, 0xA0};
3
   uint8_t SSD1306_COMSCANINC[2] = {0x80, 0xC0};
4
   lcd_command(SSD1306_SEGREMAP, sizeof(SSD1306_SEGREMAP));
5
   lcd_command(SSD1306_COMSCANINC, sizeof(SSD1306_COMSCANINC));
6
}

von Stefan F. (Gast)


Lesenswert?

Kinderschokolade schrieb:
> abe es nun dank der Tipps mit dieser Funktion hinbekommen

Wird das Bild damit nun um 180° gedreht oder nur vertikal gespiegelt?

von Kinderschokolade (Gast)


Lesenswert?

>Wird das Bild damit nun um 180° gedreht oder nur vertikal gespiegelt?

oh du hast Recht ich habe meine Funktion falsch benannt. Also damit wird 
das Bild um 180° gedreht. Spiegeln geht auch. Dann muss man das Kommando 
SEGREMAP einfach weglassen....Schreit nach einer tollen Funktion oder? 
Der Author wollte ja noch drann. Er macht es dann vernünftig :D

von Stefan F. (Gast)


Lesenswert?

Läuft, danke.
Ich konnte das auch in meine (andere) Bibliothek einbauen:
1
void OLED::rotate_180(bool enable) 
2
{
3
    i2c.beginTransmission(i2c_address);
4
    i2c.write(0x00); // command
5
6
    if (enable) 
7
    {
8
        i2c.write(0xA0); // segment remapping mode
9
        i2c.write(0xC0); // COM output scan direction
10
    }
11
    else
12
    {
13
        i2c.write(0xA1); // segment remapping mode
14
        i2c.write(0xC8); // COM output scan direction
15
    }
16
    i2c.endTransmission();
17
}

von M. K. (sylaina)


Lesenswert?

Kinderschokolade schrieb:
> Er macht es dann vernünftig :D

Brauch ich nicht, hat Stefan schon gemacht ;)

Derzeit kämpfe ich noch mit der Funktion. Das Problem: Segment-Remap 
(horizontal flip) wirkt nicht auf den RAM-Inhalt des Displays, d.h. man 
muss die Daten neu zum Display schicken. COM Scan Direction (vertical 
flip) wirkt sofort auf den RAM-Inhalt. kniffelig.

von J. S. (jojos)


Lesenswert?

Ich hatte die Funktion im Konstruktor benutzt, also nur einmal die 
Ausrichtung beim Start gesetzt. Das wird sicher schon für viele 
Anwendungen reichen.

von Tobiasz Topyla (Gast)


Lesenswert?

Der TEXTMODE 6x8 Font sieht sehr gut aus. Vielen herzlichen Dank für 
diese Lösung.

von M. K. (sylaina)


Lesenswert?

So, ich hab die Möglichkeit, das Display bzw. den Inhalt entsprechend zu 
spiegeln, implementiert. Man hat die Wahl zwischen horizontal spiegeln, 
vertikal zu spiegeln oder horizontal & vertikal zu spiegeln.

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.