Skip to content
GitLab
Menu
Projects
Groups
Snippets
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
Menu
Open sidebar
OpenDAS
mmdetection3d
Commits
b2c43ffd
Commit
b2c43ffd
authored
Jun 20, 2020
by
zhangwenwei
Browse files
Merge branch 'add_docstring' into 'master'
Add docstrings See merge request open-mmlab/mmdet.3d!72
parents
613c8844
8f88914d
Changes
31
Hide whitespace changes
Inline
Side-by-side
Showing
20 changed files
with
310 additions
and
260 deletions
+310
-260
data/scannet/load_scannet_data.py
data/scannet/load_scannet_data.py
+10
-10
data/sunrgbd/sunrgbd_utils.py
data/sunrgbd/sunrgbd_utils.py
+19
-19
mmdet3d/core/anchor/anchor_3d_generator.py
mmdet3d/core/anchor/anchor_3d_generator.py
+1
-1
mmdet3d/core/bbox/box_np_ops.py
mmdet3d/core/bbox/box_np_ops.py
+64
-51
mmdet3d/core/bbox/box_torch_ops.py
mmdet3d/core/bbox/box_torch_ops.py
+28
-23
mmdet3d/core/bbox/coders/delta_xyzwhlr_bbox_coder.py
mmdet3d/core/bbox/coders/delta_xyzwhlr_bbox_coder.py
+31
-18
mmdet3d/core/bbox/coders/partial_bin_based_bbox_coder.py
mmdet3d/core/bbox/coders/partial_bin_based_bbox_coder.py
+10
-11
mmdet3d/core/bbox/iou_calculators/iou3d_calculator.py
mmdet3d/core/bbox/iou_calculators/iou3d_calculator.py
+11
-9
mmdet3d/core/bbox/samplers/iou_neg_piecewise_sampler.py
mmdet3d/core/bbox/samplers/iou_neg_piecewise_sampler.py
+1
-1
mmdet3d/core/bbox/structures/base_box3d.py
mmdet3d/core/bbox/structures/base_box3d.py
+17
-17
mmdet3d/core/bbox/structures/box_3d_mode.py
mmdet3d/core/bbox/structures/box_3d_mode.py
+6
-6
mmdet3d/core/bbox/structures/cam_box3d.py
mmdet3d/core/bbox/structures/cam_box3d.py
+19
-19
mmdet3d/core/bbox/structures/depth_box3d.py
mmdet3d/core/bbox/structures/depth_box3d.py
+14
-14
mmdet3d/core/bbox/structures/lidar_box3d.py
mmdet3d/core/bbox/structures/lidar_box3d.py
+6
-6
mmdet3d/core/bbox/structures/utils.py
mmdet3d/core/bbox/structures/utils.py
+1
-1
mmdet3d/core/bbox/transforms.py
mmdet3d/core/bbox/transforms.py
+39
-23
mmdet3d/core/evaluation/indoor_eval.py
mmdet3d/core/evaluation/indoor_eval.py
+9
-10
mmdet3d/core/evaluation/kitti_utils/eval.py
mmdet3d/core/evaluation/kitti_utils/eval.py
+16
-13
mmdet3d/core/evaluation/kitti_utils/rotate_iou.py
mmdet3d/core/evaluation/kitti_utils/rotate_iou.py
+4
-4
mmdet3d/core/post_processing/box3d_nms.py
mmdet3d/core/post_processing/box3d_nms.py
+4
-4
No files found.
data/scannet/load_scannet_data.py
View file @
b2c43ffd
...
...
@@ -64,19 +64,19 @@ def export(mesh_file,
"""Export original files to vert, ins_label, sem_label and bbox file.
Args:
mesh_file(str): Path of the mesh_file.
agg_file(str): Path of the agg_file.
seg_file(str): Path of the seg_file.
meta_file(str): Path of the meta_file.
label_map_file(str): Path of the label_map_file.
output_file(str): Path of the output folder.
mesh_file
(str): Path of the mesh_file.
agg_file
(str): Path of the agg_file.
seg_file
(str): Path of the seg_file.
meta_file
(str): Path of the meta_file.
label_map_file
(str): Path of the label_map_file.
output_file
(str): Path of the output folder.
Default: None.
It returns a tuple, which containts the the following things:
ndarray: Vertices of points data.
ndarray: Indexes of label.
ndarray: Indexes of instance.
ndarray: Instance bboxes.
np.
ndarray: Vertices of points data.
np.
ndarray: Indexes of label.
np.
ndarray: Indexes of instance.
np.
ndarray: Instance bboxes.
dict: Map from object_id to label_id.
"""
...
...
data/sunrgbd/sunrgbd_utils.py
View file @
b2c43ffd
...
...
@@ -39,10 +39,10 @@ def flip_axis_to_camera(pc):
Flip X-right,Y-forward,Z-up to X-right,Y-down,Z-forward.
Args:
pc
(
ndarray): points in depth axis.
pc
(np.
ndarray): points in depth axis.
Returns:
ndarray: points in camera axis.
np.
ndarray: points in camera axis.
"""
pc2
=
np
.
copy
(
pc
)
pc2
[:,
[
0
,
1
,
2
]]
=
pc2
[:,
[
0
,
2
,
1
]]
# cam X,Y,Z = depth X,-Z,Y
...
...
@@ -132,10 +132,10 @@ class SUNRGBD_Calibration(object):
"""Convert pc coordinate from depth to image.
Args:
pc
(
ndarray): Point cloud in depth coordinate.
pc
(np.
ndarray): Point cloud in depth coordinate.
Returns:
pc
(
ndarray): Point cloud in camera coordinate.
pc
(np.
ndarray): Point cloud in camera coordinate.
"""
# Project upright depth to depth coordinate
pc2
=
np
.
dot
(
np
.
transpose
(
self
.
Rtilt
),
np
.
transpose
(
pc
[:,
...
...
@@ -146,11 +146,11 @@ class SUNRGBD_Calibration(object):
"""Convert pc coordinate from depth to image.
Args:
pc
(
ndarray): Point cloud in depth coordinate.
pc
(np.
ndarray): Point cloud in depth coordinate.
Returns:
ndarray: [N, 2] uv.
ndarray: [n,] depth.
np.
ndarray: [N, 2] uv.
np.
ndarray: [n,] depth.
"""
pc2
=
self
.
project_upright_depth_to_camera
(
pc
)
uv
=
np
.
dot
(
pc2
,
np
.
transpose
(
self
.
K
))
# (n,3)
...
...
@@ -173,10 +173,10 @@ def rotz(t):
"""Rotation about the z-axis.
Args:
t(float): Heading angle.
t
(float): Heading angle.
Returns:
ndarray: Transforation matrix
np.
ndarray: Transforation matrix
"""
c
=
np
.
cos
(
t
)
s
=
np
.
sin
(
t
)
...
...
@@ -187,11 +187,11 @@ def transform_from_rot_trans(R, t):
"""Transforation matrix from rotation matrix and translation vector.
Args:
R
(
ndarray): Rotation matrix.
t
(
ndarray): Translation vector.
R
(np.
ndarray): Rotation matrix.
t
(np.
ndarray): Translation vector.
Returns:
ndarray: Transforation matrix.
np.
ndarray: Transforation matrix.
"""
R
=
R
.
reshape
(
3
,
3
)
t
=
t
.
reshape
(
3
,
1
)
...
...
@@ -229,12 +229,12 @@ def extract_pc_in_box3d(pc, box3d):
"""Extract point cloud in box3d.
Args:
pc
(
ndarray): [N, 3] Point cloud.
box3d
(
ndarray): [8,3] 3d box.
pc
(np.
ndarray): [N, 3] Point cloud.
box3d
(np.
ndarray): [8,3] 3d box.
Returns:
ndarray: Selected point cloud.
ndarray: Indices of selected point cloud.
np.
ndarray: Selected point cloud.
np.
ndarray: Indices of selected point cloud.
"""
box3d_roi_inds
=
in_hull
(
pc
[:,
0
:
3
],
box3d
)
return
pc
[
box3d_roi_inds
,
:],
box3d_roi_inds
...
...
@@ -258,11 +258,11 @@ def compute_box_3d(obj, calib):
bounding box into the image plane.
Args:
obj(SUNObject3d): Instance of SUNObject3d.
calib(SUNRGBD_Calibration): Instance of SUNRGBD_Calibration.
obj
(SUNObject3d): Instance of SUNObject3d.
calib
(SUNRGBD_Calibration): Instance of SUNRGBD_Calibration.
Returns:
ndarray: [8,2] array in image coord.
np.
ndarray: [8,2] array in image coord.
corners_3d: [8,3] array in in upright depth coord.
"""
center
=
obj
.
centroid
...
...
mmdet3d/core/anchor/anchor_3d_generator.py
View file @
b2c43ffd
...
...
@@ -85,7 +85,7 @@ class Anchor3DRangeGenerator(object):
multiple feature levels.
device (str): Device where the anchors will be put on.
Return:
Return
s
:
list[torch.Tensor]: Anchors in multiple feature levels.
The sizes of each tensor should be [N, 4], where
N = width * height * num_base_anchors, width and height
...
...
mmdet3d/core/bbox/box_np_ops.py
View file @
b2c43ffd
...
...
@@ -19,18 +19,18 @@ def box_camera_to_lidar(data, r_rect, velo2cam):
def
corners_nd
(
dims
,
origin
=
0.5
):
"""
g
enerate relative box corners based on length per dim and
"""
G
enerate relative box corners based on length per dim and
origin point.
Args:
dims (
float
array, shape=[N, ndim]):
a
rray of length per dim
dims (
np.nd
array, shape=[N, ndim]):
A
rray of length per dim
origin (list or array or float): origin point relate to smallest point.
Returns:
float
array, shape=[N, 2 ** ndim, ndim]:
r
eturned corners.
np.nd
array, shape=[N, 2 ** ndim, ndim]:
R
eturned corners.
point layout example: (2d) x0y0, x0y1, x1y0, x1y1;
(3d) x0y0z0, x0y0z1, x0y1z0, x0y1z1, x1y0z0, x1y0z1, x1y1z0, x1y1z1
where x0 < x1, y0 < y1, z0 < z1
where x0 < x1, y0 < y1, z0 < z1
.
"""
ndim
=
int
(
dims
.
shape
[
1
])
corners_norm
=
np
.
stack
(
...
...
@@ -53,14 +53,14 @@ def corners_nd(dims, origin=0.5):
def
rotation_2d
(
points
,
angles
):
"""
r
otation 2d points based on origin point clockwise when angle positive.
"""
R
otation 2d points based on origin point clockwise when angle positive.
Args:
points (
float
array, shape=[N, point_size, 2]): points to be rotated.
angles (
float
array, shape=[N]): rotation angle.
points (
np.nd
array, shape=[N, point_size, 2]): points to be rotated.
angles (
np.nd
array, shape=[N]): rotation angle.
Returns:
float
array:
s
ame shape as points
np.nd
array:
S
ame shape as points
.
"""
rot_sin
=
np
.
sin
(
angles
)
rot_cos
=
np
.
cos
(
angles
)
...
...
@@ -69,16 +69,16 @@ def rotation_2d(points, angles):
def
center_to_corner_box2d
(
centers
,
dims
,
angles
=
None
,
origin
=
0.5
):
"""
c
onvert kitti locations, dimensions and angles to corners.
"""
C
onvert kitti locations, dimensions and angles to corners.
format: center(xy), dims(xy), angles(clockwise when positive)
Args:
centers (
float
array, shape=[N, 2]): locations in kitti label file.
dims (
float
array, shape=[N, 2]): dimensions in kitti label file.
angles (
float
array, shape=[N]): rotation_y in kitti label file.
centers (
np.nd
array, shape=[N, 2]): locations in kitti label file.
dims (
np.nd
array, shape=[N, 2]): dimensions in kitti label file.
angles (
np.nd
array, shape=[N]): rotation_y in kitti label file.
Returns:
[type]: [description]
np.ndarray: Corners with the shape of [N, 4, 2].
"""
# 'length' in kitti format is in x axis.
# xyz(hwl)(kitti label file)<->xyz(lhw)(camera)<->z(-x)(-y)(wlh)(lidar)
...
...
@@ -141,17 +141,18 @@ def center_to_corner_box3d(centers,
angles
=
None
,
origin
=
(
0.5
,
1.0
,
0.5
),
axis
=
1
):
"""
c
onvert kitti locations, dimensions and angles to corners
"""
C
onvert kitti locations, dimensions and angles to corners
.
Args:
centers (
float
array, shape=[N, 3]):
l
ocations in kitti label file.
dims (
float
array, shape=[N, 3]):
d
imensions in kitti label file.
angles (
float
array, shape=[N]):
r
otation_y in kitti label file.
origin (list or array or float):
o
rigin point relate to smallest point.
centers (
np.nd
array, shape=[N, 3]):
L
ocations in kitti label file.
dims (
np.nd
array, shape=[N, 3]):
D
imensions in kitti label file.
angles (
np.nd
array, shape=[N]):
R
otation_y in kitti label file.
origin (list or array or float):
O
rigin point relate to smallest point.
use (0.5, 1.0, 0.5) in camera and (0.5, 0.5, 0) in lidar.
axis (int): rotation axis. 1 for camera and 2 for lidar.
axis (int): Rotation axis. 1 for camera and 2 for lidar.
Returns:
[type]: [description]
np.ndarray: Corners with the shape of [N, 8, 3].
"""
# 'length' in kitti format is in x axis.
# yzx(hwl)(kitti label file)<->xyz(lhw)(camera)<->z(-x)(-y)(wlh)(lidar)
...
...
@@ -202,13 +203,15 @@ def corner_to_standup_nd_jit(boxes_corner):
@
numba
.
jit
(
nopython
=
True
)
def
corner_to_surfaces_3d_jit
(
corners
):
"""
c
onvert 3d box corners from corner function above
"""
C
onvert 3d box corners from corner function above
to surfaces that normal vectors all direct to internal.
Args:
corners (float array, [N, 8, 3]): 3d box corners.
corners (np.ndarray, [N, 8, 3]): 3d box corners
with the shape of [N, 8, 3].
Returns:
surfaces (float array,
[N, 6, 4, 3]
):
np.ndarray: Surfaces with the shape of
[N, 6, 4, 3]
.
"""
# box_corners: [N, 8, 3], must from corner functions in this module
num_boxes
=
corners
.
shape
[
0
]
...
...
@@ -270,9 +273,10 @@ def corner_to_surfaces_3d(corners):
to surfaces that normal vectors all direct to internal.
Args:
corners (float array, [N, 8, 3]): 3d box corners.
corners (np.ndarray, [N, 8, 3]): 3d box corners.
Returns:
surfaces (float array,
[N, 6, 4, 3]
):
np.ndarray: Surfaces with the shape of
[N, 6, 4, 3]
.
"""
# box_corners: [N, 8, 3], must from corner functions in this module
surfaces
=
np
.
array
([
...
...
@@ -318,7 +322,7 @@ def create_anchors_3d_range(feature_size,
sizes: [N, 3] list of list or array, size of anchors, xyz
Returns:
anchors
: [*feature_size, num_sizes, num_rots, 7]
tensor
.
np.ndarray
: [*feature_size, num_sizes, num_rots, 7].
"""
anchor_range
=
np
.
array
(
anchor_range
,
dtype
)
z_centers
=
np
.
linspace
(
...
...
@@ -358,10 +362,13 @@ def center_to_minmax_2d(centers, dims, origin=0.5):
def
rbbox2d_to_near_bbox
(
rbboxes
):
"""convert rotated bbox to nearest 'standing' or 'lying' bbox.
Args:
rbboxes: [N, 5(x, y, xdim, ydim, rad)] rotated bboxes
rbboxes (np.ndarray): [N, 5(x, y, xdim, ydim, rad)] rotated bboxes.
Returns:
bboxes: [N, 4(xmin, ymin, xmax, ymax)] bboxes
np.ndarray: Bboxes with the shpae of
[N, 4(xmin, ymin, xmax, ymax)].
"""
rots
=
rbboxes
[...,
-
1
]
rots_0_pi_div_2
=
np
.
abs
(
limit_period
(
rots
,
0.5
,
np
.
pi
))
...
...
@@ -373,15 +380,16 @@ def rbbox2d_to_near_bbox(rbboxes):
@
numba
.
jit
(
nopython
=
True
)
def
iou_jit
(
boxes
,
query_boxes
,
mode
=
'iou'
,
eps
=
0.0
):
"""calculate box iou. note that jit version runs ~10x faster than the
box_overlaps function in mmdet3d.core.evaluation
Parameters
----------
boxes: (N, 4) ndarray of float
query_boxes: (K, 4) ndarray of float
Returns
-------
overlaps: (N, K) ndarray of overlap between boxes and query_boxes
"""Calculate box iou. note that jit version runs ~10x faster than the
box_overlaps function in mmdet3d.core.evaluation.
Args:
boxes (np.ndarray): (N, 4) ndarray of float
query_boxes (np.ndarray): (K, 4) ndarray of float
Returns:
np.ndarray: Overlap between boxes and query_boxes
with the shape of [N, K].
"""
N
=
boxes
.
shape
[
0
]
K
=
query_boxes
.
shape
[
0
]
...
...
@@ -502,17 +510,19 @@ def _points_in_convex_polygon_3d_jit(points, polygon_surfaces, normal_vec, d,
def
points_in_convex_polygon_3d_jit
(
points
,
polygon_surfaces
,
num_surfaces
=
None
):
"""check points is in 3d convex polygons.
"""Check points is in 3d convex polygons.
Args:
points: [num_points, 3] array.
polygon_surfaces: [num_polygon, max_num_surfaces,
points
(np.ndarray)
: [num_points, 3] array.
polygon_surfaces
(np.ndarray)
: [num_polygon, max_num_surfaces,
max_num_points_of_surface, 3]
array. all surfaces' normal vector must direct to internal.
max_num_points_of_surface must at least 3.
num_surfaces: [num_polygon] array. indicate how many surfaces
a polygon contain
num_surfaces (np.ndarray): [num_polygon] array.
indicate how many surfaces a polygon contain
Returns:
[num_points, num_polygon]
bool array
.
np.ndarray: Result matrix with the shape of
[num_points, num_polygon].
"""
max_num_surfaces
,
max_num_points_of_surface
=
polygon_surfaces
.
shape
[
1
:
3
]
# num_points = points.shape[0]
...
...
@@ -528,13 +538,16 @@ def points_in_convex_polygon_3d_jit(points,
@
numba
.
jit
def
points_in_convex_polygon_jit
(
points
,
polygon
,
clockwise
=
True
):
"""check points is in 2d convex polygons. True when point in polygon
"""Check points is in 2d convex polygons. True when point in polygon.
Args:
points: [num_points, 2] array.
polygon: [num_polygon, num_points_of_polygon, 2] array.
clockwise: bool. indicate polygon is clockwise.
points (np.ndarray): Input points with the shape of [num_points, 2].
polygon (dnarray): Input polygon with the shape of
[num_polygon, num_points_of_polygon, 2].
clockwise (bool): Indicate polygon is clockwise.
Returns:
[num_points, num_polygon]
bool array
.
np.ndarray: Result matrix with the shape of
[num_points, num_polygon].
"""
# first convert polygon to directed lines
num_points_of_polygon
=
polygon
.
shape
[
1
]
...
...
@@ -569,7 +582,7 @@ def points_in_convex_polygon_jit(points, polygon, clockwise=True):
def
boxes3d_to_corners3d_lidar
(
boxes3d
,
bottom_center
=
True
):
"""
c
onvert kitti center boxes to corners
"""
C
onvert kitti center boxes to corners
.
7 -------- 4
/| /|
...
...
@@ -580,12 +593,12 @@ def boxes3d_to_corners3d_lidar(boxes3d, bottom_center=True):
2 -------- 1
Args:
boxes3d (n
umpy.
array): (N, 7) [x, y, z, w, l, h, ry] in LiDAR coords,
boxes3d (n
p.nd
array): (N, 7) [x, y, z, w, l, h, ry] in LiDAR coords,
see the definition of ry in KITTI dataset
bottom_center (bool): whether z is on the bottom center of object.
Returns:
n
umpy.
array:
b
ox corners with shape
(
N, 8, 3
)
n
p.nd
array:
B
ox corners with
the
shape
of [
N, 8, 3
].
"""
boxes_num
=
boxes3d
.
shape
[
0
]
w
,
l
,
h
=
boxes3d
[:,
3
],
boxes3d
[:,
4
],
boxes3d
[:,
5
]
...
...
mmdet3d/core/bbox/box_torch_ops.py
View file @
b2c43ffd
...
...
@@ -7,15 +7,15 @@ def limit_period(val, offset=0.5, period=np.pi):
def
corners_nd
(
dims
,
origin
=
0.5
):
"""
g
enerate relative box corners based on length per dim and
"""
G
enerate relative box corners based on length per dim and
origin point.
Args:
dims (
float
array, shape=[N, ndim]):
a
rray of length per dim
origin (list or array or float):
o
rigin point relate to smallest point.
dims (
np.nd
array, shape=[N, ndim]):
A
rray of length per dim
origin (list or array or float):
O
rigin point relate to smallest point.
Returns:
float array,
shape
=
[N, 2 ** ndim, ndim]
: returned corners
.
np.ndarray: Corners of boxes in
shape
[N, 2 ** ndim, ndim].
point layout example: (2d) x0y0, x0y1, x1y0, x1y1;
(3d) x0y0z0, x0y0z1, x0y1z0, x0y1z1, x1y0z0, x1y0z1, x1y1z0, x1y1z1
where x0 < x1, y0 < y1, z0 < z1
...
...
@@ -76,17 +76,21 @@ def center_to_corner_box3d(centers,
angles
,
origin
=
(
0.5
,
1.0
,
0.5
),
axis
=
1
):
"""
c
onvert kitti locations, dimensions and angles to corners
"""
C
onvert kitti locations, dimensions and angles to corners
.
Args:
centers (float array, shape=[N, 3]): locations in kitti label file.
dims (float array, shape=[N, 3]): dimensions in kitti label file.
angles (float array, shape=[N]): rotation_y in kitti label file.
origin (list or array or float): origin point relate to smallest point.
centers (np.ndarray): Locations in kitti label file
with the shape of [N, 3].
dims (np.ndarray): Dimensions in kitti label
file with the shape of [N, 3]
angles (np.ndarray): Rotation_y in kitti
label file with the shape of [N]
origin (list or array or float): Origin point relate to smallest point.
use (0.5, 1.0, 0.5) in camera and (0.5, 0.5, 0) in lidar.
axis (int): rotation axis. 1 for camera and 2 for lidar.
axis (int): Rotation axis. 1 for camera and 2 for lidar.
Returns:
[type]: [description]
torch.Tensor: Corners with the shape of [N, 8, 3].
"""
# 'length' in kitti format is in x axis.
# yzx(hwl)(kitti label file)<->xyz(lhw)(camera)<->z(-x)(-y)(wlh)(lidar)
...
...
@@ -130,9 +134,10 @@ def rbbox2d_to_near_bbox(rbboxes):
"""convert rotated bbox to nearest 'standing' or 'lying' bbox.
Args:
rbboxes: [N, 5(x, y, xdim, ydim, rad)] rotated bboxes
rbboxes (torch.Tensor): [N, 5(x, y, xdim, ydim, rad)] rotated bboxes.
Returns:
bboxes:
[N, 4(xmin, ymin, xmax, ymax)]
bboxes
torch.Tensor: Bboxes with the shape of
[N, 4(xmin, ymin, xmax, ymax)]
.
"""
rots
=
rbboxes
[...,
-
1
]
rots_0_pi_div_2
=
torch
.
abs
(
limit_period
(
rots
,
0.5
,
np
.
pi
))
...
...
@@ -154,16 +159,16 @@ def center_to_minmax_2d(centers, dims, origin=0.5):
def
center_to_corner_box2d
(
centers
,
dims
,
angles
=
None
,
origin
=
0.5
):
"""
c
onvert kitti locations, dimensions and angles to corners.
format: center(xy), dims(xy), angles(clockwise when positive)
"""
C
onvert kitti locations, dimensions and angles to corners.
format: center(xy), dims(xy), angles(clockwise when positive)
Args:
centers (
float
array, shape=[N, 2]): locations in kitti label file.
dims (
float
array, shape=[N, 2]): dimensions in kitti label file.
angles (
float
array, shape=[N]): rotation_y in kitti label file.
centers (
np.nd
array, shape=[N, 2]): locations in kitti label file.
dims (
np.nd
array, shape=[N, 2]): dimensions in kitti label file.
angles (
np.nd
array, shape=[N]): rotation_y in kitti label file.
Returns:
[type]: [description]
torch.Tensor: Corners with the shape of [N, 4, 2].
"""
# 'length' in kitti format is in x axis.
# xyz(hwl)(kitti label file)<->xyz(lhw)(camera)<->z(-x)(-y)(wlh)(lidar)
...
...
@@ -180,11 +185,11 @@ def rotation_2d(points, angles):
"""rotation 2d points based on origin point clockwise when angle positive.
Args:
points (
float
array, shape=[N, point_size, 2]): points to be rotated.
angles (
float
array, shape=[N]): rotation angle.
points (
np.nd
array, shape=[N, point_size, 2]): points to be rotated.
angles (
np.nd
array, shape=[N]): rotation angle.
Returns:
float
array:
s
ame shape as points
np.nd
array:
S
ame shape as points
.
"""
rot_sin
=
torch
.
sin
(
angles
)
rot_cos
=
torch
.
cos
(
angles
)
...
...
@@ -213,7 +218,7 @@ def enlarge_box3d_lidar(boxes3d, extra_width):
def
boxes3d_to_corners3d_lidar_torch
(
boxes3d
,
bottom_center
=
True
):
"""
c
onvert kitti center boxes to corners
"""
C
onvert kitti center boxes to corners
.
7 -------- 4
/| /|
...
...
mmdet3d/core/bbox/coders/delta_xyzwhlr_bbox_coder.py
View file @
b2c43ffd
...
...
@@ -12,21 +12,30 @@ class DeltaXYZWLHRBBoxCoder(BaseBBoxCoder):
self
.
code_size
=
code_size
@
staticmethod
def
encode
(
anchors
,
boxes
):
"""
:param boxes: (N, 7+n) x, y, z, w, l, h, r, velo*
:param anchors: (N, 7+n)
:return:
def
encode
(
src_boxes
,
dst_boxes
):
"""Get box regression transformation deltas
(dx, dy, dz, dw, dh, dl, dr, dv*) that can be used
to transform the `src_boxes` into the `target_boxes`.
Args:
src_boxes (torch.Tensor): source boxes, e.g., object proposals.
dst_boxes (torch.Tensor): target of the transformation, e.g.,
ground-truth boxes.
Returns:
torch.Tensor: Box transformation deltas
"""
box_ndim
=
anchor
s
.
shape
[
-
1
]
box_ndim
=
src_boxe
s
.
shape
[
-
1
]
cas
,
cgs
,
cts
=
[],
[],
[]
if
box_ndim
>
7
:
xa
,
ya
,
za
,
wa
,
la
,
ha
,
ra
,
*
cas
=
torch
.
split
(
anchors
,
1
,
dim
=-
1
)
xg
,
yg
,
zg
,
wg
,
lg
,
hg
,
rg
,
*
cgs
=
torch
.
split
(
boxes
,
1
,
dim
=-
1
)
xa
,
ya
,
za
,
wa
,
la
,
ha
,
ra
,
*
cas
=
torch
.
split
(
src_boxes
,
1
,
dim
=-
1
)
xg
,
yg
,
zg
,
wg
,
lg
,
hg
,
rg
,
*
cgs
=
torch
.
split
(
dst_boxes
,
1
,
dim
=-
1
)
cts
=
[
g
-
a
for
g
,
a
in
zip
(
cgs
,
cas
)]
else
:
xa
,
ya
,
za
,
wa
,
la
,
ha
,
ra
=
torch
.
split
(
anchor
s
,
1
,
dim
=-
1
)
xg
,
yg
,
zg
,
wg
,
lg
,
hg
,
rg
=
torch
.
split
(
boxes
,
1
,
dim
=-
1
)
xa
,
ya
,
za
,
wa
,
la
,
ha
,
ra
=
torch
.
split
(
src_boxe
s
,
1
,
dim
=-
1
)
xg
,
yg
,
zg
,
wg
,
lg
,
hg
,
rg
=
torch
.
split
(
dst_
boxes
,
1
,
dim
=-
1
)
za
=
za
+
ha
/
2
zg
=
zg
+
hg
/
2
diagonal
=
torch
.
sqrt
(
la
**
2
+
wa
**
2
)
...
...
@@ -40,21 +49,25 @@ class DeltaXYZWLHRBBoxCoder(BaseBBoxCoder):
return
torch
.
cat
([
xt
,
yt
,
zt
,
wt
,
lt
,
ht
,
rt
,
*
cts
],
dim
=-
1
)
@
staticmethod
def
decode
(
anchors
,
box_encodings
):
"""
:param box_encodings: (N, 7 + n) x, y, z, w, l, h, r
:param anchors: (N, 7)
:return:
def
decode
(
anchors
,
deltas
):
"""Apply transformation `deltas` (dx, dy, dz, dw, dh, dl, dr, dv*) to `boxes`.
Args:
anchors (torch.Tensor): Parameters of anchors with shape (N, 7).
deltas (torch.Tensor): Encoded boxes with shape
(N, 7+n) [x, y, z, w, l, h, r, velo*].
Returns:
torch.Tensor: Decoded boxes.
"""
cas
,
cts
=
[],
[]
box_ndim
=
anchors
.
shape
[
-
1
]
if
box_ndim
>
7
:
xa
,
ya
,
za
,
wa
,
la
,
ha
,
ra
,
*
cas
=
torch
.
split
(
anchors
,
1
,
dim
=-
1
)
xt
,
yt
,
zt
,
wt
,
lt
,
ht
,
rt
,
*
cts
=
torch
.
split
(
box_encodings
,
1
,
dim
=-
1
)
xt
,
yt
,
zt
,
wt
,
lt
,
ht
,
rt
,
*
cts
=
torch
.
split
(
deltas
,
1
,
dim
=-
1
)
else
:
xa
,
ya
,
za
,
wa
,
la
,
ha
,
ra
=
torch
.
split
(
anchors
,
1
,
dim
=-
1
)
xt
,
yt
,
zt
,
wt
,
lt
,
ht
,
rt
=
torch
.
split
(
box_encoding
s
,
1
,
dim
=-
1
)
xt
,
yt
,
zt
,
wt
,
lt
,
ht
,
rt
=
torch
.
split
(
delta
s
,
1
,
dim
=-
1
)
za
=
za
+
ha
/
2
diagonal
=
torch
.
sqrt
(
la
**
2
+
wa
**
2
)
...
...
mmdet3d/core/bbox/coders/partial_bin_based_bbox_coder.py
View file @
b2c43ffd
...
...
@@ -28,9 +28,8 @@ class PartialBinBasedBBoxCoder(BaseBBoxCoder):
"""Encode ground truth to prediction targets.
Args:
gt_bboxes_3d (:obj:BaseInstance3DBoxes): gt bboxes with
shape (n, 7).
gt_labels_3d (Tensor): gt classes.
gt_bboxes_3d (BaseInstance3DBoxes): gt bboxes with shape (n, 7).
gt_labels_3d (torch.Tensor): gt classes.
Returns:
tuple: Targets of center, size and direction.
...
...
@@ -67,7 +66,7 @@ class PartialBinBasedBBoxCoder(BaseBBoxCoder):
- size_res: predicted bbox size residual.
Returns:
Tensor: decoded bbox3d with shape (batch, n, 7)
torch.
Tensor: decoded bbox3d with shape (batch, n, 7)
"""
center
=
bbox_out
[
'center'
]
batch_size
,
num_proposal
=
center
.
shape
[:
2
]
...
...
@@ -99,8 +98,8 @@ class PartialBinBasedBBoxCoder(BaseBBoxCoder):
"""Split predicted features to specific parts.
Args:
preds (Tensor): predicted features to split.
base_xyz (Tensor): coordinates of points.
preds (
torch.
Tensor): predicted features to split.
base_xyz (
torch.
Tensor): coordinates of points.
Returns:
dict: split results.
...
...
@@ -161,8 +160,8 @@ class PartialBinBasedBBoxCoder(BaseBBoxCoder):
regression number from class center angle to current angle.
Args:
angle (Tensor): Angle is from 0-2pi (or -pi~pi),
class center at
0, 1*(2pi/N), 2*(2pi/N) ... (N-1)*(2pi/N)
angle (
torch.
Tensor): Angle is from 0-2pi (or -pi~pi),
class center at
0, 1*(2pi/N), 2*(2pi/N) ... (N-1)*(2pi/N)
.
Returns:
tuple: Encoded discrete class and residual.
...
...
@@ -179,12 +178,12 @@ class PartialBinBasedBBoxCoder(BaseBBoxCoder):
"""Inverse function to angle2class
Args:
angle_cls (Tensor): Angle class to decode.
angle_res (Tensor): Angle residual to decode.
angle_cls (
torch.
Tensor): Angle class to decode.
angle_res (
torch.
Tensor): Angle residual to decode.
limit_period (bool): Whether to limit angle to [-pi, pi].
Returns:
Tensor: angle decoded from angle_cls and angle_res.
torch.
Tensor: angle decoded from angle_cls and angle_res.
"""
angle_per_class
=
2
*
np
.
pi
/
float
(
self
.
num_dir_bins
)
angle_center
=
angle_cls
.
float
()
*
angle_per_class
...
...
mmdet3d/core/bbox/iou_calculators/iou3d_calculator.py
View file @
b2c43ffd
...
...
@@ -46,13 +46,14 @@ def bbox_overlaps_nearest_3d(bboxes1, bboxes2, mode='iou', is_aligned=False):
"""Calculate nearest 3D IoU
Args:
bboxes1
:
Tensor
,
shape (N, 7+N) [x, y, z, h, w, l, ry, v]
bboxes2
:
Tensor
,
shape (M, 7+N) [x, y, z, h, w, l, ry, v]
mode:
mode (str): "iou" (intersection over union) or iof
bboxes1
(torch.
Tensor
):
shape (N, 7+N) [x, y, z, h, w, l, ry, v]
.
bboxes2
(torch.
Tensor
):
shape (M, 7+N) [x, y, z, h, w, l, ry, v]
.
mode (str): "iou" (intersection over union) or iof
(intersection over foreground).
Return:
iou: (M, N) not support aligned mode currently
torch.Tensor: Bbox overlaps results of bboxes1 and bboxes2
with shape (M, N).(not support aligned mode currently).
"""
assert
bboxes1
.
size
(
-
1
)
>=
7
assert
bboxes2
.
size
(
-
1
)
>=
7
...
...
@@ -74,14 +75,15 @@ def bbox_overlaps_3d(bboxes1, bboxes2, mode='iou', coordinate='camera'):
"""Calculate 3D IoU using cuda implementation
Args:
bboxes1
:
Tensor
,
shape (N, 7) [x, y, z, h, w, l, ry]
bboxes2
:
Tensor
,
shape (M, 7) [x, y, z, h, w, l, ry]
mode:
mode (str): "iou" (intersection over union) or
bboxes1
(torch.
Tensor
):
shape (N, 7) [x, y, z, h, w, l, ry]
.
bboxes2
(torch.
Tensor
):
shape (M, 7) [x, y, z, h, w, l, ry]
.
mode (str): "iou" (intersection over union) or
iof (intersection over foreground).
coordinate (str): 'camera' or 'lidar' coordinate system
coordinate (str): 'camera' or 'lidar' coordinate system
.
Return:
iou: (M, N) not support aligned mode currently
torch.Tensor: Bbox overlaps results of bboxes1 and bboxes2
with shape (M, N).(not support aligned mode currently).
"""
assert
bboxes1
.
size
(
-
1
)
==
bboxes2
.
size
(
-
1
)
==
7
assert
coordinate
in
[
'camera'
,
'lidar'
]
...
...
mmdet3d/core/bbox/samplers/iou_neg_piecewise_sampler.py
View file @
b2c43ffd
...
...
@@ -6,7 +6,7 @@ from . import RandomSampler, SamplingResult
@
BBOX_SAMPLERS
.
register_module
()
class
IoUNegPiecewiseSampler
(
RandomSampler
):
"""IoU Piece-wise Sampling
"""IoU Piece-wise Sampling
.
Sampling negtive proposals according to a list of IoU thresholds.
The negtive proposals are divided into several pieces according
...
...
mmdet3d/core/bbox/structures/base_box3d.py
View file @
b2c43ffd
...
...
@@ -247,7 +247,7 @@ class BaseInstance3DBoxes(object):
"""Scale the box with horizontal and vertical scaling factors
Args:
scale_factors (float):
s
cale factors to scale the boxes.
scale_factors (float):
S
cale factors to scale the boxes.
"""
self
.
tensor
[:,
:
6
]
*=
scale_factor
self
.
tensor
[:,
7
:]
*=
scale_factor
...
...
@@ -256,8 +256,8 @@ class BaseInstance3DBoxes(object):
"""Limit the yaw to a given period and offset
Args:
offset (float):
t
he offset of the yaw
period (float):
t
he expected period
offset (float):
T
he offset of the yaw
.
period (float):
T
he expected period
.
"""
self
.
tensor
[:,
6
]
=
limit_period
(
self
.
tensor
[:,
6
],
offset
,
period
)
...
...
@@ -268,10 +268,10 @@ class BaseInstance3DBoxes(object):
if either of its side is no larger than threshold.
Args:
threshold (float):
t
he threshold of minimal sizes
threshold (float):
T
he threshold of minimal sizes
.
Returns:
torch.Tensor:
a
binary vector which represents whether each
torch.Tensor:
A
binary vector which represents whether each
box is empty (False) or non-empty (True).
"""
box
=
self
.
tensor
...
...
@@ -321,11 +321,11 @@ class BaseInstance3DBoxes(object):
def
cat
(
cls
,
boxes_list
):
"""Concatenates a list of Boxes into a single Boxes
Arg
ument
s:
boxes_list (list[Boxes])
Args:
boxes_list (list[Boxes])
: List of boxes.
Returns:
Boxes:
t
he concatenated Boxes
Boxes:
T
he concatenated Boxes
.
"""
assert
isinstance
(
boxes_list
,
(
list
,
tuple
))
if
len
(
boxes_list
)
==
0
:
...
...
@@ -365,7 +365,7 @@ class BaseInstance3DBoxes(object):
"""Yield a box as a Tensor of shape (4,) at a time.
Returns:
torch.Tensor:
a
box of shape (4,).
torch.Tensor:
A
box of shape (4,).
"""
yield
from
self
.
tensor
...
...
@@ -378,12 +378,12 @@ class BaseInstance3DBoxes(object):
boxes2, boxes1 and boxes2 should be in the same type.
Args:
boxes1 (:obj:BaseInstanceBoxes):
b
oxes 1 contain N boxes
boxes2 (:obj:BaseInstanceBoxes):
b
oxes 2 contain M boxes
mode (str, optional):
m
ode of iou calculation. Defaults to 'iou'.
boxes1 (:obj:BaseInstanceBoxes):
B
oxes 1 contain N boxes
.
boxes2 (:obj:BaseInstanceBoxes):
B
oxes 2 contain M boxes
.
mode (str, optional):
M
ode of iou calculation. Defaults to 'iou'.
Returns:
torch.Tensor: Calculated iou of boxes
torch.Tensor: Calculated iou of boxes
.
"""
assert
isinstance
(
boxes1
,
BaseInstance3DBoxes
)
assert
isinstance
(
boxes2
,
BaseInstance3DBoxes
)
...
...
@@ -410,12 +410,12 @@ class BaseInstance3DBoxes(object):
boxes1 and boxes2 are not necessarily to be in the same type.
Args:
boxes1 (:obj:BaseInstanceBoxes):
b
oxes 1 contain N boxes
boxes2 (:obj:BaseInstanceBoxes):
b
oxes 2 contain M boxes
mode (str, optional):
m
ode of iou calculation. Defaults to 'iou'.
boxes1 (:obj:BaseInstanceBoxes):
B
oxes 1 contain N boxes
.
boxes2 (:obj:BaseInstanceBoxes):
B
oxes 2 contain M boxes
.
mode (str, optional):
M
ode of iou calculation. Defaults to 'iou'.
Returns:
torch.Tensor: Calculated iou of boxes
torch.Tensor: Calculated iou of boxes
.
"""
assert
isinstance
(
boxes1
,
BaseInstance3DBoxes
)
assert
isinstance
(
boxes2
,
BaseInstance3DBoxes
)
...
...
mmdet3d/core/bbox/structures/box_3d_mode.py
View file @
b2c43ffd
...
...
@@ -62,19 +62,19 @@ class Box3DMode(IntEnum):
"""Convert boxes from `src` mode to `dst` mode.
Args:
box (tuple | list | np.
n
darray |
box (tuple | list | np.d
n
array |
torch.Tensor | BaseInstance3DBoxes):
c
an be a k-tuple, k-list or an Nxk array/tensor, where k = 7
src (BoxMode):
t
he src Box mode
dst (BoxMode):
t
he target Box mode
rt_mat (np.
n
darray | torch.Tensor): The rotation and translation
C
an be a k-tuple, k-list or an Nxk array/tensor, where k = 7
.
src (BoxMode):
T
he src Box mode
.
dst (BoxMode):
T
he target Box mode
.
rt_mat (np.d
n
array | torch.Tensor): The rotation and translation
matrix between different coordinates. Defaults to None.
The conversion from `src` coordinates to `dst` coordinates
usually comes along the change of sensors, e.g., from camera
to LiDAR. This requires a transformation matrix.
Returns:
(tuple | list | np.
n
darray | torch.Tensor | BaseInstance3DBoxes):
(tuple | list | np.d
n
array | torch.Tensor | BaseInstance3DBoxes):
The converted box of the same type.
"""
if
src
==
dst
:
...
...
mmdet3d/core/bbox/structures/cam_box3d.py
View file @
b2c43ffd
...
...
@@ -6,7 +6,7 @@ from .utils import limit_period, rotation_3d_in_axis
class
CameraInstance3DBoxes
(
BaseInstance3DBoxes
):
"""3D boxes of instances in CAM coordinates
"""3D boxes of instances in CAM coordinates
.
Coordinates in camera:
.. code-block:: none
...
...
@@ -26,10 +26,10 @@ class CameraInstance3DBoxes(BaseInstance3DBoxes):
the positive direction of x to the positive direction of z.
Attributes:
tensor (torch.Tensor):
f
loat matrix of N x box_dim.
box_dim (int):
i
nteger indicates the dimension of a box
tensor (torch.Tensor):
F
loat matrix of N x box_dim.
box_dim (int):
I
nteger indicates the dimension of a box
Each row is (x, y, z, x_size, y_size, z_size, yaw, ...).
with_yaw (bool):
i
f True, the value of yaw will be set to 0 as minmax
with_yaw (bool):
I
f True, the value of yaw will be set to 0 as minmax
boxes.
"""
...
...
@@ -38,7 +38,7 @@ class CameraInstance3DBoxes(BaseInstance3DBoxes):
"""Obtain the height of all the boxes.
Returns:
torch.Tensor:
a
vector with height of each box.
torch.Tensor:
A
vector with height of each box.
"""
return
self
.
tensor
[:,
4
]
...
...
@@ -47,7 +47,7 @@ class CameraInstance3DBoxes(BaseInstance3DBoxes):
"""Obtain the top height of all the boxes.
Returns:
torch.Tensor:
a
vector with the top height of each box.
torch.Tensor:
A
vector with the top height of each box.
"""
# the positive direction is down rather than up
return
self
.
bottom_height
-
self
.
height
...
...
@@ -57,7 +57,7 @@ class CameraInstance3DBoxes(BaseInstance3DBoxes):
"""Obtain the bottom's height of all the boxes.
Returns:
torch.Tensor:
a
vector with bottom's height of each box.
torch.Tensor:
A
vector with bottom's height of each box.
"""
return
self
.
tensor
[:,
1
]
...
...
@@ -66,7 +66,7 @@ class CameraInstance3DBoxes(BaseInstance3DBoxes):
"""Calculate the gravity center of all the boxes.
Returns:
torch.Tensor:
a
tensor with center of each box.
torch.Tensor:
A
tensor with center of each box.
"""
bottom_center
=
self
.
bottom_center
gravity_center
=
torch
.
zeros_like
(
bottom_center
)
...
...
@@ -99,7 +99,7 @@ class CameraInstance3DBoxes(BaseInstance3DBoxes):
down y
Returns:
torch.Tensor:
c
orners of each box with size (N, 8, 3)
torch.Tensor:
C
orners of each box with size (N, 8, 3)
"""
# TODO: rotation_3d_in_axis function do not support
# empty tensor currently.
...
...
@@ -124,7 +124,7 @@ class CameraInstance3DBoxes(BaseInstance3DBoxes):
"""Calculate the 2D bounding boxes in BEV with rotation
Returns:
torch.Tensor:
a
nx5 tensor of 2D BEV box of each box.
torch.Tensor:
A
nx5 tensor of 2D BEV box of each box.
The box is in XYWHR format.
"""
return
self
.
tensor
[:,
[
0
,
2
,
3
,
5
,
6
]]
...
...
@@ -134,7 +134,7 @@ class CameraInstance3DBoxes(BaseInstance3DBoxes):
"""Calculate the 2D bounding boxes in BEV without rotation
Returns:
torch.Tensor:
a
tensor of 2D BEV box of each box.
torch.Tensor:
A
tensor of 2D BEV box of each box.
"""
# Obtain BEV boxes with rotation in XZWHR format
bev_rotated_boxes
=
self
.
bev
...
...
@@ -221,8 +221,8 @@ class CameraInstance3DBoxes(BaseInstance3DBoxes):
"""Check whether the boxes are in the given range
Args:
box_range (list | torch.Tensor):
t
he range of box
(x_min, z_min, x_max, z_max)
box_range (list | torch.Tensor):
T
he range of box
(x_min, z_min, x_max, z_max)
.
Note:
In the original implementation of SECOND, checking whether
...
...
@@ -249,12 +249,12 @@ class CameraInstance3DBoxes(BaseInstance3DBoxes):
boxes2, boxes1 and boxes2 should be in the same type.
Args:
boxes1 (:obj:BaseInstanceBoxes):
b
oxes 1 contain N boxes
boxes2 (:obj:BaseInstanceBoxes):
b
oxes 2 contain M boxes
mode (str, optional):
m
ode of iou calculation. Defaults to 'iou'.
boxes1 (:obj:BaseInstanceBoxes):
B
oxes 1 contain N boxes
.
boxes2 (:obj:BaseInstanceBoxes):
B
oxes 2 contain M boxes
.
mode (str, optional):
M
ode of iou calculation. Defaults to 'iou'.
Returns:
torch.Tensor: Calculated iou of boxes
torch.Tensor: Calculated iou of boxes
.
"""
assert
isinstance
(
boxes1
,
BaseInstance3DBoxes
)
assert
isinstance
(
boxes2
,
BaseInstance3DBoxes
)
...
...
@@ -278,8 +278,8 @@ class CameraInstance3DBoxes(BaseInstance3DBoxes):
"""Convert self to `dst` mode.
Args:
dst (BoxMode):
t
he target Box mode
rt_mat (np.
n
darray | torch.Tensor): The rotation and translation
dst (BoxMode):
T
he target Box mode
.
rt_mat (np.d
n
array | torch.Tensor): The rotation and translation
matrix between different coordinates. Defaults to None.
The conversion from `src` coordinates to `dst` coordinates
usually comes along the change of sensors, e.g., from camera
...
...
mmdet3d/core/bbox/structures/depth_box3d.py
View file @
b2c43ffd
...
...
@@ -7,7 +7,7 @@ from .utils import limit_period, rotation_3d_in_axis
class
DepthInstance3DBoxes
(
BaseInstance3DBoxes
):
"""3D boxes of instances in Depth coordinates
"""3D boxes of instances in Depth coordinates
.
Coordinates in Depth:
.. code-block:: none
...
...
@@ -23,11 +23,11 @@ class DepthInstance3DBoxes(BaseInstance3DBoxes):
The yaw is 0 at the positive direction of x axis, and increases from
the positive direction of x to the positive direction of y.
A
ttribute
s:
tensor (
torch.
Tensor):
f
loat matrix of N x box_dim.
box_dim (int):
i
nteger indicates the dimension of a box
A
rg
s:
tensor (Tensor):
F
loat matrix of N x box_dim.
box_dim (int):
I
nteger indicates the dimension of a box
Each row is (x, y, z, x_size, y_size, z_size, yaw, ...).
with_yaw (bool):
i
f True, the value of yaw will be set to 0 as minmax
with_yaw (bool):
I
f True, the value of yaw will be set to 0 as minmax
boxes.
"""
...
...
@@ -89,17 +89,17 @@ class DepthInstance3DBoxes(BaseInstance3DBoxes):
@
property
def
bev
(
self
):
"""Calculate the 2D bounding boxes in BEV with rotation
"""Calculate the 2D bounding boxes in BEV with rotation
.
Returns:
torch.Tensor:
a
nx5 tensor of 2D BEV box of each box.
The box is in XYWHR format
torch.Tensor:
A
nx5 tensor of 2D BEV box of each box.
The box is in XYWHR format
.
"""
return
self
.
tensor
[:,
[
0
,
1
,
3
,
4
,
6
]]
@
property
def
nearest_bev
(
self
):
"""Calculate the 2D bounding boxes in BEV without rotation
"""Calculate the 2D bounding boxes in BEV without rotation
.
Returns:
torch.Tensor: a tensor of 2D BEV box of each box.
...
...
@@ -196,11 +196,11 @@ class DepthInstance3DBoxes(BaseInstance3DBoxes):
return
points
def
in_range_bev
(
self
,
box_range
):
"""Check whether the boxes are in the given range
"""Check whether the boxes are in the given range
.
Args:
box_range (list | torch.Tensor):
t
he range of box
(x_min, y_min, x_max, y_max)
box_range (list | torch.Tensor):
T
he range of box
(x_min, y_min, x_max, y_max)
.
Note:
In the original implementation of SECOND, checking whether
...
...
@@ -222,7 +222,7 @@ class DepthInstance3DBoxes(BaseInstance3DBoxes):
"""Convert self to `dst` mode.
Args:
dst (BoxMode):
t
he target Box mode
dst (BoxMode):
T
he target Box mode
.
rt_mat (np.ndarray | torch.Tensor): The rotation and translation
matrix between different coordinates. Defaults to None.
The conversion from `src` coordinates to `dst` coordinates
...
...
@@ -238,7 +238,7 @@ class DepthInstance3DBoxes(BaseInstance3DBoxes):
box
=
self
,
src
=
Box3DMode
.
DEPTH
,
dst
=
dst
,
rt_mat
=
rt_mat
)
def
points_in_boxes
(
self
,
points
):
"""Find points that are in boxes (CUDA)
"""Find points that are in boxes (CUDA)
.
Args:
points (torch.Tensor): [1, M, 3] or [M, 3], [x, y, z]
...
...
mmdet3d/core/bbox/structures/lidar_box3d.py
View file @
b2c43ffd
...
...
@@ -24,10 +24,10 @@ class LiDARInstance3DBoxes(BaseInstance3DBoxes):
the negative direction of y to the positive direction of x.
Attributes:
tensor (torch.Tensor):
f
loat matrix of N x box_dim.
box_dim (int):
i
nteger indicates the dimension of a box
tensor (torch.Tensor):
F
loat matrix of N x box_dim.
box_dim (int):
I
nteger indicates the dimension of a box
Each row is (x, y, z, x_size, y_size, z_size, yaw, ...).
with_yaw (bool):
i
f True, the value of yaw will be set to 0 as minmax
with_yaw (bool):
I
f True, the value of yaw will be set to 0 as minmax
boxes.
"""
...
...
@@ -36,7 +36,7 @@ class LiDARInstance3DBoxes(BaseInstance3DBoxes):
"""Calculate the gravity center of all the boxes.
Returns:
torch.Tensor:
a
tensor with center of each box.
torch.Tensor:
A
tensor with center of each box.
"""
bottom_center
=
self
.
bottom_center
gravity_center
=
torch
.
zeros_like
(
bottom_center
)
...
...
@@ -92,7 +92,7 @@ class LiDARInstance3DBoxes(BaseInstance3DBoxes):
"""Calculate the 2D bounding boxes in BEV with rotation
Returns:
torch.Tensor:
a
nx5 tensor of 2D BEV box of each box.
torch.Tensor:
A
nx5 tensor of 2D BEV box of each box.
The box is in XYWHR format
"""
return
self
.
tensor
[:,
[
0
,
1
,
3
,
4
,
6
]]
...
...
@@ -102,7 +102,7 @@ class LiDARInstance3DBoxes(BaseInstance3DBoxes):
"""Calculate the 2D bounding boxes in BEV without rotation
Returns:
torch.Tensor:
a
tensor of 2D BEV box of each box.
torch.Tensor:
A
tensor of 2D BEV box of each box.
"""
# Obtain BEV boxes with rotation in XYWHR format
bev_rotated_boxes
=
self
.
bev
...
...
mmdet3d/core/bbox/structures/utils.py
View file @
b2c43ffd
...
...
@@ -6,7 +6,7 @@ def limit_period(val, offset=0.5, period=np.pi):
"""Limit the value into a period for periodic function.
Args:
val (torch.Tensor): The value to be converted
val (torch.Tensor): The value to be converted
.
offset (float, optional): Offset to set the value range.
Defaults to 0.5.
period ([type], optional): Period of the value. Defaults to np.pi.
...
...
mmdet3d/core/bbox/transforms.py
View file @
b2c43ffd
...
...
@@ -14,10 +14,17 @@ def bbox3d_mapping_back(bboxes, scale_factor, flip_horizontal, flip_vertical):
def
transform_lidar_to_cam
(
boxes_lidar
):
"""
Only transform format, not exactly in camera coords
:param boxes_lidar: (N, 3 or 7) [x, y, z, w, l, h, ry] in LiDAR coords
:return: boxes_cam: (N, 3 or 7) [x, y, z, h, w, l, ry] in camera coords
"""Transform boxes from lidar coords to cam coords.
Only transform format, not exactly in camera coords.
Args:
boxes_lidar (torch.Tensor): (N, 3 or 7) [x, y, z, w, l, h, ry]
in LiDAR coords.
boxes_cam (torch.Tensor): (N, 3 or 7) [x, y, z, h, w, l, ry]
in camera coords.
Returns:
torch.Tensor: Boxes in camera coords.
"""
# boxes_cam = boxes_lidar.new_tensor(boxes_lidar.data)
boxes_cam
=
boxes_lidar
.
clone
().
detach
()
...
...
@@ -30,10 +37,15 @@ def transform_lidar_to_cam(boxes_lidar):
def
boxes3d_to_bev_torch
(
boxes3d
):
"""
:param boxes3d: (N, 7) [x, y, z, h, w, l, ry] in camera coords
:return:
boxes_bev: (N, 5) [x1, y1, x2, y2, ry]
"""Transform 3d boxes to bev in camera coords.
Args:
boxes3d (torch.Tensor): 3d boxes in camera coords
with the shape of [N, 7] (x, y, z, h, w, l, ry).
Returns:
torch.Tensor: Bev boxes with the shape of [N, 5]
(x1, y1, x2, y2, ry).
"""
boxes_bev
=
boxes3d
.
new
(
torch
.
Size
((
boxes3d
.
shape
[
0
],
5
)))
...
...
@@ -46,10 +58,13 @@ def boxes3d_to_bev_torch(boxes3d):
def
boxes3d_to_bev_torch_lidar
(
boxes3d
):
"""
:param boxes3d: (N, 7) [x, y, z, w, l, h, ry] in LiDAR coords
:return:
boxes_bev: (N, 5) [x1, y1, x2, y2, ry]
"""Transform 3d boxes to bev in lidar coords.
Args:
boxes3d (torch.Tensor): 3d boxes in lidar coords
with the shape of [N, 7] (x, y, z, h, w, l, ry).
Returns: Bev boxes with the shape of [N, 5] (x1, y1, x2, y2, ry).
"""
boxes_bev
=
boxes3d
.
new
(
torch
.
Size
((
boxes3d
.
shape
[
0
],
5
)))
...
...
@@ -65,11 +80,11 @@ def bbox3d2roi(bbox_list):
"""Convert a list of bboxes to roi format.
Args:
bbox_list (list[Tensor]): a list of bboxes
corresponding to a batch
of images.
bbox_list (list[
torch.
Tensor]): a list of bboxes
corresponding to a batch
of images.
Returns:
Tensor: shape (n, c), [batch_ind, x, y ...]
torch.
Tensor: shape (n, c), [batch_ind, x, y ...]
.
"""
rois_list
=
[]
for
img_id
,
bboxes
in
enumerate
(
bbox_list
):
...
...
@@ -87,12 +102,12 @@ def bbox3d2result(bboxes, scores, labels):
"""Convert detection results to a list of numpy arrays.
Args:
bboxes (Tensor): shape (n, 5)
labels (Tensor): shape (n, )
scores (Tensor): shape (n, )
bboxes (
torch.
Tensor): shape (n, 5)
labels (
torch.
Tensor): shape (n, )
scores (
torch.
Tensor): shape (n, )
Returns:
dict(Tensor):
b
box results in cpu mode
dict(
torch.
Tensor):
B
box results in cpu mode
.
"""
return
dict
(
boxes_3d
=
bboxes
.
to
(
'cpu'
),
...
...
@@ -106,8 +121,8 @@ def upright_depth_to_lidar_torch(points=None,
"""Convert points and boxes in upright depth coordinate to lidar.
Args:
points (None | Tensor): points in upright depth coordinate.
bboxes (None | Tensor): bboxes in upright depth coordinate.
points (None |
torch.
Tensor): points in upright depth coordinate.
bboxes (None |
torch.
Tensor): bboxes in upright depth coordinate.
to_bottom_center (bool): covert bboxes to bottom center.
Returns:
...
...
@@ -136,10 +151,11 @@ def box3d_to_corner3d_upright_depth(boxes3d):
"""Convert box3d to corner3d in upright depth coordinate
Args:
boxes3d (Tensor): boxes with shape [n,7] in upright depth coordinate
boxes3d (torch.Tensor): boxes with shape [n,7] in
upright depth coordinate.
Returns:
Tensor: boxes with [n, 8, 3] in upright depth coordinate
torch.
Tensor: boxes with [n, 8, 3] in upright depth coordinate
"""
boxes_num
=
boxes3d
.
shape
[
0
]
ry
=
boxes3d
[:,
6
:
7
]
...
...
mmdet3d/core/evaluation/indoor_eval.py
View file @
b2c43ffd
...
...
@@ -8,14 +8,14 @@ def average_precision(recalls, precisions, mode='area'):
"""Calculate average precision (for single or multiple scales).
Args:
recalls (ndarray): shape (num_scales, num_dets) or (num_dets, )
precisions (ndarray): shape (num_scales, num_dets) or (num_dets, )
recalls (
np.
ndarray): shape (num_scales, num_dets) or (num_dets, )
precisions (
np.
ndarray): shape (num_scales, num_dets) or (num_dets, )
mode (str): 'area' or '11points', 'area' means calculating the area
under precision-recall curve, '11points' means calculating
the average precision of recalls at [0, 0.1, ..., 1]
Returns:
float or ndarray: calculated average precision
float or
np.
ndarray: calculated average precision
"""
if
recalls
.
ndim
==
1
:
recalls
=
recalls
[
np
.
newaxis
,
:]
...
...
@@ -60,8 +60,8 @@ def eval_det_cls(pred, gt, iou_thr=None):
iou_thr (list[float]): a list, iou threshold.
Return:
ndarray: numpy array of length nd.
ndarray: numpy array of length nd.
np.
ndarray: numpy array of length nd.
np.
ndarray: numpy array of length nd.
float: scalar, average precision.
"""
...
...
@@ -204,7 +204,7 @@ def indoor_eval(gt_annos,
logger
=
None
,
box_type_3d
=
None
,
box_mode_3d
=
None
):
"""
Scannet
Evaluation.
"""
Indoor
Evaluation.
Evaluate the result of the detection.
...
...
@@ -212,10 +212,9 @@ def indoor_eval(gt_annos,
gt_annos (list[dict]): GT annotations.
dt_annos (list[dict]): Detection annotations. the dict
includes the following keys
- labels_3d (Tensor): Labels of boxes.
- boxes_3d (:obj:BaseInstance3DBoxes): 3d bboxes in
Depth coordinate.
- scores_3d (Tensor): Scores of boxes.
- labels_3d (torch.Tensor): Labels of boxes.
- boxes_3d (BaseInstance3DBoxes): 3d bboxes in Depth coordinate.
- scores_3d (torch.Tensor): Scores of boxes.
metric (list[float]): AP IoU thresholds.
label2cat (dict): {label: cat}.
logger (logging.Logger | str | None): The way to print the mAP
...
...
mmdet3d/core/evaluation/kitti_utils/eval.py
View file @
b2c43ffd
...
...
@@ -340,13 +340,14 @@ def fused_compute_statistics(overlaps,
def
calculate_iou_partly
(
gt_annos
,
dt_annos
,
metric
,
num_parts
=
50
):
"""
f
ast iou algorithm. this function can be used independently to
"""
F
ast iou algorithm. this function can be used independently to
do result analysis. Must be used in CAMERA coordinate system.
Args:
gt_annos
:
dict
, m
ust from get_label_annos() in kitti_common.py
dt_annos
:
dict
, m
ust from get_label_annos() in kitti_common.py
metric:
e
val type. 0: bbox, 1: bev, 2: 3d
num_parts
:
int
. a
parameter for fast calculate algorithm
gt_annos
(
dict
): M
ust from get_label_annos() in kitti_common.py
.
dt_annos
(
dict
): M
ust from get_label_annos() in kitti_common.py
.
metric
(int)
:
E
val type. 0: bbox, 1: bev, 2: 3d
.
num_parts
(
int
): A
parameter for fast calculate algorithm
.
"""
assert
len
(
gt_annos
)
==
len
(
dt_annos
)
total_dt_num
=
np
.
stack
([
len
(
a
[
'name'
])
for
a
in
dt_annos
],
0
)
...
...
@@ -456,17 +457,19 @@ def eval_class(gt_annos,
compute_aos
=
False
,
num_parts
=
200
):
"""Kitti eval. support 2d/bev/3d/aos eval. support 0.5:0.05:0.95 coco AP.
Args:
gt_annos: dict, must from get_label_annos() in kitti_common.py
dt_annos: dict, must from get_label_annos() in kitti_common.py
current_classes: list of int, 0: car, 1: pedestrian, 2: cyclist
difficultys: list of int. eval difficulty, 0: easy, 1: normal, 2: hard
metric: eval type. 0: bbox, 1: bev, 2: 3d
min_overlaps: float, min overlap. format: [num_overlap, metric, class].
num_parts: int. a parameter for fast calculate algorithm
gt_annos (dict): Must from get_label_annos() in kitti_common.py.
dt_annos (dict): Must from get_label_annos() in kitti_common.py.
current_classes (list[int]): 0: car, 1: pedestrian, 2: cyclist.
difficultys (list[int]): Eval difficulty, 0: easy, 1: normal, 2: hard
metric (int): Eval type. 0: bbox, 1: bev, 2: 3d
min_overlaps (float): Min overlap. format:
[num_overlap, metric, class].
num_parts (int): A parameter for fast calculate algorithm
Returns:
dict
of
recall, precision and aos
dict
:
recall, precision and aos
"""
assert
len
(
gt_annos
)
==
len
(
dt_annos
)
num_examples
=
len
(
gt_annos
)
...
...
mmdet3d/core/evaluation/kitti_utils/rotate_iou.py
View file @
b2c43ffd
...
...
@@ -304,19 +304,19 @@ def rotate_iou_kernel_eval(N,
def
rotate_iou_gpu_eval
(
boxes
,
query_boxes
,
criterion
=-
1
,
device_id
=
0
):
"""
r
otated box iou running in gpu. 500x faster than cpu version
"""
R
otated box iou running in gpu. 500x faster than cpu version
(take 5ms in one example with numba.cuda code).
convert from [this project](
https://github.com/hongzhenwang/RRPN-revise/tree/master/lib/rotation).
Args:
boxes (
float tensor: [N, 5]
): rbboxes. format: centers, dims,
angles(clockwise when positive)
boxes (
torch.Tensor
): rbboxes. format: centers, dims,
angles(clockwise when positive)
with the shape of [N, 5].
query_boxes (float tensor: [K, 5]): [description]
device_id (int, optional): Defaults to 0. [description]
Returns:
[type]: [description]
np.ndarray: IoU results.
"""
boxes
=
boxes
.
astype
(
np
.
float32
)
query_boxes
=
query_boxes
.
astype
(
np
.
float32
)
...
...
mmdet3d/core/post_processing/box3d_nms.py
View file @
b2c43ffd
...
...
@@ -70,13 +70,13 @@ def aligned_3d_nms(boxes, scores, classes, thresh):
"""3d nms for aligned boxes.
Args:
boxes (Tensor): Aligned box with shape [n, 6].
scores (Tensor): Scores of each box.
classes (Tensor): Class of each box.
boxes (
torch.
Tensor): Aligned box with shape [n, 6].
scores (
torch.
Tensor): Scores of each box.
classes (
torch.
Tensor): Class of each box.
thresh (float): Iou threshold for nms.
Returns:
Tensor: Indices of selected boxes.
torch.
Tensor: Indices of selected boxes.
"""
x1
=
boxes
[:,
0
]
y1
=
boxes
[:,
1
]
...
...
Prev
1
2
Next
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment