289 lines
9.1 KiB
Plaintext
289 lines
9.1 KiB
Plaintext
{
|
|
"cells": [
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {
|
|
"id": "h2q27gKz1H20"
|
|
},
|
|
"source": [
|
|
"##### Copyright 2023 The MediaPipe Authors. All Rights Reserved."
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"metadata": {
|
|
"id": "TUfAcER1oUS6"
|
|
},
|
|
"outputs": [],
|
|
"source": [
|
|
"#@title Licensed under the Apache License, Version 2.0 (the \"License\");\n",
|
|
"# you may not use this file except in compliance with the License.\n",
|
|
"# You may obtain a copy of the License at\n",
|
|
"#\n",
|
|
"# https://www.apache.org/licenses/LICENSE-2.0\n",
|
|
"#\n",
|
|
"# Unless required by applicable law or agreed to in writing, software\n",
|
|
"# distributed under the License is distributed on an \"AS IS\" BASIS,\n",
|
|
"# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n",
|
|
"# See the License for the specific language governing permissions and\n",
|
|
"# limitations under the License."
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {
|
|
"id": "L_cQX8dWu4Dv"
|
|
},
|
|
"source": [
|
|
"# Hand Landmarks Detection with MediaPipe Tasks\n",
|
|
"\n",
|
|
"This notebook shows you how to use MediaPipe Tasks Python API to detect hand landmarks from images."
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {
|
|
"id": "O6PN9FvIx614"
|
|
},
|
|
"source": [
|
|
"## Preparation\n",
|
|
"\n",
|
|
"Let's start with installing MediaPipe."
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"metadata": {
|
|
"id": "gxbHBsF-8Y_l"
|
|
},
|
|
"outputs": [],
|
|
"source": [
|
|
"!pip install -q mediapipe"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {
|
|
"id": "a49D7h4TVmru"
|
|
},
|
|
"source": [
|
|
"Then download an off-the-shelf model bundle. Check out the [MediaPipe documentation](https://developers.google.com/mediapipe/solutions/vision/hand_landmarker#models) for more information about this model bundle."
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"metadata": {
|
|
"id": "OMjuVQiDYJKF"
|
|
},
|
|
"outputs": [],
|
|
"source": [
|
|
"!wget -q https://storage.googleapis.com/mediapipe-models/hand_landmarker/hand_landmarker/float16/1/hand_landmarker.task"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {
|
|
"id": "YYKAJ5nDU8-I"
|
|
},
|
|
"source": [
|
|
"## Visualization utilities"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"metadata": {
|
|
"cellView": "form",
|
|
"id": "s3E6NFV-00Qt"
|
|
},
|
|
"outputs": [],
|
|
"source": [
|
|
"#@markdown We implemented some functions to visualize the hand landmark detection results. <br/> Run the following cell to activate the functions.\n",
|
|
"import mediapipe as mp\n",
|
|
"import numpy as np\n",
|
|
"\n",
|
|
"mp_hands = mp.tasks.vision.HandLandmarksConnections\n",
|
|
"mp_drawing = mp.tasks.vision.drawing_utils\n",
|
|
"mp_drawing_styles = mp.tasks.vision.drawing_styles\n",
|
|
"\n",
|
|
"MARGIN = 10 # pixels\n",
|
|
"FONT_SIZE = 1\n",
|
|
"FONT_THICKNESS = 1\n",
|
|
"HANDEDNESS_TEXT_COLOR = (88, 205, 54) # vibrant green\n",
|
|
"\n",
|
|
"def draw_landmarks_on_image(rgb_image, detection_result):\n",
|
|
" hand_landmarks_list = detection_result.hand_landmarks\n",
|
|
" handedness_list = detection_result.handedness\n",
|
|
" annotated_image = np.copy(rgb_image)\n",
|
|
"\n",
|
|
" # Loop through the detected hands to visualize.\n",
|
|
" for idx in range(len(hand_landmarks_list)):\n",
|
|
" hand_landmarks = hand_landmarks_list[idx]\n",
|
|
" handedness = handedness_list[idx]\n",
|
|
"\n",
|
|
" # Draw the hand landmarks.\n",
|
|
" mp_drawing.draw_landmarks(\n",
|
|
" annotated_image,\n",
|
|
" hand_landmarks,\n",
|
|
" mp_hands.HAND_CONNECTIONS,\n",
|
|
" mp_drawing_styles.get_default_hand_landmarks_style(),\n",
|
|
" mp_drawing_styles.get_default_hand_connections_style())\n",
|
|
"\n",
|
|
" # Get the top left corner of the detected hand's bounding box.\n",
|
|
" height, width, _ = annotated_image.shape\n",
|
|
" x_coordinates = [landmark.x for landmark in hand_landmarks]\n",
|
|
" y_coordinates = [landmark.y for landmark in hand_landmarks]\n",
|
|
" text_x = int(min(x_coordinates) * width)\n",
|
|
" text_y = int(min(y_coordinates) * height) - MARGIN\n",
|
|
"\n",
|
|
" # Draw handedness (left or right hand) on the image.\n",
|
|
" cv2.putText(annotated_image, f\"{handedness[0].category_name}\",\n",
|
|
" (text_x, text_y), cv2.FONT_HERSHEY_DUPLEX,\n",
|
|
" FONT_SIZE, HANDEDNESS_TEXT_COLOR, FONT_THICKNESS, cv2.LINE_AA)\n",
|
|
"\n",
|
|
" return annotated_image"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {
|
|
"id": "83PEJNp9yPBU"
|
|
},
|
|
"source": [
|
|
"## Download test image\n",
|
|
"\n",
|
|
"Let's grab a test image that we'll use later. The image is from [Unsplash](https://unsplash.com/photos/mt2fyrdXxzk)."
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"metadata": {
|
|
"id": "tzXuqyIBlXer"
|
|
},
|
|
"outputs": [],
|
|
"source": [
|
|
"!wget -q -O image.jpg https://storage.googleapis.com/mediapipe-tasks/hand_landmarker/woman_hands.jpg\n",
|
|
"\n",
|
|
"import cv2\n",
|
|
"from google.colab.patches import cv2_imshow\n",
|
|
"\n",
|
|
"img = cv2.imread(\"image.jpg\")\n",
|
|
"cv2_imshow(img)"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {
|
|
"id": "u-skLwMBmMN_"
|
|
},
|
|
"source": [
|
|
"Optionally, you can upload your own image. If you want to do so, uncomment and run the cell below."
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"metadata": {
|
|
"id": "etBjSdwImQPw"
|
|
},
|
|
"outputs": [],
|
|
"source": [
|
|
"# from google.colab import files\n",
|
|
"# uploaded = files.upload()\n",
|
|
"\n",
|
|
"# for filename in uploaded:\n",
|
|
"# content = uploaded[filename]\n",
|
|
"# with open(filename, 'wb') as f:\n",
|
|
"# f.write(content)\n",
|
|
"\n",
|
|
"# if len(uploaded.keys()):\n",
|
|
"# IMAGE_FILE = next(iter(uploaded))\n",
|
|
"# print('Uploaded file:', IMAGE_FILE)"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {
|
|
"id": "Iy4r2_ePylIa"
|
|
},
|
|
"source": [
|
|
"## Running inference and visualizing the results\n",
|
|
"\n",
|
|
"Here are the steps to run hand landmark detection using MediaPipe.\n",
|
|
"\n",
|
|
"Check out the [MediaPipe documentation](https://developers.google.com/mediapipe/solutions/vision/hand_landmarker/python) to learn more about configuration options that this solution supports.\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"metadata": {
|
|
"id": "_JVO3rvPD4RN"
|
|
},
|
|
"outputs": [],
|
|
"source": [
|
|
"# STEP 1: Import the necessary modules.\n",
|
|
"import mediapipe as mp\n",
|
|
"from mediapipe.tasks import python\n",
|
|
"from mediapipe.tasks.python import vision\n",
|
|
"\n",
|
|
"# STEP 2: Create an HandLandmarker object.\n",
|
|
"base_options = python.BaseOptions(model_asset_path='hand_landmarker.task')\n",
|
|
"options = vision.HandLandmarkerOptions(base_options=base_options,\n",
|
|
" num_hands=2)\n",
|
|
"detector = vision.HandLandmarker.create_from_options(options)\n",
|
|
"\n",
|
|
"# STEP 3: Load the input image.\n",
|
|
"image = mp.Image.create_from_file(\"image.jpg\")\n",
|
|
"\n",
|
|
"# STEP 4: Detect hand landmarks from the input image.\n",
|
|
"detection_result = detector.detect(image)\n",
|
|
"\n",
|
|
"# STEP 5: Process the classification result. In this case, visualize it.\n",
|
|
"annotated_image = draw_landmarks_on_image(image.numpy_view(), detection_result)\n",
|
|
"cv2_imshow(cv2.cvtColor(annotated_image, cv2.COLOR_RGB2BGR))"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"metadata": {
|
|
"id": "SE6_sPCXaX3g"
|
|
},
|
|
"outputs": [],
|
|
"source": []
|
|
}
|
|
],
|
|
"metadata": {
|
|
"colab": {
|
|
"collapsed_sections": [
|
|
"h2q27gKz1H20"
|
|
],
|
|
"provenance": []
|
|
},
|
|
"kernelspec": {
|
|
"display_name": "Python 3 (ipykernel)",
|
|
"language": "python",
|
|
"name": "python3"
|
|
},
|
|
"language_info": {
|
|
"codemirror_mode": {
|
|
"name": "ipython",
|
|
"version": 3
|
|
},
|
|
"file_extension": ".py",
|
|
"mimetype": "text/x-python",
|
|
"name": "python",
|
|
"nbconvert_exporter": "python",
|
|
"pygments_lexer": "ipython3",
|
|
"version": "3.8.10"
|
|
}
|
|
},
|
|
"nbformat": 4,
|
|
"nbformat_minor": 0
|
|
}
|