%% ECE 4950 - Webcam Color Symbol Detection (Improved)
clear; close all; clc;

%% Setup Webcam
cam_list = webcamlist;   % see available cameras
cam_name = 'Brio 100';   % change to your webcam name if needed
cam = webcam(cam_name);

%% Capture Background (no paper!)
disp('Capturing background');
pause(2);
background_img = snapshot(cam);
figure; imshow(background_img); title('Background Image');

%% Capture Foreground (with paper and symbols)
disp('Capturing foreground... place paper now!');
pause(5);
foreground_img = snapshot(cam);
figure; imshow(foreground_img); title('Foreground Image');

%% Background Subtraction in Grayscale
gray_bg = rgb2gray(background_img);
gray_fg = rgb2gray(foreground_img);
diff_img = imabsdiff(gray_fg, gray_bg);

% Median filter to remove salt & pepper noise
diff_filt = medfilt2(diff_img,[5 5]);

% Binarize
bw_img = imbinarize(diff_filt, 'adaptive');
figure; imshow(bw_img); title('Binary Difference Image');

%% Morphological Cleanup
SE = strel('disk', 5);
bw_clean = imopen(bw_img, SE);     % remove small specks
bw_clean = imclose(bw_clean, SE);  % close small gaps
bw_clean = imfill(bw_clean, 'holes');
figure; imshow(bw_clean); title('Cleaned Binary Image');

%% Regionprops Analysis
STATS = regionprops(bw_clean, 'Area','Centroid','PixelIdxList');

%% Convert Foreground to HSV for Color Detection
hsv_img = rgb2hsv(foreground_img);
H = hsv_img(:,:,1);  % Hue
S = hsv_img(:,:,2);  % Saturation
V = hsv_img(:,:,3);  % Brightness

%% Overlay Results
figure; imshow(foreground_img); hold on;
title('Detected Symbols with Color Labels');

for i = 1:length(STATS)
    if STATS(i).Area < 250
        continue;
    end
    
    % Get average HSV values inside blob
    region_mask = false(size(bw_clean));
    region_mask(STATS(i).PixelIdxList) = true;
    
    meanH = mean(H(region_mask));
    meanS = mean(S(region_mask));
    centroid = STATS(i).Centroid;
    
    % Initialize as "not classified"
    label = '';
    color_val = 'w';
    
    % Color classification using Hue
    if meanS > 0.3   % ensure it's not grayscale
        if (meanH < 0.05 || meanH > 0.95)
            label = 'RED';   color_val = 'r';
        elseif meanH > 0.25 && meanH < 0.45
            label = 'GREEN'; color_val = 'g';
        elseif meanH > 0.55 && meanH < 0.75
            label = 'BLUE';  color_val = 'b';
        elseif meanH > 0.12 && meanH < 0.20
            label = 'YELLOW'; color_val = [0.9 0.9 0];
        end
    end
    
    % Only draw if classified
    if ~isempty(label)
        plot(centroid(1), centroid(2), 'wo','MarkerFaceColor','w');
        text(centroid(1)+20, centroid(2), label, ...
            'Color', color_val, 'FontSize', 12, 'FontWeight','bold');
    end
end


disp('Detection complete!');
