def yolo2bb(annotations_path, images_dir, file_obj_names, bb_type=BBType.GROUND_TRUTH):
    ret = []
    if not os.path.isfile(file_obj_names):
        print(f'Warning: File with names of classes {file_obj_names} not found.')
        return ret
    # Load classes
    all_classes = []
    with open(file_obj_names, "r") as f:
        all_classes = [line.replace('\n', '') for line in f]
    # Get annotation files in the path
    annotation_files = _get_annotation_files(annotations_path)
    # Loop through each file
    for file_path in annotation_files:
        if not validations.is_yolo_format(file_path, bb_types=[bb_type]):
            continue
        img_name = os.path.basename(file_path)
        img_file = general_utils.find_file(images_dir, img_name, match_extension=False)
        img_resolution = general_utils.get_image_resolution(img_file)
        if img_resolution is None:
            print(f'Warning: It was not possible to find the resolution of image {img_name}')
            continue
        img_size = (img_resolution['width'], img_resolution['height'])
        # Loop through lines
        with open(file_path, "r") as f:
            for line in f:
                splitted_line = line.split(' ')
                class_id = splitted_line[0]
                if not general_utils.is_str_int(class_id):
                    print(
                        f'Warning: Class id represented in the {file_path} is not a valid integer.')
                    return []
                class_id = int(class_id)
                if class_id not in range(len(all_classes)):
                    print(
                        f'Warning: Class id represented in the {file_path} is not in the range of classes specified in the file {file_obj_names}.'
                    )
                    return []
                if bb_type == BBType.GROUND_TRUTH:
                    confidence = None
                    x1 = float(splitted_line[1])
                    y1 = float(splitted_line[2])
                    w = float(splitted_line[3])
                    h = float(splitted_line[4])
                elif bb_type == BBType.DETECTED:
                    confidence = float(splitted_line[1])
                    x1 = float(splitted_line[2])
                    y1 = float(splitted_line[3])
                    w = float(splitted_line[4])
                    h = float(splitted_line[5])
                bb = BoundingBox(image_name=general_utils.get_file_name_only(img_file),
                                 class_id=all_classes[class_id],
                                 coordinates=(x1, y1, w, h),
                                 img_size=img_size,
                                 confidence=confidence,
                                 type_coordinates=CoordinatesType.RELATIVE,
                                 bb_type=bb_type,
                                 format=BBFormat.XYWH)
                ret.append(bb)
    return ret
Beispiel #2
0
def openimage2bb(annotations_path, images_dir, bb_type=BBType.GROUND_TRUTH):
    ret = []
    # Get annotation files in the path
    annotation_files = _get_annotation_files(annotations_path)
    # Loop through each file
    for file_path in annotation_files:
        if not validations.is_openimage_format(file_path):
            continue
        images_shapes = {}
        # Open csv
        csv = pd.read_csv(file_path, sep=',')
        for i, row in csv.iterrows():
            # Get image resolution if it was not loaded yet
            if row['ImageID'] not in images_shapes:
                img_name = row['ImageID']
                image_file = general_utils.find_file(images_dir, img_name)
                images_shapes[image_file] = general_utils.get_image_resolution(
                    image_file)
            if images_shapes[image_file] is None:
                print(
                    f'Warning: It was not possible to find the resolution of image {img_name}'
                )
                continue
            # Three is no bounding box for the given image
            if pd.isna(row['LabelName']) or pd.isna(row['XMin']) or pd.isna(
                    row['XMax']) or pd.isna(row['YMin']) or pd.isna(
                        row['YMax']):
                continue
                # images_shapes[image_file] = general_utils.get_image_resolution(image_file)
            img_size = (images_shapes[image_file]['width'],
                        images_shapes[image_file]['height'])
            x1, x2, y1, y2 = (row['XMin'], row['XMax'], row['YMin'],
                              row['YMax'])
            x1 = x1.replace(',', '.') if isinstance(x1, str) else x1
            x2 = x2.replace(',', '.') if isinstance(x2, str) else x2
            y1 = y1.replace(',', '.') if isinstance(y1, str) else y1
            y2 = y2.replace(',', '.') if isinstance(y2, str) else y2
            x1, x2, y1, y2 = float(x1), float(x2), float(y1), float(y2)
            confidence = None if pd.isna(row['Confidence']) else float(
                row['Confidence'])
            if bb_type == BBType.DETECTED and confidence is None:
                print(
                    f'Warning: Confidence value found in the CSV file for the image {img_name}'
                )
                return ret
            bb = BoundingBox(image_name=general_utils.get_file_name_only(
                row['ImageID']),
                             class_id=row['LabelName'],
                             coordinates=(x1, y1, x2, y2),
                             img_size=img_size,
                             confidence=confidence,
                             type_coordinates=CoordinatesType.RELATIVE,
                             bb_type=bb_type,
                             format=BBFormat.XYX2Y2)
            ret.append(bb)
    return ret
Beispiel #3
0
def text2bb(annotations_path,
            bb_type=BBType.GROUND_TRUTH,
            bb_format=BBFormat.XYWH,
            type_coordinates=CoordinatesType.ABSOLUTE,
            img_dir=None):
    ret = []

    # Get annotation files in the path
    annotation_files = _get_annotation_files(annotations_path)
    for file_path in annotation_files:
        if type_coordinates == CoordinatesType.ABSOLUTE:
            if bb_type == BBType.GROUND_TRUTH and not validations.is_absolute_text_format(
                    file_path, num_blocks=[5], blocks_abs_values=[4]):
                continue
            if bb_type == BBType.DETECTED and not validations.is_absolute_text_format(
                    file_path, num_blocks=[6], blocks_abs_values=[4]):
                continue
        elif type_coordinates == CoordinatesType.RELATIVE:
            if bb_type == BBType.GROUND_TRUTH and not validations.is_relative_text_format(
                    file_path, num_blocks=[5], blocks_rel_values=[4]):
                continue
            if bb_type == BBType.DETECTED and not validations.is_relative_text_format(
                    file_path, num_blocks=[6], blocks_rel_values=[4]):
                continue
        # Loop through lines
        with open(file_path, "r") as f:

            img_filename = os.path.basename(file_path)
            img_filename = os.path.splitext(img_filename)[0]

            img_size = None
            # If coordinates are relative, image size must be obtained in the img_dir
            if type_coordinates == CoordinatesType.RELATIVE:
                img_path = general_utils.find_file(img_dir,
                                                   img_filename,
                                                   match_extension=False)
                if img_path is None or os.path.isfile(img_path) is False:
                    print(
                        f'Warning: Image not found in the directory {img_path}. It is required to get its dimensions'
                    )
                    return ret
                resolution = general_utils.get_image_resolution(img_path)
                img_size = (resolution['width'], resolution['height'])
            for line in f:
                if line.replace(' ', '') == '\n':
                    continue
                splitted_line = line.split(' ')
                class_id = splitted_line[0]
                if bb_type == BBType.GROUND_TRUTH:
                    confidence = None
                    x1 = float(splitted_line[1])
                    y1 = float(splitted_line[2])
                    w = float(splitted_line[3])
                    h = float(splitted_line[4])
                elif bb_type == BBType.DETECTED:
                    confidence = float(splitted_line[1])
                    x1 = float(splitted_line[2])
                    y1 = float(splitted_line[3])
                    w = float(splitted_line[4])
                    h = float(splitted_line[5])
                bb = BoundingBox(image_name=img_filename,
                                 class_id=class_id,
                                 coordinates=(x1, y1, w, h),
                                 img_size=img_size,
                                 confidence=confidence,
                                 type_coordinates=type_coordinates,
                                 bb_type=bb_type,
                                 format=bb_format)
                # If the format is correct, x,y,w,h,x2,y2 must be positive
                x, y, w, h = bb.get_absolute_bounding_box(format=BBFormat.XYWH)
                _, _, x2, y2 = bb.get_absolute_bounding_box(
                    format=BBFormat.XYX2Y2)
                if x < 0 or y < 0 or w < 0 or h < 0 or x2 < 0 or y2 < 0:
                    continue
                ret.append(bb)
    return ret