Spaces:
Runtime error
Runtime error
File size: 5,624 Bytes
a57c6eb |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 |
import math
from typing import Union, Tuple
from numpy import ndarray
import numpy as np
def cal_start_end_point(big: float, small: float, center: float = None):
if center is None:
center = big / 2
if center < small / 2:
center = small / 2
if center > (big - small / 2):
center = big - small / 2
start = center - small / 2
end = center + small / 2
return (start, end)
def cal_small_bbox_coord_of_big_bbox(
bigbbox_width,
bigbbox_height,
smallbbox_width,
smallbbox_height,
center_width: float = None,
center_height: float = None,
need_round2even=False,
):
"""只有宽高信息,按中心crop计算小矩形在大矩形的剪辑坐标
Args:
bigbbox_width (float): _description_
bigbbox_height (float): _description_
smallbbox_width (float): _description_
smallbbox_height (float): _description_
Returns:
(float, float, float, float): (x1, y1, x2, y2) 在大矩形中的剪辑位置
"""
x1, x2 = cal_start_end_point(bigbbox_width, smallbbox_width, center=center_width)
y1, y2 = cal_start_end_point(bigbbox_height, smallbbox_height, center=center_height)
# x1 = (bigbbox_width - smallbbox_width) / 2
# y1 = (bigbbox_height - smallbbox_height) / 2
# x2 = (bigbbox_width + smallbbox_width) / 2
# y2 = (bigbbox_height + smallbbox_height) / 2
if need_round2even:
x1, y1, x2, y2 = round_up_coord_to_even(x1, y1, x2, y2)
return (x1, y1, x2, y2)
def round_up_to_even(num):
return math.floor(num / 2.0) * 2
def round_up_coord_to_even(x1, y1, x2, y2):
x2 = x1 + round_up_to_even(x2 - x1)
y2 = y1 + round_up_to_even(y2 - y1)
return (x1, y1, x2, y2)
def cal_crop_coord(
width,
height,
target_width_height_ratio,
restricted_bbox=None,
need_round2even=False,
):
"""
(TODO): 当前只考虑crop,不考虑补全;
(TODO): 当前只考虑视频尺寸比目标尺寸大
Args:
width (float): 原视频的宽
height (float): 原视频的高
target_width (float): 目标视频的宽
target_height (float): 目标视频的高
restricted_bbox ((float, float, float, float), optional): (x1, y1, x2, y2). Defaults to None.
Returns:
(float, float, float, float): (x1, y1, x2, y2) 在原视频中的剪辑位置
"""
if restricted_bbox is None:
target_width, target_height = cal_target_width_height_by_ratio(
width=width,
height=height,
target_width_height_ratio=target_width_height_ratio,
)
crop_bbox = cal_small_bbox_coord_of_big_bbox(
width, height, target_width, target_height
)
else:
r_width = restricted_bbox[2] - restricted_bbox[0]
r_height = restricted_bbox[3] - restricted_bbox[1]
target_width, target_height = cal_target_width_height_by_ratio(
width=r_width,
height=r_height,
target_width_height_ratio=target_width_height_ratio,
)
crop_bbox = cal_small_bbox_coord_of_big_bbox(
r_width, r_height, target_width, target_height
)
crop_bbox = (
crop_bbox[0] + restricted_bbox[0],
crop_bbox[1] + restricted_bbox[1],
crop_bbox[2] + restricted_bbox[0],
crop_bbox[3] + restricted_bbox[1],
)
if need_round2even:
crop_bbox = round_up_coord_to_even(*crop_bbox)
return crop_bbox
def cal_target_width_height_by_ratio(
width, height, target_width_height_ratio, need_round2even=False
):
"""针对原视频的宽、高和目标视频宽高比,计算合适的宽、高
Args:
width (float): 原视频的宽
height (float): 原视频的高
target_width_height_ratio (float): 目标视频宽高比
Returns:
target_width (float)): 目标宽
target_height (float): 目标高
"""
width_height_ratio = width / height
if width_height_ratio >= target_width_height_ratio:
target_width = height * target_width_height_ratio
target_height = height
else:
target_width = width
target_height = width / target_width_height_ratio
if need_round2even:
target_height = round_up_to_even(target_height)
target_width = round_up_to_even(target_width)
return target_width, target_height
def cal_target_width_height(
target_width=None,
target_height=None,
target_width_height_ratio=None,
need_even=True,
):
if target_width and not target_height and target_width_height_ratio:
target_height = int(target_width / target_width_height_ratio)
if need_even:
target_height = round_up_to_even(target_height)
if target_height and not target_width and target_width_height_ratio:
target_width = int(target_height * target_width_height_ratio)
if need_even:
target_width = round_up_to_even(target_width)
if target_height and target_width:
target_width_height_ratio = target_width / target_height
return target_width, target_height, target_width_height_ratio
def find_outlier(grid: ndarray) -> ndarray:
"""find outlier coordinary out of grid
Args:
grid (ndarray): 2xHxW
Returns:
mask: ndarray, HxW, 1 for coordinary in grid, 0 for outlier
"""
c, h, w = grid.shape
mask = np.zeros((h, w))
for i, j in zip(range(h), range(w)):
x = int(grid[0, i, j])
y = int(grid[1, i, j])
if x < h and y < w:
mask[x, y] = 1
return mask
|