【Follow me第二季第4期】任务汇总
本帖最后由 mingzhe123 于 2025-1-21 18:11 编辑<p><span style="font-size:24px;"><strong>物料清单:</strong></span></p>
<p><strong>任务使用物料:</strong></p>
<ul>
<li>主板1:<a href="https://www.digikey.cn/zh/products/detail/arduino/ABX00052/14123941" target="_blank">ABX00052 Arduino | 开发板,套件,编程器 | DigiKey</a> </li>
<li>主板2:<a href="https://www.digikey.cn/zh/products/detail/raspberry-pi/SC1631/24627136" target="_blank">RASPBERRY PI PICO 2 RP2350</a></li>
<li></li>
</ul>
<p><strong>任务一:</strong></p>
<p> 基础实现: 搭建环境并开启第一步Blink三色LED / 串口打印Hello DigiKey & EEWorld!链接:<a href="https://bbs.eeworld.com.cn/thread-1300565-1-1.html" target="_blank">任务一链接</a></p>
<p><strong>基础代码:</strong> </p>
<pre>
<code class="language-cpp">#include <WiFiNINA.h>
//#include <Arduino.h>
void setup() {
Serial.begin(115200);
pinMode(LEDB, OUTPUT);
pinMode(LEDR,OUTPUT);
pinMode(LEDG,OUTPUT);
digitalWrite(LEDB,LOW);
digitalWrite(LEDR,LOW);
digitalWrite(LEDG,LOW);
Serial.println("The task began!!!");
Serial.println();
}
void loop() {
delay(2000);
digitalWrite(LEDB, HIGH);
digitalWrite(LEDG, LOW);
Serial.println("Hello DigiKey & EEWorld!");
delay(2000);
digitalWrite(LEDB, LOW);//状态翻转
digitalWrite(LEDG, HIGH);
}
</code></pre>
<p><strong>进阶代码:</strong></p>
<p> 任务一进阶适用PICO2开发板与<strong><u>Arduino</u> Nano RP2040 Connect</strong>,其主要原理是PICO2的按键通过串口控制<strong><u>Arduino</u> Nano RP2040 Connect</strong>开发板上的RGB 灯,其系统架构图如下图所示:</p>
<div></div>
<p> </p>
<p> </p>
<p>其主要代码如下:</p>
<p>PICO2代码:</p>
<pre>
<code class="language-cpp">int val;
const int BUTTON_PIN = 21; // the number of the pushbutton pin
const int SHORT_PRESS_TIME = 500; // 500 milliseconds
// Variables will change:
int lastState = LOW;// the previous state from the input pin
int currentState; // the current reading from the input pin
unsigned long pressedTime= 0;
unsigned long releasedTime = 0;
char key_flag = 0;
void setup() {
Serial1.setRX(17);
Serial1.setTX(16);
Serial1.begin(115200); // opensserial port, sets data rate to 9600 bps
while(Serial.read()>= 0){}//clear serialbuffer
pinMode(25,OUTPUT);
pinMode(BUTTON_PIN, INPUT_PULLUP);
Serial1.write(49);
}
void Key(void) {
delay(1);
}
void loop() {
delay(10);
// read the state of the switch/button:
currentState = digitalRead(BUTTON_PIN);
if(lastState == HIGH && currentState == LOW) // button is pressed
pressedTime = millis();
else if(lastState == LOW && currentState == HIGH) { // button is released
releasedTime = millis();
long pressDuration = releasedTime - pressedTime;
if( pressDuration < SHORT_PRESS_TIME )
Serial.println("A short press is detected");
key_flag = !key_flag;
if(key_flag) {
Serial1.write(49);
Serial.println("49");
digitalWrite(25,LOW);
} else {
Serial1.write(50);
Serial.println("50");
digitalWrite(25,HIGH);
}
}
// save the the last state
lastState = currentState;
}
</code></pre>
<p><u>Arduino</u> Nano RP2040 Connect代码:</p>
<pre>
<code class="language-cpp">#include <WiFiNINA.h>
int val;
void setup() {
Serial.begin(115200); // opensserial port, sets data rate to 9600 bps
Serial1.begin(115200); // opensserial port, sets data rate to 9600 bps
while(Serial1.read()>= 0){}//clear serialbuffer
while(Serial.read()>= 0){}//clear serialbuffer
pinMode(LEDB, OUTPUT);
pinMode(LEDR,OUTPUT);
pinMode(LEDG,OUTPUT);
digitalWrite(LEDB,LOW);
digitalWrite(LEDR,LOW);
digitalWrite(LEDG,LOW);
Serial.println("The pro task began!!!");
Serial.println();
}
void loop() {
if (Serial1.available() > 0) {
delay(100); // 等待数据传完
int numdata = Serial1.available();
val=Serial1.read();
Serial1.println(val);
if(val==49)
{
Serial.println("Test OK");
Serial.println(val);
// delay(2000);
digitalWrite(LEDB, HIGH);
Serial.println("Hello DigiKey & EEWorld!");
digitalWrite(LEDG, HIGH);
}
if(val==50)
{
Serial.println("Test OK!!!");
Serial.println(val);
// delay(2000);
digitalWrite(LEDB, LOW);
Serial.println("Turn off the lights!");
digitalWrite(LEDG, LOW);
}
while(Serial1.read()>=0){} //清空串口缓存
}
}
</code></pre>
<p><strong>总结:</strong></p>
<p> 树莓派的MCU,通过arduino来开发难度降低了很多,用户只需要调动封装好的库函数即可。但是有一点要吐槽一下,本来是个及其简单的程序,适用arduino IDE开发却需要很长的编译时间,实在不敢恭维,后期有时间尝试一下VS Code。</p>
<p><strong>任务视频:</strong></p>
<p>a630efe2d622147a2861f70ce74fddcd<br />
</p>
<p> </p>
<p><span style="font-size:24px;"><strong>任务二:</strong></span><br />
学习IMU基础知识,调试IMU传感器,通过串口打印输出。链接:<a href="https://bbs.eeworld.com.cn/thread-1300577-1-1.html" target="_blank">任务二链接</a></p>
<p> </p>
<p><strong>IMU编程与调试</strong></p>
<p><b><a href="https://www.digikey.cn/zh/products/detail/arduino/ABX00052/14123941" target="_blank">Arduino® Nano RP2040 Connect</a>代码:</b></p>
<pre>
<code class="language-cpp">
/* WIRING
In order to use the Adafruit lsm6dsox sensor with a ST nucleo board,
plug Nucleo "+3.3V" to AdafruitLSM6DOX "VIN",
plug Nucleo "GND" to AdafruitLSM6DOX "GND",
plug Nucleo "SCL"(D15) to AdafruitLSM6DOX "SCL",
plug Nucleo "SDA"(D14) to AdafruitLSM6DOX "SDA".*/
#include "LSM6DSOXSensor.h"
#include <Arduino.h>
// Declare LSM6DSOX sensor. Sensor address can have 2 values LSM6DSOX_I2C_ADD_L (corresponds to 0x6A I2C address) or LSM6DSOX_I2C_ADD_H (corresponds to 0x6B I2C address)
// On Adafruit lsm6dsox sensor, LSM6DSOX_I2C_ADD_L is the default address
LSM6DSOXSensor lsm6dsoxSensor = LSM6DSOXSensor(&Wire, LSM6DSOX_I2C_ADD_L);
int flag;
longlast_update_time;
// Timer variables
unsigned long lastTime = 0;
unsigned long timerDelay = 1000;
void setup() {
Serial.begin(115200);
Serial1.begin(115200); // opensserial port, sets data rate to 115200 bps
while(Serial1.read()>= 0){}//clear serialbuffer
pinMode(LED_BUILTIN,OUTPUT);
digitalWrite(LED_BUILTIN,LOW);
Wire.begin();
// Default clock is 100kHz. LSM6DSOX also supports 400kHz, let's use it
Wire.setClock(400000);
// Init the sensor
lsm6dsoxSensor.begin();
// Enable accelerometer and gyroscope, and check success
if (lsm6dsoxSensor.Enable_X() == LSM6DSOX_OK && lsm6dsoxSensor.Enable_G() == LSM6DSOX_OK) {
Serial.println("Success enabling accelero and gyro");
} else {
Serial.println("Error enabling accelero and gyro");
}
// Read ID of device and check that it is correct
uint8_t id;
lsm6dsoxSensor.ReadID(&id);
if (id != LSM6DSOX_ID) {
Serial.println("Wrong ID for LSM6DSOX sensor. Check that device is plugged");
} else {
Serial.println("Receviced correct ID for LSM6DSOX sensor");
}
// Set accelerometer scale at +- 2G. Available values are +- 2, 4, 8, 16 G
lsm6dsoxSensor.Set_X_FS(2);
// Set gyroscope scale at +- 125 degres per second. Available values are +- 125, 250, 500, 1000, 2000 dps
lsm6dsoxSensor.Set_G_FS(125);
// Set Accelerometer sample rate to 208 Hz. Available values are +- 12.0, 26.0, 52.0, 104.0, 208.0, 416.0, 833.0, 1667.0, 3333.0, 6667.0 Hz
lsm6dsoxSensor.Set_X_ODR(208.0f);
// Set Gyroscope sample rate to 208 Hz. Available values are +- 12.0, 26.0, 52.0, 104.0, 208.0, 416.0, 833.0, 1667.0, 3333.0, 6667.0 Hz
lsm6dsoxSensor.Set_G_ODR(208.0f);
}
void IMU_update(int interval)
{
// Read accelerometer
uint8_t acceleroStatus;
lsm6dsoxSensor.Get_X_DRDY_Status(&acceleroStatus);
if (acceleroStatus == 1) { // Status == 1 means a new data is available
int32_t acceleration;
lsm6dsoxSensor.Get_X_Axes(acceleration);
// Plot data for each axis in mg
Serial.print("AccelerationX=");
Serial.print(acceleration);
Serial.print("mg, AccelerationY=");
Serial.print(acceleration);
Serial.print("mg, AccelerationZ=");
Serial.print(acceleration);
Serial.println("mg");
if (millis() - last_update_time > interval)
{
if (acceleration > 1000)
{
//encoder_diff--;
flag = 1;
Serial.print("flag=1");
Serial1.write(49);
digitalWrite(LED_BUILTIN,LOW);
}
else if (acceleration < -1000)
{
// encoder_diff++;
flag = 2;
Serial.print("flag=2");
Serial1.write(50);
digitalWrite(LED_BUILTIN,HIGH);
}
else
{
flag = 0;
}
last_update_time = millis();
}
}
// Read gyroscope
uint8_t gyroStatus;
lsm6dsoxSensor.Get_G_DRDY_Status(&gyroStatus);
if (gyroStatus == 1) { // Status == 1 means a new data is available
int32_t rotation;
lsm6dsoxSensor.Get_G_Axes(rotation);
// Plot data for each axis in milli degrees per second
Serial.print("RotationX=");
Serial.print(rotation);
Serial.print("mdps, RotationY=");
Serial.print(rotation);
Serial.print("mdps, RotationZ=");
Serial.print(rotation);
Serial.println("mdps");
}
}
void loop() {
IMU_update(200);
}
</code></pre>
<p><strong>PICO2端代码:</strong></p>
<pre>
<code class="language-cpp">int val;
void setup() {
Serial1.setRX(17);
Serial1.setTX(16);
Serial1.begin(115200); // opensserial port, sets data rate to 9600 bps
while(Serial.read()>= 0){}//clear serialbuffer
pinMode(25,OUTPUT);
}
void loop() {
if (Serial1.available() > 0) {
delay(100); // 等待数据传完
int numdata = Serial1.available();
val=Serial1.read();
Serial1.println(val);
if(val==49)
{
Serial.println("Test OK");
Serial.println(val);
// delay(2000);
digitalWrite(25, LOW);
}
if(val==50)
{
Serial.println("Test OK!!!");
Serial.println(val);
digitalWrite(25, HIGH);
}
while(Serial1.read()>=0){} //清空串口缓存
}
}
</code></pre>
<p><img src="https://bbs.eeworld.com.cn/data/attachment/forum/202412/01/121103ocucc7gukkzjdq7k.png.thumb.jpg" /></p>
<p><strong>总结:</strong></p>
<p><b> </b>实现IMU的控制与数据读取还是十分简单的,只需调用官方Arduino库即可,这大大降低了开发者的开发难度。</p>
<p><strong>任务视频:</strong></p>
<p>a51009e6090e2b27a92609dbf549ae37</p>
<p> </p>
<p><span style="font-size:22px;"><strong>任务三:</strong></span><br />
学习并调试PDM麦克风,通过串口打印收音数据和音频 。链接:<a href="https://bbs.eeworld.com.cn/thread-1301147-1-1.html" target="_blank">任务三链接</a><br />
驱动程序:</p>
<pre>
<code class="language-cpp">#include <PDM.h>
static const char channels = 1;
static const int frequency = 20000;
short sampleBuffer;
volatile int samplesRead;
void setup() {
Serial.begin(115200);
while (!Serial);
PDM.onReceive(onPDMdata);
if (!PDM.begin(channels, frequency)) {
Serial.println("Failed to start PDM!");
while (1);
}
}
void loop() {
if (samplesRead) {
for (int i = 0; i < samplesRead; i++) {
if (channels == 2) {
Serial.print("L:");
Serial.print(sampleBuffer);
Serial.print(" R:");
i++;
}
Serial.println(sampleBuffer);
}
samplesRead = 0;
}
}
void onPDMdata() {
int bytesAvailable = PDM.available();
PDM.read(sampleBuffer, bytesAvailable);
samplesRead = bytesAvailable / 2;
}
</code></pre>
<p><strong>查看串口打印的波形数据</strong></p>
<p> 将代码下载到 Arduino Nano RP2040 Connect。</p>
<p> 打开 <strong>串口监视器</strong>,设置波特率为 <strong>115200</strong>。</p>
<p>使用 <strong>Arduino IDE 串口绘图器</strong>(Serial Plotter),观察音频数据的波形变化,如下图所示,下图为1KHz正弦波声音产生的波形数据。</p>
<p><img src="https://bbs.eeworld.com.cn/data/attachment/forum/202412/06/224213onxdv52j99ovc5hn.png.thumb.jpg" /></p>
<p><strong>总结</strong> </p>
<p>Arundio自带的函数库,大大降低了开发难度,我们只需要调用相应的API函数即可配置麦克风的采样频率,配合开发板的多种数据传输功能,可以实现很多有意思的功能。</p>
<p>92596a8368d38aa81897cc36d925d52d<br />
<span style="font-size:24px;"><strong>任务代码:</strong></span></p>
<div></div>
<p><strong><span style="font-size:24px;">任务总结:</span></strong></p>
<p>此次EEWORD论坛的活动,不仅增强了个人的实践能力,在硬件操作、编程技能以及传感器应用方面都有了显著提升。这些知识与经验为后面开发奠定了坚实的基础,同时也激发了个人更多的创新精神。</p>
<p><span style="font-size:24px;"><strong>任务汇总视频:</strong></span></p>
<p>0054b15e32e32d5f61f8f739b24dc49f<br />
</p>
<div></div>
<div></div>
页:
[1]