自作電子小物/TIPS/グラフィックLCD LPH7366/AVR

 
 

小型グラフィックLCDモジュールの「LPH7366」を、ATMEL ATmega328Pで制御するためのソフトウエアサブルーチンライブラリです。画像表示目的ではなく、キャラクタLCDモジュールの代わりに使うためのソフトウエア部品で、printf()関数で簡単に文字表示を行う事が出来ます。

Graphic LCD LPH7366 Library for AVR

2012年5月28日

LPH7366は、NOKIA社の携帯電話5110に使われているとされるLCDモジュールで、1.5インチ84×48ドットSTNモノクロ表示、サイドライト構造、比較的安価で入手性が良くピン数が少ないので、電子小物にはうってつけの表示デバイスです。ただし、コネクタが特殊なのと制御ソフトウエアが若干面倒です。

これは、その制御ソフトウエアの部分を克服するためのサブルーチンです。インターネット上を探せば、同様なサブルーチンを見つける事が出来ますが、ライセンス上面倒になるので自分で作りました。

2015.01.23 IDEを”AVR Studio 4”から”ATMEL STUDIO 6”に変更しました。

2015.01.23 コントラスト、電源制御のAPIを追加しました。


主な仕様

 対応LCDモジュール: LPH7366互換品

   LCDコントローラが「Philips PCD8544」の物に対応

 I/Oポート: 4〜5本、SCLK=PD0, SDA=PD1, D/C=PD3, CS=PD4, RESET=未使用(割当て可能)

 画面向き: ランドスケープ(横長)モード固定、枠の太い方が上

 座標: X方向左=0、X方向右=83、Y方向上=0、 Y方向下=47

 表示図形: 固定サイズの文字

 文字種: ASCII 7bitコード0x20-0x7f

 文字フォント: 6x8ドット(文字間込み)

 文字数: 14桁×6行

 カーソル機能: なし

 スクロール機能: なし(ラップアラウンド表示されます)

 バックライト制御: なし

 API(アプリケーションプログラムインタフェース)

#include “lph7366.h”


 初期化/終了

void lcd_open();

void lcd_close();


void lcd_start();        // I/Oポート設定のみ

void lcd_init());        // 初期化のみ

void lcd_stop();        // I/Oポート開放


 デバイス制御

extern void lcd_contrast(unsigned char level);// コントラスト変更

extern voidlcd_power(unsigned char mode);// 電源制御


 level:0(薄い)〜127(濃い)

 mode=LCD_POWER_MODE_NORMAL:通常運転

 mode=LCD_POWER_MODE_SLEEP:省電力モード(非表示)


 グラフィック表示

void lcd_draw_str(unsigned char x, unsigned char y, char *str);// 文字列描画

extern void lcd_draw_image(unsigned char x, unsigned char y,// ビットイメージ描画

             unsigned char *bitImage, unsigned char len);


 x,y: 左上を原点とする座標値、ピクセル単位、y軸は8の倍数のみ(アラインされます)

 str: 文字列、制御コードは指定出来ません

 bitimage: 1バイトがy方向に=8ピクセル(上→下、b0→b7)を表し、x方向が1バイト1ピクセル幅となります

 len: bitimageのバイト数(=ピクセル数)


 キャラクタ表示

void lcd_prString(char *str);// 文字列表示

void lcd_prCString(char *str);// 文字列描画(API互換用)

void lcd_position(unsigned char column, unsigned char row);// 表示位置指定

void lcd_control(unsigned char command);// 画面消去等の特殊機能

void lcd_setViewPort(unsigned char x, unsigned char y, unsigned char width, unsigned char height);

// 画面の矩形領域のみをキャラクタディスプレイ領域として使いたい時のみ使用


 str: 文字列、 \n,\f等の制御コードを指定する事が出来る

 column,row: 桁、行位置を指定、0〜

 command: 詳しくはヘッダファイルを見て類推して下さい

 x,y: 左上を原点とする座標値、ピクセル単位、y軸は8の倍数のみ(アラインされます)

 width,height: 幅、高さをピクセル単位で指定





ダウンロード

関連ソース全てとサンプルプログラムが入ったIDE(AVRstudio6)用のプロジェクトファイル

Graphic_LCD_LPH7366_for_AVR_files/GraphicLCD_LPH7366_Sample0.3.zip
GraphicLCD_LPH7366_Sample0.3.zip(61kB)  2015.01.23更新

回路図のEAGLE用のプロジェクトファイル

Graphic_LCD_LPH7366_for_AVR_files/GraphicLCD_sample_2.zip
GraphicLCD_sample.zip(131kB)
Graphic_LCD_LPH7366_for_AVR_files/TOG.lbr.zip
TOG.lbr.zip(36kB)


サンプルの動かし方

・回路をブレッドボード等を利用して結線し、AVRISP等のプログラマを接続。

・電源3.3Vを与える

PCで、適当なディレクトリにダウンロードしたファイルを展開する。(とりあえずビルドする必要はありません)

PCで、ISP書込みユーティリティでHEXファイル(default/GraphicLCD_LPH7366_Sample.hex)を書込み。

・書込み完了と同時に、LCDに”Hello world.”の表示が出るはずです。


ユーザアプリケーションプログラムでの使い方

ソースコードで提供されるライブラリですので、ユーザプロジェクトでコンパイル対象に入れれば、本ライブラリを呼び出せる様になります。具体的には、ユーザのプロジェクトのディレクトリ内に本ライブラリソースファイル2個をコピーし、プロジェクトにもソースファイルを追加登録させるだけです。

サブルーチン内で、WinAVRの<util/delay.h>を使用していますので、IDEのプロジェクト設定のCPUのクロック数の指定を行って下さい。具体的には内容はサンプルプロジェクトをご参照願います。指定しない場合、コンパイルエラーとなります。

使用するI/Oポートは変更可能です。ヘッダファイル”lph7366.h”内で#define定義している、ポートピンの設定箇所を変更するだけです。RESETピンを使う様にする事も可能です。この場合、コメントアウトを外して下さい。


設計情報

・開発環境

  IDE: ATMEL Studio 6.2.1502 SP1 

  Compiler: Atmel AVR(8bit) GNU Toolchain 3.4.5.1522(GCC 4.8.1)


・ソースファイル

  GraphicLCD_LPH7366_Sample.c    サンプルプログラム

  lph7366.h                    ヘッダファイル

  lph7366.c                    サブルーチン本体


・物理構造と接続

ページ頭の写真をご覧下さい。白い部分が反射材で簡単に外せます。横から光を入れてやると暗くても画面が視認できる構造になっています。半透過型の液晶パネルのようで、反射型としてもサイドライトでバックライト付としても機能し、良く出来きたモジュールです。

茶色い部分が、導電ゴムのようなものですが、縦にだけ電気を通しますので、金属接点のように電気的な接続が可能になっています。見た目では信号線の区切りが判別出来ませんが1mmピッチで9つの領域に分かれており、ここを銅箔パターンに接触して電気的な接続を行う方法となります。汎用的なコネクタ等は存在せず、専用の基板を用意する必要が有ります。


動作確認と制御プログラム開発の為に、簡単な接続基板を作りました。これは生基板(一面に銅箔が乗った基板)にカッターで1mm間隔で切れ込みを入れただけの物です。基板幅は、金属フレームの爪に引っかかる様なサイズにしてあり、うまく固定出来きるようにしました。目分量で適当に作ったせいか、接続が出来たり出来なかったりしました。データシートの寸法を見ながら、出来るだけ正確に作った方が良いでしょう。(Eagle部品ライブラリにLPH7366を登録しています)


・接続インタフェース

一般的にキャラクタタイプのLCDモジュールは、制御方法がおおむね同じか似ているので、製品が違っても対応し易いのですが、グラフィックタイプでは、制御方法が品種によってそれぞれ大きく異なる様です。

詳しくは、PCD8544のデータシートで確認して頂きたいのですが、概要を紹介させて頂きますと、入出力は独自シリアル通信で、最低3本、通常4本のI/Oポートでコントロールします。クロック信号と1本のデータラインで8ビット単位にデータもしくはコマンドコードを送り込みます。データ/コマンドの区別はもう1本の信号で与えます。もう1本のイネーブル信号ラインは固定的にイネーブルでも動作しますが、ビットずれが起こった場合の、再同期する手段となります。8ビット毎にイネーブルをオン/オフすればずれる事はあり得なくなります。書込みのみで読み出しは出来ません。

コマンドは簡単です。

機能設定コマンド:Function set

  命令モード(基本/拡張)切り替え、画面方向、パワーダウンモードを設定

  別々に指定する事は出来ません

基本命令モード:

 表示制御コマンド:Display control

   全ピクセルオフ、通常表示、全ピクセルオン、全ピクセル反転のいずれかを選択

 Y軸座標設定コマンド:Set Y address of RAM

   8ピクセル単位

 X軸座標設定コマンド:Set Y address of RAM

   1ピクセル単位

拡張命令モード:

 温度制御コマンド:Temperature control

   不明、とりあえずデフォルトで支障無し

 バイアスシステムコマンド:Bias system

   Set VOPと組み合わせて、LCDパネルの駆動条件を指定

 VOP設定コマンド:Set VOP

   表示コントラストが変わる

   Bias systemはガンマ値、VOPは濃さに影響するような感じかと思われます

詳しくはデータシートを参照。LPH7366自体のデータシートはインターネット上を探しても見つけられませんでしたが、LCDコントローラのデータシートは簡単に入手出来ますので、ソフトウエア開発は何とかなります。本当は欲しいんですけどね。

同じLPH7366というデバイスでも、コントラストが自動調整のものと、ソフトウエアから指定してあげないと全く表示されない物があります。具体的には、INSTRUCTIONのBias system、Set VOPで設定値を変化させて、見やすく表示される位置で固定するか、汎用的にしたければ設定値を外部操作等で変更する仕組みが必要になります。たぶんTemperature controlも影響するかと思われますが、とりあえず表示には問題なさそうなので、きちんと調べていません。自動調整する個体はコマンドが無視され、何の効果も出ません。

外形は全く同じなので、区別は困難です。

 

左側:コントラスト調整不要の個体例

右側:パラメータを変更しないと表示されない個体例

(接続端子をアルコール洗浄した際、先頭の文字が消えてしまった)

他に、良く見比べると、導電ゴムの質が違ったり、画面の色合いが微妙に違う等の相違があるようです。

もしかしたら、互換品とか正確には違う品種のデバイスかもしれません。


・画面更新法

PCD8544は画面を縦8ピクセル・横1ピクセルに区切り、この単位で変更します。コントローラ内にフレームバッファメモリを持っていますので、リフレッシュ動作は不要です。しかし、書込みオンリーなので1ピクセル単位での画面変更を行おうとした場合、マイコン内にフレームバッファのコピーが必要になります。

ATmega328P内のメモリは、そう大きくないので縦8ピクセル単位でのアクセスするような設計にして行かなければなりません。どうしても必要な場合、84x48/8=504バイトのRAMを確保すれば良いだけなのですが、出来れば避けたいサイズです。

今回の対応では、文字表示がメインとなりますし、縦8ピクセルのフォントにすれば解決出来ます。実用的な小さい文字フォントは縦7x横5ピクセルなので、14桁×6行のキャラクタディスプレイが実現出来ます。

なお、文字フォントはLCDコントローラ内にはありませんので、マイコンのROMに持つ必要がありますし、自分で作るか、何処かから持ってこなければなりません。自分で作るのも意外と簡単で、たまには単純作業も良いと思います。

今回は、とりあえず図形やグラフといった表示は行いたいとは思っていなかったので、キャラクタ表示ベースの制御プログラムを作り、今後の為に共通サブルーチンをとしてまとめました。


・printf()連携

文字表示は、printf()関数等のstdioが使えるととても楽です。WINAVRライブラリは、このカスタマイズに対応出来ます。


int zz_putchar(char c, FILE *stream) {

charbuf[2];


buf[0] = c;

buf[1] = '\0';

lcd_prString(buf);    // 今回作成したLCD表示サブルーチン

return(0);

}


まず、1文字出力ルーチンを任意の名前で作ります。


FDEV_SETUP_STREAM(zz_putchar, NULL, _FDEV_SETUP_WRITE);


つぎに、stdioの制御テーブルの領域を、用意されているマクロを使ってグローバル域に確保します。



stdout = &lcd_iob;


メインプログラムの最初に1回だけ、制御テーブルとstdoutを関係づける処理を行えばOK。printf(),puts()等のファイルポインタを指定しない関数群の出力先(stdout)がLCDに変わります。


・文字フォント

LCDコントローラ内に文字フォントを持っていないので、マイコン上に持たなければなりません。このクラスのマイコンのROMメモリ量では、英数字位しか用意出来ません。フォントを作るのは大変な作業なので、何処かから持ってくる事も考えましたが、著作の扱いが面倒になるので、手作りしております。5x7ドットで英数記号96文字を作りましたが、このサイズではあまり特徴が出し様がなく、だいたい決まってしまいます。なお、AVRはconst宣言した位ではROM上に定数を配置してくれません。この辺は、マイコンの種類によって実装の仕方が違うので、いつも困ってしまいます。


権利関係

GPLに準じます。他から流用したソース部分はありません。参照した情報源は以下の通り。

  1. (1)aitendo@shopping(株式会社 秋葉原)の「LCDモジュール(48×84)[NOKIA5110-LCD]」の販売ページの接続ピン情報 http://www.aitendo.com/product/1165

  2. (2)Philips(現NXP semiconducters)のホームページでダウンロード出来るPCD8544 のデータシート http://www.classic.nxp.com/acrobat_download2/datasheets/PCD8544_1.pdf