- LiTime Speicher und Akkus         
Seite 1 von 3 123 LetzteLetzte
Ergebnis 1 bis 10 von 27

Thema: LCD (KS0066) 4Bit-Mode init brauche hilfe, PIC 18f4550

  1. #1
    Benutzer Stammmitglied
    Registriert seit
    20.07.2008
    Ort
    Herford
    Alter
    39
    Beiträge
    52

    LCD (KS0066) 4Bit-Mode init brauche hilfe, PIC 18f4550

    Anzeige

    LiFePo4 Akku selber bauen - Video
    Hallo PIC freunde ich hoffe ihr seid dieses Thema noch nicht leid, und könnt mir weiterhelfen, ich versuch es schon seit einer Woche ohne erfolg.

    Ich möchte ein 4x20 LCD im 4-Bit mode ansteuern LCD Treiber ist ein KS0066.

    Ich bekomme einfach kein Zeichen auf das LCD und manchmal sieht es nach einem reset so aus als wenn er im 1-Zeilenmodus wäre.

    Bitte helft mir ich komme nicht weiter ;(

    /************************************************** ************
    C18-compiler

    PortPin: Display
    RB0 = E
    RB2 = RS
    RB3 = R/W
    RB4..RB7 = D4..D7
    ************************************************** ***************************/


    /** I N C L U D E S ************************************************** ********/

    #include <p18f4550.h>
    #include <delays.h>


    /** D E F I N I T I O N S ************************************************** **/

    #define PORTLCD LATB
    #define TRIS_LCD TRISB
    #define LCD_E PORTBbits.RB0
    #define LCD_RS PORTBbits.RB2
    #define LCD_RW PORTBbits.RB3

    //************************************************** **************************

    #pragma code


    void delay100us(unsigned char multiplikator)
    // for PicLSBK (16MHz Taktzyklus = 4 MHz Befehlszyklus)
    {
    Delay10TCYx(40*multiplikator); //40*10*0,25µs = 100 µs
    }


    void LCD_BUSY(void)
    {
    unsigned char temp1;
    // unsigned char temp2;
    do
    {
    TRIS_LCD = 0xF0; // LCD-PORT = high nibbles:eingang; low nibbles:ausgang
    //Display abfrage
    LCD_RS = 0; // LCD im Befehls-Mode
    LCD_RW = 1; // LCD im Lesen-Mode
    LCD_E = 1; // Enable (LCD)
    temp1 = PORTLCD;
    temp1 = temp1 & 0xF0; // Niederw.Nibble (steuerbits) ausmaskieren
    LCD_E = 0; // toggeln

    LCD_E = 1; // Enable (LCD)
    // temp2 = PORTLCD;
    // temp2 = (temp2>>4)&0x0f;
    // temp2 = temp1 | temp2; // Nibbles verbinden
    LCD_E = 0; // toggeln
    } while (temp1>=0x80);

    delay100us(1);
    LCD_RW = 0; // Busy = low: LCD im Schreiben-Mode
    TRIS_LCD = 0x00; // LCD-PORT = Ausgänge
    PORTLCD = 0x00; // Daten und Steuerleitungen LOW
    }


    void LCD_WriteZeichen(unsigned char zeichen)
    {
    unsigned char x;

    LCD_BUSY(); // Warten bis LCD bereit ist

    // LCD_RW = 0; // LCD im Schreiben-Mode
    LCD_RS = 1; // LCD im Befehl-Mode

    x = zeichen & 0xf0;
    PORTLCD = x; //höherwertiges nibbel

    LCD_E = 1; // Enable (LCD)
    LCD_E = 0;


    x = zeichen;
    x = (x << 4)& 0xf0; //niederwertiges nibbel
    PORTLCD = x;

    LCD_E = 1; // Enable (LCD)
    LCD_E = 0;

    LCD_RS = 0;
    }


    void LCD_WriteString(char *String)
    {
    char zeichen;

    zeichen = *String;
    while(zeichen !='\0')
    {
    LCD_WriteZeichen(zeichen); // zeichen am LC-Display ausgeben
    String++;
    zeichen = *String;
    }
    }

    void LCD_WriteRegister(char data)
    {
    unsigned char x;

    LCD_BUSY(); // Warten bis LCD bereit ist

    // LCD_RW = 0; // LCD im Schreiben-Mode
    // LCD_RS = 0; // LCD im Befehl-Mode

    x = data & 0xf0;
    PORTLCD = x; //höherwertiges nibbel

    LCD_E = 1; // Enable (LCD)
    LCD_E = 0;


    x = data;
    x = (x << 4)& 0xf0; //niederwertiges nibbel
    PORTLCD = x;

    LCD_E = 1; // Enable (LCD)
    LCD_E = 0;
    }



    void LCD_Init(void)
    {
    // LCD initialisieren

    TRIS_LCD = 0x00; // LCD-PORT = Ausgänge
    PORTLCD = 0x00; // Daten und Steuerleitungen LOW


    delay100us (150);
    delay100us (150); // warte über 30ms
    delay100us (2);

    PORTLCD = 0x30; // Interface auf 8-Bit setzen
    LCD_E = 1; // Enable (LCD)
    LCD_E = 0;
    delay100us(45);
    // Interface auf 8-Bit setzen
    LCD_E = 1; // Enable (LCD)
    LCD_E = 0;
    delay100us(45);
    // Interface auf 8-Bit setzen
    LCD_E = 1; // Enable (LCD)
    LCD_E = 0;
    delay100us(45);

    PORTLCD = 0x20; // Interface auf 4-Bit setzen
    LCD_E = 1; // Enable (LCD)
    LCD_E = 0;

    LCD_WriteRegister(0x2; // 2-zeilig, 5x8-Punkt-Matrix
    LCD_WriteRegister(0x0; // Display aus
    LCD_WriteRegister(0x01); // Display löschen
    LCD_WriteRegister(0x02); // Kursor nach rechts wandernd, kein Display-Shift
    LCD_WriteRegister(0x0C); // Display ein [ 0x0C = ein, 0x08 = aus ]
    }


    void main (void)
    {
    LCD_Init();
    LCD_WriteZeichen('t');
    LCD_WriteZeichen('e');
    LCD_WriteZeichen('s');
    LCD_WriteZeichen('t');
    }

  2. #2
    Moderator Robotik Visionär Avatar von radbruch
    Registriert seit
    27.12.2006
    Ort
    Stuttgart
    Alter
    61
    Beiträge
    5.799
    Blog-Einträge
    8
    Hallo

    Code:
    ...
    LCD_E = 1; // Enable (LCD) 
    LCD_E = 0;
    ...
    Sollte da nicht noch eine kleine Verzögerung dazwischen sein? Ich weiß nicht wie schnell so ein PIC ist, aber laut Datenblatt (Seite 31ff) sollte E min. 230ns (tw) high sein.

    Gruß

    mic
    Bild hier  
    Atmel’s products are not intended, authorized, or warranted for use
    as components in applications intended to support or sustain life!

  3. #3
    Benutzer Stammmitglied
    Registriert seit
    20.07.2008
    Ort
    Herford
    Alter
    39
    Beiträge
    52
    habe schon einen nop zwischen gelegt entspricht 0,25 µs. klappt leider auch nicht.

    und ich habe noch nen fehler in der LCD_WriteZeichen gefunden
    jetzt wird LCD_RS auch auf 1 gesetzt,
    früher wurde es mit 0 überschrieben.

    leider immernoch ohne erfolg

  4. #4
    Moderator Robotik Visionär Avatar von radbruch
    Registriert seit
    27.12.2006
    Ort
    Stuttgart
    Alter
    61
    Beiträge
    5.799
    Blog-Einträge
    8
    Hallo

    Das nop würde ich auf jeden Fall mal drinlassen, eventuell (zum Testen) sogar ein zweites. Poste doch nochmal den aktuellen Code (in code-Tags), speziell wegen dem RS- und dem RW-Bit. Ich würde RS generell auf High setzen und nur während des Inits (und bei Steuerbefehlen wie clear) auf Low schalten.

    Display off/on kannst du testweise auch weglassen. Ob deine Busy-Abfrage funktionert weis ich nicht, sicherheitshalber könntest du Zwangsverzögerungen nach den Befehlen ( bei display_clear z.B. 1,5ms!) einbauen.

    Gruß

    mic
    Bild hier  
    Atmel’s products are not intended, authorized, or warranted for use
    as components in applications intended to support or sustain life!

  5. #5
    Benutzer Stammmitglied
    Registriert seit
    20.07.2008
    Ort
    Herford
    Alter
    39
    Beiträge
    52
    hier der aktuelle code, leider immernoch ohne erfolg
    aber danke schonmal für die hilfe.

    habe die BUSY abfrage erstmal rausgenomen und 25ms eingesetzt.


    Code:
    /*******************************************************************************	
    PortPin:	Display	
    RB0			= E
    RB2			= RS
    RB3			= R/W
    RB4..RB7	= D4..D7     
    *****************************************************************************/
    
    
    /** I N C L U D E S **********************************************************/
    
    #include <p18f4550.h>
    #include <delays.h>
    
    
    /** D E F I N I T I O N S ****************************************************/
    
    #define PORTLCD 	LATB
    #define TRIS_LCD    TRISB
    #define LCD_E		PORTBbits.RB0
    #define LCD_RS		PORTBbits.RB2
    #define LCD_RW		PORTBbits.RB3
    #define nop			_asm nop _endasm
    
    //****************************************************************************
    
    #pragma code
    
    
    void delay100us(unsigned char multiplikator)
    // for  PicLSBK (16MHz Taktzyklus = 4 MHz Befehlszyklus)
    {		
    	Delay10TCYx(40*multiplikator);	//40*10*0,25µs = 100 µs
    }
    
    
    void LCD_BUSY(void)
    {
    	unsigned char temp1;
    //	unsigned char temp2;
    	do
    	{
    		TRIS_LCD = 0xF0; 		// LCD-PORT = high nibbles:eingang; low nibbles:ausgang
    //Display abfrage
    		LCD_RS = 0; 			// LCD im Befehls-Mode
    		LCD_RW = 1; 			// LCD im Lesen-Mode
    		LCD_E = 1; 				// Enable (LCD)
    		temp1 = PORTLCD;
    		temp1 = temp1 & 0xF0; 	// Niederw.Nibble (steuerbits) ausmaskieren
    		LCD_E = 0; 				//   toggeln
    		
    		LCD_E = 1; 				// Enable (LCD)
    //		temp2 = PORTLCD;
    //		temp2 = (temp2>>4)&0x0f;
    //		temp2 = temp1 | temp2; 	// Nibbles verbinden
    		LCD_E = 0; 				//   toggeln
    	} while (temp1>=0x80);	
    		
    	delay100us(1);
    	LCD_RW = 0; 		// Busy = low: LCD im Schreiben-Mode
    	TRIS_LCD = 0x00;     // LCD-PORT = Ausgänge
    	PORTLCD  = 0x00;	 // Daten und Steuerleitungen LOW
    } 
    
    
    void LCD_WriteZeichen(unsigned char zeichen)
    {
    	unsigned char x;
    delay100us(250);
    //	LCD_BUSY(); 				// Warten bis LCD bereit ist
    				
    
    	x = zeichen & 0xf0;
    //	LCD_RW = 0; 				// LCD im Schreiben-Mode
    	LCD_RS = 1; 				// LCD im Befehl-Mode	
    	PORTLCD = x;				//höherwertiges nibbel
    
    nop;
    	LCD_E = 1; 					// Enable (LCD)
    nop;					
    	LCD_E = 0;
    
    delay100us(50);
    	x = zeichen;			
    	x = (x << 4)& 0xf0;			//niederwertiges nibbel
    	LCD_RS = 1; 				// LCD im Befehl-Mode	
    	PORTLCD = x;
    	
    	LCD_E = 1; 					// Enable (LCD)
    nop;					
    	LCD_E = 0;
    nop;
    	LCD_RS = 0;
    }
    
    
    void LCD_WriteString(char *String) 
    {
    	char zeichen;
    	
    	zeichen = *String;
    	while(zeichen !='\0')
    	{
    		LCD_WriteZeichen(zeichen); 	// zeichen am LC-Display ausgeben
    		String++; 					
    		zeichen = *String; 			
    	}
    }
    
    void LCD_WriteRegister(char data) 
    {
    	unsigned char x;
    delay100us(250);
    //	LCD_BUSY(); 				// Warten bis LCD bereit ist
    
    	//	LCD_RW = 0; 				// LCD im Schreiben-Mode
    	//	LCD_RS = 0; 				// LCD im Befehl-Mode	
    					
    	x = data & 0xf0;
    	PORTLCD = x;				//höherwertiges nibbel
    
    	LCD_E = 1; 					// Enable (LCD)
    nop;					
    	LCD_E = 0;
    
    delay100us(50);
    	x = data;			
    	x = (x << 4)& 0xf0;			//niederwertiges nibbel
    	PORTLCD = x;
    	
    	LCD_E = 1; 					// Enable (LCD)
    nop;					
    	LCD_E = 0;
    }
    
    
    
    void LCD_Init(void) 
    {
    // LCD initialisieren
    
    	TRIS_LCD = 0x00;     // LCD-PORT = Ausgänge
    	PORTLCD  = 0x00;	 // Daten und Steuerleitungen LOW
    
    
    	delay100us (150);
    	delay100us (150);	// warte über 30ms
    	delay100us (100);
    
    	PORTLCD = 0x30;				// Interface auf 8-Bit setzen						
    	LCD_E = 1; 					// Enable (LCD)
    nop;					
    	LCD_E = 0;
    	delay100us(50);
    								// Interface auf 8-Bit setzen
    	LCD_E = 1; 					// Enable (LCD)
    nop;					
    	LCD_E = 0;
    	delay100us(2);
    								// Interface auf 8-Bit setzen
    	LCD_E = 1; 					// Enable (LCD)
    nop;					
    	LCD_E = 0;
    	delay100us(2);
    	
    	PORTLCD = 0x20;				// Interface auf 4-Bit setzen
    	LCD_E = 1; 					// Enable (LCD)
    nop;					
    	LCD_E = 0;
    
    	LCD_WriteRegister(0x28);  // 2-zeilig, 5x8-Punkt-Matrix
    	LCD_WriteRegister(0x08);  // Display aus	
    	LCD_WriteRegister(0x01);  // Display löschen
    	LCD_WriteRegister(0x02);  // Kursor nach rechts wandernd, kein Display-Shift
    	LCD_WriteRegister(0x0c);  // Display ein  [ 0x0C = ein, 0x08 = aus ] 
    
    }
    
    
    void main (void)
    {
    	LCD_Init();
    	LCD_WriteZeichen('t');
    	LCD_WriteZeichen('e');
    	LCD_WriteZeichen('s');
    	LCD_WriteZeichen('t');
    }

  6. #6
    Moderator Robotik Visionär Avatar von radbruch
    Registriert seit
    27.12.2006
    Ort
    Stuttgart
    Alter
    61
    Beiträge
    5.799
    Blog-Einträge
    8
    Hallo

    In LCD_WriteRegister() sollte die Verzögerung nach dem Schreiben des zweiten Nipples sein (delay100us(50);), sonst scheint mir das richtig zu sein.

    Kannst du nun mehr als eine Zeile erkennen (mit max. Kontrast)?

    In LCD_WriteZeichen() scheint mir noch ein Fehler zu sein:
    Code:
    ...
       x = zeichen & 0xf0;
    //   LCD_RW = 0;             // LCD im Schreiben-Mode
       LCD_RS = 1;             // LCD im Befehl-Mode
       PORTLCD = x;            //höherwertiges nibbel
    ...
    Nach &0xf0 sind die Bits 0-3 in x gelöscht, RS ist aber bit2 und wird mit PORTLCD = x; wieder gelöscht. Richtig wäre wohl entweder eine andere Reihenfolge:

    PORTLCD = x; //höherwertiges nibbel
    LCD_RS = 1; // LCD im Befehl-Mode

    oder eine andere Formulierung:

    PORTLCD = x | 4; //höherwertiges nibbel und Datenmode setzen

    Ich bin aber leider auch kein LCD-Profi, wir tasten uns ran ;)

    Gruß

    mic
    Bild hier  
    Atmel’s products are not intended, authorized, or warranted for use
    as components in applications intended to support or sustain life!

  7. #7
    Benutzer Stammmitglied
    Registriert seit
    20.07.2008
    Ort
    Herford
    Alter
    39
    Beiträge
    52
    LCD_WriteZeichen() hab ich kurz nach absenden des codes auch gefunden.

    habe jetzt eine verzögerung von 5 ms nach dem ersten und 2. nibble in den funktionen LCD_WriteZeichen und LCD_WriteRegister eingefügt.

    aber leider immer noch ohne licht am ender des tunels

    ja ich sehe alle 4 zeilen, wobei sie aber ganz komisch flackern auch wenn ich nur init aufrufe.

    hier der neue code

    Code:
    /** I N C L U D E S **********************************************************/
    
    #include <p18f4550.h>
    #include <delays.h>
    
    
    /** D E F I N I T I O N S ****************************************************/
    
    #define PORTLCD 	LATB
    #define TRIS_LCD    TRISB
    #define LCD_E		PORTBbits.RB0
    #define LCD_RS		PORTBbits.RB2
    #define LCD_RW		PORTBbits.RB3
    #define nop			_asm nop _endasm
    
    //****************************************************************************
    
    #pragma code
    
    
    void delay100us(unsigned char multiplikator)
    // for  PicLSBK (16MHz Taktzyklus = 4 MHz Befehlszyklus)
    {		
    	Delay10TCYx(40*multiplikator);	//40*10*0,25µs = 100 µs
    }
    
    
    void LCD_BUSY(void)
    {
    	unsigned char temp1;
    //	unsigned char temp2;
    	do
    	{
    		TRIS_LCD = 0xF0; 		// LCD-PORT = high nibbles:eingang; low nibbles:ausgang
    //Display abfrage
    		LCD_RS = 0; 			// LCD im Befehls-Mode
    		LCD_RW = 1; 			// LCD im Lesen-Mode
    		LCD_E = 1; 				// Enable (LCD)
    		temp1 = PORTLCD;
    		temp1 = temp1 & 0xF0; 	// Niederw.Nibble (steuerbits) ausmaskieren
    		LCD_E = 0; 				//   toggeln
    		
    		LCD_E = 1; 				// Enable (LCD)
    		nop;
    		LCD_E = 0; 				//   toggeln
    	} while (temp1>=0x80);	
    		
    	delay100us(1);
    	LCD_RW = 0; 		// Busy = low: LCD im Schreiben-Mode
    	TRIS_LCD = 0x00;     // LCD-PORT = Ausgänge
    	PORTLCD  = 0x00;	 // Daten und Steuerleitungen LOW
    } 
    
    
    void LCD_WriteZeichen(unsigned char zeichen)
    {
    	unsigned char x;
    delay100us(200);
    delay100us(200);
    //	LCD_BUSY(); 				// Warten bis LCD bereit ist
    				
    	LCD_RW = 0; 				// LCD im Schreiben-Mode
    	LCD_RS = 1; 				// LCD im Befehl-Mode
    
    	x = zeichen & 0xf0;
    	x = x | LCD_RS;	
    	PORTLCD = x;				//höherwertiges nibbel
    
    	nop;
    	LCD_E = 1; 					// Enable (LCD)
    	nop;nop;					
    	LCD_E = 0;
    
    delay100us(50);					//5ms warten nach den 1.nibble
    
    	x = zeichen;			
    	x = (x << 4)& 0xf0;			//niederwertiges nibbel
    	x = x | LCD_RS;
    	PORTLCD = x;
    
    delay100us(50);					//5ms warten nach den 2.nibble	
    	LCD_E = 1; 					// Enable (LCD)
    	nop;nop;					
    	LCD_E = 0;
    	nop;
    	LCD_RS = 0;
    }
    
    
    void LCD_WriteString(char *String) 
    {
    	char zeichen;
    	
    	zeichen = *String;
    	while(zeichen !='\0')
    	{
    		LCD_WriteZeichen(zeichen); 	// zeichen am LC-Display ausgeben
    		String++; 					
    		zeichen = *String; 			
    	}
    }
    
    void LCD_WriteRegister(char data) 
    {
    	unsigned char x;
    delay100us(200);
    delay100us(200);
    //	LCD_BUSY(); 				// Warten bis LCD bereit ist
    
    	//	LCD_RW = 0; 				// LCD im Schreiben-Mode
    	//	LCD_RS = 0; 				// LCD im Befehl-Mode	
    					
    	x = data & 0xf0;
    	PORTLCD = x;				//höherwertiges nibbel
    
    
    	LCD_E = 1; 					// Enable (LCD)
    	nop;nop;					
    	LCD_E = 0;
    
    delay100us(50);					//5ms warten nach den 1.nibble
    	x = data;			
    	x = (x << 4)& 0xf0;			//niederwertiges nibbel
    	PORTLCD = x;
    	
    delay100us(50);					//5ms warten nach dem 2.nibble
    	LCD_E = 1; 					// Enable (LCD)
    	nop;nop;					
    	LCD_E = 0;
    }
    
    
    
    void LCD_Init(void) 
    {
    // LCD initialisieren
    
    	TRIS_LCD = 0x00;     // LCD-PORT = Ausgänge
    	PORTLCD  = 0x00;	 // Daten und Steuerleitungen LOW
    
    
    	delay100us (150);
    	delay100us (150);	// warte über 30ms
    	delay100us (100);
    
    	PORTLCD = 0x30;				// Interface auf 8-Bit setzen						
    	LCD_E = 1; 					// Enable (LCD)
    	nop;nop;	
    	LCD_E = 0;
    	
    	delay100us(50);				//warte 5ms
    								
    	LCD_E = 1; 					// Interface auf 8-Bit setzen
    	nop;nop;					// Enable (LCD)					
    	LCD_E = 0;
    
    	delay100us(2);				//warte 200µs
    								
    	LCD_E = 1; 					// Interface auf 8-Bit setzen
    	nop;nop;					// Enable (LCD)				
    	LCD_E = 0;
    	
    	delay100us(2);				//warte 200µs
    	
    	PORTLCD = 0x20;				// Interface auf 4-Bit setzen
    	LCD_E = 1; 					// Enable (LCD)
    	nop;nop;					
    	LCD_E = 0;
    
    	LCD_WriteRegister(0x28);  // 2-zeilig, 5x8-Punkt-Matrix
    	LCD_WriteRegister(0x08);  // Display aus	
    	LCD_WriteRegister(0x01);  // Display löschen
    	LCD_WriteRegister(0x02);  // Kursor nach rechts wandernd, kein Display-Shift
    	LCD_WriteRegister(0x0c);  // Display ein  [ 0x0C = ein, 0x08 = aus ] 
    
    }
    
    
    void main (void)
    {
       LCD_Init();
    
    }

  8. #8
    Moderator Robotik Visionär Avatar von radbruch
    Registriert seit
    27.12.2006
    Ort
    Stuttgart
    Alter
    61
    Beiträge
    5.799
    Blog-Einträge
    8
    Hallo

    Die Wartezeit nach dem zweiten Nipple muss nach der Übergabe der Daten mit E erfolgen. Datentyp für Parameter bei write_register wäre unsigned char schöner, aber sollte auch mit char funktionieren. Ich würde immer noch die Display off/on-Befehle zum Testen weglassen. Bei

    LCD_WriteRegister(0x02); // Cursor nach rechts wandernd, kein Display-Shift

    müßte der Wert doch 0x06 sein, oder?
    Entry ModeSet 0 0 0 0 0 0 0 1 I/D SH Assign cursor moving direction and enable the shift of entire display.
    Gruß

    mic
    Bild hier  
    Atmel’s products are not intended, authorized, or warranted for use
    as components in applications intended to support or sustain life!

  9. #9
    Benutzer Stammmitglied
    Registriert seit
    20.07.2008
    Ort
    Herford
    Alter
    39
    Beiträge
    52
    und noch ein fehler, es muss

    void LCD_WriteRegister(unsigned char data) nur char ist zu klein
    klappt aber immer noch nicht

  10. #10
    Benutzer Stammmitglied
    Registriert seit
    20.07.2008
    Ort
    Herford
    Alter
    39
    Beiträge
    52
    mensch du bist klasse so langsam sollten die fehler aber angst bekommen und verschwinden wenn wir so weitermachen

    die wartezeit nach dem 2. nibble ist jetzt auch nach dem 2. nibble (also nach enable).

    hast recht es muss 0x06 heißen da hat sich bei sprut wohl ein fehler eingeschlichen und ich hab es bein abtippen nicht gemerkt.

    Display off ist auch raus. // on muss doch drin bleiben, oder nicht, ist ja nach der internen init aus.


    Code:
    /** I N C L U D E S **********************************************************/
    
    #include <p18f4550.h>
    #include <delays.h>
    
    
    /** D E F I N I T I O N S ****************************************************/
    
    #define PORTLCD 	LATB
    #define TRIS_LCD    TRISB
    #define LCD_E		PORTBbits.RB0
    #define LCD_RS		PORTBbits.RB2
    #define LCD_RW		PORTBbits.RB3
    #define nop			_asm nop _endasm
    
    //****************************************************************************
    
    #pragma code
    
    
    void delay100us(unsigned char multiplikator)
    // for  PicLSBK (16MHz Taktzyklus = 4 MHz Befehlszyklus)
    {		
    	Delay10TCYx(40*multiplikator);	//40*10*0,25µs = 100 µs
    }
    
    
    void LCD_BUSY(void)
    {
    	unsigned char temp1;
    //	unsigned char temp2;
    	do
    	{
    		TRIS_LCD = 0xF0; 		// LCD-PORT = high nibbles:eingang; low nibbles:ausgang
    //Display abfrage
    		LCD_RS = 0; 			// LCD im Befehls-Mode
    		LCD_RW = 1; 			// LCD im Lesen-Mode
    		LCD_E = 1; 				// Enable (LCD)
    		temp1 = PORTLCD;
    		temp1 = temp1 & 0xF0; 	// Niederw.Nibble (steuerbits) ausmaskieren
    		LCD_E = 0; 				//   toggeln
    		
    		LCD_E = 1; 				// Enable (LCD)
    		nop;
    		LCD_E = 0; 				//   toggeln
    	} while (temp1>=0x80);	
    		
    	delay100us(1);
    	LCD_RW = 0; 		// Busy = low: LCD im Schreiben-Mode
    	TRIS_LCD = 0x00;     // LCD-PORT = Ausgänge
    	PORTLCD  = 0x00;	 // Daten und Steuerleitungen LOW
    } 
    
    
    void LCD_WriteZeichen(unsigned char zeichen)
    {
    	unsigned char x;
    delay100us(200);
    delay100us(200);
    //	LCD_BUSY(); 				// Warten bis LCD bereit ist
    				
    	LCD_RW = 0; 				// LCD im Schreiben-Mode
    	LCD_RS = 1; 				// LCD im Befehl-Mode
    
    	x = zeichen & 0xf0;
    	x = x | LCD_RS;	
    	PORTLCD = x;				//höherwertiges nibbel
    
    	nop;
    	LCD_E = 1; 					// Enable (LCD)
    	nop;nop;					
    	LCD_E = 0;
    
    delay100us(50);					//5ms warten nach den 1.nibble
    
    	x = zeichen;			
    	x = (x << 4)& 0xf0;			//niederwertiges nibbel
    	x = x | LCD_RS;
    	PORTLCD = x;
    	
    	LCD_E = 1; 					// Enable (LCD)
    	nop;nop;					
    	LCD_E = 0;
    delay100us(50);					//5ms warten nach den 2.nibble
    	LCD_RS = 0;
    }
    
    
    void LCD_WriteString(unsigned char *String) 
    {
    	unsigned char zeichen;
    	
    	zeichen = *String;
    	while(zeichen !='\0')
    	{
    		LCD_WriteZeichen(zeichen); 	// zeichen am LC-Display ausgeben
    		String++; 					
    		zeichen = *String; 			
    	}
    }
    
    void LCD_WriteRegister(unsigned char data) 
    {
    	unsigned char x;
    delay100us(200);
    delay100us(200);
    //	LCD_BUSY(); 				// Warten bis LCD bereit ist
    
    	//	LCD_RW = 0; 				// LCD im Schreiben-Mode
    	//	LCD_RS = 0; 				// LCD im Befehl-Mode	
    					
    	x = data & 0xf0;
    	PORTLCD = x;				//höherwertiges nibbel
    
    
    	LCD_E = 1; 					// Enable (LCD)
    	nop;nop;					
    	LCD_E = 0;
    
    delay100us(50);					//5ms warten nach den 1.nibble
    	x = data;			
    	x = (x << 4)& 0xf0;			//niederwertiges nibbel
    	PORTLCD = x;
    	
    	LCD_E = 1; 					// Enable (LCD)
    	nop;nop;					
    	LCD_E = 0;
    delay100us(50);					//5ms warten nach dem 2.nibble
    }
    
    
    
    void LCD_Init(void) 
    {
    // LCD initialisieren
    
    	TRIS_LCD = 0x00;     // LCD-PORT = Ausgänge
    	PORTLCD  = 0x00;	 // Daten und Steuerleitungen LOW
    
    
    	delay100us (150);
    	delay100us (150);	// warte über 30ms
    	delay100us (100);
    
    	PORTLCD = 0x30;				// Interface auf 8-Bit setzen						
    	LCD_E = 1; 					// Enable (LCD)
    	nop;nop;	
    	LCD_E = 0;
    	
    	delay100us(50);				//warte 5ms
    								
    	LCD_E = 1; 					// Interface auf 8-Bit setzen
    	nop;nop;					// Enable (LCD)					
    	LCD_E = 0;
    
    	delay100us(2);				//warte 200µs
    								
    	LCD_E = 1; 					// Interface auf 8-Bit setzen
    	nop;nop;					// Enable (LCD)				
    	LCD_E = 0;
    	
    	delay100us(2);				//warte 200µs
    	
    	PORTLCD = 0x20;				// Interface auf 4-Bit setzen
    	LCD_E = 1; 					// Enable (LCD)
    	nop;nop;					
    	LCD_E = 0;
    
    	LCD_WriteRegister(0x28);  // 2-zeilig, 5x8-Punkt-Matrix
    //	LCD_WriteRegister(0x08);  // Display aus	
    	LCD_WriteRegister(0x01);  // Display löschen
    	LCD_WriteRegister(0x06);  // Kursor nach rechts wandernd, kein Display-Shift
    	LCD_WriteRegister(0x0c);  // Display ein  [ 0x0C = ein, 0x08 = aus ] 
    
    }
    
    
    void main (void)
    {
       LCD_Init();
    	LCD_WriteZeichen('t');
    }

Seite 1 von 3 123 LetzteLetzte

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •  

LiFePO4 Speicher Test