这些小活动你都参加了吗?快来围观一下吧!>>
电子产品世界 » 论坛首页 » DIY与开源设计 » 电子DIY » 【Let'sdo第3期-拾色播放器DIY】--过程帖(2)Neo三色灯的控制

共1条 1/1 1 跳转至

【Let'sdo第3期-拾色播放器DIY】--过程帖(2)Neo三色灯的控制

菜鸟
2025-12-09 18:45:55     打赏

    跟着官方给的手册成功搭建环境后我们就可以在Mu编辑器上写我们的程序了。本贴是驱动TCS3200颜色传感器并且将参数传到三色灯的函数中去

一:接线部分

image.png

如代码配置所示,将TCS3200上的引脚照着板子上的引脚用杜邦线连接起来。

S0 -> D12, S1 -> D11, S2 -> D10, S2 -> D9, OUT -> D6, LED -> D5

三色灯是板子自带的不需要接线

二:代码部分:

    三色灯初始化:调用从官方下载的库,下载链接:NeoPixel LED | Adafruit ESP32-S2 Reverse TFT Feather | Adafruit Learning System

调用pixel.fill函数,将颜色传感器读取到的三色数据传参,即可控制三色灯的颜色

import neopixel  

# Neo三色灯初始化  
pixel = neopixel.NeoPixel(board.NEOPIXEL, 1)  
pixel.brightness = 0.3
pixel.fill((R_Val, G_Val, B_Val))


    颜色传感器初始化:和上篇帖子一样

class TCS3200:
    def __init__(self, s0, s1, s2, s3, out_pin):
        self.s0 = s0
        self.s1 = s1
        self.s2 = s2
        self.s3 = s3
        self.out = out_pin

        # 设置引脚方向
        self.s0.direction = digitalio.Direction.OUTPUT
        self.s1.direction = digitalio.Direction.OUTPUT
        self.s2.direction = digitalio.Direction.OUTPUT
        self.s3.direction = digitalio.Direction.OUTPUT
        self.out.direction = digitalio.Direction.INPUT

        # 设置100%频率
        self.set_frequency(2)

        # 固定校准值 - 基于提供的白色和黑色读数
        self.max_values = {'red': 526.4, 'green': 436.9, 'blue': 464.8}  # 白色参考值
        self.min_values = {'red': 177.4, 'green': 153.3, 'blue': 169.6}  # 黑色参考值

        print("使用固定校准值:")
        print(f"白色参考 - R:{self.max_values['red']}, G:{self.max_values['green']}, B:{self.max_values['blue']}")
        print(f"黑色参考 - R:{self.min_values['red']}, G:{self.min_values['green']}, B:{self.min_values['blue']}")

    def set_frequency(self, freq_mode):
        if freq_mode == 0:
            self.s0.value = False
            self.s1.value = False
        elif freq_mode == 1:
            self.s0.value = False
            self.s1.value = True
        elif freq_mode == 2:
            self.s0.value = True
            self.s1.value = False
        else:
            self.s0.value = True
            self.s1.value = True

    def set_filter(self, filter_mode):
        if filter_mode == 0:  # Red
            self.s2.value = False
            self.s3.value = False
        elif filter_mode == 1:  # Blue
            self.s2.value = False
            self.s3.value = True
        elif filter_mode == 2:  # Clear
            self.s2.value = True
            self.s3.value = False
        elif filter_mode == 3:  # Green
            self.s2.value = True
            self.s3.value = True

    def measure_frequency(self, num_cycles=10):
        """测量输出频率"""
        timestamps = []
        last_state = self.out.value

        start_time = time.monotonic()
        while len(timestamps) < num_cycles * 2 and (time.monotonic() - start_time < 1.0):
            current_state = self.out.value
            if current_state != last_state:
                timestamps.append(time.monotonic_ns())
                last_state = current_state

        if len(timestamps) < 4:
            return 0

        # 计算周期
        periods = []
        for i in range(2, len(timestamps), 2):
            period_ns = timestamps[i] - timestamps[i-2]
            periods.append(period_ns)

        if not periods:
            return 0

        avg_period_ns = sum(periods) / len(periods)
        frequency = 1_000_000_000 / avg_period_ns
        return frequency

    def read_color_raw(self):
        """读取原始RGB颜色值"""
        # 读取红色分量
        self.set_filter(0)  # Red filter
        time.sleep(0.01)
        red = self.measure_frequency(5)

        # 读取蓝色分量
        self.set_filter(1)  # Blue filter
        time.sleep(0.01)
        blue = self.measure_frequency(5)

        # 读取绿色分量
        self.set_filter(3)  # Green filter
        time.sleep(0.01)
        green = self.measure_frequency(5)

        return red, green, blue

    def read_color_calibrated(self):
        """读取校准后的RGB颜色值 (0-255范围) - 使用固定校准值"""
        red, green, blue = self.read_color_raw()

        # 应用线性映射到0-255范围
        red_norm = int(255 * (red - self.min_values['red']) / (self.max_values['red'] - self.min_values['red']))
        green_norm = int(255 * (green - self.min_values['green']) / (self.max_values['green'] - self.min_values['green']))
        blue_norm = int(255 * (blue - self.min_values['blue']) / (self.max_values['blue'] - self.min_values['blue']))

        # 限制在0-255范围内
        red_norm = max(0, min(255, red_norm))
        green_norm = max(0, min(255, green_norm))
        blue_norm = max(0, min(255, blue_norm))

        return red_norm, green_norm, blue_norm, red, green, blue

    def detect_color(self):
        """检测颜色类型 - 使用校准后的RGB值"""
        red_norm, green_norm, blue_norm, red_raw, green_raw, blue_raw = self.read_color_calibrated()

        # 颜色判断阈值 - 基于校准后的RGB值
        # 白色: 所有值都很高
        if red_norm > 200 and green_norm > 200 and blue_norm > 200:
            return 'white', red_raw, green_raw, blue_raw, red_norm, green_norm, blue_norm

        # 黑色: 所有值都很低
        elif red_norm < 50 and green_norm < 50 and blue_norm < 50:
            return 'black', red_raw, green_raw, blue_raw, red_norm, green_norm, blue_norm

        # 黄色: 红色和绿色都很高,蓝色很低
        elif red_norm > 180 and green_norm > 180 and blue_norm < 100:
            return 'yellow', red_raw, green_raw, blue_raw, red_norm, green_norm, blue_norm

        # 紫色: 红色和蓝色都很高,绿色很低
        elif red_norm > 150 and blue_norm > 150 and green_norm < 100:
            return 'purple', red_raw, green_raw, blue_raw, red_norm, green_norm, blue_norm

        # 橙色: 红色很高,绿色中等,蓝色很低
        elif red_norm > 180 and green_norm > 100 and blue_norm < 80:
            return 'orange', red_raw, green_raw, blue_raw, red_norm, green_norm, blue_norm
        # 红色: 红色分量最高且足够高
        elif red_norm > green_norm and red_norm > blue_norm and red_norm > 150:
            return 'red', red_raw, green_raw, blue_raw, red_norm, green_norm, blue_norm

        # 绿色: 绿色分量最高且足够高
        elif green_norm > red_norm and green_norm > blue_norm and green_norm > 150:
            return 'green', red_raw, green_raw, blue_raw, red_norm, green_norm, blue_norm

        # 蓝色: 蓝色分量最高且足够高
        elif blue_norm > red_norm and blue_norm > green_norm and blue_norm > 150:
            return 'blue', red_raw, green_raw, blue_raw, red_norm, green_norm, blue_norm



        # 未知颜色
        else:
            return 'unknown', red_raw, green_raw, blue_raw, red_norm, green_norm, blue_norm

# 初始化传感器
try:
    s0 = digitalio.DigitalInOut(board.D12)
    s1 = digitalio.DigitalInOut(board.D11)
    s2 = digitalio.DigitalInOut(board.D10)
    s3 = digitalio.DigitalInOut(board.D9)
    out_pin = digitalio.DigitalInOut(board.D6)

    led1 = digitalio.DigitalInOut(board.D5)  
    
    
    led1.direction = digitalio.Direction.OUTPUT  
    led1.value = False  

    color_sensor = TCS3200(s0, s1, s2, s3, out_pin)
    print("Color sensor initialized with fixed calibration")

    


    成果展示:





1765276856616282.jpg1765276857325498.jpg1765276859624514.jpg1765276861903714.jpg1765276862708619.jpg





关键词: 拾色     播放器     过程     色灯     控制    

共1条 1/1 1 跳转至

回复

匿名不能发帖!请先 [ 登陆 注册 ]