本帖最后由 正点原子运营 于 2024-5-6 09:55 编辑
1)实验平台:正点原子 M144Z-M3 STM32F103最小系统板
2) 章节摘自【正点原子】M144Z-M3最小系统板使用指南——STM32F103版
6)正点原子STM32技术交流QQ群:725095144
本章将使用软件的方式控制STM32F103的DAC输出指定幅值、频率和个数的三角波。通过本章的学习,读者将学习到DAC的使用。 本章分为如下几个小节: 38.1 硬件设计 38.2 程序设计 38.3 下载验证
38.1 硬件设计 38.1.1 例程功能 1. 按下WKUP按键,PA4引脚输出100个三角波1(幅值3.3V,频率100Hz,采样点2000) 2. 按下KEY0按键,PA4引脚输出100个三角波2(幅值3.3V,频率100Hz,采样点20) 3. LED0闪烁,提示程序正在运行
38.1.2 硬件资源 1. LED LED0 - PB5 2. 正点原子2.8/3.5/4.3/7/10寸TFTLCD模块 3. 按键 WKUP - PA0 KEY0 - PE4 4. DAC Channel1 - PA4
38.1.3 原理图 本章实验使用的DAC为STM32F103的片上资源,因此没有对应的连接原理图。
38.2 程序设计 38.2.1 HAL库的DAC驱动 本章实验与上一章实验十分相似,上一章实验使用按键控制DACChannel1输出“离散”的电压,而本章实验的是使用软件算法控制DAC Channel1输出的电压,使之输出一个三角波,因此大部分内容都是相似的,以及操作DAC的方式都是一样的,因此请见第38.2.1小节中HAL库的DAC驱动的相关内容。
38.2.2 DAC驱动 本章实验的DAC驱动主要负责向应用层提供DAC的初始化以及控制DAC输出指定幅值、频率和个数的三角波的函数。本章实验中,DAC的驱动代码包括dac.c和dac.h两个文件。 本章实验DAC驱动中对DAC的初始化与上一章实验中对DAC的初始化方式一致,请见第38.2.2小节中DAC初始化的相关内容提供。本小节仅介绍通过软件控制DAC输出三角波的函数,如下所示: - /**
- *@brief 设置DAC输出三角波
- *@param max_value: 三角波波峰电压数字量
- *@param interval: 每个采样点的时间间隔,单位:微妙
- *@param samples: 一个三角波周期采样点的个数
- *@param number: 输出三角波的个数
- *@retval 无
- */
- voiddac_triangular_wave( uint16_t max_value,
- uint16_t interval,
- uint16_t samples,
- uint16_t number)
- {
- uint16_t incval;
- uint16_t curval;
- uint16_t sample_index;
- uint16_t wave_index;
-
- /* 确保采样点个数为偶数 */
- samples = ((samples + 1) >> 1) << 1;
- /* 计算每个采样点的步进值 */
- incval = max_value / (samples >> 1);
- if (incval == 0)
- {
- return;
- }
-
- for (wave_index=0; wave_index<number; wave_index++)
- {
- curval = 0;
- HAL_DAC_SetValue(&g_dac_handle, DAC_DACX_CHY, DAC_ALIGN_12B_R, curval);
-
- /* 输出上升沿 */
- for (sample_index=0; sample_index<(samples >> 1); sample_index++)
- {
- curval += incval;
- HAL_DAC_SetValue( &g_dac_handle,
- DAC_DACX_CHY,
- DAC_ALIGN_12B_R,
- curval);
- delay_us(interval);
- }
-
- /* 输出下降沿 */
- for (sample_index=0; sample_index<(samples >> 1); sample_index++)
- {
- curval -= incval;
- HAL_DAC_SetValue( &g_dac_handle,
- DAC_DACX_CHY,
- DAC_ALIGN_12B_R,
- curval);
- delay_us(interval);
- }
- }
- }
复制代码可以看到,该函数就是每间隔一段时间就修改一次DAC的输出电压,以控制DAC输出指定的三角波,对于该函数的实现,读者无需深究,仅需会使用该函数即可。
38.2.3 实验应用代码 本章实验的应用代码,如下所示: - int main(void)
- {
- uint8_t t = 0;
- uint8_t key;
-
- HAL_Init(); /* 初始化HAL库 */
- sys_stm32_clock_init(RCC_PLL_MUL9); /* 配置时钟,72MHz */
- delay_init(72); /* 初始化延时 */
- usart_init(115200); /* 初始化串口 */
- led_init(); /* 初始化LED */
- key_init(); /* 初始化按键 */
- lcd_init(); /* 初始化LCD */
- dac_init(); /* 初始化DAC */
-
- lcd_show_string(30, 50, 200, 16, 16, "STM32", RED);
- lcd_show_string(30, 70, 200, 16, 16, "DACTriangular Wave TEST", RED);
- lcd_show_string(30, 90, 200, 16, 16, "ATOM@ALIENTEK", RED);
-
- lcd_show_string(30, 110, 200, 16, 16, "WK_UP:Wave1KEY0:Wave2", RED);
-
- while (1)
- {
- key = key_scan(0);
- if (key == WKUP_PRES)
- {
- /* DAC输出三角波1,幅值3.3V,频率100Hz,采样点2000 */
- lcd_show_string(30, 130, 200, 16, 16, "DACWave1", BLUE);
- dac_triangular_wave(4095, 5, 2000, 100);
- lcd_show_string(30, 130, 200, 16, 16, "DACNone", BLUE);
- }
- else if (key == KEY0_PRES)
- {
- /* DAC输出三角波2,幅值3.3V,频率100Hz,采样点20 */
- lcd_show_string(30, 130, 200, 16, 16, "DACWave2", BLUE);
- dac_triangular_wave(4095, 500, 20, 100);
- lcd_show_string(30, 130, 200, 16, 16, "DACNone", BLUE);
- }
-
- if (++t == 20)
- {
- t = 0;
- LED0_TOGGLE();
- }
-
- delay_ms(10);
- }
- }
复制代码应用代码中会初始化DAC Channel1(PA4引脚),完成初始化后,便不断地扫描按键,并根据扫描到的按键,控制DAC Channel1输出指定幅值、频率和个数三角波。
38.3 下载验证 在完成编译和烧录操作后,便可分别按下KEY0按键和WKUP按键控制DAC Channel1输出不同类型的三角波,DAC Channel1输出的三角波可通过示波器观察PA4引脚(DAC Channel1输出引脚)看到。 |