サンプルプログラム N446RE_AQM1602_I2C1 の説明
I2C 接続の LCD AQM1602 の
表示を行うサンプルプログラムです。
AQM1602 は秋月電子通商で販売しています。
STMicroelectronics社製の
評価用基板、NUCLEO-F446RE と
freeの開発環境、STM32CubeIDE を
使用しています。
目次
LCD AQM1602 の表示の様子
サンプルプログラム N446RE_AQM1602_I2C1 のソース
サンプルプログラム N446RE_AQM1602_I2C1 の説明
N446RE_AQM1602_I2C1 の構成
N446RE_AQM1602_I2C1 の動作パラメータの定義
ユーザープログラムの実行開始位置
N446RE_AQM1602_I2C1 の main() の説明
1) LED点滅 と AQM1602 の表示処理 の部分
AQM1602 の表示処理 Transact_AQM1602 の説明
1) Transact_AQM1602 のソース
2) Transact_AQM1602 の動作
AQM1602 コマンド書き込み Write_Command_AQM1602 の説明
1) Write_Command_AQM1602 のソース
2) Write_Command_AQM1602 の動作
AQM1602 データ書き込み Write_DataAQM1602 の説明
1) Write_Data_AQM1602 のソース
2) Write_Data_AQM1602 の動作
動作試験用基板 の説明
動作試験用基板 Base-N446RE の説明
動作試験用基板 IF-N446RE-I2C の説明
LCD AQM1602 の表示の様子
AQM1602 を IF-N446RE-I2C 基板に接続して、表示を行っている様子を、
以下に示します。
サンプルプログラム N446RE_AQM1602_I2C1 のソース
STMicroelectronics社製のfreeの開発環境 STM32CubeIDE 1.7.0 を使用して作成しました。
ここからサンプルプログラム R_N446RE_AQM1602_I2C1.zip をダウンロードしてください。
サンプルプログラム N446RE_AQM1602_I2C1 の説明
PWMを使用してRGB 3色LEDの点灯制御を行うプログラムです。
RGBそれぞれの点灯制御を独立に行うことができます。
プロジェクトを最初に開いた画面は以下のようになります。
以下、サンプルプログラム N446RE_AQM1602_I2C1 について説明していきます。
サンプルプログラムの構成
STM32CubeIDEの画面左側、Project Explorerの
N446RE_AQM1602_I2C1を展開した画面は以下のようになります。
サンプルプログラム N446RE_AQM1602_I2C1 の構成を以下に示します。
N446RE_AQM1602_I2C1
|
|- Includes
|
|- Blink_LED_Stat : Status LED点滅処理
| |- Blink_LED_Stat.c
| |- Blink_LED_Stat.h
|
|- Cont_AQM1602 : AQM1602 の制御
| |- Cont_AQM1602.c
| |- Cont_AQM1602.h
|
|- Core
| |- Inc
| | |- main.h
| | |- stm32f4xx_hal_conf.h
| | |- stm32f4xx_it.h
| |
| |- Src
| | |- main.c
| | |- stm32f4xx_hal_msp.c
| | |- stm32f4xx_it.c : 割り込み処理
| | |- syscalls.c
| | |- system.c
| | |- system_stm32f4xx.c
| |
| |- Startup
|
|- Drivers
| |- CMSIS
| |- STM32F4xx_HAL_Driver
|
|- N446RE_I2C1_Config : 動作パラメータの定義
| |- Dev_Conf.h
|
|- Periph_F4 : 周辺インターフェース処理
| |- H_F4_GPIO.c
| |- H_F4_GPIO.h
| |- H_F4_I2C.c
| |- H_F4_I2C.h
|
|- Wait_Itvl : 時間待ち処理
| |- Wait_Itvl.c
| |- Wait_Itvl.h
|
|- N446RE_AQM1602_I2C1.launch
|- STM32F446RETX_FLASH.ld
|- STM32F446RETX_RAM.ld
N446RE_AQM1602_I2C1 の動作パラメータの定義
サンプルプログラム N446RE_AQM1602_I2C1 の動作パラメータの定義を
N446RE_I2C1_Config/Dev_Conf.h に記述しています。
使用する CPU の定義、ヘッダ名の定義、GPIO のポートとピンの定義、動作パラメータの定義、
などを記述しています。
ユーザープログラムの実行開始位置
プログラムは、int main(void) から実行開始します。
int main(void) は、フォルダ Core/Src/main.c にあります。
STM32CubeIDEでビルドされたプログラムは、自動的にCPUの初期化を
行った後、int main(void) を呼び出します。
ユーザーコード(記述したプログラム)は、
int main(void) の先頭から実行されます。
N446RE_AQM1602_I2C1 の main() の説明
サンプルプログラム N446RE_AQM1602_I2C1 の main() の記述は、
以下のとおりです。
/**
* @brief The application entry point.
* @retval int
*/
int main(void)
{
/* USER CODE BEGIN 1 */
uint8_t uint8_JobNum_LED = 0; // LED点滅処理番号
uint8_t uint8_JobNum_LCD = 0; // LCD表示処理番号
/* USER CODE END 1 */
/* MCU Configuration--------------------------------------------------------*/
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
HAL_Init();
/* USER CODE BEGIN Init */
/* USER CODE END Init */
/* Configure the system clock */
SystemClock_Config();
/* USER CODE BEGIN SysInit */
/* USER CODE END SysInit */
/* Initialize all configured peripherals */
/* USER CODE BEGIN 2 */
/* USER CODE END 2 */
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
//------------------------------------------------------
// Status LED点滅
//------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号を格納する変数のポインタ
// uint16_t uint16_Time_ON : 点灯時間
// uint16_t uint16_Time_OFF : 消灯時間
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG
//------------------------------------------------------
Blk_LED_Stat(&uint8_JobNum_LED,
GLB_uint16_Time_LED_Stat_ON, GLB_uint16_Time_LED_Stat_OFF);
//---------------------------------------------------
// LCD AQM1602 の表示処理
//---------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// 戻り値:
// -1 : 処理中
// 0 : OK
// 1 : NG
//---------------------------------------------------
Transact_AQM1602(&uint8_JobNum_LCD);
}
/* USER CODE END 3 */
}
1) 初期化の部分
a) CPUとPeripheral初期化
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
HAL_Init();
により、CPUとPeripheralなどの基本的な初期化を行います。
PeripheralとはCPUの周辺インターフェースなどのことを言います。
HAL_Init はプロジェクト構築時に自動的に組み込まれる、
HAL Drivers(フォルダ Drivers/STM32F4xx_HAL_Drivers) 内に記述されています。
b) CPU動作クロックの設定
/* Configure the system clock */
SystemClock_Config();
CPUの動作クロックとPeripheralの動作クロックを設定します。
SystemClock_Config(); の設定内容は、
int main(void)
{
.
.
.
}
の、すぐ下に記述されています。
2) LED点滅 と AQM1602 の表示処理 の部分
永久ループ部分の記述を以下に示します。
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
//------------------------------------------------------
// Status LED点滅
//------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号を格納する変数のポインタ
// uint16_t uint16_Time_ON : 点灯時間
// uint16_t uint16_Time_OFF : 消灯時間
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG
//------------------------------------------------------
Blk_LED_Stat(&uint8_JobNum_LED,
GLB_uint16_Time_LED_Stat_ON, GLB_uint16_Time_LED_Stat_OFF);
//---------------------------------------------------
// LCD AQM1602 の表示処理
//---------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// 戻り値:
// -1 : 処理中
// 0 : OK
// 1 : NG
//---------------------------------------------------
Transact_AQM1602(&uint8_JobNum_LCD);
}
/* USER CODE END 3 */
Status LED点滅処理 Blk_LED_Stat と
AQM1602 の表示処理 Transact_AQM1602 を呼び出しています。
AQM1602 の表示処理 Transact_AQM1602 の説明
1) Transact_AQM1602 のソース
モジュール Transact_AQM1602 は
Cont_AQM1602/Cont_AQM1602.c 内に記述されています。
モジュール Transact_AQM1602 のソースを以下に示します。
//---------------------------------------------------
// LCD AQM1602 の表示処理
//---------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// 戻り値:
// -1 : 処理中
// 0 : OK
// 1 : NG
//---------------------------------------------------
int16_t Transact_AQM1602(uint8_t *puint8_JobNum)
{
static uint8_t STC_uint8_JobNum_Wait; // 時間待ちの処理番号
static uint32_t STC_uint32_tikstart; // 時間待ち開始時のカウント数
static uint32_t STC_uint32_Interval; // 待ち時間
static uint8_t STC_uint8_JobNum_LCD; // LCD処理番号
static uint8_t STC_uint8_Address;
static uint8_t STC_uint8_Number_TX;
static uint8_t STC_uint8_Data_TX[16];
int16_t int16_Return;
switch(*puint8_JobNum)
{
case 0:
//-------------------------------------------------------
// I2C初期化 : AQM1602
//-------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG終了
//-------------------------------------------------------
int16_Return = Init_I2C_AQM1602(&STC_uint8_JobNum_LCD);
if(int16_Return == -1){
// 処理中
break; // 処理番号維持 : 処理継続 : case 0: をループ
}
if(int16_Return != 0){
// NG終了
HAL_I2C_DeInit(&Handle_I2C1);
GLB_int16_vI2C1_Initialize_Done = 0;
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break;
}
STC_uint8_JobNum_LCD = 0; // LCD表示処理番号初期化
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 1:
int16_Return = -1; // 処理継続
break;
case 1:
//-------------------------------------------------------
// AQM1602 の初期設定を行う。
//-------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG終了
//-------------------------------------------------------
int16_Return = Initial_Setting_AQM1602(&STC_uint8_JobNum_LCD);
if(int16_Return == -1){
// 処理中
break; // 処理番号維持 : 処理継続 : case 1: をループ
}
if(int16_Return != 0){
// NG終了
HAL_I2C_DeInit(&Handle_I2C1);
GLB_int16_vI2C1_Initialize_Done = 0;
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break;
}
STC_uint8_Address = 0x80;
STC_uint8_Number_TX = 16;
memcpy(STC_uint8_Data_TX, "0123456789ABCDEF", 16);
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 2:
int16_Return = -1; // 処理継続
break;
case 2:
//-------------------------------------------------------
// AQM1602 データ書き込み
//-------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint8_t uint8_Address : データ書き込みアドレス
// uint8_t uint8_Number_TX : 送信データ数
// uint8_t *puint8_Data_TX : 送信データを格納したバッファのポインタ
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG終了
//-------------------------------------------------------
int16_Return = Write_Data_AQM1602(&STC_uint8_JobNum_LCD,
STC_uint8_Address,
STC_uint8_Number_TX, STC_uint8_Data_TX);
if(int16_Return == -1){
// 処理中
break; // 処理番号維持 : 処理継続 : case 2: をループ
}
if(int16_Return != 0){
// NG終了
HAL_I2C_DeInit(&Handle_I2C1);
GLB_int16_vI2C1_Initialize_Done = 0;
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break;
}
STC_uint8_JobNum_Wait = 0; // 時間待ちの処理番号初期化
STC_uint32_Interval = (uint32_t)1000; // 待ち時間
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 3:
int16_Return = -1; // 処理継続
break;
case 3:
//------------------------------------------------------
// mSec待ちシーケンス : 処理番号使用 : 複数呼び出し用
//------------------------------------------------------
// 戻り値が -1 以外になるまで、繰り返し呼び出してください。
//------------------------------------------------------
// 引数 :
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint32_t *puint32_tikstart : 時間待ち開始時のカウント数
// uint32_t uint32_mSec : 待ち時間(mSec)
// 戻り値 :
// -1 : 処理中 : 時間が経過していない。
// 0 : OK終了 : 時間が経過した。
// 1 : NG終了
//------------------------------------------------------
int16_Return = Wait_mSec_Seq_Multi(&STC_uint8_JobNum_Wait,
&STC_uint32_tikstart,
STC_uint32_Interval);
if(int16_Return == -1){
// 処理中 : 時間未経過
break; // 処理番号維持 : 処理継続 : case 3: をループ
}
STC_uint8_Address = 0xC0;
STC_uint8_Number_TX = 16;
memcpy(STC_uint8_Data_TX, "GHIJKLMNOPQRSTUV", 16);
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 4:
int16_Return = -1; // 処理継続
break;
case 4:
//-------------------------------------------------------
// AQM1602 データ書き込み
//-------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint8_t uint8_Address : データ書き込みアドレス
// uint8_t uint8_Number_TX : 送信データ数
// uint8_t *puint8_Data_TX : 送信データを格納したバッファのポインタ
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG終了
//-------------------------------------------------------
int16_Return = Write_Data_AQM1602(&STC_uint8_JobNum_LCD,
STC_uint8_Address,
STC_uint8_Number_TX, STC_uint8_Data_TX);
if(int16_Return == -1){
// 処理中
break; // 処理番号維持 : 処理継続 : case 4: をループ
}
if(int16_Return != 0){
// NG終了
HAL_I2C_DeInit(&Handle_I2C1);
GLB_int16_vI2C1_Initialize_Done = 0;
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break;
}
STC_uint8_JobNum_Wait = 0; // 時間待ちの処理番号初期化
STC_uint32_Interval = (uint32_t)1000; // 待ち時間
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 5:
int16_Return = -1; // 処理継続
break;
case 5:
//------------------------------------------------------
// mSec待ちシーケンス : 処理番号使用 : 複数呼び出し用
//------------------------------------------------------
// 戻り値が -1 以外になるまで、繰り返し呼び出してください。
//------------------------------------------------------
// 引数 :
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint32_t *puint32_tikstart : 時間待ち開始時のカウント数
// uint32_t uint32_mSec : 待ち時間(mSec)
// 戻り値 :
// -1 : 処理中 : 時間が経過していない。
// 0 : OK終了 : 時間が経過した。
// 1 : NG終了
//------------------------------------------------------
int16_Return = Wait_mSec_Seq_Multi(&STC_uint8_JobNum_Wait,
&STC_uint32_tikstart,
STC_uint32_Interval);
if(int16_Return == -1){
// 処理中 : 時間未経過
break; // 処理番号維持 : 処理継続 : case 5: をループ
}
STC_uint8_Number_TX = 1; // 送信データ数セット
// コマンドセット
STC_uint8_Data_TX[0] = 0x01; // CLEAR DISPLAY
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 6:
int16_Return = -1; // 処理継続
break;
case 6:
//-------------------------------------------------------
// AQM1602 コマンド書き込み
//-------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint8_t uint8_Number_TX : 送信データ数
// uint8_t *puint8_Data_TX : 送信データを格納したバッファのポインタ
// uint32_t uint32_Interval : 待ち時間 (mSec)
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG終了
//-------------------------------------------------------
int16_Return = Write_Command_AQM1602(&STC_uint8_JobNum_LCD,
STC_uint8_Number_TX, STC_uint8_Data_TX,
(uint32_t)3);
if(int16_Return == -1){
// 処理中
break; // 処理番号維持 : 処理継続 : case 6: をループ
}
if(int16_Return != 0){
// NG終了
HAL_I2C_DeInit(&Handle_I2C1);
GLB_int16_vI2C1_Initialize_Done = 0;
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break;
}
STC_uint8_Address = 0x80;
STC_uint8_Number_TX = 16;
memcpy(STC_uint8_Data_TX, "Nice to meet you", 16);
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 7:
int16_Return = -1; // 処理継続
break;
case 7:
//-------------------------------------------------------
// AQM1602 データ書き込み
//-------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint8_t uint8_Address : データ書き込みアドレス
// uint8_t uint8_Number_TX : 送信データ数
// uint8_t *puint8_Data_TX : 送信データを格納したバッファのポインタ
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG終了
//-------------------------------------------------------
int16_Return = Write_Data_AQM1602(&STC_uint8_JobNum_LCD,
STC_uint8_Address,
STC_uint8_Number_TX, STC_uint8_Data_TX);
if(int16_Return == -1){
// 処理中
break; // 処理番号維持 : 処理継続 : case 7: をループ
}
if(int16_Return != 0){
// NG終了
HAL_I2C_DeInit(&Handle_I2C1);
GLB_int16_vI2C1_Initialize_Done = 0;
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break;
}
STC_uint8_JobNum_Wait = 0; // 時間待ちの処理番号初期化
STC_uint32_Interval = (uint32_t)1000; // 待ち時間
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 8:
int16_Return = -1; // 処理継続
break;
case 8:
//------------------------------------------------------
// mSec待ちシーケンス : 処理番号使用 : 複数呼び出し用
//------------------------------------------------------
// 戻り値が -1 以外になるまで、繰り返し呼び出してください。
//------------------------------------------------------
// 引数 :
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint32_t *puint32_tikstart : 時間待ち開始時のカウント数
// uint32_t uint32_mSec : 待ち時間(mSec)
// 戻り値 :
// -1 : 処理中 : 時間が経過していない。
// 0 : OK終了 : 時間が経過した。
// 1 : NG終了
//------------------------------------------------------
int16_Return = Wait_mSec_Seq_Multi(&STC_uint8_JobNum_Wait,
&STC_uint32_tikstart,
STC_uint32_Interval);
if(int16_Return == -1){
// 処理中 : 時間未経過
break; // 処理番号維持 : 処理継続 : case 8: をループ
}
STC_uint8_Address = 0xC0;
STC_uint8_Number_TX = 16;
memcpy(STC_uint8_Data_TX, "Take it easy! ", 16);
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 9:
int16_Return = -1; // 処理継続
break;
case 9:
//-------------------------------------------------------
// AQM1602 データ書き込み
//-------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint8_t uint8_Address : データ書き込みアドレス
// uint8_t uint8_Number_TX : 送信データ数
// uint8_t *puint8_Data_TX : 送信データを格納したバッファのポインタ
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG終了
//-------------------------------------------------------
int16_Return = Write_Data_AQM1602(&STC_uint8_JobNum_LCD,
STC_uint8_Address,
STC_uint8_Number_TX, STC_uint8_Data_TX);
if(int16_Return == -1){
// 処理中
break; // 処理番号維持 : 処理継続 : case 9: をループ
}
if(int16_Return != 0){
// NG終了
HAL_I2C_DeInit(&Handle_I2C1);
GLB_int16_vI2C1_Initialize_Done = 0;
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break;
}
STC_uint8_JobNum_Wait = 0; // 時間待ちの処理番号初期化
STC_uint32_Interval = (uint32_t)1000; // 待ち時間
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 10:
int16_Return = -1; // 処理継続
break;
case 10:
//------------------------------------------------------
// mSec待ちシーケンス : 処理番号使用 : 複数呼び出し用
//------------------------------------------------------
// 戻り値が -1 以外になるまで、繰り返し呼び出してください。
//------------------------------------------------------
// 引数 :
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint32_t *puint32_tikstart : 時間待ち開始時のカウント数
// uint32_t uint32_mSec : 待ち時間(mSec)
// 戻り値 :
// -1 : 処理中 : 時間が経過していない。
// 0 : OK終了 : 時間が経過した。
// 1 : NG終了
//------------------------------------------------------
int16_Return = Wait_mSec_Seq_Multi(&STC_uint8_JobNum_Wait,
&STC_uint32_tikstart,
STC_uint32_Interval);
if(int16_Return == -1){
// 処理中 : 時間未経過
break; // 処理番号維持 : 処理継続 : case 10: をループ
}
STC_uint8_Number_TX = 1; // 送信データ数セット
// コマンドセット
STC_uint8_Data_TX[0] = 0x01; // CLEAR DISPLAY
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 11:
int16_Return = -1; // 処理継続
break;
case 11:
//-------------------------------------------------------
// AQM1602 コマンド書き込み
//-------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint8_t uint8_Number_TX : 送信データ数
// uint8_t *puint8_Data_TX : 送信データを格納したバッファのポインタ
// uint32_t uint32_Interval : 待ち時間 (mSec)
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG終了
//-------------------------------------------------------
int16_Return = Write_Command_AQM1602(&STC_uint8_JobNum_LCD,
STC_uint8_Number_TX, STC_uint8_Data_TX,
(uint32_t)3);
if(int16_Return == -1){
// 処理中
break; // 処理番号維持 : 処理継続 : case 11: をループ
}
if(int16_Return != 0){
// NG終了
HAL_I2C_DeInit(&Handle_I2C1);
GLB_int16_vI2C1_Initialize_Done = 0;
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break;
}
STC_uint8_Address = 0x80;
STC_uint8_Number_TX = 16;
memcpy(STC_uint8_Data_TX, "0123456789ABCDEF", 16);
*puint8_JobNum = 2; // 処理番号 2 に移行する。: case 2:
int16_Return = -1; // 処理継続
break;
default:
*puint8_JobNum = 0;
int16_Return = 1;
break; // NG
}
return(int16_Return);
}
2) Transact_AQM1602 の動作
a) case 0:
AQM1602表示に使用する I2C1 を初期化します。
b) case 1:
AQM1602 の初期設定を行います。
b) case 2:
表示データ "0123456789ABCDEF" を AQM1602 の 1行目に書き込みます。
表示結果は以下のようになります。
c) case 3:
1000mSec 待ちます。
d) case 4:
表示データ "GHIJKLMNOPQRSTUV" を AQM1602 の 2行目に書き込みます。
表示結果は以下のようになります。
e) case 5:
1000mSec 待ちます。
f) case 6:
AQM1602 の表示をクリアします。
g) case 7:
表示データ "Nice to meet you" を AQM1602 の 1行目に書き込みます。
表示結果は以下のようになります。
h) case 8:
1000mSec 待ちます。
i) case 9:
表示データ "Take it easy! " を AQM1602 の 2行目に書き込みます。
表示結果は以下のようになります。
j) case 10:
1000mSec 待ちます。
k) case 11:
AQM1602 の表示をクリアします。
クリア動作終了後、表示データバッファ STC_uint8_Data_TX に
"0123456789ABCDEF" をセットして、処理番号に 2 をセットします。
Transact_AQM1602 の処理は、再び case 2: から実行されます。
こうして、Transact_AQM1602 の処理は、case 2: - case 11: をループします。
AQM1602 コマンド書き込み Write_Command_AQM1602 の説明
1) Write_Command_AQM1602 のソース
モジュール Write_Command_AQM1602 は
Cont_AQM1602/Cont_AQM1602B.c 内に記述されています。
モジュール Write_Command_AQM1602 のソースを以下に示します。
//-------------------------------------------------------
// AQM1602 コマンド書き込み
//-------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint8_t uint8_Number_TX : 送信データ数
// uint8_t *puint8_Data_TX : 送信データを格納したバッファのポインタ
// uint32_t uint32_Interval : 待ち時間 (mSec)
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG終了
//-------------------------------------------------------
int16_t Write_Command_AQM1602(uint8_t *puint8_JobNum,
uint8_t uint8_Number_TX, uint8_t *puint8_Data_TX,
uint32_t uint32_Interval)
{
static uint8_t STC_uint8_JobNum_Wait; // 時間待ちの処理番号
static uint32_t STC_uint32_tikstart; // 時間待ち開始時のカウント数
static uint32_t STC_uint32_Interval; // 待ち時間
static uint8_t STC_uint8_JobNum_I2C; // I2C処理番号
static uint8_t STC_uint8_Count_TX; // 送信回数カウンタ
static uint8_t STC_uint8_I2C_TX[2]; // I2C送信データ
int16_t int16_Return;
switch(*puint8_JobNum)
{
case 0:
STC_uint8_JobNum_I2C = 0; // I2C処理番号初期化
STC_uint8_Count_TX = 0; // 送信回数カウンタ初期化
// I2C送信データセット
STC_uint8_I2C_TX[0] = 0x00; // control bytee
STC_uint8_I2C_TX[1] = puint8_Data_TX[STC_uint8_Count_TX]; // data byte : Instruction
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 1:
int16_Return = -1; // 処理継続
break;
case 1:
//------------------------------------------------------------------------
// I2C Master送信 : Register指定 1byte + 設定データ 1byteを送信
//------------------------------------------------------------------------
//引数 :
// uint8_t *puint8_JobNum : 処理番号
// uint8_t *puint8_TxBuffer : 送信データが格納されたBufferのポインタ
// uint16_t uint16_TxNumber : 送信データ数
//戻り値 :
// -1 : 処理中
// 0 : OK
// 1 : NG
//------------------------------------------------------------------------
int16_Return = I2C1_Master_TxByte(&STC_uint8_JobNum_I2C,
STC_uint8_I2C_TX, (uint16_t)2);
if(int16_Return == -1){
// 処理中
break; // 処理番号維持 : 処理継続 : case 1: をループ
}
if(int16_Return != 0){
// NG終了
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break;
}
STC_uint8_JobNum_Wait = 0; // 時間待ちの処理番号初期化
STC_uint32_Interval = uint32_Interval; // 待ち時間
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 2:
int16_Return = -1; // 処理継続
break;
case 2:
//------------------------------------------------------
// mSec待ちシーケンス : 処理番号使用 : 複数呼び出し用
//------------------------------------------------------
// 戻り値が -1 以外になるまで、繰り返し呼び出してください。
//------------------------------------------------------
// 引数 :
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint32_t *puint32_tikstart : 時間待ち開始時のカウント数
// uint32_t uint32_mSec : 待ち時間(mSec)
// 戻り値 :
// -1 : 処理中 : 時間が経過していない。
// 0 : OK終了 : 時間が経過した。
// 1 : NG終了
//------------------------------------------------------
int16_Return = Wait_mSec_Seq_Multi(&STC_uint8_JobNum_Wait,
&STC_uint32_tikstart,
STC_uint32_Interval);
if(int16_Return == -1){
// 処理中 : 時間未経過
break; // 処理番号維持 : 処理継続 : case 2: をループ
}
STC_uint8_Count_TX++; // 送信回数カウンタ インクリメント
// 送信回数判定
if(STC_uint8_Count_TX < uint8_Number_TX){
// 指定された送信回数に達していない。
// I2C送信データセット
STC_uint8_I2C_TX[1] = puint8_Data_TX[STC_uint8_Count_TX]; // data byte : Instructio
*puint8_JobNum = 1; // 処理番号 1 に戻る。: case 1:
int16_Return = -1; // 処理継続
break;
}
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break; // 処理終了
default:
*puint8_JobNum = 0;
int16_Return = 1;
break; // NG
}
return(int16_Return);
}
2) Write_Command_AQM1602 の動作
a) case 0:
I2C処理番号初期化 と 送信回数カウンタ初期化 を行い、
送信データバッファ STC_uint8_Data_TX に
control byte と Instruction をセットします。
b) case 1:
AQM1602 に control byte と Instruction を送信します。
c) case 2:
指定された時間を待ちます。
時間待ち終了後、送信回数を判定します。
送信回数に達していない場合
STC_uint8_I2C_TX[1] に次の Instruction をセットして、
処理番号を 1 にします。
送信回数に達するまで case 1: と case 2: をループします。
送信回数に達した場合
処理番号を 0 にして、処理を終了します。
AQM1602 データ書き込み Write_Data_AQM1602 の説明
1) Write_Data_AQM1602 のソース
モジュール Write_Data_AQM1602 は
Cont_AQM1602/Cont_AQM1602B.c 内に記述されています。
モジュール Write_Data_AQM1602 のソースを以下に示します。
//-------------------------------------------------------
// AQM1602 データ書き込み
//-------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint8_t uint8_Address : データ書き込みアドレス
// uint8_t uint8_Number_TX : 送信データ数
// uint8_t *puint8_Data_TX : 送信データを格納したバッファのポインタ
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG終了
//-------------------------------------------------------
int16_t Write_Data_AQM1602(uint8_t *puint8_JobNum,
uint8_t uint8_Address,
uint8_t uint8_Number_TX, uint8_t *puint8_Data_TX)
{
static uint8_t STC_uint8_JobNum_I2C; // I2C処理番号
static uint8_t STC_uint8_Count_TX; // 送信回数カウンタ
static uint8_t STC_uint8_Data_TX[4]; // I2C送信データ
int16_t int16_Return;
switch(*puint8_JobNum)
{
case 0:
STC_uint8_JobNum_I2C = 0; // I2C処理番号初期化
STC_uint8_Count_TX = 0; // 送信回数カウンタ初期化
// 送信データセット
STC_uint8_Data_TX[0] = uint8_Address; // 表示アドレス
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 1:
int16_Return = -1; // 処理継続
break;
case 1:
//-------------------------------------
// 表示アドレスセット
//-------------------------------------
//-------------------------------------------------------
// AQM1602 コマンド書き込み
//-------------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// uint8_t uint8_Number_TX : 送信データ数
// uint8_t *puint8_Data_TX : 送信データを格納したバッファのポインタ
// uint32_t uint32_Interval : 待ち時間 (mSec)
// 戻り値:
// -1 : 処理中
// 0 : OK終了
// 1 : NG終了
//-------------------------------------------------------
int16_Return = Write_Command_AQM1602(&STC_uint8_JobNum_I2C,
(uint8_t)1, STC_uint8_Data_TX,
(uint32_t)2);
if(int16_Return == -1){
// 処理中
break; // 処理番号維持 : 処理継続 : case 1: をループ
}
if(int16_Return != 0){
// NG終了
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break; // 処理終了
}
// 送信データセット
STC_uint8_Data_TX[0] = 0x40; // control byte
STC_uint8_Data_TX[1] = puint8_Data_TX[STC_uint8_Count_TX]; // data byte ; 表示データ
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 2:
int16_Return = -1; // 処理継続
break;
case 2:
//------------------------------------
// 表示データ書き込み
//------------------------------------
//------------------------------------------------------------------------
// I2C Master送信
//------------------------------------------------------------------------
//引数 :
// uint8_t *puint8_JobNum : 処理番号
// uint8_t *puint8_TxBuffer : 送信データが格納されたBufferのポインタ
// uint16_t uint16_TxNumber : 送信データ数
//戻り値 :
// -1 : 処理中
// 0 : OK
// 1 : NG
//------------------------------------------------------------------------
int16_Return = I2C1_Master_TxByte(&STC_uint8_JobNum_I2C,
STC_uint8_Data_TX, (uint16_t)2);
if(int16_Return == -1){
// 処理中
break; // 処理番号維持 : 処理継続 : case 2: をループ
}
if(int16_Return != 0){
// NG終了
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break; // 処理終了
}
(*puint8_JobNum)++; // 次の処理番号に移行する。 : case 3:
int16_Return = -1; // 処理継続
break;
case 3:
//---------------------------------------------------
// LCD AQM1602 のビジーチェック
//---------------------------------------------------
// 引数:
// uint8_t *puint8_JobNum : 処理番号が格納される変数のポインタ
// 戻り値:
// -1 : 処理中
// 0 : OK
// 1 : NG
//---------------------------------------------------
int16_Return = Check_Busy_AQM1602(&STC_uint8_JobNum_I2C);
if(int16_Return == -1){
// 処理中
break; // 処理番号維持 : 処理継続 : case 3: をループ
}
if(int16_Return != 0){
// NG終了
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break; // 処理終了
}
STC_uint8_Count_TX++; // 送信回数カウンタ インクリメント
// 送信回数判定
if(STC_uint8_Count_TX < uint8_Number_TX){
// 指定された送信回数に達していない。
// 送信データセット
STC_uint8_Data_TX[1] = puint8_Data_TX[STC_uint8_Count_TX]; // data byte ; 表示データ
*puint8_JobNum = 2; // 処理番号 2 に移行する。: case 2:
int16_Return = -1; // 処理継続
break;
}
*puint8_JobNum = 0; // 処理番号初期化
// int16_Return : 結果
break; // 処理終了
default:
*puint8_JobNum = 0;
int16_Return = 1;
break; // NG
}
return(int16_Return);
}
2) Write_Data_AQM1602 の動作
a) case 0:
I2C処理番号初期化 と 送信回数カウンタ初期化 を行い、
送信データバッファ STC_uint8_Data_TX[0] に
指定された表示アドレスをセットします。
b) case 1:
モジュール Write_Command_AQM1602 により
AQM1602 に 表示アドレスをセットします。
Write_Command_AQM1602 の処理終了後、
送信データバッファ STC_uint8_Data_TX に
control byte と 表示データ をセットします。
c) case 2:
I2C通信により送信データバッファのデータを送信します。
d) case 3:
モジュール Check_Busy_AQM1602 により、ビジーをチェックします。
AQM1602 はI2Cインターフェースを使用する場合、ビジーフラグ BF を
読み込むことができないため、時間待ちで対応しています。
ビジーチェック終了後、送信回数を判定します。
送信回数に達していない場合
STC_uint8_I2C_TX[1] に次の 表示データ をセットして、
処理番号を 2 にします。
送信回数に達するまで case 2: と case 3: をループします。
送信回数に達した場合
処理番号を 0 にして、処理を終了します。
動作試験用基板 の説明
このサンプルプログラムは、
えがおのでんし製の試験用基板 Base-N446RE と IF-N446RE-I2C を
使用して動作を確認しています。
動作試験用基板 Base-N446RE の説明
さまざまな、インターフェース基板を接続して動作試験を行うことができます。
基板については、
Base-N446RE基板 の説明 をご覧ください。
動作試験用基板 IF-N446RE-I2C の説明
I2C通信を行うためのインターフェース基板です。
基板については、
IF-N446RE-I2C基板 の説明 をご覧ください。
A+-2C (ええ加減にC) のページに戻る
メールアドレス: apm2c.sumi@gmail.com
なんでも、気軽に ご相談ください。
担当:おの
えがおのでんし 案内