Skip to content

Crop functional transforms (augmentations.crops.functional)

def crop_and_pad_keypoints (keypoints, crop_params=None, pad_params=None, image_shape=(0, 0), result_shape=(0, 0), keep_size=False) [view source on GitHub]

Crop and pad multiple keypoints simultaneously.

Parameters:

Name Type Description
keypoints np.ndarray

Array of keypoints with shape (N, 4+) where each row is (x, y, angle, scale, ...).

crop_params Sequence[int]

Crop parameters [crop_x1, crop_y1, ...].

pad_params Sequence[int]

Pad parameters [top, bottom, left, right].

image_shape Tuple[int, int]

Original image shape (rows, cols).

result_shape Tuple[int, int]

Result image shape (rows, cols).

keep_size bool

Whether to keep the original size.

Returns:

Type Description
np.ndarray

Array of transformed keypoints with the same shape as input.

Source code in albumentations/augmentations/crops/functional.py
Python
@handle_empty_array("keypoints")
def crop_and_pad_keypoints(
    keypoints: np.ndarray,
    crop_params: tuple[int, int, int, int] | None = None,
    pad_params: tuple[int, int, int, int] | None = None,
    image_shape: tuple[int, int] = (0, 0),
    result_shape: tuple[int, int] = (0, 0),
    keep_size: bool = False,
) -> np.ndarray:
    """Crop and pad multiple keypoints simultaneously.

    Args:
        keypoints (np.ndarray): Array of keypoints with shape (N, 4+) where each row is (x, y, angle, scale, ...).
        crop_params (Sequence[int], optional): Crop parameters [crop_x1, crop_y1, ...].
        pad_params (Sequence[int], optional): Pad parameters [top, bottom, left, right].
        image_shape (Tuple[int, int]): Original image shape (rows, cols).
        result_shape (Tuple[int, int]): Result image shape (rows, cols).
        keep_size (bool): Whether to keep the original size.

    Returns:
        np.ndarray: Array of transformed keypoints with the same shape as input.
    """
    transformed_keypoints = keypoints.copy()

    if crop_params is not None:
        crop_x1, crop_y1 = crop_params[:2]
        transformed_keypoints[:, 0] -= crop_x1
        transformed_keypoints[:, 1] -= crop_y1

    if pad_params is not None:
        top, _, left, _ = pad_params
        transformed_keypoints[:, 0] += left
        transformed_keypoints[:, 1] += top

    rows, cols = image_shape[:2]
    result_rows, result_cols = result_shape[:2]

    if keep_size and (result_cols != cols or result_rows != rows):
        scale_x = cols / result_cols
        scale_y = rows / result_rows
        return fgeometric.keypoints_scale(transformed_keypoints, scale_x, scale_y)

    return transformed_keypoints

def crop_bboxes_by_coords (bboxes, crop_coords, image_shape, normalized_input=True) [view source on GitHub]

Crop bounding boxes based on given crop coordinates.

This function adjusts bounding boxes to fit within a cropped image.

Parameters:

Name Type Description
bboxes np.ndarray

Array of bounding boxes with shape (N, 4+) where each row is [x_min, y_min, x_max, y_max, ...]. The bounding box coordinates can be either normalized (in [0, 1]) if normalized_input=True or absolute pixel values if normalized_input=False.

crop_coords tuple[int, int, int, int]

Crop coordinates (x_min, y_min, x_max, y_max) in absolute pixel values.

image_shape tuple[int, int]

Original image shape (height, width).

normalized_input bool

Whether input boxes are in normalized coordinates. If True, assumes input is normalized [0,1] and returns normalized coordinates. If False, assumes input is in absolute pixels and returns absolute coordinates. Default: True for backward compatibility.

Returns:

Type Description
np.ndarray

Array of cropped bounding boxes. Coordinates will be in the same format as input (normalized if normalized_input=True, absolute pixels if normalized_input=False).

Note

Bounding boxes that fall completely outside the crop area will be removed. Bounding boxes that partially overlap with the crop area will be adjusted to fit within it.

Source code in albumentations/augmentations/crops/functional.py
Python
def crop_bboxes_by_coords(
    bboxes: np.ndarray,
    crop_coords: tuple[int, int, int, int],
    image_shape: tuple[int, int],
    normalized_input: bool = True,
) -> np.ndarray:
    """Crop bounding boxes based on given crop coordinates.

    This function adjusts bounding boxes to fit within a cropped image.

    Args:
        bboxes (np.ndarray): Array of bounding boxes with shape (N, 4+) where each row is
                             [x_min, y_min, x_max, y_max, ...]. The bounding box coordinates
                             can be either normalized (in [0, 1]) if normalized_input=True or
                             absolute pixel values if normalized_input=False.
        crop_coords (tuple[int, int, int, int]): Crop coordinates (x_min, y_min, x_max, y_max)
                                                 in absolute pixel values.
        image_shape (tuple[int, int]): Original image shape (height, width).
        normalized_input (bool): Whether input boxes are in normalized coordinates.
                               If True, assumes input is normalized [0,1] and returns normalized coordinates.
                               If False, assumes input is in absolute pixels and returns absolute coordinates.
                               Default: True for backward compatibility.

    Returns:
        np.ndarray: Array of cropped bounding boxes. Coordinates will be in the same format as input
                   (normalized if normalized_input=True, absolute pixels if normalized_input=False).

    Note:
        Bounding boxes that fall completely outside the crop area will be removed.
        Bounding boxes that partially overlap with the crop area will be adjusted to fit within it.
    """
    if not bboxes.size:
        return bboxes

    # Convert to absolute coordinates if needed
    if normalized_input:
        cropped_bboxes = denormalize_bboxes(bboxes.copy().astype(np.float32), image_shape)
    else:
        cropped_bboxes = bboxes.copy().astype(np.float32)

    x_min, y_min = crop_coords[:2]

    # Subtract crop coordinates
    cropped_bboxes[:, [0, 2]] -= x_min
    cropped_bboxes[:, [1, 3]] -= y_min

    # Calculate crop shape
    crop_height = crop_coords[3] - crop_coords[1]
    crop_width = crop_coords[2] - crop_coords[0]
    crop_shape = (crop_height, crop_width)

    # Return in same format as input
    return normalize_bboxes(cropped_bboxes, crop_shape) if normalized_input else cropped_bboxes

def crop_keypoints_by_coords (keypoints, crop_coords) [view source on GitHub]

Crop keypoints using the provided coordinates of bottom-left and top-right corners in pixels.

Parameters:

Name Type Description
keypoints np.ndarray

An array of keypoints with shape (N, 4+) where each row is (x, y, angle, scale, ...).

crop_coords tuple

Crop box coords (x1, y1, x2, y2).

Returns:

Type Description
np.ndarray

An array of cropped keypoints with the same shape as the input.

Source code in albumentations/augmentations/crops/functional.py
Python
@handle_empty_array("keypoints")
def crop_keypoints_by_coords(
    keypoints: np.ndarray,
    crop_coords: tuple[int, int, int, int],
) -> np.ndarray:
    """Crop keypoints using the provided coordinates of bottom-left and top-right corners in pixels.

    Args:
        keypoints (np.ndarray): An array of keypoints with shape (N, 4+) where each row is (x, y, angle, scale, ...).
        crop_coords (tuple): Crop box coords (x1, y1, x2, y2).

    Returns:
        np.ndarray: An array of cropped keypoints with the same shape as the input.
    """
    x1, y1 = crop_coords[:2]

    cropped_keypoints = keypoints.copy()
    cropped_keypoints[:, 0] -= x1  # Adjust x coordinates
    cropped_keypoints[:, 1] -= y1  # Adjust y coordinates

    return cropped_keypoints