I’m working on a data augmentation and im trying to generate synthetic version of every image in my dataset. So i need to rotate images and together with bounding boxes as well in the images.
im only going to rotate images by 90, 180, 270 degrees.
I’m using pascal-voc annotation format as shown here. As a result i have following info.
x_min, y_min, x_max, y_max. Origin of image(i can get it from image size)
i’ve searched a lot on it. But i couldnt find any solution for rotating bounding boxes( or rectangles)
i’ve tried something like this; i’ve got this solution from here and tried to adapt it but didnt work.
def rotateRect(bndbox, img_size, angle): angle = angle * math.pi/180 # conversion from degree to radian y_min, y_max, x_min, x_max = bndbox ox, oy = img_size[0]/2, img_size[1]/2 # coordinate of origin of image rect = [[x_min, y_min], [x_min, y_max],[x_max, y_min],[x_max, y_max]] # coordinates of points of corners of bounding box rectangle. nrp = [[0, 0], [0,0 ],[0,0],[0, 0]] #new rectangle position for i, pt in enumerate(rect): newPx = int(ox + math.cos(angle) * (pt[0] - ox) - math.sin(angle) * (pt[1] - oy)) # new coordinate of point x newPy = int(oy + math.sin(angle) * (pt[0] - ox) + math.cos(angle) * (pt[1] - oy)) # new coordinate of point y nrp[i] = newPx,newPy nx_min, ny_min, nx_max, ny_max = nrp[0][0], nrp[0][1], nrp[2][0], nrp[2][1] # new bounding boxes values. return [ny_min, ny_max, nx_min, nx_max]
thanks.
EDIT:
I need to get this rotation together with image and bounding box. First picture is original one, second one is rotated as 90 degree(counter-clockwise) and 3rd picture is rotated as -90 degree (counter-wise). i tried to rotate manually on paint to be precise. So i got these results.
original of img size:(640x480) rotation orj, 90, -90 -------------- x_min = 98, 345, 17 y_min = 345, 218, 98 x_max = 420, 462, 420 y_max = 462, 540, 134
Advertisement
Answer
Base on this aproach. We can do this calculation without using trigonometric calculations like this:
def rotate90Deg(bndbox, img_width): # just passing width of image is enough for 90 degree rotation. x_min,y_min,x_max,y_max = bndbox new_xmin = y_min new_ymin = img_width-x_max new_xmax = y_max new_ymax = img_width-x_min return [new_xmin, new_ymin,new_xmax,new_ymax] rotate90Deg([98,345,420,462],640)
this can be used over and over again. And returns new bounding boxes values in Pascal-voc format.