乐鑫Esp32学习之旅⑤ 接触实践esp32的pwm宽度脉冲功能的LEDC, 实现呼吸效果闪烁一盏LED灯。(附带Demo)



一 前言:

  • PWM的技术我们再熟悉不过了,只需要输出脉冲信号,即可调节灯具或者电机这些设备,在ESP32里面,官方把输出控制的PWM的功能控制器叫PWMC,因为是由他控制的,见下图:

这里写图片描述


二 前言:


  • 本博文的电路图为如下:

这里写图片描述


  • 效果:

2路PWM输出的管脚呼吸闪烁,从俺到亮,之后又渐变暗,不断循环交替!


三 官方API说明:


  • 此文档的地址:https://esp-idf.readthedocs.io/en/latest/api-reference/peripherals/ledc.html
  • 原文,个人翻译,大概讲的意思是如下:

           LED Control (LEDC)模块主要是为了调节LED的亮度而设计的,而且它也可以用于产生其他用途的PWM信号。它有16个通道,可以产生独立的波形,可以用来驱动例如RGB LED器件。


  • 我在认真阅读了这文档之后,发现esp32对调光的封装真是太好了,一共有6个时钟计数器,有8个通道,而且在调光过程中,还提供了渐变的函数,就是从一个占空比到另外一个占空比的过渡时候,是逐渐地,不是一下子跳过去的,这点非常适合LED行业的需求!

①:重要方法: ledc_fade_func_install():注册LEDC服务,在调用前使用,参数是作为是否允许中断。

这里写图片描述


②:结构体ledc_timer_config_t:配置定时器参数,ledc_mode_t是指定高速或者低速运行?ledc_timer_t是指哪个定时器,有四个0到3!定时器的位数ledc_timer_bit_t

这里写图片描述


③:配置好上面的结构体之后,请调用ledc_timer_config(),参数为上面的结构体!

这里写图片描述


③:每次改变占空比,请先调用ledc_set_fade_with_time():顾名思义就是设置渐变的时间,ledc_channel_t参数是指哪个通道,target_duty是要占空比,注意这个数值的取值和上面设置的duty_resolution的定时器位数有关系!比如duty_resolution = LEDC_TIMER_13_BIT指定为13位,则取值范围是0 到 2^13-1!说白了就是个被除数!最后调用ledc_fade_start()即可实现调光啦!

这里写图片描述


二 代码:


  • 详细见下面:


//定义2个GPIO作为PWM输出
#define  LEDC_TOTAL_NUM 2
#define LEDC_HS_TIMER          LEDC_TIMER_0
#define LEDC_HS_MODE           LEDC_HIGH_SPEED_MODE
#define LEDC_HS_CH0_GPIO       18
#define LEDC_HS_CH0_CHANNEL    LEDC_CHANNEL_0
#define LEDC_HS_CH1_GPIO       19
#define LEDC_HS_CH1_CHANNEL    LEDC_CHANNEL_1

//渐变的变大最终目标占空比
#define LEDC_TEST_DUTY         8000
//渐变的时间
#define LEDC_TEST_FADE_TIME    3000

void fun_pwm() {

    ledc_timer_config_t ledc_timer = { .duty_resolution = LEDC_TIMER_13_BIT, // resolution of PWM duty
            .freq_hz = 5000,                      // frequency of PWM signal
            .speed_mode = LEDC_HS_MODE,           // timer mode
            .timer_num = LEDC_HS_TIMER            // timer index
            };

    // Set configuration of timer0 for high speed channels
    ledc_timer_config(&ledc_timer);

    ledc_channel_config_t ledc_channel[LEDC_TOTAL_NUM] = { { .channel =
    LEDC_HS_CH0_CHANNEL, .duty = 0, .gpio_num = LEDC_HS_CH0_GPIO, .speed_mode =
    LEDC_HS_MODE, .timer_sel = LEDC_HS_TIMER },

    { .channel = LEDC_HS_CH1_CHANNEL, .duty = 0, .gpio_num = LEDC_HS_CH1_GPIO,
            .speed_mode = LEDC_HS_MODE, .timer_sel = LEDC_HS_TIMER },

    };

    int ch;
    // Set LED Controller with previously prepared configuration
    for (ch = 0; ch < LEDC_TOTAL_NUM; ch++) {
        ledc_channel_config(&ledc_channel[ch]);
    }

    // Initialize fade service.
    ledc_fade_func_install(0);

    while (1) {

        printf("1. PWM逐渐变大的周期目标 = %d\n", LEDC_TEST_DUTY);

        for (ch = 0; ch < LEDC_TOTAL_NUM; ch++) {
            ledc_set_fade_with_time(ledc_channel[ch].speed_mode,
                    ledc_channel[ch].channel, LEDC_TEST_DUTY,
                    LEDC_TEST_FADE_TIME);
            ledc_fade_start(ledc_channel[ch].speed_mode,
                    ledc_channel[ch].channel, LEDC_FADE_NO_WAIT);
        }
        vTaskDelay(LEDC_TEST_FADE_TIME / portTICK_PERIOD_MS);

        printf("2.  PWM逐渐变小的周期目标 = 0\n");

        for (ch = 0; ch < LEDC_TOTAL_NUM; ch++) {
            ledc_set_fade_with_time(ledc_channel[ch].speed_mode,
                    ledc_channel[ch].channel, 0, LEDC_TEST_FADE_TIME);
            ledc_fade_start(ledc_channel[ch].speed_mode,
                    ledc_channel[ch].channel, LEDC_FADE_NO_WAIT);
        }

        vTaskDelay(LEDC_TEST_FADE_TIME / portTICK_PERIOD_MS);

    }

}

其他:

猜你喜欢

转载自blog.csdn.net/xh870189248/article/details/80417430