Skip to content

Commit 36fd8b6

Browse files
committedJan 17, 2022
Update.
1 parent 7b8a106 commit 36fd8b6

35 files changed

+12038
-1
lines changed
 

‎.gitignore

+5-1
Original file line numberDiff line numberDiff line change
@@ -92,4 +92,8 @@ external/
9292

9393
draws/
9494
plot/
95-
95+
*.mp4
96+
*.torch
97+
*.onnx
98+
*.zip
99+
*.pth

‎keypoints_onnxdemo/demo_toolkit.py

+281
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,281 @@
1+
import cv2
2+
import numpy as np
3+
import os
4+
import sys
5+
from vis_utils import *
6+
import time
7+
8+
__version__ = "1.1.3"
9+
10+
joints_pair = [[0 , 1], [1 , 2], [2 , 0], [1 , 3], [2 , 4], [3 , 5], [4 , 6], [5 , 6], [5 , 11],
11+
[6 , 12], [11 , 12], [5 , 7], [7 , 9], [6 , 8], [8 , 10], [11 , 13], [13 , 15], [12 , 14], [14 , 16]]
12+
colors_tableau = [(255, 255, 255), (31, 119, 180), (174, 199, 232), (255, 127, 14), (255, 187, 120),
13+
(44, 160, 44), (152, 223, 138), (214, 39, 40), (255, 152, 150),
14+
(148, 103, 189), (197, 176, 213), (140, 86, 75), (196, 156, 148),
15+
(227, 119, 194), (247, 182, 210), (127, 127, 127), (199, 199, 199),
16+
(188, 189, 34), (219, 219, 141), (23, 190, 207), (158, 218, 229)]
17+
18+
def add_jointsv2(image, joints, color, r=3,threshold=0.1):
19+
20+
def link(a, b, color):
21+
jointa = joints[a]
22+
jointb = joints[b]
23+
if jointa[2] > threshold and jointb[2] > threshold:
24+
cv2.line(
25+
image,
26+
(int(jointa[0]), int(jointa[1])),
27+
(int(jointb[0]), int(jointb[1])),
28+
color, 2 )
29+
30+
# add link
31+
for pair in joints_pair:
32+
link(pair[0], pair[1], color)
33+
34+
# add joints
35+
for i, joint in enumerate(joints):
36+
if joint[2] > threshold and joint[0] > 1 and joint[1] > 1:
37+
cv2.circle(image, (int(joint[0]), int(joint[1])), r, colors_tableau[i], -1)
38+
39+
return image
40+
41+
def show_keypoints(image, joints, color=[0,255,0],threshold=0.1):
42+
image = np.ascontiguousarray(image)
43+
if color is None:
44+
use_random_color=True
45+
else:
46+
use_random_color = False
47+
for person in joints:
48+
if use_random_color:
49+
color = np.random.randint(0, 255, size=3)
50+
color = [int(i) for i in color]
51+
add_jointsv2(image, person, color=color,threshold=threshold)
52+
53+
return image
54+
55+
class BufferTextPainter:
56+
def __init__(self,buffer_len=30):
57+
self.buffer_nr = buffer_len
58+
self.cur_text = ""
59+
self.cur_idx = 0
60+
self.font = os.path.join(os.path.dirname(__file__),"simhei.ttf")
61+
62+
def putText(self,img,text,font_scale=20,text_color=(255,255,255)):
63+
img = np.ascontiguousarray(img)
64+
if text == "":
65+
if self.cur_idx == 0:
66+
return img
67+
else:
68+
self.cur_idx =self.buffer_nr
69+
self.cur_text = text
70+
71+
self.cur_idx = self.cur_idx-1
72+
img = draw_text(img,(12,12),self.cur_text,
73+
text_color=text_color,
74+
font_size=font_scale,
75+
font=self.font)
76+
return img
77+
78+
def resize_height(img,h,interpolation=cv2.INTER_LINEAR):
79+
shape = img.shape
80+
new_h = h
81+
new_w = int(shape[1]*new_h/shape[0])
82+
return cv2.resize(img,dsize=(new_w,new_h),interpolation=interpolation)
83+
84+
def resize_width(img,w,interpolation=cv2.INTER_LINEAR):
85+
shape = img.shape
86+
new_w = w
87+
new_h = int(shape[0]*new_w/shape[1])
88+
return cv2.resize(img,dsize=(new_w,new_h),interpolation=interpolation)
89+
90+
def resize_short_size(img,size,interpolation=cv2.INTER_LINEAR):
91+
shape = img.shape
92+
if shape[0]<shape[1]:
93+
return resize_height(img,size,interpolation)
94+
else:
95+
return resize_width(img,size,interpolation)
96+
97+
class VideoDemo:
98+
def __init__(self,model,fps=30,save_path=None,buffer_size=0,show_video=True,max_frame_cn=None,interval=None) -> None:
99+
self.model = model
100+
self.fps = fps
101+
self.save_path = save_path
102+
self.buffer_size = buffer_size
103+
self.buffer = []
104+
self.write_size = None
105+
self.video_reader = None
106+
self.video_writer = None
107+
self.show_video = show_video
108+
self.preprocess = None
109+
self.max_frame_cn = max_frame_cn
110+
self.interval = interval
111+
self.model.runner = self
112+
self.window_name = "video"
113+
print(f"Demo toolkit version {__version__}.")
114+
115+
def __del__(self):
116+
self.close()
117+
118+
def close(self):
119+
if self.video_writer is not None:
120+
self.video_writer.release()
121+
122+
123+
def init_writer(self):
124+
save_path = self.save_path
125+
if save_path is not None:
126+
fourcc = cv2.VideoWriter_fourcc(*'XVID')
127+
self.video_writer = cv2.VideoWriter(save_path,fourcc,self.fps,self.write_size)
128+
129+
def init_reader(self):
130+
if self.video_path is not None and os.path.exists(self.video_path):
131+
print(f"Use video file {self.video_path}")
132+
self.video_reader = cv2.VideoCapture(self.video_path)
133+
self.frame_cnt = int(self.video_reader.get(cv2.CAP_PROP_FRAME_COUNT))
134+
if self.max_frame_cn is not None and self.max_frame_cn>1:
135+
self.frame_cnt = min(self.frame_cnt,self.max_frame_cn)
136+
else:
137+
if self.video_path is not None:
138+
vc = int(self.video_path)
139+
else:
140+
vc = -1
141+
print(f"Use camera {vc}")
142+
self.video_reader = cv2.VideoCapture(vc)
143+
self.frame_cnt = -1
144+
145+
self.video_reader.set(cv2.CAP_PROP_BUFFERSIZE,1)
146+
self.video_reader.set(cv2.CAP_PROP_POS_FRAMES,1)
147+
148+
if self.show_video:
149+
cv2.namedWindow(self.window_name, cv2.WND_PROP_FULLSCREEN)
150+
cv2.setWindowProperty(self.window_name,cv2.WND_PROP_FULLSCREEN,cv2.WINDOW_FULLSCREEN)
151+
152+
width = int(self.video_reader.get(cv2.CAP_PROP_FRAME_WIDTH))
153+
height = int(self.video_reader.get(cv2.CAP_PROP_FRAME_HEIGHT))
154+
if self.preprocess is None:
155+
self.write_size = (width,height)
156+
else:
157+
tmp_img = np.zeros([height,width,3],dtype=np.uint8)
158+
tmp_img = self.preprocess(tmp_img)
159+
if isinstance(tmp_img,dict):
160+
tmp_img = self.get_last_img([tmp_img])
161+
self.write_size = (tmp_img.shape[1],tmp_img.shape[0])
162+
self.fps = self.video_reader.get(cv2.CAP_PROP_FPS)
163+
164+
def inference_loop(self,video_path=None):
165+
self.video_path = video_path
166+
self.init_reader()
167+
self.init_writer()
168+
idx = 0
169+
170+
print(f"Press Esc to escape.")
171+
172+
while True:
173+
idx += 1
174+
if self.interval is not None and self.interval>1:
175+
if idx%self.interval != 0:
176+
continue
177+
ret,frame = self.video_reader.read()
178+
if not ret:
179+
break
180+
frame = frame[...,::-1] #torgb
181+
if self.preprocess is not None:
182+
frame = self.preprocess(frame)
183+
img = self.inference(frame)
184+
if img is None:
185+
continue
186+
if self.show_video:
187+
cv2.imshow(self.window_name,img[...,::-1])
188+
if cv2.waitKey(30)&0xFF == 27:
189+
break
190+
if self.frame_cnt > 1:
191+
sys.stdout.write(f"{idx}/{self.frame_cnt} {idx*100/self.frame_cnt:.3f}%.\r")
192+
if idx>self.frame_cnt:
193+
break
194+
195+
def inference(self,img):
196+
if self.buffer_size <= 1:
197+
r_img = self.inference_single_img(img)
198+
else:
199+
r_img = self.inference_buffer_img(img)
200+
if self.video_writer is not None:
201+
self.video_writer.write(r_img[...,::-1])
202+
return r_img
203+
204+
def inference_single_img(self,img):
205+
return self.model(img)
206+
207+
def inference_buffer_img(self,img):
208+
self.buffer.append(img)
209+
if len(self.buffer)>self.buffer_size:
210+
self.buffer = self.buffer[-self.buffer_size:]
211+
return self.model(self.buffer)
212+
213+
@staticmethod
214+
def get_last_img(imgs):
215+
img = imgs[-1]
216+
if isinstance(img,dict):
217+
if 'raw_image' in img:
218+
return img['raw_image']
219+
return img['image']
220+
else:
221+
return img
222+
223+
@staticmethod
224+
def resize_h_and_save_raw_image_preprocess(img,h=224):
225+
r_img = resize_height(img,h).astype(np.uint8)
226+
return {'image':r_img,"raw_image":img}
227+
228+
class IntervalMode:
229+
def __init__(self,interval=30):
230+
self.interval = interval
231+
self.idx = 0
232+
233+
def add(self):
234+
self.idx += 1
235+
236+
def need_pred(self):
237+
self.add()
238+
return (self.idx%self.interval)==0
239+
240+
241+
def get_video_indexs(size,nr):
242+
delta = (size-1)/nr
243+
idxs = (np.arange(nr).astype(np.float32)*delta+delta/2).astype(np.int32)
244+
return idxs
245+
246+
def crop_imgs(imgs, crop_bbox):
247+
x1, y1, x2, y2 = crop_bbox
248+
return [img[y1:y2, x1:x2] for img in imgs]
249+
250+
def center_crop(imgs,crop_size):
251+
img_h, img_w = imgs[0].shape[:2]
252+
crop_w, crop_h = crop_size
253+
254+
left = (img_w - crop_w) // 2
255+
top = (img_h - crop_h) // 2
256+
right = left + crop_w
257+
bottom = top + crop_h
258+
259+
crop_bbox = np.array([left, top, right, bottom])
260+
261+
return crop_imgs(imgs, crop_bbox)
262+
263+
class TimeThis():
264+
def __init__(self,name="TimeThis",auto_show=True):
265+
self.begin_time = 0.
266+
self.end_time = 0
267+
self.name = name
268+
self.auto_show = auto_show
269+
270+
def __enter__(self):
271+
self.begin_time = time.time()
272+
273+
def __exit__(self, exc_type, exc_val, exc_tb):
274+
self.end_time = time.time()
275+
if self.auto_show:
276+
te = (self.end_time-self.begin_time)*1000
277+
fps = 1000/(te+1e-8)
278+
print(f"{self.name}: total time {te:.3f}, FPS={fps:.3f}.")
279+
280+
def time(self):
281+
return self.end_time-self.begin_time

‎keypoints_onnxdemo/keypoints/__init__.py

Whitespace-only changes.

0 commit comments

Comments
 (0)