Home > database >  Is there a good way to add a trackbar to cv2 Video
Is there a good way to add a trackbar to cv2 Video

Time:09-25

I wanted to add a filter(where everything is grayscaled except for the color chosen) that I can manipulate with a trackbar. The trackbar shows up but it shows no effect when the video is played. How should I solve this? please help, wise people.

import cv2
import sys
import numpy as np
import os

FILE_PATH = os.path.dirname(os.path.abspath(__file__))

video = cv2.VideoCapture(FILE_PATH  '/city_ex.mp4')
if not video.isOpened():
    print("Video Open Failed")
    sys.exit()
def trackbar(pos):
    global frame

    h, w = frame.shape[:2]
    frame = cv2.resize(frame, (w//2, h//2))
    frame_hsv = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV)
    hue_min = cv2.getTrackbarPos('Hue_min', 'video')
    hue_max = cv2.getTrackbarPos('Hue_max', 'video')

    mask = cv2.inRange(frame_hsv, (hue_min, 0, 0), (hue_max, 255, 255))
    mask_inv = cv2.bitwise_not(mask)

    colored_portion = cv2.bitwise_and(frame, frame, mask=mask)

    video_gray = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV)
    gray_portion = cv2.bitwise_or(video_gray, video_gray, mask=mask_inv)
    # gray_portion = np.stack((gray_portion,)*3, axis=-1)

    combined = colored_portion   gray_portion

    cv2.imshow('video', combined)

cv2.namedWindow('video')
cv2.createTrackbar('Hue_min', 'video', 0, 179, trackbar)
cv2.createTrackbar('Hue_max', 'video', 0, 179, trackbar)


while True:
    ret, frame = video.read()

    if not ret:
        break
    
    
    frame = show_change(frame)

    cv2.imshow('video', frame)
    
  

    

    key = cv2.waitKey(1)
    if key == 27:
        break

video.release()
cv2.destroyAllWindows()

CodePudding user response:

I see two problems

  1. you run two imshow('video', ...) so it tries to display two diferent images in the same window and original frame may fast replace combined so you can see only frame. You should use only one imshow and display combined.

  2. tracebar() is executed only when you move tracebar and it creates one image only at this. You should use tracebar() on to get values and assign to global variables hue_min, hue_max - and rest you should run in while True so it will create combined for all frames from file/webcam.


My version

import cv2
import sys
import numpy as np
import os

# --- functions ---

def trackbar(pos):
    global hue_min
    global hue_max
    
    hue_min = cv2.getTrackbarPos('Hue_min', 'video')
    hue_max = cv2.getTrackbarPos('Hue_max', 'video')

# --- main ---

hue_min = 0
hue_max = 179

#FILE_PATH = os.path.dirname(os.path.abspath(__file__))
#video = cv2.VideoCapture(os.path.join(FILE_PATH, 'city_ex.mp4'))

video = cv2.VideoCapture(0) # webcam

if not video.isOpened():
    print("Video Open Failed")
    sys.exit()

cv2.namedWindow('video')
cv2.createTrackbar('Hue_min', 'video', 0, 179, trackbar)
cv2.createTrackbar('Hue_max', 'video', 0, 179, trackbar)

while True:
    ret, frame = video.read()

    if not ret:
        break
    
    h, w = frame.shape[:2]
    frame = cv2.resize(frame, (w//2, h//2))
    frame_hsv = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV)

    mask = cv2.inRange(frame_hsv, (hue_min, 0, 0), (hue_max, 255, 255))
    mask_inv = cv2.bitwise_not(mask)

    colored_portion = cv2.bitwise_and(frame, frame, mask=mask)

    video_gray = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV)
    gray_portion = cv2.bitwise_or(video_gray, video_gray, mask=mask_inv)
    # gray_portion = np.stack((gray_portion,)*3, axis=-1)

    combined = colored_portion   gray_portion

    cv2.imshow('video', combined)
    
    key = cv2.waitKey(1)
    if key == 27:
        break

video.release()
cv2.destroyAllWindows()
  • Related