logo elektroda
logo elektroda
X
logo elektroda
Adblock/uBlockOrigin/AdGuard mogą powodować znikanie niektórych postów z powodu nowej reguły.

[solved]atmega8 + KS108 + uart + zew_osc... da się?

Yazutsu 26 Lis 2010 22:38 1188 9
  • #1 8793826
    Yazutsu
    Poziom 10  
    pytanie jak w temacie, jak to wszystko pomieścić.

    Korzystam ze sterownika Radzia do obsługi KS108B
    niestety wymaga on całego jednego portu dla danych.
    (a może da się ustawić aby port data podzielić na dwa?)

    W atmega 8 tylko dwa porty są pełne ale w każdym z nich jest coś czego bede potrzebował, znaczy z portu D musze użyć Uarta, a z portu B zewnętrzny kwarc.

    Da się?
  • #2 8793901
    tadzik85
    Poziom 38  
    Da się. To zapewne kwestia modyfikacji jednej czy dwóch funkcji.
  • #3 8793911
    Yazutsu
    Poziom 10  
    tadzik85 napisał:
    Da się. To zapewne kwestia modyfikacji jednej czy dwóch funkcji.


    Piszesz o modyfikacji sterownika do glcd?
  • #4 8793938
    tadzik85
    Poziom 38  
    Tak.

    np.
    void lcdWriteCmd(unsigned char x)
    {
    lcdWait();
    CLR_RS();
    CLR_RW();
    LCD_DATA_DDR = 0xFF;
    LCD_DATA_PORT = x;
    SET_EN();
    delay();
    CLR_EN();
    }


    troszkę zmian w 4 i 5 linii i pozostałych w bibliotece i już.
  • #5 8794002
    Yazutsu
    Poziom 10  
    U mnie to wygląda troszkę inaczej, deklaruje porty tak:
    #define KS0108_DATA_PORT	PORTC
    #define KS0108_DATA_DIR		DDRC
    #define KS0108_DATA_PIN		PINC


    a odpowiednik Twojej funkcji zapisu komendy wygląda tak:
    void GLCD_WriteCommand(unsigned char commandToWrite, unsigned char controller)
    {
    
    while(GLCD_ReadStatus(controller)&DISPLAY_STATUS_BUSY);
    
    
    KS0108_DATA_DIR = 0xFF;
    KS0108_CTRL_PORT &= ~(KS0108_RW | KS0108_RS);
    
    GLCD_EnableController(controller);
    
    KS0108_DATA_PORT = commandToWrite;
    KS0108_CTRL_PORT |= KS0108_EN;
    GLCD_Delay();
    KS0108_CTRL_PORT &= ~KS0108_EN;
    
    GLCD_DisableController(controller);
    }
    


    nie za bardzo wiem jak bym się miał do tego zabrać, pomoże ktoś?
  • #6 8794015
    tadzik85
    Poziom 38  
    #define KS0108_DATA_PORT	PORTC
    #define KS0108_DATA_DIR		DDRC
    #define KS0108_DATA_PIN		PINC

    to musisz rzecz jasna odpowiednio zadeklarować


    void GLCD_WriteCommand(unsigned char commandToWrite, unsigned char controller)
    {
    
    while(GLCD_ReadStatus(controller)&DISPLAY_STATUS_BUSY);
    
    
    KS0108_DATA_DIR = 0xFF;     // tu modyfikacja
    KS0108_CTRL_PORT &= ~(KS0108_RW | KS0108_RS);
    
    GLCD_EnableController(controller);
    
    KS0108_DATA_PORT = commandToWrite;       //// tu modyfikacja
    KS0108_CTRL_PORT |= KS0108_EN;
    GLCD_Delay();
    KS0108_CTRL_PORT &= ~KS0108_EN;
    
    GLCD_DisableController(controller);
    }
    


    A w ogólności wszystkie linie zawierające "KS0108_DATA" musisz zmienić.
  • #7 8794106
    Yazutsu
    Poziom 10  
    nie chce wyjść na głupka więc od razu powiem że nie wiem jak to zrobić ale kilka pomysłów się urodziło, pewnie wszystkie do bani...

    deklaracja w ten sposób raczej nie zadziała:
    #define KS0108_DATA_PORT   PORTC,PORTD


    ale może tak jakoś:
    
    #define KS0108_DATA_PORT   PORT?    //???
    
    #define  KS0108_DATA_0       PC0
    #define  KS0108_DATA_1       PC1
    #define  KS0108_DATA_2       PC2
    #define  KS0108_DATA_3       PC3
    #define  KS0108_DATA_4       PC4
    #define  KS0108_DATA_5       PC5
    
    #define  KS0108_DATA_6       PD2       //??
    #define  KS0108_DATA_7       PD3       //??
    


    i już w funkcji jakoś złączyć że:
    
    (KS0108_DATA_0 | KS0108_DATA_1 | ... | KS0108_DATA_7) = KS0108_DATA_PORT
    

    Nawet nie wiem czy tak można...
    Idę chociaż dobrym tropem?

    Dodano po 15 [minuty]:

    albo może jeszcze gdzieś głębiej da się zmienić że to co kompilator uważa za PD2 ma uważać za PC6?

    Chyba by to o wiele ułatwiło?
  • Pomocny post
    #8 8795287
    tadzik85
    Poziom 38  
    Przekombinowałeś. Zobacz jak radzio zrobił to w przypadku alfanumerycznego wyświetlacza, Tam każda linia może być dowolnie podłączona.
  • #9 8795827
    Konto nie istnieje
    Konto nie istnieje  
  • #10 8798098
    Yazutsu
    Poziom 10  
    tak, tak, już sobie z tym poradziłem, było trochę więcej do zmieniania niż dwie linie, ale dało rade, wystarczyło mi rozdzielić obsługę Portu DATA na dwa porty.
    Dla potomnych umieszczam rozwiązanie:

    Definicje:
    
    #define KS0108_DATA_PORT1		PORTA
    #define KS0108_DATA_DIR1		DDRA
    #define KS0108_DATA_PIN1		PINA
    #define KS0108_DATA_DB0			(1 << PA0)
    #define KS0108_DATA_DB1			(1 << PA1)
    #define KS0108_DATA_DB2			(1 << PA2)
    #define KS0108_DATA_DB3			(1 << PA3)
    
    #define KS0108_DATA_PORT2		PORTC
    #define KS0108_DATA_DIR2		DDRC
    #define KS0108_DATA_PIN2		PINC
    #define KS0108_DATA_DB4			(1 << PC0)
    #define KS0108_DATA_DB5			(1 << PC1)
    #define KS0108_DATA_DB6			(1 << PC2)
    #define KS0108_DATA_DB7			(1 << PC3)
    


    w szystkie przeróbki funkcji tak:
    
    void _LCD_OutNibble(unsigned char nibbleToWrite)
    {
    
    	if(nibbleToWrite & 0x01)
    		KS0108_DATA_PORT1 |= KS0108_DATA_DB0;
    	else
    		KS0108_DATA_PORT1  &= ~KS0108_DATA_DB0;
    		
    	if(nibbleToWrite & 0x02)
    		KS0108_DATA_PORT1 |= KS0108_DATA_DB1;
    	else
    		KS0108_DATA_PORT1  &= ~KS0108_DATA_DB1;
    		
    	if(nibbleToWrite & 0x04)
    		KS0108_DATA_PORT1 |= KS0108_DATA_DB2;
    	else
    		KS0108_DATA_PORT1  &= ~KS0108_DATA_DB2;
    		
    	if(nibbleToWrite & 0x08)
    		KS0108_DATA_PORT1 |= KS0108_DATA_DB3;
    	else
    		KS0108_DATA_PORT1  &= ~KS0108_DATA_DB3;
    		
    		
    	if(nibbleToWrite & 0x10)
    		KS0108_DATA_PORT2 |= KS0108_DATA_DB4;
    	else
    		KS0108_DATA_PORT2  &= ~KS0108_DATA_DB4;
    		
    	if(nibbleToWrite & 0x20)
    		KS0108_DATA_PORT2 |= KS0108_DATA_DB5;
    	else
    		KS0108_DATA_PORT2  &= ~KS0108_DATA_DB5;
    		
    	if(nibbleToWrite & 0x40)
    		KS0108_DATA_PORT2 |= KS0108_DATA_DB6;
    	else
    		KS0108_DATA_PORT2  &= ~KS0108_DATA_DB6;
    		
    	if(nibbleToWrite & 0x80)
    		KS0108_DATA_PORT2 |= KS0108_DATA_DB7;
    	else
    		KS0108_DATA_PORT2  &= ~KS0108_DATA_DB7;
    }
    
    unsigned char _LCD_InNibble(void)
    {
    	unsigned char tmp = 0;
    
    	if(KS0108_DATA_PIN1 & KS0108_DATA_DB0)
    		tmp |= (1 << 0);
    	if(KS0108_DATA_PIN1 & KS0108_DATA_DB1)
    		tmp |= (1 << 1);
    	if(KS0108_DATA_PIN1 & KS0108_DATA_DB2)
    		tmp |= (1 << 2);
    	if(KS0108_DATA_PIN1 & KS0108_DATA_DB3)
    		tmp |= (1 << 3);
    		
    	if(KS0108_DATA_PIN2 & KS0108_DATA_DB4)
    		tmp |= (1 << 4);
    	if(KS0108_DATA_PIN2 & KS0108_DATA_DB5)
    		tmp |= (1 << 5);
    	if(KS0108_DATA_PIN2 & KS0108_DATA_DB6)
    		tmp |= (1 << 6);
    	if(KS0108_DATA_PIN2 & KS0108_DATA_DB7)
    		tmp |= (1 << 7);
    		
    	return tmp;
    }
    unsigned char GLCD_ReadStatus(unsigned char controller)
    {
    	unsigned char status;
    	KS0108_DATA_DIR1 &= ~(KS0108_DATA_DB0|KS0108_DATA_DB1|KS0108_DATA_DB2|KS0108_DATA_DB3);
    	KS0108_DATA_DIR2 &= ~(KS0108_DATA_DB4|KS0108_DATA_DB5|KS0108_DATA_DB6|KS0108_DATA_DB7);
    	KS0108_CTRL_PORT |= KS0108_RW;
    	KS0108_CTRL_PORT &= ~KS0108_RS;
    	GLCD_EnableController(controller);
    	KS0108_CTRL_PORT |= KS0108_EN;
    	GLCD_Delay();
    	status = _LCD_InNibble();
    	KS0108_CTRL_PORT &= ~KS0108_EN;
    	GLCD_DisableController(controller);
    	return status;
    }
    void GLCD_WriteCommand(unsigned char commandToWrite, unsigned char controller)
    {
    while(GLCD_ReadStatus(controller)&DISPLAY_STATUS_BUSY);
    KS0108_DATA_DIR1 |= (KS0108_DATA_DB0|KS0108_DATA_DB1|KS0108_DATA_DB2|KS0108_DATA_DB3);
    KS0108_DATA_DIR2 |= (KS0108_DATA_DB4|KS0108_DATA_DB5|KS0108_DATA_DB6|KS0108_DATA_DB7);
    KS0108_CTRL_PORT &= ~(KS0108_RW | KS0108_RS);
    GLCD_EnableController(controller);
    _LCD_OutNibble(commandToWrite) ;
    KS0108_CTRL_PORT |= KS0108_EN;
    GLCD_Delay();
    KS0108_CTRL_PORT &= ~KS0108_EN;
    GLCD_DisableController(controller);
    }
    unsigned char GLCD_ReadData(void)
    {
    	unsigned char data;
    	while(GLCD_ReadStatus(screen_x / 64)&DISPLAY_STATUS_BUSY);
    	KS0108_DATA_DIR1 &= ~(KS0108_DATA_DB0|KS0108_DATA_DB1|KS0108_DATA_DB2|KS0108_DATA_DB3);
    	KS0108_DATA_DIR2 &= ~(KS0108_DATA_DB4|KS0108_DATA_DB5|KS0108_DATA_DB6|KS0108_DATA_DB7);
    	KS0108_CTRL_PORT |= (KS0108_RW | KS0108_RS);
    	GLCD_EnableController(screen_x / 64);
    	KS0108_CTRL_PORT |= KS0108_EN;
    	GLCD_Delay();
    	data = _LCD_InNibble();
    	KS0108_CTRL_PORT &= ~KS0108_EN;
    	GLCD_DisableController(screen_x / 64);
    	screen_x++;
    	return data;
    }
    void GLCD_WriteData(unsigned char dataToWrite)
    {
    	while(GLCD_ReadStatus(screen_x / 64)&DISPLAY_STATUS_BUSY);
    	KS0108_DATA_DIR1 |= (KS0108_DATA_DB0|KS0108_DATA_DB1|KS0108_DATA_DB2|KS0108_DATA_DB3);
    	KS0108_DATA_DIR2 |= (KS0108_DATA_DB4|KS0108_DATA_DB5|KS0108_DATA_DB6|KS0108_DATA_DB7);
    	KS0108_CTRL_PORT &= ~KS0108_RW;
    	KS0108_CTRL_PORT |= KS0108_RS;
    	_LCD_OutNibble(dataToWrite);
    	GLCD_EnableController(screen_x / 64);
    	KS0108_CTRL_PORT |= KS0108_EN;
    	GLCD_Delay();
    	KS0108_CTRL_PORT &= ~KS0108_EN;
    	GLCD_DisableController(screen_x / 64);
    	screen_x++;
    }
    


    Wszystkie te funkcje są autorstwa:
    
    //-------------------------------------------------------------------------------------------------
    // Universal KS0108 driver library
    // Atmel AVR MCU low-level driver.
    // (c) Radosław Kwiecień, radek@dxp.pl
    //-------------------------------------------------------------------------------------------------
    
    ja je tylko pozmieniałem.

    temat zostawię parę dni otwarty jak by były jakieś pytania bądź uwagi.tadzik85 dostajesz "pomógł" :)
REKLAMA