不爱胡萝卜的仓鼠 发表于 2025-1-12 21:54

【Follow me第二季第4期】④汇总篇

本帖最后由 不爱胡萝卜的仓鼠 于 2025-1-13 15:44 编辑

<p><strong><span style="font-size:24px;">1、展示所有任务的视频</span></strong></p>

<p>任务1:</p>

<p>EE大学堂视频链接:<a href="https://training.eeworld.com.cn/video/42146" target="_blank">https://training.eeworld.com.cn/video/42146</a></p>

<p>任务2:</p>

<p>EE大学堂视频链接:<a href="https://training.eeworld.com.cn/video/42148" target="_blank">https://training.eeworld.com.cn/video/42148</a></p>

<p>任务3:</p>

<p>EE大学堂视频链接:<a href="https://training.eeworld.com.cn/video/42150" target="_blank">https://training.eeworld.com.cn/video/42150</a></p>

<p>&nbsp;</p>

<p>&nbsp;</p>

<p>汇总:</p>

<p>44dd7708854e5b723818909f8b1de3c5<br />
&nbsp;</p>

<p>&nbsp;</p>

<p><strong><span style="font-size:24px;">2、所使用的物料清单</span></strong></p>

<p>本次任务我在得捷电子采购的产品有ARDUINO NANO RP2040 CONNECT、SEEEDSTUDIO XIAO ESP32S3</p>

<div style="text-align: center;"></div>

<p>&nbsp;</p>

<p>&nbsp;</p>

<p><strong><span style="font-size:24px;">3、展示每个任务</span></strong></p>

<p><strong><span style="font-size:18px;">3.1 任务一:搭建环境并开启第一步Blink三色LED / 串口打印Hello DigiKey &amp; EEWorld!</span></strong></p>

<p>详细内容:<a href="https://bbs.eeworld.com.cn/thread-1301578-1-1.html" target="_blank">【Follow me第二季第4期】①任务一:Blink与串口打印</a></p>

<p>&nbsp;</p>

<p>基础的点灯,串口功能比较基础,有点没意思,我看到RP2040 connect有带BLE和WiFi,因此我额外购买了一块ESP32-S3。我想实现通过WiFi的方式实现点灯,顺便可以学习一下Arduino上如何连接WiFi、启动server、作为client连接server、TCP通讯数据收发等。</p>

<p>&nbsp;</p>

<p>RP2040:上电后实现三色LED、LED的闪烁,并串口打印指定内容。随后连接WiFi,启动server,等待client连接,并接收控制指令,执行指令对应的代码。</p>

<p>ESP32:上电后连接WiFi,并以Client的角色连接server,通过TCP通讯发送控制指令给RP2040,控制2040的LED灯</p>

<div style="text-align: center;"></div>

<div style="text-align: center;"></div>

<p>&nbsp;</p>

<p><strong>RP2040代码</strong></p>

<pre>
<code>/***************************/
//RGB LED需要安装WiFiNINA库,
/***************************/
#include &lt;WiFiNINA.h&gt;
#include &lt;SPI.h&gt;

#defineWIFI_CTL_LED (1)

#if WIFI_CTL_LED
#include "wifi_info.h"

const char wifi_ssid[]      = SECRET_SSID;
const char wifi_password[]= SECRET_PASS;
int wifi_conn_state = WL_IDLE_STATUS;

#define SERVER_PORT (80)
WiFiServer server(SERVER_PORT);

void printWifiStatus()
{
/* 打印WiFi SSID*/
Serial.print("SSID: ");
Serial.println(WiFi.SSID());

/* 打印IP地址 */
IPAddress ip = WiFi.localIP();
Serial.print("IP Address: ");
Serial.println(ip);

/* 打印信号强度 */
long rssi = WiFi.RSSI();
Serial.print("signal strength (RSSI):");
Serial.print(rssi);
Serial.println(" dBm");
}
#endif
void setup()
{
/* 初始化串口 */
Serial.begin(115200);
/* delay一下,保证串口监视器成功连接 */
delay(3000);

/* 初始化LED灯的GPIO,并开灯 */
pinMode(LED_BUILTIN, OUTPUT);
digitalWrite(LED_BUILTIN, HIGH);

/* 初始RGB LED灯的GPIO,并开灯 */
pinMode(LEDR, OUTPUT);
pinMode(LEDG, OUTPUT);
pinMode(LEDB, OUTPUT);
digitalWrite(LEDR, HIGH);
digitalWrite(LEDG, HIGH);
digitalWrite(LEDB, HIGH);

/* 打印和闪灯,完成指定任务 */
for(uint8_t j = 0; j &lt; 4; j++)
{
    Serial.println("Hello DigiKey &amp; EEWorld!");
    digitalWrite(LED_BUILTIN, LOW);
    digitalWrite(LEDR, LOW);
    digitalWrite(LEDG, LOW);
    digitalWrite(LEDB, LOW);
    delay(1000);

    digitalWrite(LED_BUILTIN, HIGH);
    digitalWrite(LEDR, HIGH);
    digitalWrite(LEDG, HIGH);
    digitalWrite(LEDB, HIGH);
    delay(1000);
}

#if WIFI_CTL_LED
/* 检查wifi模块状态是否可用 */
if (WiFi.status() == WL_NO_MODULE)
{
    Serial.println("Communication with WiFi module failed!");
    while (1);
}

/* 检查wifi模块版本号(非必选,可去掉) */
String fv = WiFi.firmwareVersion();
if (fv &lt; WIFI_FIRMWARE_LATEST_VERSION)
{
    Serial.println("now wifi firmware = " + fv + ", lastest version is " +
      WIFI_FIRMWARE_LATEST_VERSION + ", suggest update!");
}

/* 检查SSID和PSW是否填写 */
if (strlen(wifi_ssid) &lt;= 0)
{
    Serial.println("ERROR: Plase enter WiFi SSID in \"wifi_info.h\"");
    while(1);
}
if (strlen(wifi_password) &lt;= 0)
{
    Serial.println("ERROR: Plase enter WiFi password in \"wifi_info.h\"");
    while(1);
}

/* 尝试使用预设的账号密码,连接路由器 */
uint8_t i = 0;
for (i = 0; i &lt; 5; i++) //wifi连接超时时间5 * 10s
{
    wifi_conn_state = WiFi.begin(wifi_ssid, wifi_password);

    if (WL_CONNECTED == wifi_conn_state)
    {
      Serial.println("wifi connect success");
      break;
    }
    delay(10000);
}
if (i == 5)
{
    Serial.println("wifi connect failed");
    while(1);
}

/* 打印wifi信息*/
printWifiStatus();

/* 开启客户端 */
server.begin();
Serial.print("server started,addr:");
Serial.print(WiFi.localIP());
Serial.print(":");
Serial.println(SERVER_PORT);
#endif
}

void loop()
{
#if WIFI_CTL_LED
WiFiClient client = server.available();   // listen for incoming clients

/* 是否有客户端连接我 */
if (client)
{
    /* 打印,提示有客户端连接我 */
    Serial.println("new client");

    /* 从client接收到的数据的buffer */
    String recv_buffer = "";
   
    /* 持续监测客户端是否与我断连 */
    while (client.connected())
    {
      /* 客户端是否可用 */
      if (client.available())
      {
      /* 读取客户端发送的数据,并串口打印 */
      /* read接口一次只能读一个字节,每读取一个字节后就把它拼到recv_buffer中 */
      char c = client.read();
      Serial.write(c);
      recv_buffer += c;

      /* 通过检查字符串结尾和制定的字符串是否一致,来决定是否需要执行开关灯指令 */
      if (recv_buffer.endsWith("CTL_RGB_R_ON"))
      {
          digitalWrite(LEDR, HIGH);
      }
      if (recv_buffer.endsWith("CTL_RGB_R_OFF"))
      {
          digitalWrite(LEDR, LOW);            
      }
      if (recv_buffer.endsWith("CTL_RGB_G_ON"))
      {
          digitalWrite(LEDG, HIGH);            
      }
      if (recv_buffer.endsWith("CTL_RGB_G_OFF"))
      {
          digitalWrite(LEDG, LOW);         
      }
      if (recv_buffer.endsWith("CTL_RGB_B_ON"))
      {
          digitalWrite(LEDB, HIGH);            
      }
      if (recv_buffer.endsWith("CTL_RGB_B_OFF"))
      {
          digitalWrite(LEDB, LOW);            
      }
      if (recv_buffer.endsWith("CTL_LED_ON"))
      {
          digitalWrite(LED_BUILTIN, HIGH);            
      }
      if (recv_buffer.endsWith("CTL_LED_OFF"))
      {
          digitalWrite(LED_BUILTIN, LOW);            
      }
      }
    }

    /* 客户端与我断连,需要关闭client连接,并打印提示信息 */
    client.stop();
    Serial.println("client disconnected");
    /* 断连后灯回复原装 */
    digitalWrite(LED_BUILTIN, HIGH);
    digitalWrite(LEDR, HIGH);
    digitalWrite(LEDG, HIGH);
    digitalWrite(LEDB, HIGH);
}
#else
Serial.println("Hello DigiKey &amp; EEWorld!");
digitalWrite(LED_BUILTIN, HIGH);
digitalWrite(LEDR, HIGH);
digitalWrite(LEDG, HIGH);
digitalWrite(LEDB, HIGH);
delay(1000);

Serial.println("Hello DigiKey &amp; EEWorld!");
digitalWrite(LED_BUILTIN, LOW);
digitalWrite(LEDR, LOW);
digitalWrite(LEDG, LOW);
digitalWrite(LEDB, LOW);
delay(1000);
#endif
}
</code></pre>

<p>&nbsp;</p>

<p><strong>ESP32代码</strong></p>

<pre>
<code>#include &lt;Arduino.h&gt;
#include &lt;WiFi.h&gt;
#include "wifi_info.h"

const char wifi_ssid[]      = SECRET_SSID;
const char wifi_password[]= SECRET_PASS;
int wifi_conn_state = WL_IDLE_STATUS;

const IPAddress serverIP(192,168,31,215); //填写服务器的实际IP地址
uint16_t serverPort = 80; //端口默认80,服务器端也是默认80
WiFiClient client;

void printWifiStatus()
{
/* 打印WiFi SSID*/
Serial.print("SSID: ");
Serial.println(WiFi.SSID());

/* 打印IP地址 */
IPAddress ip = WiFi.localIP();
Serial.print("IP Address: ");
Serial.println(ip);

/* 打印信号强度 */
long rssi = WiFi.RSSI();
Serial.print("signal strength (RSSI):");
Serial.print(rssi);
Serial.println(" dBm");
}

void wifi_init()
{
/* 设置工作在STA模式 */
WiFi.mode(WIFI_STA);
/* 断开之前的连接 */
WiFi.disconnect(true, true);
}

void wifi_connect_AP()
{
/* 检查SSID和PSW是否填写 */
if (strlen(wifi_ssid) &lt;= 0)
{
    Serial.println("ERROR: Plase enter WiFi SSID in \"wifi_info.h\"");
    while(1);
}
if (strlen(wifi_password) &lt;= 0)
{
    Serial.println("ERROR: Plase enter WiFi password in \"wifi_info.h\"");
    while(1);
}

Serial.print("Attempting to connect to WPA SSID: ");
Serial.println(wifi_ssid);

/* 尝试使用预设的账号密码,连接路由器 */
uint8_t i = 0;
WiFi.begin(wifi_ssid, wifi_password);
/* 检测是否链接成功 */
for (i = 0; i &lt; 20; i++)
{
    delay(500);
    if (WiFi.status() != WL_CONNECTED)
    {
      Serial.println("wifi connect success");
      /* delay一会儿,等待IP等信息都拿到了再继续后续操作 */
      delay(3000);
      break;
    }
}

if (i == 20)
{
    Serial.println("wifi connect failed");
    while(1);
}

/* 打印wifi信息*/
printWifiStatus();
}

void connect_server()
{
if (client.connect(serverIP, serverPort))
{
    Serial.println("Connected to server");
}
else
{
    Serial.println("Connection failed");
    while(1);
}
}

void setup()
{
/* 初始化串口 */
Serial.begin(115200);

/* 初始化wifi模块 */
wifi_init();

/* wifi连接路由器 */
wifi_connect_AP();

/* 连接到服务器 */
connect_server();
}

void loop()
{
String cmd1 = "CTL_LED_ON";
String cmd2 = "CTL_LED_OFF";
/* 如果连接到服务器,就定时发送开关灯指令 */
if (client.connected())
{
    Serial.println("ON");
    client.write(cmd1.c_str());
    delay(1000);
    Serial.println("0FF");
    client.write(cmd2.c_str());
    delay(1000);
}
}


</code></pre>

<p>&nbsp;</p>

<p><strong><span style="font-size:18px;">3.2 任务二:学习IMU基础知识,调试IMU传感器,通过串口打印六轴原始数据</span></strong></p>

<p>详细内容:<a href="https://bbs.eeworld.com.cn/thread-1301579-1-1.html" target="_blank">【Follow me第二季第4期】②任务二:IMU传感器</a></p>

<div style="text-align: center;"></div>

<p>代码</p>

<pre>
<code>/***************************/
//IMU需要安装Arduino_LSM6DSOXk库
/***************************/
#include &lt;Arduino_LSM6DSOX.h&gt;

float ACC_x, ACC_y, ACC_z, GYR_x, GYR_y, GYR_z;

void setup()
{
/* 初始化串口 */
Serial.begin(115200);

/* 初始化IMU传感器 */
if (!IMU.begin())
{
    Serial.println("Failed to initialize IMU!");
    while (1);
}

/* 打印ACC和GYR的采样率 */
Serial.print("Accelerometer sample rate = ");
Serial.print(IMU.accelerationSampleRate());
Serial.println("Hz");
Serial.print("Gyroscope sample rate = ");
Serial.print(IMU.gyroscopeSampleRate());
Serial.println("Hz");
}

void loop()
{
if (IMU.accelerationAvailable())
{
    IMU.readAcceleration(ACC_x, ACC_y, ACC_z);
}
if (IMU.gyroscopeAvailable())
{
    IMU.readGyroscope(GYR_x, GYR_y, GYR_z);
}

Serial.print("ACC_x: ");
Serial.print(ACC_x);
Serial.print(", ");
Serial.print("ACC_y: ");
Serial.print(ACC_y);
Serial.print(", ");
Serial.print("ACC_z: ");
Serial.print(ACC_z);
Serial.print(", ");

Serial.print("GYR_x: ");
Serial.print(GYR_x);
Serial.print(", ");
Serial.print("GYR_y: ");
Serial.print(GYR_y);
Serial.print(", ");
Serial.print("GYR_z: ");
Serial.println(GYR_z);

delay(100);
}
</code></pre>

<p>&nbsp;</p>

<p><strong>3.3 任务三:学习PDM麦克风技术知识,调试PDM麦克风,通过串口打印收音数据和音频波形。</strong></p>

<p>详细内容:<a href="https://bbs.eeworld.com.cn/thread-1301580-1-1.html" target="_blank">【Follow me第二季第4期】③任务三:PDM麦克风</a></p>

<div style="text-align: center;"></div>

<p>代码;</p>

<pre>
<code>#include &lt;PDM.h&gt;

/* 输出通道的数量 */
static const char channels = 1;
/* 采样频率 */
static const int frequency = 20000;
/* 采样buffer,每次采样的数据大小为16bit,所以变量类型为short */
short sampleBuffer;
/* 已经读到的采样次数 */
volatile int samplesRead;

void onPDMdata()
{
/* 查询一共有多少数据 */
int bytesAvailable = PDM.available();

/* 把采样数据保存到buffer里 */
PDM.read(sampleBuffer, bytesAvailable);

/* 更新采样计数。一次采样的数据大小为16bit,所以采样计数需要除以2 */
samplesRead = bytesAvailable / 2;
}

void setup()
{
/* 初始化串口 */
Serial.begin(9600);

/* 设置PDM数据接收回调函数*/
PDM.onReceive(onPDMdata);

/* 初始化PDM,并开始采样 */
if (!PDM.begin(channels, frequency))
{
    Serial.println("Failed to start PDM!");
    while (1);
}
}

void loop()
{
/* 是否有采样数据 */
if (samplesRead)
{
    /* 打印buffer中的所有数据 */
    for (int i = 0; i &lt; samplesRead; i++)
    {
      Serial.println(sampleBuffer);
    }

    /* 清零采样计数 */
    samplesRead = 0;
}
}



</code></pre>

<p>&nbsp;</p>

<p><strong><span style="font-size:24px;">4、对本活动的心得体会</span></strong></p>

<p>很感谢得捷电子与EEWORLD共同举办的本次活动,这次的开发板非常有意思,板载各种传感器十分丰富,还有WiFi和BLE,可玩性很高。本次活动我学习到麦克风传感器、开启一个Server、client连接server、TCP通讯等新知识,收获颇丰。希望下次有机会继续参加类似的活动。</p>

<p>&nbsp;</p>

<p><strong><span style="font-size:24px;">5.可编译下载的代码包</span></strong></p>

<div></div>

<p>任务一:EEWORLD论坛下载中心下载链接:<a href="https://download.eeworld.com.cn/detail/%E7%9A%84%E5%88%A0%E9%99%A4%E5%A4%B1%E8%B4%A5v/635430" target="_blank">https://download.eeworld.com.cn/detail/%E7%9A%84%E5%88%A0%E9%99%A4%E5%A4%B1%E8%B4%A5v/635430</a></p>

<p>任务二:EEWORLD论坛下载中心下载链接:<a href="https://download.eeworld.com.cn/detail/%E7%9A%84%E5%88%A0%E9%99%A4%E5%A4%B1%E8%B4%A5v/635431" target="_blank">https://download.eeworld.com.cn/detail/%E7%9A%84%E5%88%A0%E9%99%A4%E5%A4%B1%E8%B4%A5v/635431</a></p>

<p>任务三:EEWORLD论坛下载中心下载链接:<a href="https://download.eeworld.com.cn/detail/%E7%9A%84%E5%88%A0%E9%99%A4%E5%A4%B1%E8%B4%A5v/635432" target="_blank">https://download.eeworld.com.cn/detail/%E7%9A%84%E5%88%A0%E9%99%A4%E5%A4%B1%E8%B4%A5v/635432</a></p>
页: [1]
查看完整版本: 【Follow me第二季第4期】④汇总篇