让 ESP32 连接到你的 WiFi 热点

本工程已托管到 GitHub,具体路径是 https://github.com/tidyjiang8/esp32-projects/tree/master/sta

git 加上 --recursive


功能说明将 ESP32 当做一个 STA,连接到一个 WiFi 热点。

【快速开始】

【假设】

  • 你已经安装好 ESP-IDF 和工具链。
  • 你已经有一个 WiFi 热点。

【步骤】

  • 使用数据线将开发板连接到你的系统中,让系统能够识别到你的板子(Windows 是COM\*, Linux 是/dev/ttyUSB\*)。
  • 进入sta所在目录。
  • 执行命名make menuconfig进行配置。 
    • 对热点的 SSID 和密码进行配置。依次进入配置选项Demo Configuration --->,然后在WiFi SSIDWiFi Password中填写你的 SSID 和密码。然后退出配置菜单,保存配置。
    • 对串口进行配置。
  • 执行命令make进行编译
  • 执行命令make flash monitor将编译生成的镜像烧写到 ESP32 开发板上面,并查看串口输出。

【现象】

串口输出如下图所示,从图中框出的部分可以看出,我们的 ESP32 已经成功连接到热点,并获取到 IP 地址了。

这里写图片描述

图 -  串口输出

【源码分析】

整个源码非常简单,一共就几十行代码,几乎都是在调用 ESP-IDF 给我们提供的接口,整个过程的流程如下:

这里写图片描述

上面这个流程中,我们需要强调的有三处:

  • 初始化事件处理模块 esp_event_loop_init()
  • 设置 wifi 模式 esp_wifi_set_mode()
  • 配置接口的参数 esp_wifi_set_config()

【初始化事件调度器】

在 ESP-IDF 中,整个 wifi 协议栈是一个状态机,它在各个时刻都有一个状态。用户可以根据自己的需要,让协议栈在某个状态时自动处理某些工作。在调用 esp_event_loop_init()函数时 ,我们传入了一个参数 event_handler,它是一个函数指针,当wifi状态机的状态变化时,会调用函数 event_handler(),并给它传递适当的参数。这一部分内容我们将在下一篇博客中详细介绍,所以这里就不再说明,请参考深入分析 ESP32 的 WiFi 状态机

【设置 wifi 模式】

ESP32 支持三种 wifi 模式,它们被定义为三个枚举值:

typedef enum {
    WIFI_MODE_NULL = 0,  /**< null mode */
    WIFI_MODE_STA,       /**< WiFi station mode */
    WIFI_MODE_AP,        /**< WiFi soft-AP mode */
    WIFI_MODE_APSTA,     /**< WiFi station + soft-AP mode */
    WIFI_MODE_MAX
} wifi_mode_t;
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

第一个枚举值WIFI_MODE_NULL和最后一个枚举值WIFI_MODE_MAX只是一个标记,不是真正支持的模式,因此支持的模式包括:

  • station 模式
  • soft-AP 模式
  • station + soft-AP 模式

设置模式的接口为 esp_err_t esp_wifi_set_mode(wifi_mode_t mode);,它需要的参数就是我们上面所看到的三种模式中的其中一个。

另外还有一个问题,WIFI_MODE_NULL 和 WIFI_MODE_MAX 有啥作用?在函数 esp_wifi_set_mode 内部,可以通过这两个值来进行入参检测,判断传入的参数是否有效。

【配置接口的参数】

在上面设置 wifi 模式时,wifi 库会根据我们传入的参数来分配接口。如果我们传入的参数是 WIFI_MODE_STA,则 wifi 库会创建一个 sta 接口;如果我们传入的参数是 WIFI_MODE_AP,则 wifi 库会创建一个 ap 接口;如果我们传入的参数是 WIFI_MODE_APSTA,则 wif 库会同时创建一个 sta 接口和一个 ap 接口。wifi 库在运行时需要知道这些接口的参数,所以我们需要在启动 wifi 前设置接口的参数。

设置 wifi 接口参数的 API 原型是 esp_err_t esp_wifi_set_config(wifi_interface_t ifx, wifi_config_t *conf);,包含两个参数:

  • wifi_interface_t ifx,即需要配置的接口
  • wifi_config_t *conf,即传递给该接口的参数

sta 接口和 ap 接口需要的参数是不同的,这里一定要注意,它们通过一个 联合体 来定义的:

typedef union {
    wifi_ap_config_t  ap;  /**< AP 的配置 */
    wifi_sta_config_t sta; /**< STA 的配置 */
} wifi_config_t;
  • 1
  • 2
  • 3
  • 4

对于 sta 接口,需要配置的参数一般包括 ssid 和 password。注意,这里的ssidpassword的长度是由限制的,具体请看结构体:

typedef struct {
    uint8_t ssid[32];      /**< SSID of target AP*/
    uint8_t password[64];  /**< password of target AP*/
    bool bssid_set;        /**< whether set MAC address of target AP or not. Generally, station_config.bssid_set needs to be 0; and it needs to be 1 only when users need to check the MAC address of the AP.*/
    uint8_t bssid[6];     /**< MAC address of target AP*/
    uint8_t channel;       /**< channel of target AP. Set to 1~13 to scan starting from the specified channel before connecting to AP. If the channel of AP is unknown, set it to 0.*/
} wifi_sta_config_t;
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

对于 ap 接口,第一个需要确定的参数是 authmode,即客户端连接到这个 AP 时的授权模式。如果配置的授权模式是 WIFI_AUTH_OPEN,则不再需要配置其它参数。否则,则需要根据授权模式来判断还需要其它啥参数,不过一般都至少还需要 ssid 和 password 两个参数,其它参数的作用请自行研究。ap 接口的配置结构体如下:

typedef struct {
    uint8_t ssid[32];           /**< SSID of ESP32 soft-AP */
    uint8_t password[64];       /**< Password of ESP32 soft-AP */
    uint8_t ssid_len;           /**< Length of SSID. If softap_config.ssid_len==0, check the SSID until there is a termination character; otherwise, set the SSID length according to softap_config.ssid_len. */
    uint8_t channel;            /**< Channel of ESP32 soft-AP */
    wifi_auth_mode_t authmode;  /**< Auth mode of ESP32 soft-AP. Do not support AUTH_WEP in soft-AP mode */
    uint8_t ssid_hidden;        /**< Broadcast SSID or not, default 0, broadcast the SSID */
    uint8_t max_connection;     /**< Max number of stations allowed to connect in, default 4, max 4 */
    uint16_t beacon_interval;   /**< Beacon interval, 100 ~ 60000 ms, default 100 ms */
} wifi_ap_config_t;
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10

【总结】

虽然只有短短的几十行代码,但是如果我们仔细追踪源码的话,里面其实藏着很多干货的!

我们这里也只是简单分析了下源码,没有太深入,比如,tcp/ip 适配层初始化时都干了啥?事件调度器是干嘛的/wifi 状态机是如何运行是?对于后者,理解清楚了有利于我们编写出更好的应用程序,我们将在下一篇博客中介绍,请参考 分析 ESP32 的 WiFi 状态机;对于前者,如果有兴趣,请自行追踪源码,这部分内容也是开源的。


  • 1
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
可以使用ESP32WiFi连接WiFi热点,然后使用声音传感器模块来检测声音强度。以下是一些基本的步骤: 1. 连接ESP32WiFi热点: ```c #include <WiFi.h> const char* ssid = "YOUR_SSID"; const char* password = "YOUR_PASSWORD"; void setup() { Serial.begin(115200); WiFi.begin(ssid, password); while (WiFi.status() != WL_CONNECTED) { delay(1000); Serial.println("Connecting to WiFi..."); } Serial.println("Connected to WiFi"); } void loop() { // Your code here } ``` 2. 连接声音传感器模块: 连接模块的引脚到ESP32的对应引脚,例如: - VCC -> 3.3V - GND -> GND - Analog Out -> A0 3. 读取声音传感器模块输出的模拟信号: ```c int sensorPin = 34; // A0 void setup() { Serial.begin(115200); } void loop() { int sensorValue = analogRead(sensorPin); Serial.println(sensorValue); delay(100); } ``` 这个程序会每100毫秒读取一次声音传感器的值,并在串口输出。 4. 控制声音传感器: 你可以根据声音传感器的值来控制一些操作,例如控制一个蜂鸣器的开关: ```c int sensorPin = 34; // A0 int buzzerPin = 25; void setup() { Serial.begin(115200); pinMode(buzzerPin, OUTPUT); } void loop() { int sensorValue = analogRead(sensorPin); if (sensorValue > 500) { // 如果声音传感器的值大于500 digitalWrite(buzzerPin, HIGH); // 打开蜂鸣器 } else { digitalWrite(buzzerPin, LOW); // 关闭蜂鸣器 } delay(100); } ``` 这个程序会每100毫秒读取一次声音传感器的值,如果传感器的值大于500,就会打开蜂鸣器。否则,蜂鸣器会关闭。 希望这些代码能够帮助你连接WiFi热点并控制声音传感器。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值