Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- import cv2
- import numpy as np
- import os
- def get_average_color(image: np.ndarray) -> np.ndarray:
- """
- Calculate the average color of an image.
- Parameters:
- image (numpy.ndarray): The input image.
- Returns:
- numpy.ndarray: The average color of the image.
- """
- average_color_per_row = np.average(image, axis=0)
- average_color = np.average(average_color_per_row, axis=0)
- return average_color
- def remove_outliers(data: list) -> list:
- """
- Remove outliers using the Interquartile Range (IQR) method.
- Parameters:
- data (list): The input data.
- Returns:
- list: The data with outliers removed.
- """
- q1, q3 = np.percentile(data, [25, 75])
- iqr = q3 - q1
- lower_bound = q1 - 1.5 * iqr
- upper_bound = q3 + 1.5 * iqr
- return [x for x in data if lower_bound <= x <= upper_bound]
- def get_color_limits_from_dataset(dataset_path: str) -> tuple:
- """
- Calculate color limits (HSV) based on a dataset of images, removing outliers.
- Parameters:
- dataset_path (str): The path to the dataset of images.
- Returns:
- tuple: The lower and upper color limits in HSV.
- """
- hues, saturations, values = [], [], []
- for filename in os.listdir(dataset_path):
- if filename.endswith(".jpg") or filename.endswith(".png"):
- image_path = os.path.join(dataset_path, filename)
- image = cv2.imread(image_path)
- hsv_image = cv2.cvtColor(image, cv2.COLOR_BGR2HSV)
- average_color = get_average_color(hsv_image)
- hues.append(average_color[0]) # Hue component
- saturations.append(average_color[1]) # Saturation component
- values.append(average_color[2]) # Value component
- # Remove outliers
- hues = remove_outliers(hues)
- saturations = remove_outliers(saturations)
- values = remove_outliers(values)
- lower_limit = np.array([min(hues), min(saturations), min(values)], dtype=np.uint8)
- upper_limit = np.array([max(hues), max(saturations), max(values)], dtype=np.uint8)
- return lower_limit, upper_limit
- def get_color_limits_from_hsv(
- base_color: tuple,
- hue_percentage: float,
- saturation_percentage: float,
- value_percentage: float,
- ) -> tuple:
- """
- Calculate color limits (HSV) based on a given color and user-provided percentages.
- Parameters:
- base_color (tuple): The base color in HSV.
- hue_percentage (float): The percentage range for hue.
- saturation_percentage (float): The percentage range for saturation.
- value_percentage (float): The percentage range for value.
- Returns:
- tuple: The lower and upper color limits in HSV.
- """
- hue, saturation, value = base_color
- hue_range = 255 * hue_percentage / 100
- saturation_range = 255 * saturation_percentage / 100
- value_range = 255 * value_percentage / 100
- lower_limit = np.array(
- [
- max(0, hue - hue_range),
- max(0, saturation - saturation_range),
- max(0, value - value_range),
- ],
- dtype=np.uint8,
- )
- upper_limit = np.array(
- [
- min(255, hue + hue_range),
- min(255, saturation + saturation_range),
- min(255, value + value_range),
- ],
- dtype=np.uint8,
- )
- return lower_limit, upper_limit
- def process_webcam_video(lower_limit: np.ndarray, upper_limit: np.ndarray):
- """
- Process video from the webcam to identify and highlight areas matching the color limits.
- Parameters:
- lower_limit (numpy.ndarray): The lower HSV color limit.
- upper_limit (numpy.ndarray): The upper HSV color limit.
- """
- cap = cv2.VideoCapture(0)
- while True:
- ret, frame = cap.read()
- if not ret:
- break
- hsv_frame = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV)
- # Create a mask based on color limits
- mask = cv2.inRange(hsv_frame, lower_limit, upper_limit)
- # Find contours of areas that match the color range
- contours, _ = cv2.findContours(mask, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
- # Draw rectangles around each found contour
- for contour in contours:
- if cv2.contourArea(contour) > 500: # Filter small contours
- x, y, w, h = cv2.boundingRect(contour)
- frame = cv2.rectangle(frame, (x, y), (x + w, y + h), (0, 255, 0), 5)
- # Add color limit legend to the main frame
- lower_color_bgr = cv2.cvtColor(np.uint8([[lower_limit]]), cv2.COLOR_HSV2BGR)[0][
- 0
- ]
- upper_color_bgr = cv2.cvtColor(np.uint8([[upper_limit]]), cv2.COLOR_HSV2BGR)[0][
- 0
- ]
- cv2.rectangle(frame, (10, 10), (30, 30), lower_color_bgr.tolist(), -1)
- cv2.putText(
- frame,
- "Lower Limit",
- (35, 25),
- cv2.FONT_HERSHEY_SIMPLEX,
- 0.5,
- (255, 255, 255),
- 1,
- )
- cv2.rectangle(frame, (10, 40), (30, 60), upper_color_bgr.tolist(), -1)
- cv2.putText(
- frame,
- "Upper Limit",
- (35, 55),
- cv2.FONT_HERSHEY_SIMPLEX,
- 0.5,
- (255, 255, 255),
- 1,
- )
- # Add color limit legend to the mask
- mask_with_legend = cv2.cvtColor(mask, cv2.COLOR_GRAY2BGR)
- cv2.rectangle(
- mask_with_legend, (10, 10), (30, 30), lower_color_bgr.tolist(), -1
- )
- cv2.putText(
- mask_with_legend,
- "Lower Limit",
- (35, 25),
- cv2.FONT_HERSHEY_SIMPLEX,
- 0.5,
- (255, 255, 255),
- 1,
- )
- cv2.rectangle(
- mask_with_legend, (10, 40), (30, 60), upper_color_bgr.tolist(), -1
- )
- cv2.putText(
- mask_with_legend,
- "Upper Limit",
- (35, 55),
- cv2.FONT_HERSHEY_SIMPLEX,
- 0.5,
- (255, 255, 255),
- 1,
- )
- # Show the frame and mask with legend
- cv2.imshow("frame", frame)
- cv2.imshow("mask", mask_with_legend)
- # Exit the loop by pressing 'q'
- if cv2.waitKey(1) & 0xFF == ord("q"):
- break
- # Release video capture and close all windows
- cap.release()
- cv2.destroyAllWindows()
- def identify_color_in_image(
- image_path: str, lower_limit: np.ndarray, upper_limit: np.ndarray
- ):
- """
- Identify and highlight areas matching the color limits in an image.
- Parameters:
- image_path (str): The path to the input image.
- lower_limit (numpy.ndarray): The lower HSV color limit.
- upper_limit (numpy.ndarray): The upper HSV color limit.
- """
- image = cv2.imread(image_path)
- hsv_image = cv2.cvtColor(image, cv2.COLOR_BGR2HSV)
- # Create a mask based on color limits
- mask = cv2.inRange(hsv_image, lower_limit, upper_limit)
- # Find contours of areas that match the color range
- contours, _ = cv2.findContours(mask, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
- # Draw rectangles around each found contour
- for contour in contours:
- if cv2.contourArea(contour) > 500: # Filter small contours
- x, y, w, h = cv2.boundingRect(contour)
- image = cv2.rectangle(image, (x, y), (x + w, y + h), (0, 255, 0), 5)
- # Add color limit legend to the main image
- lower_color_bgr = cv2.cvtColor(np.uint8([[lower_limit]]), cv2.COLOR_HSV2BGR)[0][0]
- upper_color_bgr = cv2.cvtColor(np.uint8([[upper_limit]]), cv2.COLOR_HSV2BGR)[0][0]
- cv2.rectangle(image, (10, 10), (30, 30), lower_color_bgr.tolist(), -1)
- cv2.putText(
- image,
- "Lower Limit",
- (35, 25),
- cv2.FONT_HERSHEY_SIMPLEX,
- 0.5,
- (255, 255, 255),
- 1,
- )
- cv2.rectangle(image, (10, 40), (30, 60), upper_color_bgr.tolist(), -1)
- cv2.putText(
- image,
- "Upper Limit",
- (35, 55),
- cv2.FONT_HERSHEY_SIMPLEX,
- 0.5,
- (255, 255, 255),
- 1,
- )
- # Show the image with legend
- cv2.imshow("image", image)
- cv2.imshow("mask", mask)
- # Wait for a key press and close all windows
- cv2.waitKey(0)
- cv2.destroyAllWindows()
- if __name__ == "__main__":
- # Path to the dataset of images
- # dataset_path = "path/to/your/dataset"
- # Example usage
- base_color = (30, 255, 255) # Base HSV color (yellow)
- # Calculate color limits from the dataset
- # lower_limit, upper_limit = get_color_limits_from_dataset(dataset_path)
- lower_limit, upper_limit = get_color_limits_from_hsv(base_color, 3, 70, 70)
- process_webcam_video(lower_limit, upper_limit)
- import cv2
- import numpy as np
- # Function to select points on an image
- def select_points(event, x, y, flags, param):
- if event == cv2.EVENT_LBUTTONDOWN:
- points.append((x, y))
- cv2.circle(img, (x, y), 5, (0, 255, 0), -1)
- cv2.putText(
- img,
- f"Points: {len(points)}",
- (10, 30),
- cv2.FONT_HERSHEY_SIMPLEX,
- 1,
- (255, 0, 0),
- 2,
- cv2.LINE_AA,
- )
- cv2.imshow(window_name, img)
- # Load the images
- img1 = cv2.imread(
- r"C:\Users\Admin\Documents\GitHub\PhotoColorAnalyzer\ITT\imageAlignment\test2.jpg"
- )
- img2 = cv2.imread(
- r"C:\Users\Admin\Documents\GitHub\PhotoColorAnalyzer\ITT\imageAlignment\test2.jpg"
- )
- # Check if images are loaded
- if img1 is None:
- print("Error: Could not load image1.jpg")
- exit()
- if img2 is None:
- print("Error: Could not load image2.jpg")
- exit()
- # Create windows to display the images
- window_name = "Select 5 points in image 1"
- cv2.imshow(window_name, img1)
- points = []
- cv2.setMouseCallback(window_name, select_points)
- cv2.waitKey(0)
- points1 = points.copy()
- # Mark the selected points on the first image
- for point in points1:
- cv2.circle(img1, point, 5, (0, 0, 255), -1)
- cv2.putText(
- img1,
- f"Points: {len(points1)}",
- (10, 30),
- cv2.FONT_HERSHEY_SIMPLEX,
- 1,
- (255, 0, 0),
- 2,
- cv2.LINE_AA,
- )
- cv2.imshow(window_name, img1)
- cv2.waitKey(0)
- window_name = "Select 5 points in image 2"
- cv2.imshow(window_name, img2)
- points = []
- cv2.setMouseCallback(window_name, select_points)
- cv2.waitKey(0)
- points2 = points.copy()
- # Mark the selected points on the second image
- for point in points2:
- cv2.circle(img2, point, 5, (0, 0, 255), -1)
- cv2.putText(
- img2,
- f"Points: {len(points2)}",
- (10, 30),
- cv2.FONT_HERSHEY_SIMPLEX,
- 1,
- (255, 0, 0),
- 2,
- cv2.LINE_AA,
- )
- cv2.imshow(window_name, img2)
- cv2.waitKey(0)
- # Convert points to numpy arrays
- points1 = np.array(points1, dtype=np.float32)
- points2 = np.array(points2, dtype=np.float32)
- # Compute the homography matrix
- H, _ = cv2.findHomography(points1, points2, cv2.RANSAC)
- # Warp the first image to align with the second image
- aligned_img = cv2.warpPerspective(img1, H, (img2.shape[1], img2.shape[0]))
- # Display the aligned image
- cv2.imshow("Aligned Image", aligned_img)
- cv2.waitKey(0)
- cv2.destroyAllWindows()
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement