実装プロセス
(同じローカル静止画を使用して同じように)このツールは、グレースケール画像を返すカメラビデオストリームから得られた、一の画像に変換し、その後画像処理ライブラリOpenCVのに情報を渡します
プログラムは、リスナー情報に従って、whileループを使用開始した後、ビデオ・イメージをロードし続け、その後、画像情報を提示するOpenCVのツールに戻します。
キーボードイベントリスナーを作成し、(、あなたはいつでも移動することができます。このプロセスは動的である)そして、顔照合、およびマスクロードを実行するために始めた、「D」キーを押してください。
顔が存在するかどうかを確認するためにDLIBにおける顔検出アルゴリズムを使用して顔照合。もしそうなら、それは終了位置を作成し、メガネや吸殻が直面するすべての人のためにそこに移動します。
その後、我々は皆の顔に合わせて拡張し、私たちのメガネを回転させる必要があります。私たちは、68ポイントを返しDLIBモデルセットポイントから目と口を見つけるために、センターを利用し、それらの間のスペースを回転します。
我々は最終的には、画面の上部にタバコやメガネ、メガネやタバコのリアルタイム位置を取得した後、あなたのメガネと口を一致させるようになりました。
何人の顔が存在しない場合、プログラムはマスクを移動させる効果を持っていないでしょう、あなたのビデオ情報に直接戻ります。
デフォルトは4秒の周期です。その後、再び「D」キーをテストすることができます。
「Q」キーを使用してプログラムを終了します。
ここで私は、この機能は、マスクロードサービスに抽象化されます、それはすべてのものを見るために私のコードに従ってください。
1.インポートし、対応するツールキット
時間インポートスリープから
輸入CV2の
NPとしてインポートnumpyの
PILのインポートイメージから
imutils輸入face_utilsから、サイズを変更
試してみてください。
DLIBインポートget_frontal_face_detector、shape_predictorから
はImportError除く:
上げます
それに対応するサービスクラスDynamicStreamMaskServiceの初期化プロパティをロードするためにマスクを作成します。
DynamicStreamMaskServiceクラス(オブジェクト):
「」「
動的な接着剤マスクサービス
」「」
__init __ DEF(セルフ、= Falseの保存):
self.saved =#写真を保存するために保存された
self.listenerを= Trueの#の起動パラメータ
self.video_capture = cv2.VideoCapture(0)#呼び出しローカルカメラ
self.doing = Falseの#顔かどうかマスク
self.speed = 0.1#マスクの移動速度
self.detector = get_frontal_face_detector()#顔認識部
self.predictor = shape_predictor( "shape_predictor_68_face_landmarks.dat")は # 顔アナライザ
self.fps = 4時間ベース#マスクがある
自己。アニメーションサイクルのanimation_time = 0#初期値
self.duration = self.fps * 4#アニメーションサイクル最大
self.fixed_time =延伸後#4、滞留時間
self.max_width = 500#画像サイズ
self.deal、self.text、自己.cigarette =なし、なし、なし#マスクオブジェクト
上記の紹介によると、我々は最初の画像に機能ビデオストリームを読ん実現します:
READ_DATA DEF(自己):
「」「
カメラからビデオストリームを取得し、画像をフレームに変換される
:リターンの画像に関する情報を返し
「」」
_、= self.video_capture.readデータ()
リターンデータ
次に、私たちは、顔の位置機能を実現し、メガネやタバコの所在地:
DEF(自己、face_shape、face_width)get_glasses_info:
"" "
获取当前面部的眼镜信息
:PARAM face_shape:
:PARAM face_width:
:リターン
:"""
left_eye = face_shape [36:42]
right_eye = face_shape [42:48]
left_eye_center = left_eye.mean(軸= 0).astype( "INT")
right_eye_center = right_eye.mean(軸= 0).astype( "INT")
Y = left_eye_center [1] - right_eye_center [1]
X = left_eye_center [0] - right_eye_center [0]
eye_angle = np.rad2deg(np.arctan2(Y、X))
取引= self.deal.resize(
(face_width、INT(face_width * self.deal.size [1] / self.deal.size [0]))、
リサンプル= Image.LANCZOS)
取引= deal.rotate(eye_angle、=真を拡大)
取引= deal.transpose(Image.FLIP_TOP_BOTTOM)
left_eye_x = left_eye [0,0] - face_width // 4
left_eye_y = left_eye [0,1] - face_width // 6
リターン{ "イメージ":取引は、 "POS"(left_eye_x、left_eye_y)}
DEF get_cigarette_info(自己、face_shape、face_width):
"" "
获取当前面部的烟卷信息
:PARAM face_shape:
:PARAM face_width:
:リターン
:"""
口= face_shape [49:68]
mouth_center = mouth.mean(軸= 0 ).astype( "INT")
シガレット= self.cigarette.resize(
(face_width、INT(face_width * self.cigarette.size [1] / self.cigarette.size [0]))、
リサンプル= Image.LANCZOS)
X =口[0,0] - face_width + INT(16 * face_width / self.cigarette.size [0])
Y = mouth_center [1]
リターン{ "イメージ":タバコ、 "POS"(X、Y)}
DEF向き(自己、rects、img_gray):
"" "
人脸定位
:リターン
:"""
顔= []
rectsでRECT用:
顔= {}
face_shades_width = rect.right() - rect.left()
predictor_shape = self.predictor(img_gray、RECT)
face_shape = face_utils.shape_to_np(predictor_shape)
面[ 'タバコ'] = self.get_cigarette_info(face_shape、face_shades_width)
面[ 'メガネ'] = self.get_glasses_info(face_shape、face_shades_width)
faces.append(顔)
顔を返します
私達はちょうど私たちが何この機能を実現するイベント、を聞くために、キーボードを言及しています:
listener_keys DEF(自己):
"" "
を設定し、キーボード・モニター・イベント
:リターン:
" ""
キー= cv2.waitKey(1)&0xFFの
IFキー== ORD( "Q"):
self.listener = Falseの
self.console( "プログラムを終了「)
SLEEP(1)
self.exit()
もし、キー== ORD( "D"):
self.doing = self.doingありません
次はマスク情報をロードする機能を実現するために来ます。
デフinit_mask(自己):
"" "
加载面具
:リターン
:"""
self.console( "加载面具...")
self.deal、self.text、self.cigarette =(
xに対するImage.open(X) [ "画像/ deals.png"、 "画像/ text.png"、 "画像/ cigarette.png"]で
)
上記の基本的な機能が実装されている、我々は描画機能、および機能の原理と私はビブラート効果を達成するためにAIの顔認識技術でエッセイを書いた前に実現し、私は詳細には触れませんが、同じである、あなたはgithubのを行くことができますPythonの中国の社会や公共のマイクロチャンネル番号表示。
DEF(自己、draw_imgに面する)描画:
"" "
画图
:PARAM draw_img:
:PARAMが直面:
:リターン
:"""
顔について顔では:
self.animation_time <self.duration場合- self.fixed_time:
current_x = INT(顔[ "眼鏡"] [ "POS"] [0])
current_y = INT(顔[ "眼鏡"] [ "POS"] [1] * self.animation_time /(self.duration - self.fixed_time))
draw_img。ペースト(顔[ "眼鏡"] [ "画像"]、(current_x、current_y)、顔[ "眼鏡"] [ "画像"])
cigarette_x = INT(顔[ "シガレット"] [ "POS"] [0])
cigarette_y = INT(顔[ "シガレット"] [ "POS"] [1] * self.animation_time /(self.duration - self.fixed_time ))
draw_img.paste(顔[ "シガレット"] [ "画像"]、(cigarette_x、cigarette_y)、
顔[ "シガレット"] [ "画像"])
他:
draw_img.paste(顔[ "眼鏡"] [」画像"]、顔["眼鏡"] [" POS "]、顔["眼鏡"] ["画像"])
draw_img.paste(顔["シガレット"] ["画像"]、顔["タバコ」] [ "POS"]、顔[ "シガレット"] [ "画像"])
draw_img.paste(self.text、(75、draw_img.height // 2 + 128)、self.text)
それは機能が最終的に開始し、それを終了し、しているサービスクラスであるので、我々はそれについて記述する必要があります。
単に連続的にビデオストリームを監視し、情報を表示OpenCVのことで画像に変換されるストリーミングを聴取開始後の初期化情報に応じて、開始()関数を記述しています。
そして、常にリスナーは、画像の顔検出に成功している場合は、マスクをロードするために「D」キーを押すかどうかを監視し、マスクを移動し、ファンクションキーリスナーを呼び出して
、あなたのマスクに基づいて、この時間は、時間の持続期間の終了顔の動きの動き。絵の上部に、物品の最終的なレンダリング。
DEF開始(自己):
"" "
启动程序
:リターン
:"""
self.console( "程序启动成功")
self.init_mask()
一方self.listener:
フレーム= self.read_data()
フレーム=リサイズ(フレーム、幅= self.max_width)
img_gray = cv2.cvtColor(フレーム、cv2.COLOR_BGR2GRAY)
rects = self.detector(img_gray、0)
= self.orientation(rects、img_gray)対向
draw_img = Image.fromarray(cv2.cvtColor(フレーム、cv2.COLOR_BGR2RGB))
場合self.doing:
self.drawing(draw_img、対向)
self.animation_time + = self.speed
self.save_data(draw_img)
もしself.animation_time> self.duration:
self.doing = Falseの
self.animation_time = 0
他:
フレーム= cv2.cvtColor(np.asarray(draw_img)、cv2.COLOR_RGB2BGR)
cv2.imshow( "ハローマスク"、フレーム)
自己.listener_keys()
デフ出口(自己):
"" "
程序退出
:リターン
:"""
self.video_capture.release()
cv2.destroyAllWindows()
最後に、試してみましょう:
もし__name__ == '__main__':
MS = DynamicStreamMaskService()
ms.start()
私はあなたに、この小さな機能は、我々としても見て何かを使用することができ、達成された書き込み。
---------------------