• color_detection(AI开发框架esp-who)


    LCD示例代码

    app_main.cpp

    #include "who_camera.h"
    #include "who_color_detection.hpp"
    #include "who_lcd.h"
    #include "who_button.h"
    #include "event_logic.hpp"
    #include "who_adc_button.h"
    
    static QueueHandle_t xQueueAIFrame = NULL;
    static QueueHandle_t xQueueLCDFrame = NULL;
    static QueueHandle_t xQueueADCKeyState = NULL;
    static QueueHandle_t xQueueGPIOKeyState = NULL;
    static QueueHandle_t xQueueEventLogic = NULL;
    static button_adc_config_t buttons[4] = {{1, 2800, 3000}, {2, 2250, 2450}, {3, 300, 500}, {4, 850, 1050}};
    
    #define GPIO_BOOT GPIO_NUM_0
    
    extern "C" void app_main()
    {
        gpio_config_t gpio_conf;
        gpio_conf.mode = GPIO_MODE_OUTPUT_OD;
        gpio_conf.intr_type = GPIO_INTR_DISABLE;
        gpio_conf.pin_bit_mask = 1LL << GPIO_NUM_3;
        gpio_config(&gpio_conf);
        
        xQueueAIFrame = xQueueCreate(2, sizeof(camera_fb_t *));
        xQueueLCDFrame = xQueueCreate(2, sizeof(camera_fb_t *));
        xQueueADCKeyState = xQueueCreate(1, sizeof(int));
        xQueueGPIOKeyState = xQueueCreate(1, sizeof(int));
        xQueueEventLogic = xQueueCreate(1, sizeof(int));
    
        register_camera(PIXFORMAT_RGB565, FRAMESIZE_240X240, 2, xQueueAIFrame);
        register_adc_button(buttons, 4, xQueueADCKeyState);
        register_button(GPIO_NUM_0, xQueueGPIOKeyState);
        register_event(xQueueADCKeyState, xQueueGPIOKeyState, xQueueEventLogic);
        register_color_detection(xQueueAIFrame, xQueueEventLogic, NULL, xQueueLCDFrame, false);
        register_lcd(xQueueLCDFrame, NULL, true);
    
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38

    event_logic.hpp

    #pragma once
    
    #include "freertos/FreeRTOS.h"
    #include "freertos/queue.h"
    #include "freertos/task.h"
    
    /**
     * @brief 
     * 
     * @param key_state_i_adc 
     * @param key_state_i_gpio 
     * @param event_o 
     */
    void register_event(const QueueHandle_t key_state_i_adc, const QueueHandle_t key_state_i_gpio, const QueueHandle_t event_o);
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14

    event_logic.cpp

    #include 
    #include "event_logic.hpp"
    #include "who_button.h"
    #include "who_color_detection.hpp"
    
    typedef enum
    {
        MENU = 1,
        PLAY,
        UP,
        DOWN
    } key_name_t;
    
    static QueueHandle_t xQueueKeyStateIGPIO = NULL;
    static QueueHandle_t xQueueKeyStateIADC = NULL;
    static QueueHandle_t xQueueEventO = NULL;
    static key_state_t key_state;
    static key_name_t adc_button_name;
    static color_detection_state_t detector_state;
    
    void event_generate_from_gpio_button(void *arg)
    {
        color_detection_state_t switch_mode = SWITCH_RESULT;
        while (1)
        {
            xQueueReceive(xQueueKeyStateIGPIO, &key_state, portMAX_DELAY);
            xQueueSend(xQueueEventO, &switch_mode, portMAX_DELAY);
        }
    }
    
    void event_generate_from_adc_button(void *arg)
    {
        bool register_mode = false;
        while (1)
        {
            xQueueReceive(xQueueKeyStateIADC, &adc_button_name, portMAX_DELAY);
            switch (adc_button_name)
            {
            case MENU:
                detector_state = register_mode ? CLOSE_REGISTER_COLOR_BOX : OPEN_REGISTER_COLOR_BOX;
                register_mode = !register_mode;
                break;
    
            case PLAY:
                detector_state = register_mode ? REGISTER_COLOR : DELETE_COLOR;
                register_mode = false;
                break;
    
            case UP:
                detector_state = INCREASE_COLOR_AREA;
                break;
    
            case DOWN:
                detector_state = DECREASE_COLOR_AREA;
                break;
    
            default:
                detector_state = COLOR_DETECTION_IDLE;
                break;
            }
            xQueueSend(xQueueEventO, &detector_state, portMAX_DELAY);
        }
    }
    
    void register_event(const QueueHandle_t key_state_i_adc, const QueueHandle_t key_state_i_gpio, const QueueHandle_t event_o)
    {
        xQueueKeyStateIADC = key_state_i_adc;
        xQueueKeyStateIGPIO = key_state_i_gpio;
        xQueueEventO = event_o;
        if (xQueueKeyStateIADC != NULL)
            xTaskCreatePinnedToCore(event_generate_from_adc_button, "event_logic_task1", 1024, NULL, 5, NULL, 0);
        if (xQueueKeyStateIGPIO != NULL)
            xTaskCreatePinnedToCore(event_generate_from_gpio_button, "event_logic_task2", 1024, NULL, 5, NULL, 0);
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73
    • 74

    请添加图片描述

    esp32-s3-eye开发板的摄像头获取到数据后,通过register_camera()的函数将每一帧的数据输出到xQueueAIFrame队列缓冲区中。按键MENU PLAY UP和DN键在本示例充当的是ADC button的功能,可以将模拟信号转换为数字信号,这4个ADC按键的状态的先后顺序也需要有一个队列缓冲区去排队进行管理,就可以调用
    register_adc_button()的函数,将按键的状态输出到xQueueADCKeyState队列缓冲区里面。同样,BOOT按键的状态也需要进行记录,通过register_button()将BOOT按键的状态输出到xQueueGPIOKeyState队列缓冲区中。这样就记录了这5个按键的按下与松开,那么其实按键在按下与松开的时候会触发一些事件,通过调用register_event()的函数将xQueueADCKeyState和xQueueGPIOKeyState传入,传出一个xQueueEventLogic事件队列。调用register_color_detection()函数将帧的输入流xQueueAIFrame和事件队列xQueueEventLogic传入,输出一个作为帧的输出流的队列缓冲区xQueueLCDFrame,再调用register_lcd()函数将xQueueLCDFrame作为帧的输入流传入,即可显示到LCD屏幕上。

    如何运行示例

    • 交互按键为Boot键,MENU键,PLAY键,UP键和DN键。
    • 按下BOOT键:切换输出显示模式。
    • 按下MENU:切换录入模式和检测模式。
    • 按下PLAY键(录入模式): 录入指示框内的颜色。
    • 按下PLAY键(检测模式): 删除最后一个被录入的颜色。
    • 按下UP键(录入模式): 增大指示框的尺寸。
    • 按下UP键(检测模式): 增大颜色检测过滤的最小色块的面积。
    • 按下DN键(录入模式): 减小指示框的尺寸。
    • 按下DN键(检测模式): 减小颜色检测过滤的最小色块的面积。
  • 相关阅读:
    create® 3入门教程-导航
    Docker高级篇之Docker微服务实战
    Unity 设置Inspect上问号的跳转链接
    DevOps 前端开发和 Spug
    uniapp实现拍照涂鸦
    matlab调用python自定义函数模块进行数据分析总结
    TMMi测试成熟度模型.概念总结
    检验科LIS系统源码,多家二甲医院实际使用,三年持续优化和运维,系统稳定可靠
    【仿牛客网笔记】 Spring Boot进阶,开发社区核心功能-发布帖子
    Java常见异常
  • 原文地址:https://blog.csdn.net/qq_45671732/article/details/126460821