python - Drawing line between hand landmarks - Stack Overflow

here is my code thatdraws landmarks on hand using mediapipeimport cv2import timeimport mediapipe a

here is my code that draws landmarks on hand using mediapipe

import cv2
import time
import mediapipe as mp

mp_holistic = mp.solutions.holistic

holistic_model = mp_holistic.Holistic(
    min_detection_confidence=0.5,
    min_tracking_confidence=0.5
)

# Initializing the drawing utils for drawing the facial landmarks on image
mp_drawing = mp.solutions.drawing_utils

# (0) in VideoCapture is used to connect to your computer's default camera
capture = cv2.VideoCapture(0)

# Initializing current time and precious time for calculating the FPS
previousTime = 0
currentTime = 0

while capture.isOpened():
    # capture frame by frame
    ret, frame = capture.read()

    # resizing the frame for better view
    frame = cv2.resize(frame, (800, 600))

    # Converting the from BGR to RGB
    image = cv2.cvtColor(frame, cv2.COLOR_BGR2RGB)

    # Making predictions using holistic model
    # To improve performance, optionally mark the image as not writeable to
    # pass by reference.
    image.flags.writeable = False
    results = holistic_model.process(image)
    image.flags.writeable = True

    # Converting back the RGB image to BGR
    image = cv2.cvtColor(image, cv2.COLOR_RGB2BGR)

    # Drawing the Facial Landmarks
    # mp_drawing.draw_landmarks(
    #     image,
    #     results.face_landmarks,
    #     mp_holistic.FACEMESH_CONTOURS,
    #     mp_drawing.DrawingSpec(
    #         color=(255, 0, 255),
    #         thickness=1,
    #         circle_radius=1
    #     ),
    #     mp_drawing.DrawingSpec(
    #         color=(0, 255, 255),
    #         thickness=1,
    #         circle_radius=1
    #     )
    # )

    # Drawing Right hand Land Marks
    mp_drawing.draw_landmarks(
        image,
        results.right_hand_landmarks,
        mp_holistic.HAND_CONNECTIONS
    )
    for landmark in mp_holistic.HandLandmark:
        print(landmark,landmark.value)

    # Drawing Left hand Land Marks
    mp_drawing.draw_landmarks(
        image,
        results.left_hand_landmarks,
        mp_holistic.HAND_CONNECTIONS
    )

    # Calculating the FPS
    currentTime = time.time()
    fps = 1 / (currentTime - previousTime)
    previousTime = currentTime

    # Displaying FPS on the image
    cv2.putText(image, str(int(fps)) + " FPS", (10, 70), cv2.FONT_HERSHEY_COMPLEX, 1, (0, 255, 0), 2)

    # Display the resulting image
    cv2.imshow("Facial and Hand Landmarks", image)

    # Enter key 'q' to break the loop
    if cv2.waitKey(5) & 0xFF == ord('q'):
        break

# When all the process is done
# Release the capture and destroy all windows
capture.release()
cv2.destroyAllWindows()

for both left and right hand, but my goal is : to draw straight line between hand, in order to understand my question, let us discuess following image :

from the figure we can say for instance that line between hands should be perfectly horizontan (so angle should be zero, as if we consider following equation :

it is easy to say that in order to be perfectly horizontal lines , y coordinates should be equal to each other, so please help me to detect how to determine coordinates and how to draw line between two point? drawing is easy as cv2.line exist, but what about coordinates?

here is my code that draws landmarks on hand using mediapipe

import cv2
import time
import mediapipe as mp

mp_holistic = mp.solutions.holistic

holistic_model = mp_holistic.Holistic(
    min_detection_confidence=0.5,
    min_tracking_confidence=0.5
)

# Initializing the drawing utils for drawing the facial landmarks on image
mp_drawing = mp.solutions.drawing_utils

# (0) in VideoCapture is used to connect to your computer's default camera
capture = cv2.VideoCapture(0)

# Initializing current time and precious time for calculating the FPS
previousTime = 0
currentTime = 0

while capture.isOpened():
    # capture frame by frame
    ret, frame = capture.read()

    # resizing the frame for better view
    frame = cv2.resize(frame, (800, 600))

    # Converting the from BGR to RGB
    image = cv2.cvtColor(frame, cv2.COLOR_BGR2RGB)

    # Making predictions using holistic model
    # To improve performance, optionally mark the image as not writeable to
    # pass by reference.
    image.flags.writeable = False
    results = holistic_model.process(image)
    image.flags.writeable = True

    # Converting back the RGB image to BGR
    image = cv2.cvtColor(image, cv2.COLOR_RGB2BGR)

    # Drawing the Facial Landmarks
    # mp_drawing.draw_landmarks(
    #     image,
    #     results.face_landmarks,
    #     mp_holistic.FACEMESH_CONTOURS,
    #     mp_drawing.DrawingSpec(
    #         color=(255, 0, 255),
    #         thickness=1,
    #         circle_radius=1
    #     ),
    #     mp_drawing.DrawingSpec(
    #         color=(0, 255, 255),
    #         thickness=1,
    #         circle_radius=1
    #     )
    # )

    # Drawing Right hand Land Marks
    mp_drawing.draw_landmarks(
        image,
        results.right_hand_landmarks,
        mp_holistic.HAND_CONNECTIONS
    )
    for landmark in mp_holistic.HandLandmark:
        print(landmark,landmark.value)

    # Drawing Left hand Land Marks
    mp_drawing.draw_landmarks(
        image,
        results.left_hand_landmarks,
        mp_holistic.HAND_CONNECTIONS
    )

    # Calculating the FPS
    currentTime = time.time()
    fps = 1 / (currentTime - previousTime)
    previousTime = currentTime

    # Displaying FPS on the image
    cv2.putText(image, str(int(fps)) + " FPS", (10, 70), cv2.FONT_HERSHEY_COMPLEX, 1, (0, 255, 0), 2)

    # Display the resulting image
    cv2.imshow("Facial and Hand Landmarks", image)

    # Enter key 'q' to break the loop
    if cv2.waitKey(5) & 0xFF == ord('q'):
        break

# When all the process is done
# Release the capture and destroy all windows
capture.release()
cv2.destroyAllWindows()

for both left and right hand, but my goal is : to draw straight line between hand, in order to understand my question, let us discuess following image :

from the figure we can say for instance that line between hands should be perfectly horizontan (so angle should be zero, as if we consider following equation :

it is easy to say that in order to be perfectly horizontal lines , y coordinates should be equal to each other, so please help me to detect how to determine coordinates and how to draw line between two point? drawing is easy as cv2.line exist, but what about coordinates?

Share Improve this question edited Mar 3 at 15:04 Christoph Rackwitz 15.9k5 gold badges39 silver badges51 bronze badges asked Mar 3 at 12:18 rain snowrain snow 294 bronze badges
Add a comment  | 

2 Answers 2

Reset to default 3

You're using the built-in Mediapipe function draw_landmarks to handle all the drawings. This function takes an image, a normalized landmark list, and connections as inputs. However, the NormalizedLandmarkList type in Mediapipe doesn’t support merging multiple landmark lists, making it difficult to pass landmarks for both hands to the function and find connections.

An alternative approach is to extract the coordinates from the hand landmarks and draw a line using the cv2.line method, as you mentioned. Here’s the code to implement this approach:

    # extract hand landmarks from mediapipe result
    right_hand_landmarks = results.right_hand_landmarks
    left_hand_landmarks = results.left_hand_landmarks
    
    # try to render a line if both hands are detected
    if right_hand_landmarks and left_hand_landmarks:
    
        # find the position of wrist landmark (as it is normalized, it should multiplied by width and height for x and y respectively)
        right_wrist = np.array([right_hand_landmarks.landmark[0].x * image.shape[1], right_hand_landmarks.landmark[0].y * image.shape[0]]).astype("int")
        left_wrist = np.array([left_hand_landmarks.landmark[0].x * image.shape[1], left_hand_landmarks.landmark[0].y * image.shape[0]]).astype("int")
        
        # draw a line between two wrists
        cv2.line(image, right_wrist, left_wrist, color=(255,255,255), thickness=3)

If you want to select another landmark other than the wrist, check this link to see landmark indices.

We can try decreasing the confidence threshold too, e.g., if hands are not detected due to low confidence (although it increases the risk of false positives). Also, from here note the hand keypoints:

Left hand and right hand positions can be roughly computed by mean location of these keypoints. and from here, since 'NormalizedLandmarkList' object is not iterable mediapipe, we need to access the landmarks using results.left_hand_landmarks.landmark . Also, as mentioned by @Milad, the coordinates are normalized and have values in the range [0,1], so we need to scale by image size properly. Putting all these together, we can use the following code to detect the hand landmarks and draw line between the hands:

import cv2
import time
import mediapipe as mp

mp_holistic = mp.solutions.holistic
holistic_model = mp_holistic.Holistic(
    min_detection_confidence=0.3, # adjust the confidence thresholds
    min_tracking_confidence=0.4 # adjust the confidence thresholds
)

# Initializing the drawing utils for drawing the facial landmarks on image
mp_drawing = mp.solutions.drawing_utils

# (0) in VideoCapture is used to connect to your computer's default camera
capture = cv2.VideoCapture('wtlft.mp4') # the input video
output = cv2.VideoWriter("output.mp4", cv2.VideoWriter_fourcc(*'mp4v'), capture.get(cv2.CAP_PROP_FPS), (800, 600)) # the output video

# Initializing current time and precious time for calculating the FPS
previousTime = 0
currentTime = 0

while capture.isOpened():
    # capture frame by frame
    ret, frame = capture.read()
    if not ret:
        break
    # resizing the frame for better view
    frame = cv2.resize(frame, (800, 600))
    # Converting the from BGR to RGB
    image = cv2.cvtColor(frame, cv2.COLOR_BGR2RGB)
    
    # Making predictions using holistic model
    # To improve performance, optionally mark the image as not writeable to
    # pass by reference.
    image.flags.writeable = False
    results = holistic_model.process(image)
    image.flags.writeable = True
    
    # Converting back the RGB image to BGR
    image = cv2.cvtColor(image, cv2.COLOR_RGB2BGR)
    
    # Drawing Right hand Land Marks
    mp_drawing.draw_landmarks(
        image,
        results.right_hand_landmarks,
        mp_holistic.HAND_CONNECTIONS
    )
    
    # Drawing Left hand Land Marks
    mp_drawing.draw_landmarks(
        image,
        results.left_hand_landmarks,
        mp_holistic.HAND_CONNECTIONS
    )
    
    # Calculating the FPS
    currentTime = time.time()
    fps = 1 / (currentTime - previousTime)
    previousTime = currentTime
    
    # Displaying FPS on the image
    cv2.putText(image, str(int(fps)) + " FPS", (10, 70), \
                       cv2.FONT_HERSHEY_COMPLEX, 1, (0, 255, 0), 2)
    lh, rh = results.left_hand_landmarks, results.right_hand_landmarks
    if lh and rh: # if both hands detected
        x_l = int(np.mean([p.x for p in lh.landmark]) * image.shape[1])
        y_l = int(np.mean([p.y for p in lh.landmark]) * image.shape[0])
        x_r = int(np.mean([p.x for p in rh.landmark]) * image.shape[1])
        y_r  = int(np.mean([p.y for p in rh.landmark]) * image.shape[0])
        # draw line
        cv2.line(image, (x_l, y_l), (x_r, y_r), (0, 255, 0), 9)             
    
    # write the frame
    output.write(image) 
    
output.release() 
capture.release() 

发布者:admin,转转请注明出处:http://www.yc00.com/questions/1745095125a4610930.html

相关推荐

  • python - Drawing line between hand landmarks - Stack Overflow

    here is my code thatdraws landmarks on hand using mediapipeimport cv2import timeimport mediapipe a

    16小时前
    10

发表回复

评论列表(0条)

  • 暂无评论

联系我们

400-800-8888

在线咨询: QQ交谈

邮件:admin@example.com

工作时间:周一至周五,9:30-18:30,节假日休息

关注微信