视障辅助程序开发:如何快速分类RGB三元组至指定颜色组?
Hey there! No need to apologize at all—this is such a meaningful project, and your requirements are totally clear and practical. Let’s walk through a straightforward, high-fault-tolerance approach for the second step that checks all your boxes.
Unlike RGB (which is hardware-focused), HSV aligns much closer to how humans perceive color. The H (Hue) channel defines the actual color (red, blue, etc.), S (Saturation) measures vividness, and V (Value) controls brightness/darkness. This makes it perfect for:
- Fast, non-machine-learning execution
- Distinguishing light/dark shades of the same color
- Adapting to natural light brightness variations
- Easy tuning for high fault tolerance
Step 1: Convert RGB to HSV (Quick & Built-In)
Most programming languages have built-in tools for this conversion—no external libraries needed. Here’s a Python example using the standard colorsys module:
import colorsys def rgb_to_hsv(r, g, b): # Normalize RGB values from 0-255 to 0-1 r_norm = r / 255.0 g_norm = g / 255.0 b_norm = b / 255.0 # Convert to HSV (returns h: 0-1, s:0-1, v:0-1) h, s, v = colorsys.rgb_to_hsv(r_norm, g_norm, b_norm) # Convert hue to 0-360 for easier rule-writing return (h * 360, s, v)
Step 2: Define Color Group Rules (Covers All Required Categories)
We’ll split rules into two groups: neutral colors (black, white, gray, beige) and colored shades (with light/dark distinctions). Rules are intentionally fuzzy to boost fault tolerance for natural light.
Neutral Color Rules
| Color | HSV Conditions |
|---|---|
| Black | v < 0.2 (too dark to be any other color) |
| White | v > 0.85 AND s < 0.15 (bright, low saturation) |
| Gray | 0.2 ≤ v ≤ 0.85 AND s < 0.15 (mid-brightness, low saturation) |
| Beige | 0.7 ≤ v ≤ 0.95 AND s < 0.3 AND 20 ≤ h ≤ 60 (warm, low-saturation light neutral) |
Colored Shade Rules
Each color includes thresholds to distinguish light/dark variants:
- Red: Hue
0-15or345-360- Dark (栗色):
s > 0.3ANDv < 0.5 - Bright Red:
s > 0.3ANDv ≥ 0.5 - Pink:
s < 0.4ANDv ≥ 0.6(low-saturation light red)
- Dark (栗色):
- Orange: Hue
15-45- Dark Orange:
s > 0.25ANDv < 0.5 - Bright Orange:
s > 0.25ANDv ≥ 0.5
- Dark Orange:
- Yellow: Hue
45-75- Dark Yellow:
s > 0.2ANDv < 0.5 - Bright Yellow:
s > 0.2ANDv ≥ 0.5
- Dark Yellow:
- Green: Hue
75-160- Dark Green:
s > 0.2ANDv < 0.5 - Bright Green:
s > 0.2ANDv ≥ 0.5
- Dark Green:
- Blue: Hue
160-260- Dark (藏青):
s > 0.2ANDv < 0.5 - Bright Blue:
s > 0.2ANDv ≥ 0.5
- Dark (藏青):
- Purple: Hue
260-345- Dark Purple:
s > 0.2ANDv < 0.5 - Bright Purple:
s > 0.2ANDv ≥ 0.5
- Dark Purple:
Step 3: Full Implementation with Fault Tolerance
Here’s a complete function that wraps everything up, with a fallback for edge cases (critical for accessibility):
import colorsys def classify_color(r, g, b): h, s, v = rgb_to_hsv(r, g, b) # Handle neutral colors first if v < 0.2: return "黑色" elif v > 0.85 and s < 0.15: return "白色" elif 0.2 <= v <= 0.85 and s < 0.15: return "灰色" elif 0.7 <= v <= 0.95 and s < 0.3 and 20 <= h <= 60: return "米色" # Handle colored shades # Red/Pink family if (0 <= h <= 15) or (345 <= h <= 360): if s > 0.3: return "栗色(深红色)" if v < 0.5 else "红色" elif s < 0.4 and v >= 0.6: return "粉色" # Orange elif 15 < h <= 45: if s > 0.25: return "深橙色" if v < 0.5 else "橙色" # Yellow elif 45 < h <= 75: if s > 0.2: return "深黄色" if v < 0.5 else "黄色" # Green elif 75 < h <= 160: if s > 0.2: return "深绿色" if v < 0.5 else "绿色" # Blue elif 160 < h <= 260: if s > 0.2: return "藏青(深蓝色)" if v < 0.5 else "蓝色" # Purple elif 260 < h <= 345: if s > 0.2: return "深紫色" if v < 0.5 else "紫色" # Fallback for edge cases (critical for accessibility) return "灰色" # Helper function from earlier def rgb_to_hsv(r, g, b): r_norm = r / 255.0 g_norm = g / 255.0 b_norm = b / 255.0 h, s, v = colorsys.rgb_to_hsv(r_norm, g_norm, b_norm) return (h * 360, s, v)
Step 4: Tuning Tips for Your Use Case
Since you’re targeting natural light and high fault tolerance:
- Test with real-world samples: Take photos of your target colors in sunny, cloudy, and indoor light, then adjust H/S/V thresholds if classifications are off.
- Add majority voting: If your first step extracts multiple main colors (e.g., top 3), classify all and return the most frequent result—this reduces single-pixel errors.
- Simplify voice output: For visually impaired users, use clear, concise labels (e.g., "深红色" instead of "栗色(深红色)" if preferred).
Hope this helps you get up and running quickly! This approach is beginner-friendly, fast, and designed to prioritize accessibility and accuracy.
内容的提问来源于stack exchange,提问作者Shahd Seddik

