1. 项目需求
利用TI MSPM0L1306开发板设计一个基于温度变化的展示系统实现:
1)利用热敏电阻检测温度的变化
2)模块上LCD屏实时显示当前温度和设定的温度阈值
3)RGB LED根据温度高低展示不同颜色
4)利用按键设置温度阈值
5)利用电位计调节LED显示的模式和强度
2. 功能完成
2.1 温度获取
温度获取借助温度传感器得到温度数据,经过数据处理即可得到温度值。给加热模块供电后,传感器实时获取周围变化的温度。
2.2 LCD显示
LCD可实现对所获得的温度以及人为设定的阈值温度的实时显示,并通过ASCII编码实现了对汉字的显示。
2.3 RGB LED显示
如果实时温度低于25℃,RGB LED显示为绿色;实时温度在25℃到阈值温度之间,RGB LED显示为蓝色;实时温度高于阈值温度,RGB LED显示为红色。
2.4 温度阈值设置
初始阈值温度为40℃,按键S1阈值温度增加一度,按键S2阈值温度降低一度,可以设置的阈值温度范围为10~50℃,如果设置超出范围,所显示的阈值温度会变为20℃。
2.5 电位计调节LED显示
利用定时器的捕获功能来获取电位计输出pwm波的占空比,判断电位计所处位置,电位计位置发生移动时,LED颜色随之改变。
3. 实现思路
3.1 温度传感器通过IIC接口和MCU完成通信,发回温度寄存器里的数据,然后MCU根据数据格式完成相应转换得到正确温度值。
3.2 LCD利用软件模拟的SPI,将LCD显存和屏幕像素点一一对应,给显存里的某个位置写入RGB不同的颜色,以此完成LCD的显示。
3.3 电位计的输出是通过运放电路输出pwm波,电位计不同数值的情况输出的pwm波脉宽是不一样的,也就是占空比不一样,通过定时器的捕获功能来获取占空比,来判断电位器位置。
4. 硬件介绍
本项目利用了TI MSPM0L1306开发板和ESP32模块,功能实现中使用了ESP32模块的LCD显示屏、RGB LED、电位计、电阻加热电路模块以及温度传感器。
通过已有平台资料,知道了温度传感器型号为nst112,由此查询到对应的数据手册,便于之后温度获取代码的编写。
5. 功能实现
5.1 温度获取
5.1.1 程序流程图
5.1.2 温度传感器数据获取
利用IIC通信获取温度传感器模块数据,IIC使用标准读写时序,主先发一个地址信号,然后对应地址的芯片接收到后发一个确认,然后在读模式,访问温度寄存器,读回温度数据。
通过对nst112数据手册的学习可知,IIC读时序所返回的温度值默认是十二位,所以取前一个的八位和后一个的四位,拼成全部的未经处理的初始温度值。
DL_I2C_startControllerTransfer(I2C_INST, I2C_TARGET_ADDRESS,
DL_I2C_CONTROLLER_DIRECTION_RX, I2C_RX_PACKET_SIZE);
for (uint8_t i = 0; i < I2C_RX_PACKET_SIZE; i++)
{
while (DL_I2C_isControllerRXFIFOEmpty(I2C_INST));
gRxPacket[i] = DL_I2C_receiveControllerData(I2C_INST);
}
temp_value = ((gRxPacket[0]<<8)|gRxPacket[0]) >> 4;
5.1.3 温度转换计算
查找数据手册得到以下温度转换计算公式:
temp = ((float)temp_value) * VAL_BASE;
VAL_BASE取值为0.0625(通过nst112数据手册查找所得)
5.2 LCD显示
5.2.1 代码逻辑说明
LCD使用SPI通信,利用软件模拟SPI。工作逻辑是将LCD的显存和整个屏幕上的像素点一一对应,给显存里的某个位置写入RGB不同的颜色,就会在LCD的对应位置上显示。
整个LCD显示是通过先描点,然后根据描点函数写字符函数,再到写字符串函数,再到写汉字函数、写数字函数,这样一级一级嵌套显示的。
5.2.2 显示代码程序流程图
5.2.3 LCD主代码展示(附代码注释)
void lcd_show_hz1616(uint16_t x, uint16_t y, uint8_t c[2], uint16_t pen_color, uint16_t back_color)
{
unsigned char i, j, k, m;
unsigned short x0, y0;
x0 = x;
y0=y;
lcd_set_address(x, y, x + 16 - 1, y + 16 - 1); //选择坐标位置
for (k = 0; k < 64; k++)
{
if ((code_GB_16[k].Index[0]==c[0]) && (code_GB_16[k].Index[1]==c[1])) //寻找对应汉字(一个汉字需要两个字节)
{
for(i = 0; i < 32; i++)
{
m = code_GB_16[k].Msk[i]; //读取对应字节数据
for(j = 0; j < 8; j++) //显示一个字节,一个字节8位也就是8个点
{
//判断是否是要写入点
if( (m&0x80) == 0x80)
{
lcd_drawpoint(x, y, pen_color); // 如果是给字体颜色
}
else
{
lcd_drawpoint(x, y, back_color); //如果不是为背景,给背景色
}
m <<= 1; //左移一位,判断下一点
x++;
if(x - x0 == 16)
{
x = x0;
y++;
if(y - y0 >= 16)
{
return;
}
}
}
}
}
}
}
5.3 RGB LED显示
RGB LED根据温度高低展示不同颜色的任务功能在实现逻辑上并无难度,只需要设定不同温度范围所对应的LED颜色,对实时温度进行范围判定后利用DL_GPIO_clearPins()和DL_GPIO_setPins()函数进行颜色显示即可。
5.4 温度阈值设置
初始温度阈值定义为temp_thre,按S1键上升沿触发中断,检测到处于高电平,温度阈值增加一度(temp_thre++);按S2键下降沿触发中断,检测到处于低电平,温度阈值降低一度(temp_thre--)。
同时,在阈值温度随人为按键改变时,对阈值温度进行范围判断,如果超出10~50℃的设置范围,则将阈值温度重设为20℃(temp_thre=20)。
5.5 电位计调节LED显示
5.5.1 代码逻辑说明
电位计的输出是通过运放电路输出pwm波,电位计不同数值的情况输出的pwm波脉宽是不一样的,也就是占空比不一样,通过定时器的捕获功能来获取占空比,由此来判断电位器位置,根据电位计位置对LED显示进行调整。
5.5.2 程序流程图
5.5.3 占空比获取
gLoadValue = DL_TimerG_getLoadValue(CAPTURE_0_INST);
pwmPeriod = gLoadValue - gCaptureCnt;
pwmDuty = ((gLoadValue - DL_TimerG_getCaptureCompareValue(CAPTURE_0_INST, DL_TIMER_CC_0_INDEX)) *100)
6. 遇到的主要难题
6.1 陌生的主板和开发环境
本次寒假练的项目是我第一次使用TI的主板进行项目设计,TI现目前在市面和高校中的使用率较低,因此市面上对于TI主板的学习资料较少,本次项目所使用的TI MSPM0L1306主板的资料更是少见。对于本次所使用的开发软件CCS Theia 1.3.0也是第一次使用。毫无疑问,本次项目开发最困难的是学习并上手本次所用的对我来说无比陌生的主板和开发环境。
对此无比感谢硬禾学堂在项目前期所提供的培训和相关资料,在加上对B站UP主物联世界相关视频的学习,对TI主板和CCS也逐渐上手,在项目设计过程中不断学习,不断熟悉。
6.2 温度传感器
温度传感器nst112的使用上手着实困难,无疑,温度实时检测是整个项目的关键,但nst112的数据手册是全英文版本,阅读理解难度较高,只能借助翻译软件和网络现有资料逐步理解。
6.3 RGB LED的颜色显示
LED的三色是红绿蓝,与现实生活中红黄蓝的三原色有出于,刚开始使用时确实在DL_GPIO_clearPins()和DL_GPIO_setPins()两个函数的使用上闹了乌龙。
7. 未来的计划和建议
计划:
TI MSPM0L1306开发板以及活动配套的适用于数字系统输入、输出的扩展板元器件丰富,所能实现的功能强大,计划在之后的学习中继续使用,避免浪费。同时,借助这个活动使自己开始上手了TI的主板以及配套的CCS软件,这无疑是最大的收获。nst112的使用也从最开始的一塌糊涂不知从何开始到后来的得心应手,相信在之后的学习中面对类似的陌生器件也能更快上手。这次项目中编写了许多器件的驱动代码,这无疑是一笔巨大的财富,下次在使用相关器件时可以直接上手使用。感谢此次活动,大大提升了我的编程能力、硬件使用能力和手册阅读能力,也为我参加之后的电赛以及相关的设计活动提供了莫大的帮助。
建议:
1)可以提供更加丰富的平台选择,比如STM32。
毫无疑问,STM32的使用人群更广,可以调动更多高校学生参与,同时使用同学们更熟悉的主板,可以提高题目难度,更好地达到“寒假练”的效果。
2)项目前期的培训可以提供一些实操的演示,便于同学们初步上手学习。
学堂所提供的项目前期的培训很细致,强调了不少重点,但希望可以带着观看的同学们进行一些实操的演示和讲解,使后期同学们使用时更加容易和熟悉。