ultralytics 8.2.17__py3-none-any.whl → 8.2.18__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of ultralytics might be problematic. Click here for more details.

@@ -13,49 +13,12 @@ from shapely.geometry import Point, Polygon
13
13
 
14
14
 
15
15
  class QueueManager:
16
- """A class to manage the queue management in real-time video stream based on their tracks."""
16
+ """A class to manage the queue in a real-time video stream based on object tracks."""
17
17
 
18
- def __init__(self):
19
- """Initializes the queue manager with default values for various tracking and counting parameters."""
20
-
21
- # Mouse events
22
- self.is_drawing = False
23
- self.selected_point = None
24
-
25
- # Region & Line Information
26
- self.reg_pts = [(20, 60), (20, 680), (1120, 680), (1120, 60)]
27
- self.counting_region = None
28
- self.region_color = (255, 0, 255)
29
- self.region_thickness = 5
30
-
31
- # Image and annotation Information
32
- self.im0 = None
33
- self.tf = None
34
- self.view_img = False
35
- self.view_queue_counts = True
36
- self.fontsize = 0.6
37
-
38
- self.names = None # Classes names
39
- self.annotator = None # Annotator
40
- self.window_name = "Ultralytics YOLOv8 Queue Manager"
41
-
42
- # Object counting Information
43
- self.counts = 0
44
- self.count_txt_color = (255, 255, 255)
45
-
46
- # Tracks info
47
- self.track_history = defaultdict(list)
48
- self.track_thickness = 2
49
- self.draw_tracks = False
50
- self.track_color = None
51
-
52
- # Check if environment support imshow
53
- self.env_check = check_imshow(warn=True)
54
-
55
- def set_args(
18
+ def __init__(
56
19
  self,
57
20
  classes_names,
58
- reg_pts,
21
+ reg_pts=None,
59
22
  line_thickness=2,
60
23
  track_thickness=2,
61
24
  view_img=False,
@@ -68,48 +31,65 @@ class QueueManager:
68
31
  fontsize=0.7,
69
32
  ):
70
33
  """
71
- Configures the Counter's image, bounding box line thickness, and counting region points.
34
+ Initializes the QueueManager with specified parameters for tracking and counting objects.
72
35
 
73
36
  Args:
74
- line_thickness (int): Line thickness for bounding boxes.
75
- view_img (bool): Flag to control whether to display the video stream.
76
- view_queue_counts (bool): Flag to control whether to display the counts on video stream.
77
- reg_pts (list): Initial list of points defining the counting region.
78
- classes_names (dict): Classes names
79
- region_color (RGB color): Color of queue region
80
- track_thickness (int): Track thickness
81
- draw_tracks (Bool): draw tracks
82
- count_txt_color (RGB color): count text color value
83
- track_color (RGB color): color for tracks
84
- region_thickness (int): Object counting Region thickness
85
- fontsize (float): Text display font size
37
+ classes_names (dict): A dictionary mapping class IDs to class names.
38
+ reg_pts (list of tuples, optional): Points defining the counting region polygon. Defaults to a predefined
39
+ rectangle.
40
+ line_thickness (int, optional): Thickness of the annotation lines. Defaults to 2.
41
+ track_thickness (int, optional): Thickness of the track lines. Defaults to 2.
42
+ view_img (bool, optional): Whether to display the image frames. Defaults to False.
43
+ region_color (tuple, optional): Color of the counting region lines (BGR). Defaults to (255, 0, 255).
44
+ view_queue_counts (bool, optional): Whether to display the queue counts. Defaults to True.
45
+ draw_tracks (bool, optional): Whether to draw tracks of the objects. Defaults to False.
46
+ count_txt_color (tuple, optional): Color of the count text (BGR). Defaults to (255, 255, 255).
47
+ track_color (tuple, optional): Color of the tracks. If None, different colors will be used for different
48
+ tracks. Defaults to None.
49
+ region_thickness (int, optional): Thickness of the counting region lines. Defaults to 5.
50
+ fontsize (float, optional): Font size for the text annotations. Defaults to 0.7.
86
51
  """
52
+
53
+ # Mouse events state
54
+ self.is_drawing = False
55
+ self.selected_point = None
56
+
57
+ # Region & Line Information
58
+ self.reg_pts = reg_pts if reg_pts is not None else [(20, 60), (20, 680), (1120, 680), (1120, 60)]
59
+ self.counting_region = (
60
+ Polygon(self.reg_pts) if len(self.reg_pts) >= 3 else Polygon([(20, 60), (20, 680), (1120, 680), (1120, 60)])
61
+ )
62
+ self.region_color = region_color
63
+ self.region_thickness = region_thickness
64
+
65
+ # Image and annotation Information
66
+ self.im0 = None
87
67
  self.tf = line_thickness
88
68
  self.view_img = view_img
89
69
  self.view_queue_counts = view_queue_counts
90
- self.track_thickness = track_thickness
91
- self.draw_tracks = draw_tracks
92
- self.region_color = region_color
70
+ self.fontsize = fontsize
93
71
 
94
- if len(reg_pts) >= 3:
95
- print("Queue region initiated...")
96
- self.reg_pts = reg_pts
97
- self.counting_region = Polygon(self.reg_pts)
98
- else:
99
- print("Invalid region points provided...")
100
- print("Using default region now....")
101
- self.counting_region = Polygon(self.reg_pts)
72
+ self.names = classes_names # Class names
73
+ self.annotator = None # Annotator
74
+ self.window_name = "Ultralytics YOLOv8 Queue Manager"
102
75
 
103
- self.names = classes_names
104
- self.track_color = track_color
76
+ # Object counting Information
77
+ self.counts = 0
105
78
  self.count_txt_color = count_txt_color
106
- self.region_thickness = region_thickness
107
- self.fontsize = fontsize
79
+
80
+ # Tracks info
81
+ self.track_history = defaultdict(list)
82
+ self.track_thickness = track_thickness
83
+ self.draw_tracks = draw_tracks
84
+ self.track_color = track_color
85
+
86
+ # Check if environment supports imshow
87
+ self.env_check = check_imshow(warn=True)
108
88
 
109
89
  def extract_and_process_tracks(self, tracks):
110
90
  """Extracts and processes tracks for queue management in a video stream."""
111
91
 
112
- # Annotator Init and queue region drawing
92
+ # Initialize annotator and draw the queue region
113
93
  self.annotator = Annotator(self.im0, self.tf, self.names)
114
94
 
115
95
  if tracks[0].boxes.id is not None:
@@ -122,48 +102,48 @@ class QueueManager:
122
102
  # Draw bounding box
123
103
  self.annotator.box_label(box, label=f"{self.names[cls]}#{track_id}", color=colors(int(track_id), True))
124
104
 
125
- # Draw Tracks
105
+ # Update track history
126
106
  track_line = self.track_history[track_id]
127
107
  track_line.append((float((box[0] + box[2]) / 2), float((box[1] + box[3]) / 2)))
128
108
  if len(track_line) > 30:
129
109
  track_line.pop(0)
130
110
 
131
- # Draw track trails
111
+ # Draw track trails if enabled
132
112
  if self.draw_tracks:
133
113
  self.annotator.draw_centroid_and_tracks(
134
114
  track_line,
135
- color=self.track_color if self.track_color else colors(int(track_id), True),
115
+ color=self.track_color or colors(int(track_id), True),
136
116
  track_thickness=self.track_thickness,
137
117
  )
138
118
 
139
119
  prev_position = self.track_history[track_id][-2] if len(self.track_history[track_id]) > 1 else None
140
120
 
121
+ # Check if the object is inside the counting region
141
122
  if len(self.reg_pts) >= 3:
142
123
  is_inside = self.counting_region.contains(Point(track_line[-1]))
143
124
  if prev_position is not None and is_inside:
144
125
  self.counts += 1
145
126
 
146
- label = "Queue Counts : " + str(self.counts)
147
-
127
+ # Display queue counts
128
+ label = f"Queue Counts : {str(self.counts)}"
148
129
  if label is not None:
149
130
  self.annotator.queue_counts_display(
150
131
  label,
151
132
  points=self.reg_pts,
152
133
  region_color=self.region_color,
153
134
  txt_color=self.count_txt_color,
154
- fontsize=self.fontsize,
155
135
  )
156
136
 
157
- self.counts = 0
137
+ self.counts = 0 # Reset counts after displaying
158
138
  self.display_frames()
159
139
 
160
140
  def display_frames(self):
161
- """Display frame."""
141
+ """Displays the current frame with annotations."""
162
142
  if self.env_check:
163
143
  self.annotator.draw_region(reg_pts=self.reg_pts, thickness=self.region_thickness, color=self.region_color)
164
144
  cv2.namedWindow(self.window_name)
165
145
  cv2.imshow(self.window_name, self.im0)
166
- # Break Window
146
+ # Close window on 'q' key press
167
147
  if cv2.waitKey(1) & 0xFF == ord("q"):
168
148
  return
169
149
 
@@ -175,13 +155,14 @@ class QueueManager:
175
155
  im0 (ndarray): Current frame from the video stream.
176
156
  tracks (list): List of tracks obtained from the object tracking process.
177
157
  """
178
- self.im0 = im0 # store image
179
- self.extract_and_process_tracks(tracks) # draw region even if no objects
158
+ self.im0 = im0 # Store the current frame
159
+ self.extract_and_process_tracks(tracks) # Extract and process tracks
180
160
 
181
161
  if self.view_img:
182
- self.display_frames()
162
+ self.display_frames() # Display the frame if enabled
183
163
  return self.im0
184
164
 
185
165
 
186
166
  if __name__ == "__main__":
187
- QueueManager()
167
+ classes_names = {0: "person", 1: "car"} # example class names
168
+ queue_manager = QueueManager(classes_names)
@@ -11,73 +11,52 @@ from ultralytics.utils.plotting import Annotator, colors
11
11
 
12
12
 
13
13
  class SpeedEstimator:
14
- """A class to estimation speed of objects in real-time video stream based on their tracks."""
14
+ """A class to estimate the speed of objects in a real-time video stream based on their tracks."""
15
15
 
16
- def __init__(self):
17
- """Initializes the speed-estimator class with default values for Visual, Image, track and speed parameters."""
16
+ def __init__(self, names, reg_pts=None, view_img=False, line_thickness=2, region_thickness=5, spdl_dist_thresh=10):
17
+ """
18
+ Initializes the SpeedEstimator with the given parameters.
18
19
 
19
- # Visual & im0 information
20
+ Args:
21
+ names (dict): Dictionary of class names.
22
+ reg_pts (list, optional): List of region points for speed estimation. Defaults to [(20, 400), (1260, 400)].
23
+ view_img (bool, optional): Whether to display the image with annotations. Defaults to False.
24
+ line_thickness (int, optional): Thickness of the lines for drawing boxes and tracks. Defaults to 2.
25
+ region_thickness (int, optional): Thickness of the region lines. Defaults to 5.
26
+ spdl_dist_thresh (int, optional): Distance threshold for speed calculation. Defaults to 10.
27
+ """
28
+ # Visual & image information
20
29
  self.im0 = None
21
30
  self.annotator = None
22
- self.view_img = False
31
+ self.view_img = view_img
23
32
 
24
33
  # Region information
25
- self.reg_pts = [(20, 400), (1260, 400)]
26
- self.region_thickness = 3
34
+ self.reg_pts = reg_pts if reg_pts is not None else [(20, 400), (1260, 400)]
35
+ self.region_thickness = region_thickness
27
36
 
28
- # Predict/track information
37
+ # Tracking information
29
38
  self.clss = None
30
- self.names = None
39
+ self.names = names
31
40
  self.boxes = None
32
41
  self.trk_ids = None
33
42
  self.trk_pts = None
34
- self.line_thickness = 2
43
+ self.line_thickness = line_thickness
35
44
  self.trk_history = defaultdict(list)
36
45
 
37
- # Speed estimator information
46
+ # Speed estimation information
38
47
  self.current_time = 0
39
48
  self.dist_data = {}
40
49
  self.trk_idslist = []
41
- self.spdl_dist_thresh = 10
50
+ self.spdl_dist_thresh = spdl_dist_thresh
42
51
  self.trk_previous_times = {}
43
52
  self.trk_previous_points = {}
44
53
 
45
- # Check if environment support imshow
54
+ # Check if the environment supports imshow
46
55
  self.env_check = check_imshow(warn=True)
47
56
 
48
- def set_args(
49
- self,
50
- reg_pts,
51
- names,
52
- view_img=False,
53
- line_thickness=2,
54
- region_thickness=5,
55
- spdl_dist_thresh=10,
56
- ):
57
- """
58
- Configures the speed estimation and display parameters.
59
-
60
- Args:
61
- reg_pts (list): Initial list of points defining the speed calculation region.
62
- names (dict): object detection classes names
63
- view_img (bool): Flag indicating frame display
64
- line_thickness (int): Line thickness for bounding boxes.
65
- region_thickness (int): Speed estimation region thickness
66
- spdl_dist_thresh (int): Euclidean distance threshold for speed line
67
- """
68
- if reg_pts is None:
69
- print("Region points not provided, using default values")
70
- else:
71
- self.reg_pts = reg_pts
72
- self.names = names
73
- self.view_img = view_img
74
- self.line_thickness = line_thickness
75
- self.region_thickness = region_thickness
76
- self.spdl_dist_thresh = spdl_dist_thresh
77
-
78
57
  def extract_tracks(self, tracks):
79
58
  """
80
- Extracts results from the provided data.
59
+ Extracts results from the provided tracking data.
81
60
 
82
61
  Args:
83
62
  tracks (list): List of tracks obtained from the object tracking process.
@@ -88,11 +67,14 @@ class SpeedEstimator:
88
67
 
89
68
  def store_track_info(self, track_id, box):
90
69
  """
91
- Store track data.
70
+ Stores track data.
92
71
 
93
72
  Args:
94
- track_id (int): object track id.
95
- box (list): object bounding box data
73
+ track_id (int): Object track id.
74
+ box (list): Object bounding box data.
75
+
76
+ Returns:
77
+ (list): Updated tracking history for the given track_id.
96
78
  """
97
79
  track = self.trk_history[track_id]
98
80
  bbox_center = (float((box[0] + box[2]) / 2), float((box[1] + box[3]) / 2))
@@ -106,43 +88,39 @@ class SpeedEstimator:
106
88
 
107
89
  def plot_box_and_track(self, track_id, box, cls, track):
108
90
  """
109
- Plot track and bounding box.
91
+ Plots track and bounding box.
110
92
 
111
93
  Args:
112
- track_id (int): object track id.
113
- box (list): object bounding box data
114
- cls (str): object class name
115
- track (list): tracking history for tracks path drawing
94
+ track_id (int): Object track id.
95
+ box (list): Object bounding box data.
96
+ cls (str): Object class name.
97
+ track (list): Tracking history for drawing tracks path.
116
98
  """
117
- speed_label = f"{int(self.dist_data[track_id])}km/ph" if track_id in self.dist_data else self.names[int(cls)]
99
+ speed_label = f"{int(self.dist_data[track_id])} km/h" if track_id in self.dist_data else self.names[int(cls)]
118
100
  bbox_color = colors(int(track_id)) if track_id in self.dist_data else (255, 0, 255)
119
101
 
120
102
  self.annotator.box_label(box, speed_label, bbox_color)
121
-
122
103
  cv2.polylines(self.im0, [self.trk_pts], isClosed=False, color=(0, 255, 0), thickness=1)
123
104
  cv2.circle(self.im0, (int(track[-1][0]), int(track[-1][1])), 5, bbox_color, -1)
124
105
 
125
106
  def calculate_speed(self, trk_id, track):
126
107
  """
127
- Calculation of object speed.
108
+ Calculates the speed of an object.
128
109
 
129
110
  Args:
130
- trk_id (int): object track id.
131
- track (list): tracking history for tracks path drawing
111
+ trk_id (int): Object track id.
112
+ track (list): Tracking history for drawing tracks path.
132
113
  """
133
-
134
114
  if not self.reg_pts[0][0] < track[-1][0] < self.reg_pts[1][0]:
135
115
  return
136
116
  if self.reg_pts[1][1] - self.spdl_dist_thresh < track[-1][1] < self.reg_pts[1][1] + self.spdl_dist_thresh:
137
117
  direction = "known"
138
-
139
118
  elif self.reg_pts[0][1] - self.spdl_dist_thresh < track[-1][1] < self.reg_pts[0][1] + self.spdl_dist_thresh:
140
119
  direction = "known"
141
-
142
120
  else:
143
121
  direction = "unknown"
144
122
 
145
- if self.trk_previous_times[trk_id] != 0 and direction != "unknown" and trk_id not in self.trk_idslist:
123
+ if self.trk_previous_times.get(trk_id) != 0 and direction != "unknown" and trk_id not in self.trk_idslist:
146
124
  self.trk_idslist.append(trk_id)
147
125
 
148
126
  time_difference = time() - self.trk_previous_times[trk_id]
@@ -156,21 +134,24 @@ class SpeedEstimator:
156
134
 
157
135
  def estimate_speed(self, im0, tracks, region_color=(255, 0, 0)):
158
136
  """
159
- Calculate object based on tracking data.
137
+ Estimates the speed of objects based on tracking data.
160
138
 
161
139
  Args:
162
- im0 (nd array): Image
140
+ im0 (ndarray): Image.
163
141
  tracks (list): List of tracks obtained from the object tracking process.
164
- region_color (tuple): Color to use when drawing regions.
142
+ region_color (tuple, optional): Color to use when drawing regions. Defaults to (255, 0, 0).
143
+
144
+ Returns:
145
+ (ndarray): The image with annotated boxes and tracks.
165
146
  """
166
147
  self.im0 = im0
167
148
  if tracks[0].boxes.id is None:
168
149
  if self.view_img and self.env_check:
169
150
  self.display_frames()
170
151
  return im0
171
- self.extract_tracks(tracks)
172
152
 
173
- self.annotator = Annotator(self.im0, line_width=2)
153
+ self.extract_tracks(tracks)
154
+ self.annotator = Annotator(self.im0, line_width=self.line_thickness)
174
155
  self.annotator.draw_region(reg_pts=self.reg_pts, color=region_color, thickness=self.region_thickness)
175
156
 
176
157
  for box, trk_id, cls in zip(self.boxes, self.trk_ids, self.clss):
@@ -188,11 +169,12 @@ class SpeedEstimator:
188
169
  return im0
189
170
 
190
171
  def display_frames(self):
191
- """Display frame."""
172
+ """Displays the current frame."""
192
173
  cv2.imshow("Ultralytics Speed Estimation", self.im0)
193
174
  if cv2.waitKey(1) & 0xFF == ord("q"):
194
175
  return
195
176
 
196
177
 
197
178
  if __name__ == "__main__":
198
- SpeedEstimator()
179
+ names = {0: "person", 1: "car"} # example class names
180
+ speed_estimator = SpeedEstimator(names)
@@ -378,7 +378,7 @@ class Annotator:
378
378
  cv2.polylines(self.im, [points], isClosed=False, color=color, thickness=track_thickness)
379
379
  cv2.circle(self.im, (int(track[-1][0]), int(track[-1][1])), track_thickness * 2, color, -1)
380
380
 
381
- def queue_counts_display(self, label, points=None, region_color=(255, 255, 255), txt_color=(0, 0, 0), fontsize=0.7):
381
+ def queue_counts_display(self, label, points=None, region_color=(255, 255, 255), txt_color=(0, 0, 0)):
382
382
  """
383
383
  Displays queue counts on an image centered at the points with customizable font size and colors.
384
384
 
@@ -387,14 +387,14 @@ class Annotator:
387
387
  points (tuple): region points for center point calculation to display text
388
388
  region_color (RGB): queue region color
389
389
  txt_color (RGB): text display color
390
- fontsize (float): text fontsize
391
390
  """
391
+
392
392
  x_values = [point[0] for point in points]
393
393
  y_values = [point[1] for point in points]
394
394
  center_x = sum(x_values) // len(points)
395
395
  center_y = sum(y_values) // len(points)
396
396
 
397
- text_size = cv2.getTextSize(label, 0, fontScale=fontsize, thickness=self.tf)[0]
397
+ text_size = cv2.getTextSize(label, 0, fontScale=self.sf, thickness=self.tf)[0]
398
398
  text_width = text_size[0]
399
399
  text_height = text_size[1]
400
400
 
@@ -413,13 +413,12 @@ class Annotator:
413
413
  label,
414
414
  (text_x, text_y),
415
415
  0,
416
- fontScale=fontsize,
416
+ fontScale=self.sf,
417
417
  color=txt_color,
418
418
  thickness=self.tf,
419
419
  lineType=cv2.LINE_AA,
420
420
  )
421
421
 
422
- ### Parking management utils
423
422
  def display_objects_labels(self, im0, text, txt_color, bg_color, x_center, y_center, margin):
424
423
  """
425
424
  Display the bounding boxes labels in parking management app.
@@ -445,7 +444,6 @@ class Annotator:
445
444
  cv2.rectangle(im0, (rect_x1, rect_y1), (rect_x2, rect_y2), bg_color, -1)
446
445
  cv2.putText(im0, text, (text_x, text_y), 0, self.sf, txt_color, self.tf, lineType=cv2.LINE_AA)
447
446
 
448
- # Parking lot and object counting app
449
447
  def display_analytics(self, im0, text, txt_color, bg_color, margin):
450
448
  """
451
449
  Display the overall statistics for parking lots
@@ -459,12 +457,12 @@ class Annotator:
459
457
 
460
458
  horizontal_gap = int(im0.shape[1] * 0.02)
461
459
  vertical_gap = int(im0.shape[0] * 0.01)
462
-
463
460
  text_y_offset = 0
464
-
465
461
  for label, value in text.items():
466
462
  txt = f"{label}: {value}"
467
- text_size = cv2.getTextSize(txt, 0, int(self.sf * 1.5), int(self.tf * 1.5))[0]
463
+ text_size = cv2.getTextSize(txt, 0, self.sf, self.tf)[0]
464
+ if text_size[0] < 5 or text_size[1] < 5:
465
+ text_size = (5, 5)
468
466
  text_x = im0.shape[1] - text_size[0] - margin * 2 - horizontal_gap
469
467
  text_y = text_y_offset + text_size[1] + margin * 2 + vertical_gap
470
468
  rect_x1 = text_x - margin * 2
@@ -472,9 +470,7 @@ class Annotator:
472
470
  rect_x2 = text_x + text_size[0] + margin * 2
473
471
  rect_y2 = text_y + margin * 2
474
472
  cv2.rectangle(im0, (rect_x1, rect_y1), (rect_x2, rect_y2), bg_color, -1)
475
- cv2.putText(
476
- im0, txt, (text_x, text_y), 0, int(self.sf * 1.5), txt_color, int(self.tf * 1.5), lineType=cv2.LINE_AA
477
- )
473
+ cv2.putText(im0, txt, (text_x, text_y), 0, self.sf, txt_color, self.tf, lineType=cv2.LINE_AA)
478
474
  text_y_offset = rect_y2
479
475
 
480
476
  @staticmethod
@@ -518,7 +514,9 @@ class Annotator:
518
514
  cv2.circle(self.im, (int(x_coord), int(y_coord)), radius, (0, 255, 0), -1, lineType=cv2.LINE_AA)
519
515
  return self.im
520
516
 
521
- def plot_angle_and_count_and_stage(self, angle_text, count_text, stage_text, center_kpt, line_thickness=2):
517
+ def plot_angle_and_count_and_stage(
518
+ self, angle_text, count_text, stage_text, center_kpt, color=(104, 31, 17), txt_color=(255, 255, 255)
519
+ ):
522
520
  """
523
521
  Plot the pose angle, count value and step stage.
524
522
 
@@ -527,16 +525,17 @@ class Annotator:
527
525
  count_text (str): counts value for workout monitoring
528
526
  stage_text (str): stage decision for workout monitoring
529
527
  center_kpt (int): centroid pose index for workout monitoring
530
- line_thickness (int): thickness for text display
528
+ color (tuple): text background color for workout monitoring
529
+ txt_color (tuple): text foreground color for workout monitoring
531
530
  """
531
+
532
532
  angle_text, count_text, stage_text = (f" {angle_text:.2f}", f"Steps : {count_text}", f" {stage_text}")
533
- font_scale = 0.6 + (line_thickness / 10.0)
534
533
 
535
534
  # Draw angle
536
- (angle_text_width, angle_text_height), _ = cv2.getTextSize(angle_text, 0, font_scale, line_thickness)
535
+ (angle_text_width, angle_text_height), _ = cv2.getTextSize(angle_text, 0, self.sf, self.tf)
537
536
  angle_text_position = (int(center_kpt[0]), int(center_kpt[1]))
538
537
  angle_background_position = (angle_text_position[0], angle_text_position[1] - angle_text_height - 5)
539
- angle_background_size = (angle_text_width + 2 * 5, angle_text_height + 2 * 5 + (line_thickness * 2))
538
+ angle_background_size = (angle_text_width + 2 * 5, angle_text_height + 2 * 5 + (self.tf * 2))
540
539
  cv2.rectangle(
541
540
  self.im,
542
541
  angle_background_position,
@@ -544,19 +543,19 @@ class Annotator:
544
543
  angle_background_position[0] + angle_background_size[0],
545
544
  angle_background_position[1] + angle_background_size[1],
546
545
  ),
547
- (255, 255, 255),
546
+ color,
548
547
  -1,
549
548
  )
550
- cv2.putText(self.im, angle_text, angle_text_position, 0, font_scale, (0, 0, 0), line_thickness)
549
+ cv2.putText(self.im, angle_text, angle_text_position, 0, self.sf, txt_color, self.tf)
551
550
 
552
551
  # Draw Counts
553
- (count_text_width, count_text_height), _ = cv2.getTextSize(count_text, 0, font_scale, line_thickness)
552
+ (count_text_width, count_text_height), _ = cv2.getTextSize(count_text, 0, self.sf, self.tf)
554
553
  count_text_position = (angle_text_position[0], angle_text_position[1] + angle_text_height + 20)
555
554
  count_background_position = (
556
555
  angle_background_position[0],
557
556
  angle_background_position[1] + angle_background_size[1] + 5,
558
557
  )
559
- count_background_size = (count_text_width + 10, count_text_height + 10 + (line_thickness * 2))
558
+ count_background_size = (count_text_width + 10, count_text_height + 10 + self.tf)
560
559
 
561
560
  cv2.rectangle(
562
561
  self.im,
@@ -565,13 +564,13 @@ class Annotator:
565
564
  count_background_position[0] + count_background_size[0],
566
565
  count_background_position[1] + count_background_size[1],
567
566
  ),
568
- (255, 255, 255),
567
+ color,
569
568
  -1,
570
569
  )
571
- cv2.putText(self.im, count_text, count_text_position, 0, font_scale, (0, 0, 0), line_thickness)
570
+ cv2.putText(self.im, count_text, count_text_position, 0, self.sf, txt_color, self.tf)
572
571
 
573
572
  # Draw Stage
574
- (stage_text_width, stage_text_height), _ = cv2.getTextSize(stage_text, 0, font_scale, line_thickness)
573
+ (stage_text_width, stage_text_height), _ = cv2.getTextSize(stage_text, 0, self.sf, self.tf)
575
574
  stage_text_position = (int(center_kpt[0]), int(center_kpt[1]) + angle_text_height + count_text_height + 40)
576
575
  stage_background_position = (stage_text_position[0], stage_text_position[1] - stage_text_height - 5)
577
576
  stage_background_size = (stage_text_width + 10, stage_text_height + 10)
@@ -583,10 +582,10 @@ class Annotator:
583
582
  stage_background_position[0] + stage_background_size[0],
584
583
  stage_background_position[1] + stage_background_size[1],
585
584
  ),
586
- (255, 255, 255),
585
+ color,
587
586
  -1,
588
587
  )
589
- cv2.putText(self.im, stage_text, stage_text_position, 0, font_scale, (0, 0, 0), line_thickness)
588
+ cv2.putText(self.im, stage_text, stage_text_position, 0, self.sf, txt_color, self.tf)
590
589
 
591
590
  def seg_bbox(self, mask, mask_color=(255, 0, 255), det_label=None, track_label=None):
592
591
  """
@@ -626,29 +625,30 @@ class Annotator:
626
625
  line_color (RGB): Distance line color.
627
626
  centroid_color (RGB): Bounding box centroid color.
628
627
  """
629
- (text_width_m, text_height_m), _ = cv2.getTextSize(f"Distance M: {distance_m:.2f}m", 0, 0.8, 2)
630
- cv2.rectangle(self.im, (15, 25), (15 + text_width_m + 10, 25 + text_height_m + 20), (255, 255, 255), -1)
628
+
629
+ (text_width_m, text_height_m), _ = cv2.getTextSize(f"Distance M: {distance_m:.2f}m", 0, self.sf, self.tf)
630
+ cv2.rectangle(self.im, (15, 25), (15 + text_width_m + 10, 25 + text_height_m + 20), line_color, -1)
631
631
  cv2.putText(
632
632
  self.im,
633
633
  f"Distance M: {distance_m:.2f}m",
634
634
  (20, 50),
635
635
  0,
636
- 0.8,
637
- (0, 0, 0),
638
- 2,
636
+ self.sf,
637
+ centroid_color,
638
+ self.tf,
639
639
  cv2.LINE_AA,
640
640
  )
641
641
 
642
- (text_width_mm, text_height_mm), _ = cv2.getTextSize(f"Distance MM: {distance_mm:.2f}mm", 0, 0.8, 2)
643
- cv2.rectangle(self.im, (15, 75), (15 + text_width_mm + 10, 75 + text_height_mm + 20), (255, 255, 255), -1)
642
+ (text_width_mm, text_height_mm), _ = cv2.getTextSize(f"Distance MM: {distance_mm:.2f}mm", 0, self.sf, self.tf)
643
+ cv2.rectangle(self.im, (15, 75), (15 + text_width_mm + 10, 75 + text_height_mm + 20), line_color, -1)
644
644
  cv2.putText(
645
645
  self.im,
646
646
  f"Distance MM: {distance_mm:.2f}mm",
647
647
  (20, 100),
648
648
  0,
649
- 0.8,
650
- (0, 0, 0),
651
- 2,
649
+ self.sf,
650
+ centroid_color,
651
+ self.tf,
652
652
  cv2.LINE_AA,
653
653
  )
654
654
 
@@ -656,7 +656,7 @@ class Annotator:
656
656
  cv2.circle(self.im, centroids[0], 6, centroid_color, -1)
657
657
  cv2.circle(self.im, centroids[1], 6, centroid_color, -1)
658
658
 
659
- def visioneye(self, box, center_point, color=(235, 219, 11), pin_color=(255, 0, 255), thickness=2, pins_radius=10):
659
+ def visioneye(self, box, center_point, color=(235, 219, 11), pin_color=(255, 0, 255)):
660
660
  """
661
661
  Function for pinpoint human-vision eye mapping and plotting.
662
662
 
@@ -665,13 +665,11 @@ class Annotator:
665
665
  center_point (tuple): center point for vision eye view
666
666
  color (tuple): object centroid and line color value
667
667
  pin_color (tuple): visioneye point color value
668
- thickness (int): int value for line thickness
669
- pins_radius (int): visioneye point radius value
670
668
  """
671
669
  center_bbox = int((box[0] + box[2]) / 2), int((box[1] + box[3]) / 2)
672
- cv2.circle(self.im, center_point, pins_radius, pin_color, -1)
673
- cv2.circle(self.im, center_bbox, pins_radius, color, -1)
674
- cv2.line(self.im, center_point, center_bbox, color, thickness)
670
+ cv2.circle(self.im, center_point, self.tf * 2, pin_color, -1)
671
+ cv2.circle(self.im, center_bbox, self.tf * 2, color, -1)
672
+ cv2.line(self.im, center_point, center_bbox, color, self.tf)
675
673
 
676
674
 
677
675
  @TryExcept() # known issue https://github.com/ultralytics/yolov5/issues/5395