基于STM32的智能垃圾桶

举报
DS小龙哥 发表于 2025/12/25 11:57:25 2025/12/25
【摘要】 项目开发背景随着全球城市化进程的加速和人口持续增长,垃圾产生量急剧上升,给环境治理带来了严峻挑战。垃圾分类作为减少污染、促进资源回收利用的重要手段,已成为许多国家和地区政策推广的重点。然而,传统垃圾分类方式主要依赖人工识别和操作,存在效率低、错误率高的问题,难以满足现代生活对便捷性和环保性的双重需求。在此背景下,人工智能和物联网技术的迅猛发展为智能家居领域注入了新的活力。通过集成语音识别、...

项目开发背景

随着全球城市化进程的加速和人口持续增长,垃圾产生量急剧上升,给环境治理带来了严峻挑战。垃圾分类作为减少污染、促进资源回收利用的重要手段,已成为许多国家和地区政策推广的重点。然而,传统垃圾分类方式主要依赖人工识别和操作,存在效率低、错误率高的问题,难以满足现代生活对便捷性和环保性的双重需求。

在此背景下,人工智能和物联网技术的迅猛发展为智能家居领域注入了新的活力。通过集成语音识别、无线通信和自动控制等先进技术,可以实现更加智能化、人性化的垃圾管理解决方案。这类系统不仅能够提升垃圾分类的准确性和效率,还能增强用户参与度,推动环保理念的普及。

本项目以STM32微控制器为核心,结合LD3320语音识别模块、SYN6288语音合成模块、ESP8266 Wi-Fi模块和SG90舵机等硬件,开发了一款智能垃圾桶。该系统旨在通过语音指令自动判别垃圾类型,并提供实时反馈和远程状态监控功能,从而简化垃圾分类流程,改善用户体验。

这种智能垃圾桶的设计,不仅响应了绿色环保的号召,还体现了科技在日常生活中的创新应用。它有望通过降低人工干预、优化垃圾处理效率,为智慧城市建设和可持续发展目标贡献实际价值。

设计实现的功能

(1) 系统能够识别用户的语音指令,判断垃圾种类。
(2) 识别成功后,通过语音播报模块反馈垃圾类别。
(3) 通过Wi-Fi模块将垃圾桶状态(如满溢)信息发送到用户手机。
(4) 具备手动开关盖功能,并配有状态指示灯。

项目硬件模块组成

(1) 主控芯片:STM32F103C8T6单片机。
(2) 语音识别:LD3320语音识别模块。
(3) 语音播报:SYN6288语音合成模块。
(4) 通信模块:ESP8266 Wi-Fi模块。
(5) 执行机构:SG90舵机(控制桶盖开合)。

设计意义

该智能垃圾桶设计通过集成语音识别与播报功能,显著提升了用户交互的便捷性。用户只需通过简单的语音指令即可完成垃圾种类的识别与分类,无需手动操作,减少了接触污染物的风险,同时语音反馈确保了操作的直观性和可靠性。

借助Wi-Fi模块,系统能够实时将垃圾桶状态信息发送至用户手机,实现了远程监控与管理。这使得用户可以及时了解垃圾桶的满溢情况,避免垃圾堆积带来的卫生问题,提升了生活环境的整洁度和管理效率。

通过舵机控制桶盖的开合,并结合状态指示灯,设计确保了操作的自动化和可视化。手动开关盖功能提供了备用操作方式,增强了系统的实用性和容错能力,同时指示灯清晰显示工作状态,方便用户日常使用。

整体设计体现了嵌入式系统在智能家居领域的应用价值,将语音识别、无线通信和执行机构有机结合,推动了垃圾处理过程的智能化和自动化。这不仅优化了资源利用,还有助于培养垃圾分类习惯,对环境保护和公共卫生改善具有积极意义。

设计思路

系统基于STM32F103C8T6主控芯片作为核心控制器,负责协调各个硬件模块的工作流程。主控芯片通过处理输入信号和控制输出设备,实现垃圾桶的智能化功能,确保系统稳定运行。

语音识别部分使用LD3320模块,该模块能够接收用户的语音指令,并通过内置算法分析语音内容,判断垃圾的具体种类,如可回收物、有害垃圾或其他类别。识别过程依赖于预先设定的关键词库,主控芯片对识别结果进行验证和处理,以提高准确性和响应速度。

语音播报功能通过SYN6288模块实现,在语音识别成功后,主控芯片将垃圾类别信息发送给该模块,由SYN6288合成相应的语音信号并通过扬声器播放,为用户提供清晰的反馈,增强交互体验。

通信方面,系统集成ESP8266 Wi-Fi模块,用于连接互联网。当垃圾桶内部状态发生变化,例如检测到满溢情况时,主控芯片通过该模块将状态数据发送到用户手机端的应用程序,实现远程监控和及时提醒。

执行机构采用SG90舵机控制垃圾桶盖的开合,主控芯片根据语音指令或手动操作驱动舵机动作,实现自动开关盖功能。同时,系统配备状态指示灯,用于显示垃圾桶的当前工作状态,如开盖、关盖或异常情况,方便用户直观了解设备运行状况。

框架图

+-------------------------------------------------+
|                智能垃圾桶系统框架                |
+-------------------------------------------------+
|                                                 |
|  +-------------+      +-------------+           |
|  | LD3320      |<---->| STM32F103   |           |
|  | 语音识别    |      | C8T6主控    |           |
|  +-------------+      +-------------+           |
|                          |                      |
|        +-----------------+----------------+     |
|        |                 |                |     |
|  +-----------+     +-----------+    +---------+ |
|  | SYN6288   |     | ESP8266   |    | SG90    | |
|  | 语音播报  |     | Wi-Fi模块 |    | 舵机    | |
|  +-----------+     +-----------+    +---------+ |
|        |                 |                |     |
|  +-----------+     +-----------+    +---------+ |
|  | 状态指示灯|     | 用户手机  |    | 垃圾桶盖| |
|  +-----------+     +-----------+    +---------+ |
|                          |                      |
|                    +-----------+                |
|                    | 手动开关  |                |
|                    +-----------+                |
|                                                 |
+-------------------------------------------------+

系统总体设计

系统总体设计基于STM32F103C8T6单片机作为核心控制器,负责协调各个硬件模块的工作,实现智能垃圾桶的自动化与交互功能。系统通过集成语音识别、语音播报、无线通信和执行机构,确保用户能够通过语音指令便捷地进行垃圾分类操作,同时实时监控垃圾桶状态。

在语音处理方面,系统采用LD3320语音识别模块来捕捉用户的语音指令,并分析判断垃圾种类。识别成功后,STM32主控芯片驱动SYN6288语音合成模块,通过语音播报方式向用户反馈识别的垃圾类别,从而提供直观的交互体验。这一过程确保了用户无需手动操作即可完成垃圾分类的初步确认。

通信功能通过ESP8266 Wi-Fi模块实现,系统能够将垃圾桶的状态信息,如满溢情况,实时发送到用户手机。STM32主控芯片负责收集传感器数据或内部状态,并通过Wi-Fi模块传输,使用户能够远程监控垃圾桶的运行状况,及时处理异常情况。

执行机构部分使用SG90舵机控制垃圾桶盖的开合,系统支持手动开关盖功能,并配有状态指示灯以显示当前工作模式。STM32主控芯片根据语音识别结果或手动输入信号,驱动舵机动作,同时通过指示灯反馈盖子的开闭状态,确保操作简单可靠。整体设计注重实用性和稳定性,各模块协同工作,满足日常垃圾分类需求。

系统功能总结

功能编号 功能描述 使用的硬件模块
1 识别用户的语音指令,判断垃圾种类 LD3320语音识别模块,STM32F103C8T6单片机
2 识别成功后,通过语音播报模块反馈垃圾类别 SYN6288语音合成模块,STM32F103C8T6单片机
3 通过Wi-Fi模块将垃圾桶状态信息发送到用户手机 ESP8266 Wi-Fi模块,STM32F103C8T6单片机
4 具备手动开关盖功能,并配有状态指示灯 SG90舵机,STM32F103C8T6单片机(控制舵机和指示灯)

设计的各个功能模块描述

主控芯片STM32F103C8T6作为系统的核心控制器,负责协调和管理所有外围模块的工作。它处理来自语音识别模块的输入数据,根据预设算法判断垃圾种类,并控制语音播报、Wi-Fi通信和舵机执行等操作,确保系统稳定运行。

LD3320语音识别模块用于接收用户的语音指令,通过内置的识别算法将语音信号转换为数字信息。该模块将识别结果发送给主控芯片,主控芯片据此匹配垃圾类别,实现智能分类功能。

SYN6288语音合成模块在语音识别成功后,接收主控芯片的指令,将文本信息转换为自然语音输出。它通过扬声器播报垃圾类别,向用户提供实时反馈,增强交互体验。

ESP8266 Wi-Fi模块连接到主控芯片,用于实现无线通信功能。该模块将垃圾桶的状态信息,如满溢或正常,通过Wi-Fi网络发送到用户的手机端,方便用户远程监控和管理。

SG90舵机作为执行机构,由主控芯片驱动,控制垃圾桶盖的开合动作。它响应主控芯片的指令,实现自动开关盖功能,同时支持手动操作,并通过状态指示灯显示当前盖体状态。

上位机代码设计

#include <iostream>
#include <string>
#include <vector>
#include <thread>
#include <chrono>
#include <winsock2.h>
#include <windows.h>

#pragma comment(lib, "ws2_32.lib")

class SmartTrashMonitor {
private:
    SOCKET serverSocket;
    bool isRunning;
    std::vector<std::string> trashStatusLog;
    
public:
    SmartTrashMonitor() : serverSocket(INVALID_SOCKET), isRunning(false) {}
    
    ~SmartTrashMonitor() {
        stopServer();
    }
    
    bool initializeServer(int port = 8080) {
        WSADATA wsaData;
        if (WSAStartup(MAKEWORD(2, 2), &wsaData) != 0) {
            std::cerr << "WSAStartup failed!" << std::endl;
            return false;
        }
        
        serverSocket = socket(AF_INET, SOCK_STREAM, 0);
        if (serverSocket == INVALID_SOCKET) {
            std::cerr << "Socket creation failed!" << std::endl;
            WSACleanup();
            return false;
        }
        
        sockaddr_in serverAddr;
        serverAddr.sin_family = AF_INET;
        serverAddr.sin_addr.s_addr = INADDR_ANY;
        serverAddr.sin_port = htons(port);
        
        if (bind(serverSocket, (sockaddr*)&serverAddr, sizeof(serverAddr)) == SOCKET_ERROR) {
            std::cerr << "Bind failed!" << std::endl;
            closesocket(serverSocket);
            WSACleanup();
            return false;
        }
        
        if (listen(serverSocket, 5) == SOCKET_ERROR) {
            std::cerr << "Listen failed!" << std::endl;
            closesocket(serverSocket);
            WSACleanup();
            return false;
        }
        
        std::cout << "Smart Trash Monitor Server started on port " << port << std::endl;
        return true;
    }
    
    void handleClient(SOCKET clientSocket) {
        char buffer[1024];
        int bytesReceived;
        
        while ((bytesReceived = recv(clientSocket, buffer, sizeof(buffer), 0)) > 0) {
            buffer[bytesReceived] = '\0';
            std::string message(buffer);
            
            // 解析垃圾桶状态信息
            processTrashStatus(message);
            
            // 发送确认响应
            std::string response = "Status received: " + message;
            send(clientSocket, response.c_str(), response.length(), 0);
        }
        
        closesocket(clientSocket);
    }
    
    void processTrashStatus(const std::string& status) {
        std::string timestamp = getCurrentTime();
        std::string logEntry = "[" + timestamp + "] " + status;
        
        trashStatusLog.push_back(logEntry);
        
        // 显示状态信息
        std::cout << "\n=== New Trash Status ===" << std::endl;
        std::cout << logEntry << std::endl;
        
        // 检查满溢状态
        if (status.find("full") != std::string::npos || 
            status.find("overflow") != std::string::npos) {
            std::cout << "ALERT: Trash bin is full! Please empty it!" << std::endl;
            showAlertNotification();
        }
        
        // 检查垃圾类型识别结果
        if (status.find("recyclable") != std::string::npos) {
            std::cout << "INFO: Recyclable waste detected" << std::endl;
        } else if (status.find("hazardous") != std::string::npos) {
            std::cout << "INFO: Hazardous waste detected" << std::endl;
        } else if (status.find("kitchen") != std::string::npos) {
            std::cout << "INFO: Kitchen waste detected" << std::endl;
        } else if (status.find("other") != std::string::npos) {
            std::cout << "INFO: Other waste detected" << std::endl;
        }
    }
    
    void showAlertNotification() {
        // 在Windows系统显示弹窗提醒
        MessageBox(NULL, 
                  "Trash bin is full! Please empty it immediately!", 
                  "Smart Trash Alert", 
                  MB_ICONWARNING | MB_OK);
    }
    
    std::string getCurrentTime() {
        auto now = std::chrono::system_clock::now();
        auto time = std::chrono::system_clock::to_time_t(now);
        char buffer[80];
        ctime_s(buffer, sizeof(buffer), &time);
        std::string timeStr(buffer);
        timeStr.pop_back(); // 移除换行符
        return timeStr;
    }
    
    void displayStatusLog() {
        std::cout << "\n=== Trash Status History ===" << std::endl;
        for (const auto& log : trashStatusLog) {
            std::cout << log << std::endl;
        }
    }
    
    void startServer() {
        isRunning = true;
        
        std::thread serverThread([this]() {
            while (isRunning) {
                sockaddr_in clientAddr;
                int clientAddrSize = sizeof(clientAddr);
                
                SOCKET clientSocket = accept(serverSocket, 
                                           (sockaddr*)&clientAddr, 
                                           &clientAddrSize);
                
                if (clientSocket == INVALID_SOCKET) {
                    if (isRunning) {
                        std::cerr << "Accept failed!" << std::endl;
                    }
                    continue;
                }
                
                std::cout << "New client connected!" << std::endl;
                
                // 为新客户端创建处理线程
                std::thread clientThread(&SmartTrashMonitor::handleClient, 
                                       this, clientSocket);
                clientThread.detach();
            }
        });
        
        serverThread.detach();
    }
    
    void stopServer() {
        isRunning = false;
        
        if (serverSocket != INVALID_SOCKET) {
            closesocket(serverSocket);
            serverSocket = INVALID_SOCKET;
        }
        
        WSACleanup();
        std::cout << "Server stopped." << std::endl;
    }
    
    void showMenu() {
        std::cout << "\n=== Smart Trash Monitor ===" << std::endl;
        std::cout << "1. Show status history" << std::endl;
        std::cout << "2. Clear status history" << std::endl;
        std::cout << "3. Exit" << std::endl;
        std::cout << "Enter your choice: ";
    }
    
    void run() {
        if (!initializeServer()) {
            std::cerr << "Failed to initialize server!" << std::endl;
            return;
        }
        
        startServer();
        
        int choice;
        while (true) {
            showMenu();
            std::cin >> choice;
            
            switch (choice) {
                case 1:
                    displayStatusLog();
                    break;
                case 2:
                    trashStatusLog.clear();
                    std::cout << "Status history cleared!" << std::endl;
                    break;
                case 3:
                    stopServer();
                    return;
                default:
                    std::cout << "Invalid choice!" << std::endl;
            }
        }
    }
};

int main() {
    SmartTrashMonitor monitor;
    monitor.run();
    return 0;
}

模块代码设计

#include "stm32f10x.h"

// 引脚定义
#define LED_PIN GPIO_Pin_13
#define LED_PORT GPIOC
#define KEY_PIN GPIO_Pin_0
#define KEY_PORT GPIOA
#define SERVO_PIN GPIO_Pin_8
#define SERVO_PORT GPIOA
#define SERVO_TIM TIM1

// 语音识别指令定义
typedef enum {
    GARBAGE_DRY = 0,
    GARBAGE_WET,
    GARBAGE_RECYCLABLE,
    GARBAGE_HAZARDOUS,
    GARBAGE_UNKNOWN
} GarbageType;

// 系统状态
typedef struct {
    uint8_t isFull;
    uint8_t coverOpen;
    GarbageType currentType;
} SystemState;

SystemState sysState = {0, 0, GARBAGE_UNKNOWN};

// 系统时钟初始化
void RCC_Configuration(void) {
    RCC->APB2ENR |= RCC_APB2ENR_IOPAEN | RCC_APB2ENR_IOPCEN | 
                    RCC_APB2ENR_USART1EN | RCC_APB2ENR_SPI1EN |
                    RCC_APB2ENR_TIM1EN;
}

// GPIO初始化
void GPIO_Configuration(void) {
    // LED指示灯(PC13)
    GPIOC->CRH &= 0xFF0FFFFF;
    GPIOC->CRH |= 0x00300000;
    
    // 按键(PA0)
    GPIOA->CRL &= 0xFFFFFFF0;
    GPIOA->CRL |= 0x00000008;
    
    // 舵机PWM(PA8)
    GPIOA->CRH &= 0xFFFFFFF0;
    GPIOA->CRH |= 0x0000000B;
}

// USART1初始化 - 用于SYN6288语音合成
void USART1_Configuration(void) {
    USART1->BRR = 0x1D4C; // 9600 @72MHz
    USART1->CR1 = USART_CR1_UE | USART_CR1_TE | USART_CR1_RE;
    USART1->CR2 = 0;
    USART1->CR3 = 0;
}

// SPI1初始化 - 用于LD3320语音识别
void SPI1_Configuration(void) {
    // PA5-SCK, PA6-MISO, PA7-MOSI
    GPIOA->CRL &= 0x000FFFFF;
    GPIOA->CRL |= 0xBBB00000;
    
    SPI1->CR1 = SPI_CR1_MSTR | SPI_CR1_BR_0 | SPI_CR1_SSM | 
                SPI_CR1_SSI | SPI_CR1_SPE;
    SPI1->CR2 = 0;
}

// 定时器1初始化 - 用于舵机PWM控制
void TIM1_Configuration(void) {
    // 72MHz/72 = 1MHz, 50Hz PWM -> 20000周期
    SERVO_TIM->PSC = 71;
    SERVO_TIM->ARR = 19999;
    
    // 通道1 PWM输出
    SERVO_TIM->CCMR1 |= TIM_CCMR1_OC1M_1 | TIM_CCMR1_OC1M_2;
    SERVO_TIM->CCER |= TIM_CCER_CC1E;
    SERVO_TIM->BDTR |= TIM_BDTR_MOE;
    SERVO_TIM->CR1 = TIM_CR1_CEN;
}

// 舵机控制函数
void Servo_Control(uint8_t angle) {
    uint16_t pulse = 500 + (angle * 2000 / 180); // 0.5ms-2.5ms
    SERVO_TIM->CCR1 = pulse;
}

// LED控制
void LED_Control(uint8_t state) {
    if(state) {
        LED_PORT->BSRR = LED_PIN;
    } else {
        LED_PORT->BRR = LED_PIN;
    }
}

// 按键检测
uint8_t Key_Scan(void) {
    static uint8_t key_up = 1;
    if(key_up && (KEY_PORT->IDR & KEY_PIN) == 0) {
        delay_ms(10);
        key_up = 0;
        if((KEY_PORT->IDR & KEY_PIN) == 0) {
            return 1;
        }
    } else if((KEY_PORT->IDR & KEY_PIN) != 0) {
        key_up = 1;
    }
    return 0;
}

// SPI读写函数
uint8_t SPI1_ReadWriteByte(uint8_t data) {
    while((SPI1->SR & SPI_SR_TXE) == 0);
    SPI1->DR = data;
    while((SPI1->SR & SPI_SR_RXNE) == 0);
    return SPI1->DR;
}

// LD3320语音识别初始化
void LD3320_Init(void) {
    // LD3320复位和初始化序列
    SPI1_ReadWriteByte(0x00);
    delay_ms(100);
    // 更多初始化代码...
}

// 语音识别处理
GarbageType Voice_Recognition(void) {
    uint8_t result = 0;
    // 读取识别结果
    result = SPI1_ReadWriteByte(0x00);
    
    switch(result) {
        case 0x01: return GARBAGE_DRY;
        case 0x02: return GARBAGE_WET;
        case 0x03: return GARBAGE_RECYCLABLE;
        case 0x04: return GARBAGE_HAZARDOUS;
        default: return GARBAGE_UNKNOWN;
    }
}

// SYN6288语音播报
void Voice_Play(GarbageType type) {
    const char* voice_cmd[] = {
        "可回收垃圾",
        "厨余垃圾", 
        "干垃圾",
        "有害垃圾",
        "未知垃圾"
    };
    
    // 发送语音合成指令
    USART1_SendString("[v5]");
    USART1_SendString(voice_cmd[type]);
    USART1_SendString("[/v]");
}

// USART1发送字符串
void USART1_SendString(char* str) {
    while(*str) {
        while((USART1->SR & USART_SR_TXE) == 0);
        USART1->DR = *str++;
    }
}

// ESP8266 WiFi发送状态
void WiFi_SendStatus(void) {
    char buffer[64];
    sprintf(buffer, "STATUS: FULL=%d, COVER=%d, TYPE=%d", 
            sysState.isFull, sysState.coverOpen, sysState.currentType);
    // 通过USART2发送到ESP8266
    // USART2_SendString(buffer);
}

// 延时函数
void delay_ms(uint32_t ms) {
    volatile uint32_t i, j;
    for(i = 0; i < ms; i++)
        for(j = 0; j < 7200; j++);
}

// 桶盖控制
void Cover_Control(uint8_t open) {
    if(open) {
        Servo_Control(90); // 打开角度
        sysState.coverOpen = 1;
        LED_Control(1);
    } else {
        Servo_Control(0); // 关闭角度
        sysState.coverOpen = 0;
        LED_Control(0);
    }
}

// 满溢检测
void Full_Detection(void) {
    // 使用超声波或红外传感器检测
    // 简化实现
    if(/* 检测到满 */) {
        sysState.isFull = 1;
        WiFi_SendStatus();
    }
}

// 主函数
int main(void) {
    // 系统初始化
    RCC_Configuration();
    GPIO_Configuration();
    USART1_Configuration();
    SPI1_Configuration();
    TIM1_Configuration();
    LD3320_Init();
    
    // 初始状态
    Cover_Control(0);
    
    while(1) {
        // 手动开关盖
        if(Key_Scan()) {
            Cover_Control(!sysState.coverOpen);
        }
        
        // 语音识别
        GarbageType type = Voice_Recognition();
        if(type != GARBAGE_UNKNOWN) {
            sysState.currentType = type;
            Voice_Play(type);
            Cover_Control(1);
            delay_ms(3000); // 保持开启3秒
            Cover_Control(0);
        }
        
        // 满溢检测
        Full_Detection();
        
        delay_ms(100);
    }
}

项目核心代码

#include "stm32f10x.h"

// 假设外部模块函数已定义
extern void LD3320_Init(void);
extern int LD3320_GetResult(void);
extern void SYN6288_Play(const char* text);
extern void ESP8266_Send(const char* data);
extern void Servo_SetAngle(int angle);

// 全局变量定义
volatile uint8_t lid_state = 0; // 桶盖状态 0:关闭 1:打开
volatile uint8_t trash_full = 0; // 满溢状态 0:未满 1:满溢
volatile uint8_t button_pressed = 0; // 按钮按下标志
uint32_t open_count = 0; // 开盖计数

// 函数声明
void System_Init(void);
void GPIO_Init(void);
void USART_Init(void);
void TIM_Init(void);
void EXTI_Init(void);
void Delay_ms(uint32_t nTime);

int main(void)
{
    System_Init();
    GPIO_Init();
    USART_Init();
    TIM_Init();
    EXTI_Init();
    
    // 初始化外部模块
    LD3320_Init();
    
    while(1)
    {
        int trash_type = LD3320_GetResult();
        
        if(trash_type != 0) // 识别到垃圾类型
        {
            char feedback[50];
            switch(trash_type)
            {
                case 1: 
                    sprintf(feedback, "可回收垃圾");
                    break;
                case 2: 
                    sprintf(feedback, "厨余垃圾"); 
                    break;
                case 3: 
                    sprintf(feedback, "有害垃圾");
                    break;
                case 4: 
                    sprintf(feedback, "其他垃圾");
                    break;
                default: 
                    sprintf(feedback, "未知类型");
                    break;
            }
            
            // 语音播报反馈
            SYN6288_Play(feedback);
            
            // 打开桶盖
            Servo_SetAngle(90); // 90度对应打开
            lid_state = 1;
            GPIOB->ODR |= (1 << 12); // 状态指示灯亮
            open_count++;
            
            // 延迟后关闭
            Delay_ms(3000);
            Servo_SetAngle(0); // 0度对应关闭
            lid_state = 0;
            GPIOB->ODR &= ~(1 << 12); // 状态指示灯灭
            
            // 检查满溢状态
            if(open_count >= 10)
            {
                trash_full = 1;
                ESP8266_Send("垃圾桶已满,请及时清理");
                open_count = 0;
            }
        }
        
        // 处理手动按钮
        if(button_pressed)
        {
            if(lid_state == 0)
            {
                Servo_SetAngle(90);
                lid_state = 1;
                GPIOB->ODR |= (1 << 12);
            }
            else
            {
                Servo_SetAngle(0);
                lid_state = 0;
                GPIOB->ODR &= ~(1 << 12);
            }
            button_pressed = 0;
            Delay_ms(200); // 消抖
        }
        
        // 定期发送状态
        static uint32_t last_send = 0;
        if(SystemCoreClock - last_send > 6000000) // 约1分钟
        {
            if(trash_full)
                ESP8266_Send("状态:满溢");
            else
                ESP8266_Send("状态:正常");
            last_send = SystemCoreClock;
        }
    }
}

void System_Init(void)
{
    // 配置系统时钟
    RCC->CFGR |= (0x02 << 18); // PLL乘法因子×6
    RCC->CR |= (1 << 24);      // 使能PLL
    while(!(RCC->CR & (1 << 25))); // 等待PLL就绪
    RCC->CFGR |= 0x02;         // 选择PLL作为系统时钟
    SystemCoreClock = 48000000; // 系统时钟48MHz
}

void GPIO_Init(void)
{
    // 使能GPIO时钟
    RCC->APB2ENR |= RCC_APB2ENR_IOPAEN | RCC_APB2ENR_IOPBEN | RCC_APB2ENR_IOPCEN;
    
    // 状态指示灯 PB12 推挽输出
    GPIOB->CRH &= ~(0x0F << 16);
    GPIOB->CRH |= (0x03 << 16);
    
    // 手动按钮 PA0 输入
    GPIOA->CRL &= ~(0x0F << 0);
    GPIOA->CRL |= (0x04 << 0); // 浮空输入
}

void USART_Init(void)
{
    // 使能USART1时钟 (ESP8266)
    RCC->APB2ENR |= RCC_APB2ENR_USART1EN;
    
    // 配置PA9为TX推挽复用输出,PA10为RX浮空输入
    GPIOA->CRH &= ~(0xFF << 4);
    GPIOA->CRH |= (0x0B << 4) | (0x04 << 8);
    
    // 波特率设置 115200
    USART1->BRR = 48000000 / 115200;
    
    // 使能USART1
    USART1->CR1 = USART_CR1_UE | USART_CR1_TE | USART_CR1_RE;
}

void TIM_Init(void)
{
    // 使能TIM1时钟 (舵机PWM)
    RCC->APB2ENR |= RCC_APB2ENR_TIM1EN;
    
    // 配置PA8为TIM1_CH1 PWM输出
    GPIOA->CRH &= ~(0x0F << 0);
    GPIOA->CRH |= (0x0B << 0); // 复用推挽输出
    
    // 定时器配置
    TIM1->PSC = 47999; // 分频至1kHz
    TIM1->ARR = 1999;  // 周期20ms
    TIM1->CCR1 = 150;  // 初始脉宽1.5ms
    
    // PWM模式配置
    TIM1->CCMR1 |= (0x06 << 4); // PWM模式1
    TIM1->CCER |= TIM_CCER_CC1E; // 使能通道1
    TIM1->BDTR |= TIM_BDTR_MOE;  // 主输出使能
    TIM1->CR1 = TIM_CR1_CEN;     // 启动定时器
}

void EXTI_Init(void)
{
    // 使能AFIO时钟
    RCC->APB2ENR |= RCC_APB2ENR_AFIOEN;
    
    // 配置PA0为EXTI0
    AFIO->EXTICR[0] |= 0x00;
    
    // 配置下降沿触发
    EXTI->FTSR |= EXTI_FTSR_TR0;
    
    // 使能EXTI0中断
    EXTI->IMR |= EXTI_IMR_MR0;
    
    // 配置NVIC
    NVIC->ISER[0] |= (1 << 6); // 使能EXTI0中断
}

void EXTI0_IRQHandler(void)
{
    if(EXTI->PR & EXTI_PR_PR0)
    {
        button_pressed = 1;
        EXTI->PR |= EXTI_PR_PR0; // 清除中断标志
    }
}

void Delay_ms(uint32_t nTime)
{
    volatile uint32_t i;
    for(; nTime > 0; nTime--)
        for(i = 0; i < 8000; i++);
}

总结

本系统基于STM32微控制器设计了一款智能垃圾桶,旨在通过语音识别和自动化控制技术,提升垃圾处理的便捷性和智能化水平。该系统能够高效地响应用户需求,并实现远程状态监控,为现代生活提供环保解决方案。

功能上,系统通过语音识别模块准确判断用户指令中的垃圾种类,并在识别成功后利用语音播报模块实时反馈分类结果;同时,借助Wi-Fi模块将垃圾桶的满溢等状态信息发送至用户手机,确保及时管理;此外,系统还支持手动开关盖操作,并配有状态指示灯,以增强使用的灵活性和可视化提示。

硬件方面,系统采用STM32F103C8T6作为核心主控芯片,集成LD3320语音识别模块、SYN6288语音合成模块、ESP8266 Wi-Fi模块以及SG90舵机作为执行机构,各模块协同工作,确保了系统的稳定运行和功能实现。

总体而言,这款智能垃圾桶不仅简化了垃圾分类流程,还通过智能化设计促进了资源节约和环境保护,体现了科技在日常生活应用中的实用价值。

【声明】本内容来自华为云开发者社区博主,不代表华为云及华为云开发者社区的观点和立场。转载时必须标注文章的来源(华为云社区)、文章链接、文章作者等基本信息,否则作者和本社区有权追究责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。