(Mediapipe pose estimation) TypeError: type list doesn't define __round__ method

(Mediapipe pose estimation) TypeError: type list doesn't define __round__ method

我正在尝试将归一化坐标转换为像素坐标

因为 mediapipe 使用归一化坐标,而 mouse.move 使用像素坐标

但它一直给我这个错误:TypeError: type list doesn't define round method

import cv2
import mediapipe as mp
import numpy as np
import time
import pyautogui
import mouse

mp_drawing = mp.solutions.drawing_utils
mp_pose = mp.solutions.pose


# display screen resolution, get it from your OS settings
SCREEN_SIZEX = (1920)
SCREEN_SIZEY = (1080)
# define the codec
fourcc = cv2.VideoWriter_fourcc(*"XVID")
# create the video write object
out = cv2.VideoWriter("output.avi", fourcc, 20.0, (SCREEN_SIZEX, SCREEN_SIZEY))

with mp_pose.Pose(min_detection_confidence=0.1, min_tracking_confidence=0.9) as pose:
    while True:
        # make a screenshot
        img = pyautogui.screenshot()
        # convert these pixels to a proper numpy array to work with OpenCV
        frame = np.array(img)
        # convert colors from BGR to RGB
        frame = cv2.cvtColor(frame, cv2.COLOR_BGR2RGB)
        # Recolor image to RGB
        image = cv2.cvtColor(frame, cv2.COLOR_BGR2RGB)
        image.flags.writeable = False

        # Make detection
        results = pose.process(image)

        # Recolor back to BGR
        image.flags.writeable = True
        image = cv2.cvtColor(image, cv2.COLOR_RGB2BGR)


        landmarks = results.pose_landmarks.landmark
        lndmark = landmarks[mp_pose.PoseLandmark.NOSE.value]
        x = [landmarks[mp_pose.PoseLandmark.NOSE.value].x]
        y = [landmarks[mp_pose.PoseLandmark.NOSE.value].y]

        #xx = ''.join(str(e) for e in x)
        #yy = ''.join(str(e) for e in y)

        #xx = [int(i) for i in xx]
        #yy = [int(i) for i in yy]

        test_coord = (x, y)

        SCREEN_DIMENSIONS = (1920, 1080)


        def to_pixel_coords(relative_coords):
            return tuple(round(coord * dimension) for coord, dimension in zip(relative_coords, SCREEN_DIMENSIONS))


        print(to_pixel_coords(test_coord))




        #print(xxx)
        #print(yyy)

        #mouse.move(xxx, yyy)


        # Render detections
        mp_drawing.draw_landmarks(image, results.pose_landmarks, mp_pose.POSE_CONNECTIONS,
                                mp_drawing.DrawingSpec(color=(245,117,66), thickness=2, circle_radius=2),
                                mp_drawing.DrawingSpec(color=(245,66,230), thickness=2, circle_radius=2)
                                 )

        # write the frame
        out.write(frame)

        pTime = 0

        cTime = time.time()
        fps = 1 / (cTime - pTime)
        pTime = cTime
        cv2.putText(image, str(int(fps)), (20, 50), cv2.FONT_HERSHEY_PLAIN, 3,
        (255, 0, 0), 3)



        cv2.imshow('Mediapipe Feed', image)

        if cv2.waitKey(10) & 0xFF == ord('q'):
            break

    out.release()
    cv2.destroyAllWindows()


    #for lndmark in mp_pose.PoseLandmark:
        #print(lndmark)

我试过将它转换为字符串或元组,但它给了我同样的错误:

TypeError: type string doesn't define __round__ method
TypeError: type tuple doesn't define __round__ method

我假设您需要将其转换为 int,但我不知道该怎么做

所以我希望有人能帮助

看到这两行代码了吗?

        x = [landmarks[mp_pose.PoseLandmark.NOSE.value].x]
        y = [landmarks[mp_pose.PoseLandmark.NOSE.value].y]

请注意,它们将作为列表返回。所以在你的函数中...

        def to_pixel_coords(relative_coords):
            return tuple(round(coord * dimension) for coord, dimension in zip(relative_coords, SCREEN_DIMENSIONS))

...列表乘以数字。这样做的输出是另一个列表,原始列表按数字重复。这就是您最终尝试四舍五入列表的方式。

我建议将第一个代码片段更改为:

        x = landmarks[mp_pose.PoseLandmark.NOSE.value].x
        y = landmarks[mp_pose.PoseLandmark.NOSE.value].y

或者这个:

        x = float(landmarks[mp_pose.PoseLandmark.NOSE.value].x)
        y = float(landmarks[mp_pose.PoseLandmark.NOSE.value].y)