本文转自RA生态工作室:
瑞萨“RA MCU众测宝典”OLED专题再添实战新篇!
开启宝典
前期回顾
瑞萨RA MCU众测宝典 | 手把手搞定瑞萨FPB-RA0E2驱动OLED显示
瑞萨RA MCU众测宝典 | 手把手搞定瑞萨FPB-RA0E2串口打印ADC电压
本文介绍了瑞萨FPB RA0E2开发板实现OLED驱动显示ADC采集电压值,并串口打印ADC值和电压值的项目设计。
一
项目介绍
驱动OLED:配置硬件IIC通信,实现OLED驱动;
OLED实时显示ADC电压;
串口输出ADC采集数值和电压转换数值;
二
工程创建
打开e2studio软件,依次选择文件-新建-C/C++-RA项目;
设备选择-Board-选择FPB-RA0E2,选择正确的工具链和调试器,进入工程配置界面;
进入Clocks标签页,使能UTASEL Src:HOCO;
IIC配置
新建IIC通信堆栈New Stack-Connectivity-I2C Master (r_sau_i2c) ;
属性配置中,Slave Address设置为0x3c,检查引脚对应关系为SCL00-P500、SDA00-P502;
ADC配置
进入Stacks标签页,新建ADC堆栈New Stack-Analog-ADC (r_adc_d) ;
选中ADC堆栈,进入属性标签及参数配置;
在Input选项下,通道模式为扫描,输入通道选择7,可根据开发板Arduino扩展接口选择;
中断配置,Interrupts-Callback值修改为adc_callback,优先级设置为Priority 2,触发源为软件;
引脚Pins开启AN007对应P015引脚;
配置完成后,点击Generate Project Content,生成工程代码,构建工程。
三
工程代码
在左侧的项目目录中,打开src/hal_entry.c文件,添加如下关键代码:
滑动查看完整内容
#include"hal_data.h"#include"oled.h"#include"bmp.h"FSP_CPP_HEADERvoidR_BSP_WarmStart(bsp_warm_start_event_t event);FSP_CPP_FOOTER
i2c_master_event_t i2c_event = I2C_MASTER_EVENT_ABORTED;voidsau_i2c_master_callback(i2c_master_callback_args_t *p_args){ i2c_event = I2C_MASTER_EVENT_ABORTED; if (NULL != p_args) { /* capture callback event for validating the i2c transfer event*/ i2c_event = p_args->event; }}fsp_err_t err = FSP_SUCCESS;int timeout_ms = 100;
/*------------- ADC callback -------------*/volatilebool scan_complete_flag = false;voidadc_callback(adc_callback_args_t * p_args){ FSP_PARAMETER_NOT_USED(p_args); scan_complete_flag = true;}
voidhal_entry(void){ /* TODO: add your own code here */ /* Initializes the ADC module. */ err = R_ADC_D_Open(&g_adc_ctrl, &g_adc_cfg); /* Handle any errors. This function should be defined by the user. */ assert(FSP_SUCCESS == err);
/* Enable channels. */ err = R_ADC_D_ScanCfg(&g_adc_ctrl, &g_adc_channel_cfg); assert(FSP_SUCCESS == err);
/* Initialize IIC OLED */ err = R_SAU_I2C_Open(&g_i2c0_ctrl, &g_i2c0_cfg); assert(FSP_SUCCESS == err); OLED_Init(); OLED_Clear(); OLED_DrawBMP(0, 0, 128, 8, BMP1, 0); // initialized page -> Renesas logo R_BSP_SoftwareDelay(200, BSP_DELAY_UNITS_MILLISECONDS);
/*----------- Frame ------------*/ OLED_Clear(); OLED_ShowString(0, 0, " ADC ", 16, 1); OLED_ShowCHinese(56, 0, 0, 1); // 电 OLED_ShowCHinese(72, 0, 1, 1); // 压 OLED_ShowCHinese(88, 0, 2, 1); // 表 OLED_ShowString(104, 0, " ", 16, 1);
OLED_ShowString(4, 3, "ADC", 16, 0); OLED_ShowCHinese(32, 3, 3, 0); // 值 OLED_ShowChar(48, 3, ':', 16, 0);
OLED_ShowCHinese(0, 6, 0, 0); // 电 OLED_ShowCHinese(16, 6, 1, 0); // 压 OLED_ShowCHinese(32, 6, 3, 0); // 值 OLED_ShowChar(48, 6, ':', 16, 0); OLED_ShowChar(100, 6, 'V', 16, 0);
while (1) { uint16_t adc_data0 = 0; double a0; /* Enable scan triggering from ELC events. */ (void) R_ADC_D_ScanStart(&g_adc_ctrl); scan_complete_flag = false; while (!scan_complete_flag) { /* Wait for callback to set flag. */ }
err = R_ADC_D_Read(&g_adc_ctrl, ADC_CHANNEL_7, &adc_data0); assert(FSP_SUCCESS == err); a0 = (double)(adc_data0 / 4095.0) * 3.3; OLED_ShowNum(60, 3, adc_data0, 4, 16, 0); OLED_ShowDecimal(60, 6, a0, 1, 2, 16, 0); R_BSP_SoftwareDelay(500, BSP_DELAY_UNITS_MILLISECONDS); }
#if BSP_TZ_SECURE_BUILD /* Enter non-secure code */ R_BSP_NonSecureEnter();#endif}
保存文件,右键项目-构建程序;
右键项目-调试项目-上传固件至开发板。
测试效果
按照硬件连接示意图,连接开发板和OLED对应引脚;
进入调试模式,或上电复位运行;
实现了OLED实时显示ADC数值和电压转换值。
四
串口输出
在OLED显示ADC电压的同时,串口打印电压值。
工程调试
进入Stacks标签页,新建串口通信堆栈New Stack-Connectivity-UART (r_uarta) ;
串口属性配置,包括Name、回调函数、中断优先级、引脚定义(RXD-P100和TXD-P101);
进入BSP标签页,配置RA Common属性,修改Heap size (bytes) 值为 0x2000;
右键项目进入属性,选择C/C++构建-设置-GNU Arm Cross C Linker-Miscellaneous,勾选 printf、scanf以及syscalls选项。
点击Generate Project Content按钮,生成工程代码。
流程图
(向上滑动启阅)
工程代码
修改src/hal_entry.c文件,代码如下:
滑动查看完整内容
#include"hal_data.h"#include"oled.h"#include"bmp.h"#include<stdio.h>FSP_CPP_HEADERvoidR_BSP_WarmStart(bsp_warm_start_event_t event);FSP_CPP_FOOTER
fsp_err_t err = FSP_SUCCESS;volatilebool uart_send_complete_flag = false;voiduarta_callback(uart_callback_args_t * p_args){ if(p_args->event == UART_EVENT_TX_COMPLETE) { uart_send_complete_flag = true; }}
/*------------- 串口重定向 -------------*/#ifdef __GNUC__ #define PUTCHAR_PROTOTYPE int __io_putchar(int ch)#else
#endif
PUTCHAR_PROTOTYPE{ err = R_UARTA_Write(&g_uarta_ctrl, (uint8_t *)&ch, 1); if(FSP_SUCCESS != err) __BKPT(); while(uart_send_complete_flag == false){} uart_send_complete_flag = false; return ch;}
int _write(int fd,char *pBuffer,int size){ for(int i=0;i<size;i++) { __io_putchar(*pBuffer++); } return size;}
/* ------------- IIC ------------*/i2c_master_event_t i2c_event = I2C_MASTER_EVENT_ABORTED;voidsau_i2c_master_callback(i2c_master_callback_args_t *p_args){ i2c_event = I2C_MASTER_EVENT_ABORTED; if (NULL != p_args) { /* capture callback event for validating the i2c transfer event*/ i2c_event = p_args->event; }}//fsp_err_t err = FSP_SUCCESS;int timeout_ms = 100;
/*------------- ADC callback -------------*/volatilebool scan_complete_flag = false;voidadc_callback(adc_callback_args_t * p_args){ FSP_PARAMETER_NOT_USED(p_args); scan_complete_flag = true;}
voidhal_entry(void){ /* TODO: add your own code here */ err = R_UARTA_Open(&g_uarta_ctrl, &g_uarta_cfg); assert(FSP_SUCCESS == err); /* Initializes the ADC module. */ err = R_ADC_D_Open(&g_adc_ctrl, &g_adc_cfg); /* Handle any errors. This function should be defined by the user. */ assert(FSP_SUCCESS == err);
/* Enable channels. */ err = R_ADC_D_ScanCfg(&g_adc_ctrl, &g_adc_channel_cfg); assert(FSP_SUCCESS == err);
/* Initialize IIC OLED */ err = R_SAU_I2C_Open(&g_i2c0_ctrl, &g_i2c0_cfg); assert(FSP_SUCCESS == err);
OLED_Init(); OLED_Clear(); OLED_DrawBMP(0, 0, 128, 8, BMP1, 0); // initialized page -> Renesas logo R_BSP_SoftwareDelay(200, BSP_DELAY_UNITS_MILLISECONDS);
/*----------- Frame ------------*/ OLED_Clear(); OLED_ShowString(0, 0, " ADC ", 16, 1); OLED_ShowCHinese(56, 0, 0, 1); // 电 OLED_ShowCHinese(72, 0, 1, 1); // 压 OLED_ShowCHinese(88, 0, 2, 1); // 表 OLED_ShowString(104, 0, " ", 16, 1);
OLED_ShowString(4, 3, "ADC", 16, 0); OLED_ShowCHinese(32, 3, 3, 0); // 值 OLED_ShowChar(48, 3, ':', 16, 0);
OLED_ShowCHinese(0, 6, 0, 0); // 电 OLED_ShowCHinese(16, 6, 1, 0); // 压 OLED_ShowCHinese(32, 6, 3, 0); // 值 OLED_ShowChar(48, 6, ':', 16, 0); OLED_ShowChar(100, 6, 'V', 16, 0);
while (1) { uint16_t adc_data0 = 0; double a0;
/* Enable scan triggering from ELC events. */ (void) R_ADC_D_ScanStart(&g_adc_ctrl); scan_complete_flag = false;
while (!scan_complete_flag) { /* Wait for callback to set flag. */ }
err = R_ADC_D_Read(&g_adc_ctrl, ADC_CHANNEL_7, &adc_data0); assert(FSP_SUCCESS == err);
a0 = (double)(adc_data0 / 4095.0) * 3.3; printf("P015(AN007)=%d, voltage=%f\n",adc_data0,a0); OLED_ShowNum(60, 3, adc_data0, 4, 16, 0); OLED_ShowDecimal(60, 6, a0, 1, 2, 16, 0); R_BSP_SoftwareDelay(500, BSP_DELAY_UNITS_MILLISECONDS); }
#if BSP_TZ_SECURE_BUILD /* Enter non-secure code */ R_BSP_NonSecureEnter();#endif}
右键项目-调试项目-上传固件至开发板。
测试效果
OLED实时显示A0管脚采集的电压值。
同时串口输出ADC值和电压转换数值。
五
总结
本文介绍了瑞萨FPB RA0E2开发板实现OLED实时显示ADC电压、同时串口打印ADC值和电压值的项目设计,为瑞萨系列产品的快速开发和应用提供了参考。
#瑞萨电子 #单片机 #嵌入式硬件 #物联网
需要技术支持?
如您在使用瑞萨MCU/MPU产品中有任何问题,可识别下方二维码或复制网址到浏览器中打开,进入瑞萨MCU/MPU官方技术论坛寻找答案或获取在线技术支持。
https://bbs.21ic.com/renesas
1
END
1
推荐阅读
瑞萨RA MCU众测宝典 | 环境搭建之【FPB-RA0E2】批量加载例程
瑞萨RA MCU众测宝典 | ADC/DAC之【FPB-RA0E2】ADC快速使用
瑞萨RA MCU众测宝典 | 串口实战之【FPB-RA0E2】UART串口打印HELLO WORLD一步到位!
股票
板块
用户
资讯
评论 (0)