OpenCV区域提取与OCR问题求助:HSV处理致文本断裂
Hey there! Let's work through your OpenCV region extraction problems together. It sounds like you're stuck on two main issues: HSV masking for white regions is breaking your text (making it unrecognizable), and THRESH_BINARY_INV isn't giving you the results you want. Let's break this down with practical fixes and code examples.
Fixing HSV-Based White Region Extraction
First, white has a tricky range in HSV space—since it's low saturation and high value, a lot of folks mess up the lower/upper bounds, which leads to broken text. Here's the correct range to target white, plus a quick fix for those text gaps using morphological operations:
import cv2 import numpy as np def tracking(): frame = cv2.imread('test4.png') hsv = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV) # Correct HSV range for white (low saturation, high brightness) lower_white = np.array([0, 0, 200]) upper_white = np.array([180, 30, 255]) # Create the initial mask mask = cv2.inRange(hsv, lower_white, upper_white) # Use a closing operation to fix broken text (fills small gaps) # Adjust the kernel size if your text is thicker/thinner kernel = np.ones((2, 2), np.uint8) mask = cv2.morphologyEx(mask, cv2.MORPH_CLOSE, kernel) # Extract the white region result = cv2.bitwise_and(frame, frame, mask=mask) # Preview results cv2.imshow('Original', frame) cv2.imshow('White Mask', mask) cv2.imshow('Extracted White Region', result) cv2.waitKey(0) cv2.destroyAllWindows() tracking()
The closing operation (dilation followed by erosion) is key here—it fills in tiny gaps in your text that the initial HSV mask might have missed. If your text is still broken, try increasing the kernel size to (3,3) or (4,4).
Fixing THRESH_BINARY_INV Issues
If you're using THRESH_BINARY_INV and it's not working, the problem is likely either incorrect grayscale conversion, a bad fixed threshold, or uneven lighting. Adaptive thresholding is usually better for text extraction because it accounts for lighting variations:
import cv2 import numpy as np def extract_text_with_threshold(): frame = cv2.imread('test4.png') gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY) # Use adaptive thresholding instead of fixed (great for uneven lighting) thresh_inv = cv2.adaptiveThreshold( gray, 255, cv2.ADAPTIVE_THRESH_GAUSSIAN_C, cv2.THRESH_BINARY_INV, 11, 2 ) # Again, use closing to fix text gaps kernel = np.ones((2, 2), np.uint8) thresh_inv = cv2.morphologyEx(thresh_inv, cv2.MORPH_CLOSE, kernel) # Extract the text region result = cv2.bitwise_and(frame, frame, mask=thresh_inv) # Preview results cv2.imshow('Grayscale', gray) cv2.imshow('Inverted Threshold', thresh_inv) cv2.imshow('Extracted Text', result) cv2.waitKey(0) cv2.destroyAllWindows() extract_text_with_threshold()
Adaptive thresholding calculates a unique threshold for small patches of the image, which helps if your image has shadows or uneven lighting. If you still prefer fixed thresholding, tweak the threshold value (the 200 in cv2.threshold) based on your image—lower it if some white text is being cut off, raise it if too much noise is included.
Quick Extra Tips
- Reduce noise first: If your image has a lot of speckles, run a Gaussian blur before processing:
blur = cv2.GaussianBlur(frame, (3,3), 0) - Tweak HSV values interactively: Write a small script with trackbars to adjust H, S, V bounds in real-time—this makes it way easier to find the perfect range for your specific image.
- For OCR: If you're extracting text to run OCR (like Tesseract), make sure the final mask has solid, unbroken text—this will drastically improve recognition accuracy.
内容的提问来源于stack exchange,提问作者엄기환

