This commit is contained in:
Q
2025-06-25 22:26:31 +03:00
parent 829d8295df
commit d7d2e7549e

View File

@@ -282,7 +282,7 @@ class Marker:
(current[1], current[2]),
(current[3], current[4]),
color,
1,
2,
)
cv2.circle(frame, (current[6], current[7]), 10, color, 1)
@@ -483,80 +483,13 @@ class Marker:
if self.opts.output_points is None:
return
old_nr = self.nr
curr_point = self.get_point()
if curr_point[0] is None:
self.add_message("Not in point frame (green)")
return
max_frames = int(min(self.point_tracking_length * self.fps, self.frames - self.nr - 1))
cv2.namedWindow("tsmark - tracker", flags=cv2.WINDOW_AUTOSIZE | cv2.WINDOW_KEEPRATIO | cv2.WINDOW_GUI_NORMAL)
tracker = cv2.TrackerKCF_create()
self.video_reader.set(cv2.CAP_PROP_POS_FRAMES, self.nr)
ok, frame = self.video_reader.read()
frame = cv2.resize(frame.copy(), self.video_res)
bbox = tuple([*curr_point[0:2], *curr_point[6:8]])
ok = tracker.init(frame, bbox)
tracked = {}
for i in range(max_frames):
# Read a new frame
ok, frame = self.video_reader.read()
frame = cv2.resize(frame.copy(), self.video_res)
if not ok:
break
ok, bbox = tracker.update(frame)
# Draw bounding box
if ok:
# Tracking success
p1 = (int(bbox[0]), int(bbox[1]))
p2 = (int(bbox[0] + bbox[2]), int(bbox[1] + bbox[3]))
cv2.rectangle(frame, p1, p2, (255, 0, 0), 2, 1)
tracked[i] = bbox
cv2.putText(frame, "Tracking...", (100, 80), cv2.FONT_HERSHEY_SIMPLEX, 0.75, (0, 0, 255), 2)
else:
# Tracking failure
cv2.putText(
frame, "Tracking failure detected", (100, 80), cv2.FONT_HERSHEY_SIMPLEX, 0.75, (0, 0, 255), 2
)
# Display result
cv2.imshow("tsmark - tracker", frame)
# Exit if ESC pressed
if cv2.waitKey(1) & 0xFF == ord("q"): # if press SPACE bar
break
done = False
while True:
if done:
break
self.video_reader.set(cv2.CAP_PROP_POS_FRAMES, self.nr + 1)
for i in range(max_frames):
show_time = time.time()
ok, frame = self.video_reader.read()
frame = cv2.resize(frame.copy(), self.video_res)
cv2.putText(frame, "Replay...", (100, 80), cv2.FONT_HERSHEY_SIMPLEX, 0.75, (0, 0, 255), 2)
if i in tracked:
bbox = tracked[i]
p1 = (int(bbox[0]), int(bbox[1]))
p2 = (int(bbox[0] + bbox[2]), int(bbox[1] + bbox[3]))
cv2.rectangle(frame, p1, p2, (255, 0, 0), 2, 1)
cv2.imshow("tsmark - tracker", frame)
if cv2.waitKey(1) & 0xFF == ord("q"): # if press SPACE bar
done = True
break
time_to_wait = self.viewer_spf - time.time() + show_time
if time_to_wait > 0:
time.sleep(time_to_wait)
cv2.destroyWindow("tsmark - tracker")
self.nr = old_nr - 1
self.read_next = True
tracker_gui = TrackerGUI(self)
if len(tracker_gui.points) > 0:
for nr in tracker_gui.points:
self.points[self.point_index][nr] = tracker_gui.points[nr]
self.interpolate_points()
self.nr = max(tracker_gui.points)-1
self.read_next = True
def interpolate_points(self):
@@ -936,7 +869,7 @@ class Marker:
ret, frame = self.video_reader.read()
if ret == True:
draw_wait = 200 if self.paused or self.point_click == 0 else 1
draw_wait = 200 if self.paused or ( self.paused and self.point_click == 0 ) else 1
if (not self.paused) or self.read_next:
self.read_next = False
@@ -1037,7 +970,7 @@ class Marker:
elif k & 0xFF == ord("f"): # modify FPS
FPS_modifier = (FPS_modifier + 1) % len(FPS_modifiers)
self.add_message(f"Player speed {FPS_modifiers[FPS_modifier]}")
self.add_message(f"Player speed {round(1/FPS_modifiers[FPS_modifier],2)}")
elif k & 0xFF == ord("a"): # toggle crop offset
self.crop_click = 0 if self.crop_click == 1 else 1
self.crop[2] = True
@@ -1064,6 +997,54 @@ class Marker:
self.point_click = 0
else:
self.point_index = chr(k2)
elif k & 0xFF == ord("g"): # Go to
self.shadow_text(
frame_visu,
"Enter frame or time",
(20, 70),
0.9,
2,
(255,255,255),
)
cv2.imshow("tsmark", frame_visu)
entered_chars=""
while True:
frame_query = frame_visu.copy()
self.shadow_text(
frame_query,
entered_chars,
(20, 100),
0.9,
2,
(255,255,255),
)
cv2.imshow("tsmark", frame_query)
del frame_query
k2 = cv2.waitKey(0)
if k2 & 0xFF == ord("q") or k2 & 0xFF == 27:
break
elif k2 & 0xFF == ord("g") or k2 & 0xFF == 13:
try:
self.nr = int(entered_chars) -1
except ValueError:
try:
self.nr = self.parse_time(entered_chars)
except Exception:
self.add_message("Cannot parse time")
break
self.read_next = True
break
elif k2 & 0xFF == 8: # backspace
entered_chars = entered_chars[0:-1]
elif k2 & 0xFF in digits_ords:
entered_chars += str(digits_ords.index(k2 & 0xFF))
elif k2 & 0xFF == ord(":"):
entered_chars += ":"
elif k2 & 0xFF == ord("."):
entered_chars += "."
else:
pass
elif k & 0xFF == ord("t"): # tracking
self.track_point()
@@ -1106,3 +1087,150 @@ class Marker:
cv2.destroyAllWindows()
self.print_timestamps()
self.save_timestamps()
class TrackerGUI:
def __init__(self, marker):
self.marker = marker
self.start()
def start(self):
old_nr = self.marker.nr
curr_point = self.marker.get_point()
if curr_point[0] is None:
self.marker.add_message("Not in point frame (green)")
return
max_frames = int(min(self.marker.point_tracking_length * self.marker.fps, self.marker.frames - self.marker.nr - 1))
cv2.namedWindow("tsmark - tracker", flags=cv2.WINDOW_AUTOSIZE | cv2.WINDOW_KEEPRATIO | cv2.WINDOW_GUI_NORMAL)
tracker = cv2.TrackerKCF_create()
self.marker.video_reader.set(cv2.CAP_PROP_POS_FRAMES, self.marker.nr)
ok, frame = self.marker.video_reader.read()
frame = cv2.resize(frame.copy(), self.marker.video_res)
bbox = tuple([*curr_point[0:2], *curr_point[6:8]])
ok = tracker.init(frame, bbox)
tracked = {}
for i in range(max_frames):
# Read a new frame
ok, frame = self.marker.video_reader.read()
frame = cv2.resize(frame.copy(), self.marker.video_res)
if not ok:
break
ok, bbox = tracker.update(frame)
# Draw bounding box
if ok:
# Tracking success
p1 = (int(bbox[0]), int(bbox[1]))
p2 = (int(bbox[0] + bbox[2]), int(bbox[1] + bbox[3]))
cv2.rectangle(frame, p1, p2, (255, 0, 0), 2, 1)
tracked[i] = [*bbox,1]
cv2.putText(frame, "Tracking...", (100, 80), cv2.FONT_HERSHEY_SIMPLEX, 0.75, (0, 0, 255), 2)
else:
# Tracking failure
cv2.putText(
frame, "Tracking failure detected", (100, 80), cv2.FONT_HERSHEY_SIMPLEX, 0.75, (0, 0, 255), 2
)
# Display result
cv2.imshow("tsmark - tracker", frame)
# Exit if ESC pressed
if cv2.waitKey(1) & 0xFF == ord("q"): # if press SPACE bar
break
done = False
paused = False
seek = False
cut_after = max_frames
while True:
if done:
break
self.marker.video_reader.set(cv2.CAP_PROP_POS_FRAMES, self.marker.nr + 1)
i = 0
while True:
show_time = time.time()
if done:
break
if paused:
frame = frame_copy.copy()
if (not paused) or seek:
ok, frame = self.marker.video_reader.read()
frame = cv2.resize(frame.copy(), self.marker.video_res)
frame_copy = frame.copy()
i += 1
seek = False
cv2.putText(frame, f"Replay... {i}", (100, 80), cv2.FONT_HERSHEY_SIMPLEX, 0.75, (0, 0, 255), 2)
if i in tracked:
bbox = tracked[i]
p1 = (int(bbox[0]), int(bbox[1]))
p2 = (int(bbox[0] + bbox[2]), int(bbox[1] + bbox[3]))
color = (0,255,0) if cut_after > i else (0, 192, 192)
thicc = 2 if cut_after > i else 1
cv2.rectangle(frame, p1, p2, color, thicc, 1)
cv2.imshow("tsmark - tracker", frame)
k = cv2.waitKey(1)
if k & 0xFF == ord("q"): # if press SPACE bar
done = True
break
elif k & 0xFF == 32: # space
paused = not paused
# Movement =================
elif k & 0xFF == 83 or k & 0xFF == ord("l"): # right arrow
i += int(self.marker.fps) - 1
seek = True
elif k & 0xFF == 81 or k & 0xFF == ord("j"): # left arrow
i -= int(self.marker.fps) + 1
seek = True
# Move by frame
elif k & 0xFF == ord("."):
paused = True
seek = True
elif k & 0xFF == ord(","):
paused = True
i -= 2
seek = True
elif k & 0xFF == ord("x"):
cut_after = i
#if i in tracked:
# tracked[i][4] = 1 - tracked[i][4]
time_to_wait = self.marker.viewer_spf - time.time() + show_time
if time_to_wait > 0:
time.sleep(time_to_wait)
if i >= max_frames:
i = max_frames-1
paused = True
seek = True
if i<0:
i=0
paused = True
seek = True
if seek:
self.marker.video_reader.set(cv2.CAP_PROP_POS_FRAMES, self.marker.nr + 1 + i)
cv2.destroyWindow("tsmark - tracker")
self.marker.nr = old_nr - 1
self.marker.read_next = True
self.points = {}
for i in sorted(list(tracked.keys())):
if i >= cut_after:
continue
self.points[self.marker.nr+1+i] = [
tracked[i][0],
tracked[i][1],
tracked[i][0]+tracked[i][2],
tracked[i][1]+tracked[i][3],
]