Sim's blog

電子工作はじめてみました

SG12864Aを使ってみました

2009-03-28 23:24:45 | AVR
秋月でSG12864Aという128x64ドットのグラフィック液晶が売られています(通販番号P-02159)。発売当時はもっと高かったのですが、いつのまにか値下げしています(2100円→1700円)。発売当時に書いた記事です。

この液晶の特長はなんといっても5Vで動かせることです。他に手に入るものは3.3V系のものが多いです。どうして5Vかというと、ATmarquinoで動かしたかったからです。でもって、慣れないせいもあってか、未だに動かせていません。しかたないので、配線やロジックの確認のために素のATMega168を使ってCでプログラムを書いてみました。一応、以前V850用に書いたことがあったので、すんなり動きました。そのときは、サイキットさんの液晶用だったのですが、秋月のも互換性があります。って、久々にサイキットさんを見たら液晶が値下がりしてます。

出力例です。

ネギは振りません。とりあえず静止画です。

配線はもじゃー

データが8本、制御が6本です。

コードです。<と>は全角になっています。
#include <avr/io.h>
#include <util/delay.h>
#include <avr/pgmspace.h>

#define DC PB5  // 19→4
#define RW PB4  // 18→5
#define E  PB3  // 17→6
#define D0 PD0  //  2→7
#define D1 PD1  //  3→8
#define D2 PD2  //  4→9
#define D3 PD3  //  5→10
#define D4 PD4  //  6→11
#define D5 PD5  // 11→12
#define D6 PD6  // 12→13
#define D7 PD7  // 13→14
#define CS1 PB2 // 15→16
#define CS2 PB1 // 14→17
#define RST PB0 // 13→18

#define lcd_d() PORTB |= _BV(DC)
#define lcd_c() PORTB &= ~_BV(DC)
#define lcd_r() PORTB |= _BV(RW)
#define lcd_w() PORTB &= ~_BV(RW)
#define lcd_e1() PORTB |= _BV(E)
#define lcd_e0() PORTB &= ~_BV(E)
#define busy (PIND & 0x80)


void busywait(void)
{
    DDRD = 0x00;
    lcd_c();
    lcd_r();
    do {
        lcd_e1();
        lcd_e0();
    } while(busy);
    DDRD = 0xff;
    lcd_w();
}

void left(void)
{
    PORTB &= ~_BV(CS2);
    PORTB |= _BV(CS1);
}

void right(void)
{
    PORTB &= ~_BV(CS1);
    PORTB |= _BV(CS2);
}

void lcd_cmd(uint8_t c)
{
    busywait();
    lcd_c();
    PORTD = c;
    lcd_e1();
    lcd_e0();
}

void lcd_data(uint8_t c)
{
    busywait();
    lcd_d();
    PORTD = c;
    lcd_e1();
    lcd_e0();
}

void lcd_locate(uint8_t x, uint8_t y)
{
    lcd_cmd(0x40 | (x & 0x3f));
    lcd_cmd(0xb8 | (y & 7));
}

void lcd_init(void)
{
    DDRD = 0xff;
    DDRB = 0xff;

    // リセット
    PORTB = 0x00;
    _delay_ms(1);
    PORTB |= _BV(RST);

    left();
    lcd_cmd(0xc0);
    lcd_cmd(0x3f);

    right();
    lcd_cmd(0xc0);
    lcd_cmd(0x3f);
}

PROGMEM uint8_t pic[128*8] = {
    0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x40,0xe0,0xf0,0xfc,0xf8,0xf0,0xe0,0xe0,0x80,0x00,0x00,0x00,0x00,0xe0,0xe0,0xf0,0xf0,0xf8,0xc0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
    0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x04,0x09,0x1b,0x17,0x3f,0x7f,0xff,0xff,0xff,0xfe,0xfc,0xf8,0xf1,0xff,0xff,0xff,0xff,0xff,0xfc,0xe0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xc0,0xe0,0xf0,0xf8,0xf8,0xfc,0xfe,0xfd,0xfd,0xfd,0xfe,0xfe,0xfe,0xfe,0xfe,0xfe,0xff,0xff,0xff,0xff,0xff,0xff,0xfe,0xfe,0xfe,0xfe,0xfc,0xfc,0xfc,0xf8,0xf0,0xf0,0xf0,0xf8,0xfc,0xf4,0xfc,0xfc,0xf0,0xe0,0xc0,0x80,0x00,0x00,0x00,0x00,0x00,
    0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x03,0x03,0x07,0x0f,0x1f,0x3f,0x7f,0xff,0xff,0xff,0x7f,0x3f,0x3e,0x60,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xc0,0xf0,0xf8,0xfe,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x7f,0x3f,0x1f,0x0f,0x0f,0x07,0x07,0x03,0xff,0xff,0xff,0xff,0xff,0x0f,0x03,0x07,0x0f,0x1f,0x3f,0x7f,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xfc,0xf0,0xc0,0x00,
    0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x03,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xc0,0xfc,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xdf,0x47,0x27,0x20,0x42,0x82,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x07,0x1f,0x7f,0xff,0xff,0x00,0x04,0x84,0x40,0x48,0x48,0x81,0x17,0x3f,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,
    0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,0x60,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0xe0,0xfc,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x3f,0x9f,0x0f,0x00,0x03,0x06,0x04,0x04,0x06,0x03,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x00,0x00,0x00,0x03,0x03,0x03,0x07,0x0c,0x08,0x08,0x07,0x00,0x00,0x07,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,
    0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x08,0xe0,0xff,0xfc,0xfc,0xfe,0xfe,0xfe,0xfe,0xfe,0xfe,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xf8,0xf9,0xf0,0x80,0x80,0x00,0x00,0x00,0x00,0xff,0x03,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0xc1,0x3f,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0xc0,0xe0,0xff,0xff,0xff,0xff,0x7f,0x3f,0x1f,0x0f,0x0f,0x0f,0x07,0x07,0xff,0xff,0xff,0xff,0xff,
    0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x3f,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x24,0x40,0x4e,0x59,0x10,0x90,0x90,0x90,0x90,0x90,0xf0,0xf0,0x7f,0x70,0x70,0xf0,0xf0,0xf0,0xf8,0xf8,0xf0,0x7c,0x0c,0x0f,0x0f,0x1f,0x1f,0x3f,0x23,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x03,0xff,0xff,0xff,0xff,
    0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xc3,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x0f,0x0f,0x0f,0x1f,0x98,0xd0,0x70,0x30,0xfc,0xfe,0xff,0xff,0xff,0xff,0x3f,0xfc,0xf8,0xf8,0x3e,0x0f,0x07,0x07,0x7f,0xe3,0x80,0x80,0x00,0x20,0x20,0x00,0x82,0x8c,0xf0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xff,0xff,0xff,0xff,
};

int main()
{
    uint8_t *p = pic;
    uint8_t x, y;

    DDRC = _BV(PC5);

    lcd_init();
    for(y = 0; y < 8; y++){
        left();
        lcd_locate(0, y);
        for(x = 0; x < 64; x++) lcd_data(pgm_read_byte(p++));
        right();
        lcd_locate(0, y);
        for(x = 0; x < 64; x++) lcd_data(pgm_read_byte(p++));
    }

    while(1){
        PORTC ^= _BV(PC5);
        _delay_ms(200);
    }
}


Arduinoを使って分かったことは、デジタル出力の0と1はなるべく使わない方がいいということです。RXとTXなのでプログラミングするのにも使われているからです。あとは、DDRB、PORTB、PINBといったポートへのバイト入出力が普通に使えることです。
回路図は後で描きます。

ATMega168って、実質的に連続して8ビットとれるポートがPORTDしかないです。Arduinoだとデジタル出力の0~7です。

うーん、せっかくのArduinoなのに、全然プロトタイプしてないです><