Example #1
0
    ty += h/2.0
    return h,w,l,tx,ty,tz,ry

if __name__=='__main__':
    import mayavi.mlab as mlab
    sys.path.append(os.path.join(ROOT_DIR, 'mayavi'))
    from viz_util import draw_lidar, draw_gt_boxes3d
    median_list = []
    dataset = FrustumDataset(1024, split='val',
        rotate_to_center=True, random_flip=True, random_shift=True)
    for i in range(len(dataset)):
        data = dataset[i]
        print(('Center: ', data[2], \
            'angle_class: ', data[3], 'angle_res:', data[4], \
            'size_class: ', data[5], 'size_residual:', data[6], \
            'real_size:', g_type_mean_size[g_class2type[data[5]]]+data[6]))
        print(('Frustum angle: ', dataset.frustum_angle_list[i]))
        median_list.append(np.median(data[0][:,0]))
        print((data[2], dataset.box3d_list[i], median_list[-1]))
        box3d_from_label = get_3d_box(class2size(data[5],data[6]), class2angle(data[3], data[4],12), data[2])

        ps = data[0]
        seg = data[1]
        fig = mlab.figure(figure=None, bgcolor=(0.4,0.4,0.4), fgcolor=None, engine=None, size=(1000, 500))
        mlab.points3d(ps[:,0], ps[:,1], ps[:,2], seg, mode='point', colormap='gnuplot', scale_factor=1, figure=fig)
        mlab.points3d(0, 0, 0, color=(1,1,1), mode='sphere', scale_factor=0.2, figure=fig)
        draw_gt_boxes3d([box3d_from_label], fig, color=(1,0,0))
        mlab.orientation_axes()
        raw_input()
    print(np.mean(np.abs(median_list)))
Example #2
0
def parse_crop_predictions(end_points, point_cloud, DC):
    pred_center = end_points['center'].clone()  # B,num_proposal,3
    pred_heading_class = torch.argmax(end_points['heading_scores'].clone(),
                                      -1)  # B,num_proposal
    pred_heading_residual = torch.gather(
        end_points['heading_residuals'].clone(), 2,
        pred_heading_class.unsqueeze(-1))  # B,num_proposal,1
    pred_heading_residual.squeeze_(2)
    pred_size_class = torch.argmax(end_points['size_scores'].clone(),
                                   -1)  # B,num_proposal
    pred_size_residual = torch.gather(
        end_points['size_residuals'].clone(), 2,
        pred_size_class.unsqueeze(-1).unsqueeze(-1).repeat(
            1, 1, 1, 3))  # B,num_proposal,1,3
    pred_size_residual.squeeze_(2)
    pred_sem_cls = torch.argmax(end_points['sem_cls_scores'].clone(),
                                -1)  # B,num_proposal
    sem_cls_probs = softmax(end_points['sem_cls_scores'].detach().cpu().clone(
    ).numpy())  # B,num_proposal,10
    pred_sem_cls_prob = np.max(sem_cls_probs, -1)  # B,num_proposal

    bsize = pred_center.shape[0]
    assert bsize == 1
    num_proposal = pred_center.shape[1]

    # Since we operate in upright_depth coord for points, while util functions
    # assume upright_camera coord.
    pred_corners_3d_upright_camera = np.zeros((bsize, num_proposal, 8, 3))
    pred_center_upright_camera = flip_axis_to_camera(
        pred_center.detach().cpu().numpy())
    for i in range(bsize):
        for j in range(num_proposal):
            heading_angle = DC.class2angle(
                pred_heading_class[i, j].detach().cpu().numpy(),
                pred_heading_residual[i, j].detach().cpu().numpy())
            box_size = DC.class2size(
                int(pred_size_class[i, j].detach().cpu().numpy()),
                pred_size_residual[i, j].detach().cpu().numpy())
            corners_3d_upright_camera = get_3d_box(
                box_size, heading_angle, pred_center_upright_camera[i, j, :])
            pred_corners_3d_upright_camera[i, j] = corners_3d_upright_camera

    K = pred_center.shape[1]  # K==num_proposal
    nonempty_box_mask = np.ones((bsize, K))

    # -------------------------------------
    # Remove predicted boxes without any point within them..
    batch_pc = point_cloud.copy()[:, 0:3]  # B,N,3
    i = 0
    pc = batch_pc[:, :]  # (N,3)
    for j in range(K):
        box3d = pred_corners_3d_upright_camera[i, j, :, :]  # (8,3)
        # -- OG version of getting in-box points
        box3d = flip_axis_to_depth(box3d)
        pc_in_box, inds = extract_pc_in_box3d(pc, box3d)
        if len(pc_in_box) < 5:
            nonempty_box_mask[i, j] = 0

        # -- new version
        #min_bound_box = np.min(box3d, axis=0)
        #max_bound_box = np.max(box3d, axis=0)
        #in_bound_pc = np.all(pc > min_bound_box, axis=1) *\
        #              np.all(pc < max_bound_box, axis=1)
        #if np.sum(in_bound_pc) < 5:
        #    nonempty_box_mask[i,j] = 0
    end_points['center'] = end_points['center'][i][nonempty_box_mask[i, :], :]
    end_points['heading_scores'] = end_points['heading_scores'][i][
        nonempty_box_mask[i, :], :]
    end_points['heading_residuals'] = end_points['heading_residuals'][i][
        nonempty_box_mask[i, :], :]
    end_points['heading_residuals_normalized'] = end_points[
        'heading_residuals_normalized'][i][nonempty_box_mask[i, :], :]
    end_points['size_scores'] = end_points['size_scores'][i][nonempty_box_mask[
        i, :], :]
    end_points['size_residuals'] = end_points['size_residuals'][i][
        nonempty_box_mask[i, :], :]
    end_points['size_residuals_normalized'] = end_points[
        'size_residuals_normalized'][i][nonempty_box_mask[i, :], :]
    end_points['sem_cls_scores'] = end_points['sem_cls_scores'][i][
        nonempty_box_mask[i, :], :]
    end_points['objectness_scores'] = end_points['objectness_scores'][i][
        nonempty_box_mask[i, :], :]

    end_points['center'] = end_points['center'].unsqueeze(0)
    end_points['heading_scores'] = end_points['heading_scores'].unsqueeze(0)
    end_points['heading_residuals'] = end_points[
        'heading_residuals'].unsqueeze(0)
    end_points['heading_residuals_normalized'] = end_points[
        'heading_residuals_normalized'].unsqueeze(0)
    end_points['size_scores'] = end_points['size_scores'].unsqueeze(0)
    end_points['size_residuals'] = end_points['size_residuals'].unsqueeze(0)
    end_points['size_residuals_normalized'] = end_points[
        'size_residuals_normalized'].unsqueeze(0)
    end_points['sem_cls_scores'] = end_points['sem_cls_scores'].unsqueeze(0)
    end_points['objectness_scores'] = end_points[
        'objectness_scores'].unsqueeze(0)

    return end_points
Example #3
0
def parse_predictions(end_points, config_dict):
    """ Parse predictions to OBB parameters and suppress overlapping boxes
    
    Args:
        end_points: dict
            {point_clouds, center, heading_scores, heading_residuals,
            size_scores, size_residuals, sem_cls_scores}
        config_dict: dict
            {dataset_config, remove_empty_box, use_3d_nms, nms_iou,
            use_old_type_nms, conf_thresh, per_class_proposal}

    Returns:
        batch_pred_map_cls: a list of len == batch size (BS)
            [pred_list_i], i = 0, 1, ..., BS-1
            where pred_list_i = [(pred_sem_cls, box_params, box_score)_j]
            where j = 0, ..., num of valid detections - 1 from sample input i
    """
    pred_center = end_points['center']  # B,num_proposal,3
    pred_heading_class = torch.argmax(end_points['heading_scores'],
                                      -1)  # B,num_proposal
    pred_heading_residual = torch.gather(
        end_points['heading_residuals'], 2,
        pred_heading_class.unsqueeze(-1))  # B,num_proposal,1
    pred_heading_residual.squeeze_(2)
    pred_size_class = torch.argmax(end_points['size_scores'],
                                   -1)  # B,num_proposal
    pred_size_residual = torch.gather(
        end_points['size_residuals'], 2,
        pred_size_class.unsqueeze(-1).unsqueeze(-1).repeat(
            1, 1, 1, 3))  # B,num_proposal,1,3
    pred_size_residual.squeeze_(2)
    pred_sem_cls = torch.argmax(end_points['sem_cls_scores'],
                                -1)  # B,num_proposal
    sem_cls_probs = softmax(end_points['sem_cls_scores'].detach().cpu().numpy(
    ))  # B,num_proposal,10
    pred_sem_cls_prob = np.max(sem_cls_probs, -1)  # B,num_proposal

    num_proposal = pred_center.shape[1]
    # Since we operate in upright_depth coord for points, while util functions
    # assume upright_camera coord.
    bsize = pred_center.shape[0]
    pred_corners_3d_upright_camera = np.zeros((bsize, num_proposal, 8, 3))
    pred_center_upright_camera = flip_axis_to_camera(
        pred_center.detach().cpu().numpy())
    for i in range(bsize):
        for j in range(num_proposal):
            heading_angle = config_dict['dataset_config'].class2angle(\
                pred_heading_class[i,j].detach().cpu().numpy(), pred_heading_residual[i,j].detach().cpu().numpy())
            box_size = config_dict['dataset_config'].class2size(\
                int(pred_size_class[i,j].detach().cpu().numpy()), pred_size_residual[i,j].detach().cpu().numpy())
            corners_3d_upright_camera = get_3d_box(
                box_size, heading_angle, pred_center_upright_camera[i, j, :])
            pred_corners_3d_upright_camera[i, j] = corners_3d_upright_camera

    K = pred_center.shape[1]  # K==num_proposal
    nonempty_box_mask = np.ones((bsize, K))

    if config_dict['remove_empty_box']:
        # -------------------------------------
        # Remove predicted boxes without any point within them..
        batch_pc = end_points['point_clouds'].cpu().numpy()[:, :, 0:3]  # B,N,3
        for i in range(bsize):
            pc = batch_pc[i, :, :]  # (N,3)
            for j in range(K):
                box3d = pred_corners_3d_upright_camera[i, j, :, :]  # (8,3)
                box3d = flip_axis_to_depth(box3d)
                pc_in_box, inds = extract_pc_in_box3d(pc, box3d)
                if len(pc_in_box) < 5:
                    nonempty_box_mask[i, j] = 0
        # -------------------------------------

    obj_logits = end_points['objectness_scores'].detach().cpu().numpy()
    obj_prob = softmax(obj_logits)[:, :, 1]  # (B,K)
    if not config_dict['use_3d_nms']:
        # ---------- NMS input: pred_with_prob in (B,K,7) -----------
        pred_mask = np.zeros((bsize, K))
        for i in range(bsize):
            boxes_2d_with_prob = np.zeros((K, 5))
            for j in range(K):
                boxes_2d_with_prob[j, 0] = np.min(
                    pred_corners_3d_upright_camera[i, j, :, 0])
                boxes_2d_with_prob[j, 2] = np.max(
                    pred_corners_3d_upright_camera[i, j, :, 0])
                boxes_2d_with_prob[j, 1] = np.min(
                    pred_corners_3d_upright_camera[i, j, :, 2])
                boxes_2d_with_prob[j, 3] = np.max(
                    pred_corners_3d_upright_camera[i, j, :, 2])
                boxes_2d_with_prob[j, 4] = obj_prob[i, j]
            nonempty_box_inds = np.where(nonempty_box_mask[i, :] == 1)[0]
            pick = nms_2d_faster(
                boxes_2d_with_prob[nonempty_box_mask[i, :] == 1, :],
                config_dict['nms_iou'], config_dict['use_old_type_nms'])
            assert (len(pick) > 0)
            pred_mask[i, nonempty_box_inds[pick]] = 1
        end_points['pred_mask'] = pred_mask
        # ---------- NMS output: pred_mask in (B,K) -----------
    elif config_dict['use_3d_nms'] and (not config_dict['cls_nms']):
        # ---------- NMS input: pred_with_prob in (B,K,7) -----------
        pred_mask = np.zeros((bsize, K))
        for i in range(bsize):
            boxes_3d_with_prob = np.zeros((K, 7))
            for j in range(K):
                boxes_3d_with_prob[j, 0] = np.min(
                    pred_corners_3d_upright_camera[i, j, :, 0])
                boxes_3d_with_prob[j, 1] = np.min(
                    pred_corners_3d_upright_camera[i, j, :, 1])
                boxes_3d_with_prob[j, 2] = np.min(
                    pred_corners_3d_upright_camera[i, j, :, 2])
                boxes_3d_with_prob[j, 3] = np.max(
                    pred_corners_3d_upright_camera[i, j, :, 0])
                boxes_3d_with_prob[j, 4] = np.max(
                    pred_corners_3d_upright_camera[i, j, :, 1])
                boxes_3d_with_prob[j, 5] = np.max(
                    pred_corners_3d_upright_camera[i, j, :, 2])
                boxes_3d_with_prob[j, 6] = obj_prob[i, j]
            nonempty_box_inds = np.where(nonempty_box_mask[i, :] == 1)[0]
            pick = nms_3d_faster(
                boxes_3d_with_prob[nonempty_box_mask[i, :] == 1, :],
                config_dict['nms_iou'], config_dict['use_old_type_nms'])
            assert (len(pick) > 0)
            pred_mask[i, nonempty_box_inds[pick]] = 1
        end_points['pred_mask'] = pred_mask
        # ---------- NMS output: pred_mask in (B,K) -----------
    elif config_dict['use_3d_nms'] and config_dict['cls_nms']:
        # ---------- NMS input: pred_with_prob in (B,K,8) -----------
        pred_mask = np.zeros((bsize, K))
        for i in range(bsize):
            boxes_3d_with_prob = np.zeros((K, 8))
            for j in range(K):
                boxes_3d_with_prob[j, 0] = np.min(
                    pred_corners_3d_upright_camera[i, j, :, 0])
                boxes_3d_with_prob[j, 1] = np.min(
                    pred_corners_3d_upright_camera[i, j, :, 1])
                boxes_3d_with_prob[j, 2] = np.min(
                    pred_corners_3d_upright_camera[i, j, :, 2])
                boxes_3d_with_prob[j, 3] = np.max(
                    pred_corners_3d_upright_camera[i, j, :, 0])
                boxes_3d_with_prob[j, 4] = np.max(
                    pred_corners_3d_upright_camera[i, j, :, 1])
                boxes_3d_with_prob[j, 5] = np.max(
                    pred_corners_3d_upright_camera[i, j, :, 2])
                boxes_3d_with_prob[j, 6] = obj_prob[i, j]
                boxes_3d_with_prob[j, 7] = pred_sem_cls[
                    i,
                    j]  # only suppress if the two boxes are of the same class!!
            nonempty_box_inds = np.where(nonempty_box_mask[i, :] == 1)[0]
            pick = nms_3d_faster_samecls(
                boxes_3d_with_prob[nonempty_box_mask[i, :] == 1, :],
                config_dict['nms_iou'], config_dict['use_old_type_nms'])
            assert (len(pick) > 0)
            pred_mask[i, nonempty_box_inds[pick]] = 1
        end_points['pred_mask'] = pred_mask
        # ---------- NMS output: pred_mask in (B,K) -----------

    batch_pred_map_cls = [
    ]  # a list (len: batch_size) of list (len: num of predictions per sample) of tuples of pred_cls, pred_box and conf (0-1)
    for i in range(bsize):
        if config_dict['per_class_proposal']:
            cur_list = []
            for ii in range(config_dict['dataset_config'].num_class):
                cur_list += [(ii, pred_corners_3d_upright_camera[i,j], sem_cls_probs[i,j,ii]*obj_prob[i,j]) \
                    for j in range(pred_center.shape[1]) if pred_mask[i,j]==1 and obj_prob[i,j]>config_dict['conf_thresh']]
            batch_pred_map_cls.append(cur_list)
        else:
            batch_pred_map_cls.append([(pred_sem_cls[i,j].item(), pred_corners_3d_upright_camera[i,j], obj_prob[i,j]) \
                for j in range(pred_center.shape[1]) if pred_mask[i,j]==1 and obj_prob[i,j]>config_dict['conf_thresh']])
    end_points['batch_pred_map_cls'] = batch_pred_map_cls

    return batch_pred_map_cls
def evaluate_one_epoch():
    stat_dict = {}
    ap_calculator_list = [APCalculator(iou_thresh, DATASET_CONFIG.class2type) \
        for iou_thresh in AP_IOU_THRESHOLDS]
    net.eval()  # set model to eval mode (for bn and dp)
    for batch_idx, batch_data_label in enumerate(TEST_DATALOADER):

        scan_name_list = batch_data_label['scan_name']
        del batch_data_label['scan_name']

        if batch_idx % 10 == 0:
            print('Eval batch: %d' % (batch_idx))

        for key in batch_data_label:
            batch_data_label[key] = batch_data_label[key].to(device)

        # Forward pass
        inputs = {'point_clouds': batch_data_label['point_clouds']}
        with torch.no_grad():
            end_points = net(inputs)

        # Compute loss
        for key in batch_data_label:
            assert (key not in end_points)
            end_points[key] = batch_data_label[key]
        loss, end_points = criterion(end_points, DATASET_CONFIG)

        # Accumulate statistics and print out
        for key in end_points:
            if 'loss' in key or 'acc' in key or 'ratio' in key:
                if key not in stat_dict: stat_dict[key] = 0
                stat_dict[key] += end_points[key].item()

        batch_pred_map_cls = parse_predictions(end_points, CONFIG_DICT)
        batch_gt_map_cls = parse_groundtruths(end_points, CONFIG_DICT)
        for ap_calculator in ap_calculator_list:
            ap_calculator.step(batch_pred_map_cls, batch_gt_map_cls)

        ######## Saving data ########
        save_dir = '/home/sirdome/katefgroup/language_grounding/mlcvnet_dump'

        # INPUT
        point_clouds = end_points['point_clouds'].cpu().numpy()
        batch_size = point_clouds.shape[0]

        # NETWORK OUTPUTS
        seed_xyz = end_points['seed_xyz'].detach().cpu().numpy(
        )  # (B,num_seed,3)
        if 'vote_xyz' in end_points:
            aggregated_vote_xyz = end_points['aggregated_vote_xyz'].detach(
            ).cpu().numpy()
            vote_xyz = end_points['vote_xyz'].detach().cpu().numpy(
            )  # (B,num_seed,3)
            aggregated_vote_xyz = end_points['aggregated_vote_xyz'].detach(
            ).cpu().numpy()
        objectness_scores = end_points['objectness_scores'].detach().cpu(
        ).numpy()  # (B,K,2)
        pred_center = end_points['center'].detach().cpu().numpy()  # (B,K,3)
        pred_heading_class = torch.argmax(end_points['heading_scores'],
                                          -1)  # B,num_proposal
        pred_heading_residual = torch.gather(
            end_points['heading_residuals'], 2,
            pred_heading_class.unsqueeze(-1))  # B,num_proposal,1
        pred_heading_class = pred_heading_class.detach().cpu().numpy(
        )  # B,num_proposal
        pred_heading_residual = pred_heading_residual.squeeze(
            2).detach().cpu().numpy()  # B,num_proposal
        pred_size_class = torch.argmax(end_points['size_scores'],
                                       -1)  # B,num_proposal
        pred_size_residual = torch.gather(
            end_points['size_residuals'], 2,
            pred_size_class.unsqueeze(-1).unsqueeze(-1).repeat(
                1, 1, 1, 3))  # B,num_proposal,1,3
        pred_size_residual = pred_size_residual.squeeze(
            2).detach().cpu().numpy()  # B,num_proposal,3

        # OTHERS
        pred_mask = end_points['pred_mask']  # B,num_proposal
        idx_beg = 0
        pred_center_upright_camera = flip_axis_to_camera(pred_center)

        for i in range(batch_size):
            objectness_prob = softmax(objectness_scores[i, :, :])[:, 1]  # (K,)

            # Dump predicted bounding boxes
            if np.sum(objectness_prob > 0.5) > 0:
                num_proposal = pred_center.shape[1]
                sr3d_boxes = []
                for j in range(num_proposal):

                    heading_angle = CONFIG_DICT['dataset_config'].class2angle(\
                        pred_heading_class[i,j], pred_heading_residual[i,j])
                    box_size = CONFIG_DICT['dataset_config'].class2size(\
                        int(pred_size_class[i,j]), pred_size_residual[i,j])

                    corners_3d_upright_camera = get_3d_box(
                        box_size, heading_angle,
                        pred_center_upright_camera[i, j, :])
                    box3d = corners_3d_upright_camera
                    box3d = flip_axis_to_depth(box3d)

                    sr3d_box = _convert_all_corners_to_end_points(box3d)
                    # sr3d_box = convert_mlcvnetbox_to_sr3d(DATASET_CONFIG, pred_center[i,j,0:3],
                    # pred_size_class[i,j], pred_size_residual[i,j])
                    sr3d_boxes.append(sr3d_box)

                if len(sr3d_boxes) > 0:
                    sr3d_boxes = np.vstack(
                        tuple(sr3d_boxes))  # (num_proposal, 6)
                    # Output boxes according to their semantic labels
                    pred_sem_cls = torch.argmax(end_points['sem_cls_scores'],
                                                -1)  # B,num_proposal
                    pred_sem_cls = pred_sem_cls.detach().cpu().numpy()
                    mask = np.logical_and(objectness_prob > 0.5,
                                          pred_mask[i, :] == 1)
                    sr3d_boxes = sr3d_boxes[mask, :]

                sr3d_boxes = list(sr3d_boxes)

            scan_name = scan_name_list[i]
            class_label_list = [
                DATASET_CONFIG.class2type[p[0]] for p in batch_pred_map_cls[i]
            ]

            print(len(class_label_list))

            assert (len(sr3d_boxes) == len(class_label_list))

            data_dict = {
                "class": class_label_list,
                "box": sr3d_boxes,
                "pc": point_clouds[i]
            }

            np.save(f'{save_dir}/{scan_name}.npy', data_dict)

    # Log statistics
    for key in sorted(stat_dict.keys()):
        log_string('eval mean %s: %f' % (key, stat_dict[key] /
                                         (float(batch_idx + 1))))

    # Evaluate average precision
    for i, ap_calculator in enumerate(ap_calculator_list):
        print('-' * 10, 'iou_thresh: %f' % (AP_IOU_THRESHOLDS[i]), '-' * 10)
        metrics_dict = ap_calculator.compute_metrics()
        for key in metrics_dict:
            log_string('eval %s: %f' % (key, metrics_dict[key]))

    mean_loss = stat_dict['loss'] / float(batch_idx + 1)
    return mean_loss