作者:wangwei8638
升级后的手部关键点识别提供了21个骨节点的位置信息,可应用于智能家电、可穿戴VR设备手势控制等,也可用于视频直播平台、线下互动屏幕等场景,增加身体道具、体感游戏等互动形式,丰富娱乐体验。
一.平台接入
此步骤比较简单,不多阐述。可参照之前文档:
https://ai.baidu.com/forum/topic/show/943162
二.分析接口文档
1.打开API文档页面,分析接口要求
https://ai.baidu.com/docs#/Body-API/2757b503
(1)接口描述
对于输入的一张图片(可正常解码,且长宽比适宜),检测图片中的所有人手,输出每只手的坐标框、21个骨节点坐标信息。
(2)请求说明
需要用到的信息有:
请求URL:https://aip.baidubce.com/rest/2.0/image-classify/v1/hand_analysis
Header格式:Content-Type:application/x-www-form-urlencoded
Body中放置请求参数,参数详情如下:
(3)返回参数
返回示例
{'hand_num': 1,
'log_id': 8059073514507408547,
'hand_info': [{
'location': {'score': 0.9908163547515869, 'top': 71, 'left': 30, 'width': 458, 'height': 478},
'hand_parts': {
'11': {'score': 0.7767238616943359, 'y': 193, 'x': 384},
'10': {'score': 0.8792312145233154, 'y': 238, 'x': 339},
'7': {'score': 0.8266968727111816, 'y': 157, 'x': 312},
'9': {'score': 0.6800566911697388, 'y': 301, 'x': 285},
'3': {'score': 0.8536556363105774, 'y': 238, 'x': 150},
'17': {'score': 0.7472577691078186, 'y': 391, 'x': 330},
'18': {'score': 0.8863479495048523, 'y': 355, 'x': 375},
'4': {'score': 0.8486065864562988, 'y': 157, 'x': 177},
'19': {'score':0.8561264276504517, 'y': 328, 'x': 411},
'5': {'score': 0.7263614535331726, 'y': 274, 'x': 231},
'14': {'score': 0.8745924234390259, 'y': 292, 'x': 366},
'6': {'score': 0.8760672807693481, 'y': 202, 'x': 276},
'2': {'score': 0.8125947117805481, 'y': 292, 'x': 132},
'12': {'score': 0.8767789602279663, 'y': 139, 'x': 447},
'16': {'score': 0.8797457814216614, 'y': 202, 'x': 474},
'1': {'score': 0.5965365767478943, 'y': 373, 'x': 114},
'15': {'score': 0.8359962105751038, 'y': 256, 'x': 411},
'0': {'score': 0.6162715554237366, 'y': 517, 'x': 105},
'8': {'score': 0.8763289451599121, 'y': 103, 'x': 366},
'13': {'score': 0.731921911239624,'y': 337, 'x': 312},
'20': {'score': 0.9211868643760681, 'y': 292, 'x': 447}}}]}
2.获取access_token
# encoding:utf-8
import base64
import urllib
import urllib2
request_url = " https://aip.baidubce.com/rest/2.0/image-classify/v1/hand_analysis "
# 二进制方式打开视频文件
f = open('[本地文件]', 'rb')
img = base64.b64encode(f.read())
params = {"data": data }
params = urllib.urlencode(params)
access_token = '[调用鉴权接口获取的token]'
request_url = request_url + "?access_token=" + access_token
request = urllib2.Request(url=request_url, data=params)
request.add_header('Content-Type', 'application/x-www-form-urlencoded')
response = urllib2.urlopen(request)
content = response.read()
if content:
print content
三.识别结果
- 正面
识别结果:正确
识别结果:正确
3.握拳
识别结果:正确
4.多个情况
识别结果:‘hand_num’: 3
结论:
识别结果方面:区分单个和多个手掌的情况,分别从手心、手背、握拳几个角度拍摄的照片进行测试,识别结果比较准确。但多个手掌情况下返回hand_num准确度下降。
处理速度方面:每张图片处理时间在1-3s,可以接受。
四.源码共享
# -*- coding: utf-8 -*-
#!/usr/bin/env python
import urllib
import urllib.parse
import urllib.request
import base64
import json
import time
#client_id 为官网获取的AK, client_secret 为官网获取的SK
client_id = '*******************'
client_secret = '*******************'
#获取token
def get_token():
host = 'https://aip.baidubce.com/oauth/2.0/token?grant_type=client_credentials&client_id=' + client_id + '&client_secret=' + client_secret
request = urllib.request.Request(host)
request.add_header('Content-Type', 'application/json; charset=UTF-8')
response = urllib.request.urlopen(request)
token_content = response.read()
if token_content:
token_info = json.loads(token_content.decode("utf-8"))
token_key = token_info['access_token']
return token_key
# 读取图片
def get_file_content(filePath):
with open(filePath, 'rb') as fp:
return fp.read()
#绘制关键节点
def drow_hand_point(path,hand_num,hand_info,img_out):
from PIL import Image, ImageDraw
img = Image.open(path)
draw = ImageDraw.Draw(img)
while hand_num>0:
hand_parts=hand_info[hand_num-1]['hand_parts']
for point in hand_parts:
center_x=hand_parts[point]['x']
center_y=hand_parts[point]['y']
draw.ellipse((int(center_x)-5,int(center_y)-5, int(center_x)+5,int(center_y)+5), fill = (255, 0, 0))
hand_num=hand_num-1
# print (hand_num)
img.show()
img.save(img_out, "JPEG")
#获取手部关节信息
def get_license_plate(path):
request_url = "https://aip.baidubce.com/rest/2.0/image-classify/v1/hand_analysis"
f = get_file_content(path)
access_token=get_token()
img = base64.b64encode(f)
params = {"image": img}
params = urllib.parse.urlencode(params).encode('utf-8')
request_url = request_url + "?access_token=" + access_token
tic = time.clock()
request = urllib.request.Request(url=request_url, data=params)
request.add_header('Content-Type', 'application/x-www-form-urlencoded')
response = urllib.request.urlopen(request)
content = response.read()
toc = time.clock()
print('处理时长: '+'%.2f' %(toc - tic) +' s')
if content:
result = json.loads(content.decode("utf-8"))
print (result)
hand_num = result['hand_num']
print ('手掌个数:'+str(hand_num))
hand_info = result['hand_info']
drow_hand_point(path,hand_num,hand_info,'out.jpg')
return content
else:
return ''
image_path='F:\paddle\hand\s3.jpg'
get_license_plate(image_path)