AQM1602_rev2.pdf (akizukidenshi.com) にて半田するのでモシニャガ本のpullup不要
> コピペで超簡単!PICマイコンでI2C接続のLCD(AQM1
<私もこのサイトを参考にさせていただきました。秋月の付属データ
> (ちなみにモシニャガ先生はソフト的にsda,sclをweak pullupする方法をとっていました) それとsda,sclをinputにしておくのはackを受け取
<先にお送りしたAQM1602のライブラリではハードでプルアッ
よろしくお願いします。
//コピペで超簡単!PICマイコンでI2C接続のLCD(AQM1602)を使う【PIC16F1938】 | Wak-tech を参考にしているとのこと
/* from yosino san
* AQM1602 【16F1827】
* AQM1602/main.c Created on 2024/04/20, 21:48
*/
// config1
#pragma config FOSC = INTOSC , WDTE = OFF , PWRTE = ON , MCLRE = ON , CP = OFF , CPD = OFF
#pragma config BOREN = OFF , CLKOUTEN = OFF , IESO = OFF , FCMEN = OFF
// config2
#pragma config WRT = OFF , PLLEN = OFF , STVREN = ON , LVP = OFF
#include <xc.h>
#define _XTAL_FREQ 8000000
#define LCD_ADD 0x7C // 下記参照
char moji[] = "Hello,World!";
char moji2[] = "PIC16F1827";
void I2C_Master_Init(const unsigned long c){
// OPTION_REGbits.nWPUEN = 0; // この2行はプルアップ半田したので不要
// WPUB |= 0b00010010;
SSP1CON1 = 0b00101000;
SSP1CON2 = 0;
SSPADD = (_XTAL_FREQ/(4*c))-1; // これでcに1000000 つまり100khZを入れる
// つまり SSP1ADD = 19; // (_XTAL_FREQ / (4*c))-1;
SSP1STAT = 0b00000000 ; // 標準速度モードに設定する(100kHz)
}
void I2C_Master_Wait(){
while ((SSP1STAT & 0x04) || (SSP1CON2 & 0x1F));
// start sequence 検出 または acken=1 & rcen=1 & pen=1 & rsen=1 & sen=1
// https://nukomabo.work/post-528/ ssp1stat == 0x04 は送信中
// 【PIC】I2C通信のやり方 | 理系男子の電子工作 (rikeden.net) では後半も含めて
// trasnmission is in progresと表現
// cf I2C温度センサーLM75ADをPIC12F1822で使う (r271-635) (netlog.jpn.org)
}
void I2C_Master_Start(){
I2C_Master_Wait();
SSP1CON2bits.SEN = 1;
}
void I2C_Master_Stop(){
I2C_Master_Wait();
SSP1CON2bits.PEN = 1;
}
void I2C_Master_Write(unsigned char d){
I2C_Master_Wait();
SSP1BUF = d;
}
void writeData(char t_data){
I2C_Master_Start();
I2C_Master_Write(LCD_ADD);
I2C_Master_Write(0x40);
I2C_Master_Write(t_data);
I2C_Master_Stop();
__delay_ms(10);
}
void writeCommand(char t_command){
I2C_Master_Start();
I2C_Master_Write(LCD_ADD);
I2C_Master_Write(0x00);
I2C_Master_Write(t_command);
I2C_Master_Stop();
__delay_ms(10);
}
void LCD_Init(){ //LCDの初期化
I2C_Master_Init(100000);
__delay_ms(400);
writeCommand(0x38);
__delay_ms(20);
writeCommand(0x39);
__delay_ms(20);
writeCommand(0x14);
__delay_ms(20);
writeCommand(0x73);
__delay_ms(20);
writeCommand(0x52);
__delay_ms(20);
writeCommand(0x6C);
__delay_ms(250);
writeCommand(0x38);
__delay_ms(20);
writeCommand(0x01);
__delay_ms(20);
writeCommand(0x0C);
__delay_ms(20);
}
void LCD_str(char *c) { //LCDに配列の文字を表示
unsigned char i,wk;
for (i=0 ; ; i++) {
wk = c[i];
if (wk == 0x00) {break;}
writeData(wk);
}
}
int main(void){
OSCCON=0x72; // 8MHz
ANSELA=0x00;
ANSELB=0x00;
TRISA=0x00;
TRISB=0x12; // 0b00010010 for sda and scl
PORTB=0x00;
LCD_Init();
writeCommand(0x01); //画面をクリア
__delay_ms(20);
writeCommand(0x02); //ホームへカーソル移動
__delay_ms(2); // LCD側の処理待ち
while(1){
writeCommand(0x02); //ホームへカーソル移動
LCD_str(moji);
writeCommand(0x40+0x80); //2列目へ移動
__delay_ms(200);
LCD_str(moji2);
__delay_ms(1000);
writeCommand(0x01); //画面をクリア
__delay_ms(200);
}
return 0;
}
--------------------------------------------------------------------
I2C接続AQMシリーズのキャラクタ表示LCDをArduinoで使う (2) AQM1602 | 電子工作の環境向上 (denshi.club) より 上記0x7cはwriteの0を含んでいる!
※ライブラリFaBoLCDmini_AQM0802Aのヘッダ・ファイルには、スレーブ・アドレスが、0x3eと固定されています。AQM1602のデータシートには0x7cと書かれています。マスタがスレーブのLCDに対してスレーブ・アドレスを指定するとき、最後にRead/Writeビットを追加します。LCDはライト・オンリなので、8ビットの0x7c(01111100)の最後のwriteビット0を取り去ると0111110=0x3eになります。
ーーーーーーーーーーー以下をheader,lib,mainにわけたーーーーーーーーーーーーーーーーーーー
/*
* AQM1602 ライブラリ用 ヘッダファイル aqm1602.h
*/
#include <xc.h>
#ifndef AQM1602_H
#define AQM1602_H
void I2C_Master_Init(const unsigned long c);
void I2C_Master_Wait(void);
void I2C_Master_Start(void);
void I2C_Master_Stop(void);
void I2C_Master_Write(unsigned char d);
void writeData(unsigned char t_data);
void writeCommand(unsigned char t_command);
void LCD_Init(void); // LCDの初期化
void LCD_str(char *c); // LCDに配列の文字を表示
void LCD_clear(void); // LCDの画面をクリア
void LCD_home(void); // LCDのカーソルをホームへ
void LCD_locate(unsigned char row, unsigned char col);
// LCDのカーソル位置を指定(行,列))
// 行:1,2 列:1~16
#endif
ーーーーーーーーーーーーーーーーーーーーーーーーーー