[工业级智能控制MCU 匠芯创D133CBS] 6 - PWM 输出
本帖最后由 御坂10032号 于 2024-8-24 20:04 编辑<p><strong><span style="font-size:24px;">简介</span></strong></p>
<p> </p>
<p>PWM(Pulse Width Modulation , 脉冲宽度调制) 是一种对模拟信号电平进行数字编码的方法,通过不同频率的脉冲使用方波的占空比用来对一个具体模拟信号的电平进行编码,使输出端得到一系列幅值相等的脉冲,用这些脉冲来代替所需要波形的设备。</p>
<p> </p>
<div style="text-align: center;"></div>
<div>
<p>上图是一个简单的 PWM 原理示意图,假定定时器工作模式为向上计数,当计数值小于阈值时,则输出一种电平状态,比如高电平,当计数值大于阈值时则输出相反的电平状态,比如低电平。当计数值达到最大值是,计数器从0开始重新计数,又回到最初的电平状态。高电平持续时间(脉冲宽度)和周期时间的比值就是占空比,范围为0~100%。上图高电平的持续时间刚好是周期时间的一半,所以占空比为50%。</p>
<p>一个比较常用的pwm控制情景就是用来调节灯或者屏幕的亮度,根据占空比的不同,就可以完成亮度的调节。PWM调节亮度并不是持续发光的,而是在不停地点亮、熄灭屏幕。当亮、灭交替够快时,肉眼就会认为一直在亮。在亮、灭的过程中,灭的状态持续时间越长,屏幕给肉眼的观感就是亮度越低。亮的时间越长,灭的时间就相应减少,屏幕就会变亮。</p>
</div>
<p> </p>
<p> </p>
<div style="text-align: center;"></div>
<p> </p>
<p>上文来自 <a href="https://www.rt-thread.org/document/site/#/rt-thread-version/rt-thread-standard/programming-manual/device/pwm/pwm" target="_blank">RT-Thread文档中心PWM</a>, 同时在匠芯创AIC文档中心RTOS SDK-> 接口-> <a href="https://aicdoc.artinchip.com/topics/sdk/pwm-user-guide-luban-lite.html">PWM 使用指南</a> -> <a href="https://aicdoc.artinchip.com/topics/sdk/pwm-configuration-luban-lite.html">PWM 配置</a> 下也有具体的PWM使用说明(如下图所示)</p>
<p> </p>
<p> </p>
<p> </p>
<p><strong><span style="font-size:24px;">正文</span></strong></p>
<p> </p>
<p>由于匠芯创D133CBS集成了RT-Thread,所有我们可以直接使用RT-Thread的驱动框架来驱动PWM。但是在我们使用PWM之前我们最好先在匠芯创D133CBS原理图上找到PWM的输出PIN</p>
<p> </p>
<p> </p>
<p>正好这个PWM1的输出PIN接了一个无源蜂鸣器。(需要提供振荡才会蜂鸣)</p>
<p> </p>
<p> </p>
<p>根据上述原理图得知,我们只需要给BUZZER的这个PIN提供一个PWM信号,那么就会控制 Q2的这个三极管通断,那么就会驱动蜂鸣器进行蜂鸣。</p>
<p> </p>
<p><strong><span style="font-size:24px;">配置及其编码</span></strong></p>
<p> </p>
<p>1- 首先使用<strong>menuconfig </strong>, 在<strong>board options </strong>下打开<strong>PWM1</strong> 空格选中</p>
<p> </p>
<p> </p>
<p> </p>
<p>2- 如果现在什么代码都不下,在保存配置文件之后烧录这个镜像到D132CBS中之后其中PWM命令会被导出到finsh中。 其实到这里我们就可以直接使用pwm 命令来控制蜂鸣器了.</p>
<p> </p>
<p> </p>
<p> </p>
<p>3- 尝试使用PWM 命令控制蜂鸣器 1- 初始化PWM设备(<strong>pwm probe pwm</strong>) 2- 设置pwm 频率周期等 (<strong>pwm set 1 250000 125000</strong>)3- 启动PWM输出 (<strong>pwm enable 1</strong>)</p>
<p> </p>
<p> </p>
<p>如果你按照上述步骤进行操作的话,那么蜂鸣器应该会被正确的启动,并且在执行pwm disable 1的时候会被正常关闭。</p>
<p> </p>
<p><span style="font-size:20px;"><strong>解释</strong></span></p>
<p> </p>
<p><strong>pwm probe 【device】</strong>的命令主要是为了初始化PWM设备。 这里的 <strong>device </strong>可以使用 <strong>list device </strong>命令找到</p>
<p> </p>
<p> </p>
<p> </p>
<p><strong>pwm set [通道] [周期] </strong>的命令请参考RT-thread 关于PWM的<a href="https://www.rt-thread.org/document/site/#/rt-thread-version/rt-thread-standard/programming-manual/device/pwm/pwm" target="_blank">文档</a>, 如下图所示</p>
<p> </p>
<p> </p>
<p> </p>
<p><strong><span style="font-size:24px;">代码实现</span></strong></p>
<p> </p>
<p>下面我们来看下,如何使用代码来实现PWM的输出。</p>
<p> </p>
<p>1- 首先包含 rtdevice的头文件</p>
<pre>
<code>#include <rtdevice.h></code></pre>
<p>2- 定义pwm设备的名称和pwm设备的结构体</p>
<pre>
<code>#define PWM_DEV_NAME "pwm" /* PWM设备名称 */
struct rt_device_pwm *pwm_dev;</code></pre>
<p>3- 定义pwm周期和pulse时间</p>
<pre>
<code>rt_uint32_t period, pulse;</code></pre>
<p>4- 设置PWM周期,和pulse时间以及初始化pwm设备</p>
<pre>
<code class="language-cpp"> period = 250000; /* 周期为0.5ms,单位为纳秒ns */
pulse = 125000;/* PWM脉冲宽度值,单位为纳秒ns */
pwm_dev = (struct rt_device_pwm *)rt_device_find(PWM_DEV_NAME);
if (pwm_dev != RT_NULL)
{
rt_kprintf("Fond PWM\r\n");
}</code></pre>
<p>5- 设置PWM通道频率pulse时间等</p>
<pre>
<code>rt_pwm_set(pwm_dev, 1, period, pulse);</code></pre>
<p>6- 启动PWM</p>
<pre>
<code class="language-cpp">rt_pwm_enable(pwm_dev, 1);</code></pre>
<p> </p>
<p><strong>完整代码如下</strong></p>
<pre>
<code class="language-cpp">/*
* Copyright (c) 2022, ArtInChip Technology Co., Ltd
*
* SPDX-License-Identifier: Apache-2.0
*
* Authors: weilin.peng@artinchip.com
*/
#include <rtthread.h>
#include <rtdevice.h>
#ifdef RT_USING_ULOG
#include <ulog.h>
#endif
#define PWM_DEV_NAME "pwm" /* PWM设备名称 */
struct rt_device_pwm *pwm_dev;
rt_uint32_t period, pulse;
int main(void)
{
period = 250000; /* 周期为0.5ms,单位为纳秒ns */
pulse = 125000;/* PWM脉冲宽度值,单位为纳秒ns */
pwm_dev = (struct rt_device_pwm *)rt_device_find(PWM_DEV_NAME);
if (pwm_dev != RT_NULL)
{
rt_kprintf("Fond PWM\r\n");
}
rt_pwm_set(pwm_dev, 1, period, pulse);
rt_pwm_enable(pwm_dev, 1);
return 0;
}
</code></pre>
<p> </p>
<p>将代码烧录到开发板上之后,上电的时候蜂鸣器即开始蜂鸣。同时将开发板倒过来使用万用表打到频率档即可测量出PWM的占空比和周期(可能由于万用表没电了的缘故,我刚刚测量,非常准4khz 和正好50%的占空比, 现在误差变的很大)</p>
<p> </p>
<p> </p>
<p><strong>频率</strong></p>
<p> </p>
<p> </p>
<p> </p>
<p><strong>占空比</strong></p>
<p> </p>
<p> </p>
<p> </p>
<p><strong><span style="font-size:24px;">总结</span></strong></p>
<p> </p>
<p>本文主要介绍了匠芯创D133CBS如何在RTT环境下的PWM配置以及应用过程。通过上文的配置以及编码,极大的降低了用户使用PWM的难度,用户可以轻松自由配置PWM输出任意频率以及占空比等。</p>
<p> </p>
<p><strong>历史测评链接</strong></p>
<p> </p>
<p>[工业级智能控制MCU 匠芯创D133CBS] 1 - 开箱及其环境搭建 <a href="https://bbs.eeworld.com.cn/thread-1290588-1-1.html" target="_blank">https://bbs.eeworld.com.cn/thread-1290588-1-1.html</a></p>
<p>[工业级智能控制MCU 匠芯创D133CBS] 2 - 创建项目及其注意事项 <a href="https://bbs.eeworld.com.cn/thread-1290861-1-1.html" target="_blank">https://bbs.eeworld.com.cn/thread-1290861-1-1.html</a></p>
<p>[工业级智能控制MCU 匠芯创D133CBS] 3 - GPIO-IO中断 <a href="https://bbs.eeworld.com.cn/thread-1290902-1-1.html" target="_blank">https://bbs.eeworld.com.cn/thread-1290902-1-1.html</a></p>
<p>[工业级智能控制MCU 匠芯创D133CBS] 4- BUG 反馈 (SDK lunch11 包更新错误) <a href="https://bbs.eeworld.com.cn/thread-1290904-1-1.html" target="_blank">https://bbs.eeworld.com.cn/thread-1290904-1-1.html</a></p>
<p>[工业级智能控制MCU 匠芯创D133CBS] 5- 使用RTT-软件包结合IIC读取BH1750 <a href="https://bbs.eeworld.com.cn/thread-1291002-1-1.html" target="_blank">https://bbs.eeworld.com.cn/thread-1291002-1-1.html</a></p>
<p>用示波器测一下 PWM 输出波形就更完美</p>
Jacktang 发表于 2024-8-25 21:48
用示波器测一下 PWM 输出波形就更完美
<p>可惜了啊, 我没有示波器,一直都想测量测量电源的纹波</p>
页:
[1]