OpenCV Python cv2.perspectiveTransform

В настоящее время я пытаюсь стабилизировать видео с помощью OpenCV и Python. Я использую следующую функцию для расчета вращения:

def accumulate_rotation(src, theta_x, theta_y, theta_z, timestamps, prev, current, f, gyro_delay=None, gyro_drift=None, shutter_duration=None):
    if prev == current:
        return src

    pts = []
    pts_transformed = []
    for x in range(10):
        current_row = []
        current_row_transformed = []
        pixel_x = x * (src.shape[1] / 10)
        for y in range(10):
            pixel_y = y * (src.shape[0] / 10)
            current_row.append([pixel_x, pixel_y])

            if shutter_duration:
                y_timestamp = current + shutter_duration * (pixel_y - src.shape[0] / 2)
            else:
                y_timestamp = current

            transform = getAccumulatedRotation(src.shape[1], src.shape[0], theta_x, theta_y, theta_z, timestamps, prev,
                                               current, f, gyro_delay, gyro_drift)

            output = cv2.perspectiveTransform(np.array([[pixel_x, pixel_y]], dtype="float32"), transform)
            current_row_transformed.append(output)

        pts.append(current_row)
        pts_transformed.append(current_row_transformed)

    o = utilities.meshwarp(src, pts_transformed)
    return o

Я получаю следующую ошибку, когда дело доходит до output = cv2.perspectiveTransform(np.array([[pixel_x, pixel_y]], dtype="float32"), transform):

cv2.error: /Users/travis/build/skvark/opencv-python/opencv/modules/core/src/matmul.cpp:2271: error: (-215) scn + 1 == m.cols in function perspectiveTransform

Любая помощь или предложения будут действительно оценены.

1 ответ

Решение

Эта реализация действительно должна быть изменена в будущей версии.

Из документов OpenCV для perspectiveTransform():

src - входной двухканальный (...) массив с плавающей точкой

Косой акцент добавлен мной.

>>> A = np.array([[0, 0]], dtype=np.float32)
>>> A.shape
(1, 2)

Итак, мы видим отсюда, что A это просто одноканальная матрица, то есть двумерная. Один ряд, два кол. Вместо этого вам нужно двухканальное изображение, то есть трехмерная матрица, где длина третьего измерения равна 2 или 3, в зависимости от того, отправляете ли вы в 2D или 3D точках.

Короче говоря, вам нужно добавить еще один набор скобок, чтобы сделать набор точек, которые вы отправляете в трехмерном, где x значения находятся в первом канале, а y значения находятся во втором канале.

>>> A = np.array([[[0, 0]]], dtype=np.float32)
>>> A.shape
(1, 1, 2)

Это не интуитивно, и хотя это задокументировано, это не очень ясно по этому вопросу. Это все, что вам нужно. Я уже отвечал на такой же вопрос раньше, но для cv2.transform() функция.

Другие вопросы по тегам