微雪 esp32c3 深度睡眠和 gpio 喚醒

LiuChengloong發表於2024-04-26

當專案由電源介面卡供電時,我們一般不會太關心功耗。但是,如果要使用電池為專案供電,則需要精打細算。

esp32 深度睡眠

在深度睡眠模式下,CPU、大多數 RAM 和所有數字外圍裝置都可以關閉。從深度睡眠中出來後,晶片透過復位重新啟動,並從一開始就開始執行程式。系統無法自動進入深度睡眠模式。 esp_deep_sleep_start() 函式用於配置喚醒源後立即進入深度睡眠。

esp32 深度睡眠喚醒源

esp32c3 可以使用 定時器 gpio 等方式喚醒。

esp32 喚醒源:定時器

esp32RTC 控制器具有一個內建定時器,您可以在預定義的時間後用來喚醒 ESP32。

此功能在需要時間戳或日常任務的同時保持低功耗的專案中特別有用。

esp_sleep_enable_timer_wakeup(time_in_us) 函式用於將計時器配置為喚醒源。

#define uS_TO_S_FACTOR 1000000ULL  /* Conversion factor for micro seconds to seconds */
#define TIME_TO_SLEEP  5           /* Time ESP32 will go to sleep (in seconds) */

void setup(){
  Serial.begin(115200);
  delay(2000); // 給於一定的時間用於開啟 Serial 控制檯,在深度睡眠的時候是無法連線 esp32 的
  esp_sleep_enable_timer_wakeup(TIME_TO_SLEEP * uS_TO_S_FACTOR);
  
  Serial.println("Going to sleep now");
  esp_deep_sleep_start();
}

這個程式將每 5s 喚醒一次,然後再次入睡。

esp32 喚醒源:gpio 喚醒

有時候我們需要透過按鈕來喚醒 esp32。這裡透過 gpio0 來喚醒。注意 esp32c3 只能透過 gpio 0-5 來喚醒。

程式碼演示使用 gpio0 觸發低電平(接地)來喚醒。

void setup(){
  Serial.begin(115200);
  delay(2000); // 給於一定的時間用於開啟 Serial 控制檯,在深度睡眠的時候是無法連線 esp32 的
  
  // 要使得 gpio0 喚醒,下面 2 行程式碼是關鍵
  gpio_set_direction(GPIO_NUM_0, GPIO_MODE_INPUT);
  esp_deep_sleep_enable_gpio_wakeup(BIT(0), ESP_GPIO_WAKEUP_GPIO_LOW);

  Serial.println("Going to sleep now");
  esp_deep_sleep_start();
}

微雪 esp32c3 深度睡眠後亮燈程式碼:

#include <Arduino.h>
#include <FastLED.h>
#include "OneButton.h"

#define NUM_LEDS 1
#define DATA_PIN 10
CRGB leds[NUM_LEDS];

void print_wakeup_reason()
{
    esp_sleep_wakeup_cause_t wakeup_reason;

    wakeup_reason = esp_sleep_get_wakeup_cause();

    switch (wakeup_reason)
    {
    case ESP_SLEEP_WAKEUP_EXT0:
        Serial.println("Wakeup caused by external signal using RTC_IO");
        break;
    case ESP_SLEEP_WAKEUP_EXT1:
        Serial.println("Wakeup caused by external signal using RTC_CNTL");
        break;
    case ESP_SLEEP_WAKEUP_TIMER:
        Serial.println("Wakeup caused by timer");
        break;
    case ESP_SLEEP_WAKEUP_TOUCHPAD:
        Serial.println("Wakeup caused by touchpad");
        break;
    case ESP_SLEEP_WAKEUP_ULP:
        Serial.println("Wakeup caused by ULP program");
        break;
    default:
        Serial.printf("Wakeup was not caused by deep sleep: %d\n", wakeup_reason);
        break;
    }
}

void setup()
{
    delay(2500);
    Serial.begin(115200);
    print_wakeup_reason();

    FastLED.addLeds<WS2812, DATA_PIN, RGB>(leds, NUM_LEDS);
    FastLED.setBrightness(32);
    leds[0] = CRGB::Green;
    FastLED.show();
    delay(1500);
    FastLED.clear();
    delay(1500);

    delay(2500);
    Serial.println("ready to deep sleep");
    gpio_set_direction(GPIO_NUM_0, GPIO_MODE_INPUT);
    esp_deep_sleep_enable_gpio_wakeup(BIT(0), ESP_GPIO_WAKEUP_GPIO_LOW);
    esp_deep_sleep_start();
}

void loop()
{
}

platformio.ini

[env:esp32-c3-devkitm-1]
platform = espressif32
board = esp32-c3-devkitm-1
framework = arduino
board_build.flash_mode = dio
monitor_speed = 115200
lib_deps = 
	fastled/FastLED@^3.6.0
build_flags = 
	-D ARDUINO_USB_MODE=1
	-D ARDUINO_USB_CDC_ON_BOOT=1

相關文章