如何使用pytesseract在图像特定文本行周围绘制矩形?
实现特定文本行的高亮检测
你的现有代码是给每个识别出的独立文本块加框,无法实现整行高亮的需求。要完成匹配特定文本行并高亮整行的功能,需要先按行聚合文本内容,判断是否包含目标字符串,再计算整行的边界框来绘制矩形。
修改思路
- 按行分组:利用Tesseract返回的
line_num字段,将同一行的所有文本块归为一组 - 拼接行文本:把同一行的零散文本拼接成完整的行内容
- 匹配目标文本:检查行文本是否包含你指定的内容(比如
times, it was the worst) - 绘制整行矩形:匹配成功后,计算该行所有文本块的最大边界,绘制覆盖整行的高亮矩形
修改后的代码
import cv2 as cv from pytesseract import pytesseract, Output # 读取原始图像和灰度图 unchanged_image = cv.imread("i1Abv.png", cv.IMREAD_UNCHANGED) initial_image = cv.imread("i1Abv.png", 0) # 二值化处理(可根据图像实际情况调整阈值) ret, image = cv.threshold(initial_image, 100, 255, cv.THRESH_BINARY) # 调用Tesseract识别,保留行号等详细信息 results = pytesseract.image_to_data(image, output_type=Output.DICT, config="--psm 6") # 按行号分组存储文本内容和边界信息 line_data = {} for i in range(len(results["text"])): conf = float(results["conf"][i]) if conf > 10: # 过滤低置信度的识别结果 line_num = results["line_num"][i] text = results["text"][i].strip() # 初始化该行的数据结构 if line_num not in line_data: line_data[line_num] = { "text": [], "x_min": float('inf'), "y_min": float('inf'), "x_max": 0, "y_max": 0 } # 拼接该行的文本内容 if text: line_data[line_num]["text"].append(text) # 更新该行的边界框范围 x = results["left"][i] y = results["top"][i] w = results["width"][i] h = results["height"][i] line_data[line_num]["x_min"] = min(line_data[line_num]["x_min"], x) line_data[line_num]["y_min"] = min(line_data[line_num]["y_min"], y) line_data[line_num]["x_max"] = max(line_data[line_num]["x_max"], x + w) line_data[line_num]["y_max"] = max(line_data[line_num]["y_max"], y + h) # 你要检测的目标文本 target_text = "times, it was the worst" # 遍历每一行,匹配目标并绘制高亮 for line_num, data in line_data.items(): full_line_text = " ".join(data["text"]) # 检查行文本是否包含目标内容(可加.lower()实现大小写不敏感匹配) if target_text in full_line_text: # 绘制覆盖整行的高亮矩形 cv.rectangle(unchanged_image, (data["x_min"], data["y_min"]), (data["x_max"], data["y_max"]), (0, 255, 0), 2) # 可选:在行首标注匹配提示 cv.putText(unchanged_image, "MATCHED", (data["x_min"], data["y_min"] - 5), cv.FONT_HERSHEY_SIMPLEX, 0.5, (0, 0, 255), 2) # 显示最终结果 cv.imshow("Highlighted Result", unchanged_image) cv.waitKey(0) cv.destroyAllWindows()
关键说明
- 行分组逻辑:通过
line_num字段区分不同行,合并同一行所有文本块的边界坐标,得到整行的最小/最大边界 - 文本匹配:拼接行内所有文本后直接判断目标字符串是否存在,若需要忽略大小写,可改为
if target_text.lower() in full_line_text.lower() - 边界计算:取该行所有文本块的最左、最上、最右、最下坐标,确保矩形能完整覆盖整行内容
内容的提问来源于stack exchange,提问作者Ivan
相关产品推荐
相关产品推荐

