document-similarity-matching-using-visual-layout-features-archive
/
utils
/visualize_bboxes_on_image.py
# This file is used to visualize bounding boxes on an image | |
from urllib.parse import urlparse | |
from PIL import Image, ImageDraw, ImageFont | |
import numpy as np | |
import requests | |
from typing import List | |
from functools import cache | |
def get_font(path_or_url: str = 'https://github.com/googlefonts/roboto/raw/main/src/hinted/Roboto-Regular.ttf', size: int = 10): | |
if urlparse(path_or_url).scheme in ["http", "https"]: # Online | |
return ImageFont.truetype(requests.get(path_or_url, stream=True).raw, size=size) | |
else: # Local | |
return ImageFont.truetype(path_or_url, size=size) | |
def visualize_bboxes_on_image( | |
image: Image.Image, | |
bboxes: List[List[int]], | |
titles: List[str] = None, | |
width = 2, | |
bbox_color="red", | |
label_text_color="black", | |
label_rectangle_color="red", | |
convert_to_x0y0x1y1 = None, | |
label_text_padding = 2, | |
label_rectangle_left_padding=10, | |
label_rectangle_top_padding=10, | |
label_text_size = 10) -> Image.Image: | |
''' | |
Visualize bounding boxes on an image | |
Args: | |
image: Image to visualize | |
bboxes: List of bounding boxes | |
titles: Titles of the bounding boxes | |
width: Width of the bounding box | |
bbox_color: Color of the bounding box | |
label_text_color: Color of the label text | |
label_rectangle_color: Color of the label rectangle | |
convert_to_x0y0x1y1: Function to convert bounding box to x0y0x1y1 format | |
label_text_padding: Padding of the label text | |
label_rectangle_left_padding: Left padding of the label rectangle | |
label_rectangle_top_padding: Top padding of the label rectangle | |
label_text_size: Font size of the label text | |
Returns: | |
Image: Image with bounding boxes''' | |
image = image.copy().convert("RGB") | |
draw = ImageDraw.Draw(image) | |
font = get_font(size = label_text_size) | |
titles = (titles or []) + np.full(len(bboxes) - len(titles or []), None).tolist() | |
for bbox, title in zip(bboxes, titles): | |
x0, y0, x1, y1 = convert_to_x0y0x1y1(bbox) if convert_to_x0y0x1y1 is not None else bbox | |
draw.rectangle([x0, y0, x1, y1], outline=bbox_color, width=width) | |
if title is not None: | |
text_position = (x0 + label_rectangle_left_padding, y0 - label_rectangle_top_padding) | |
text_bbox_left, text_bbox_top, text_bbox_right, text_bbox_bottom = draw.textbbox(text_position, title, font=font) | |
draw.rectangle( | |
( | |
text_bbox_left - label_text_padding, | |
text_bbox_top - label_text_padding, | |
text_bbox_right + label_text_padding, | |
text_bbox_bottom + label_text_padding | |
), | |
fill=label_rectangle_color) | |
draw.text(text_position, title, font=font, fill=label_text_color) | |
return image |