megadetector 5.0.27__py3-none-any.whl → 5.0.28__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 megadetector might be problematic. Click here for more details.

Files changed (26) hide show
  1. megadetector/data_management/mewc_to_md.py +1 -1
  2. megadetector/data_management/read_exif.py +2 -0
  3. megadetector/detection/process_video.py +1 -1
  4. megadetector/detection/pytorch_detector.py +4 -4
  5. megadetector/detection/run_detector.py +10 -3
  6. megadetector/detection/run_detector_batch.py +4 -3
  7. megadetector/detection/run_tiled_inference.py +65 -13
  8. megadetector/detection/video_utils.py +2 -2
  9. megadetector/postprocessing/classification_postprocessing.py +517 -20
  10. megadetector/postprocessing/create_crop_folder.py +1 -1
  11. megadetector/postprocessing/generate_csv_report.py +499 -0
  12. megadetector/postprocessing/load_api_results.py +4 -4
  13. megadetector/postprocessing/postprocess_batch_results.py +6 -4
  14. megadetector/taxonomy_mapping/preview_lila_taxonomy.py +0 -3
  15. megadetector/taxonomy_mapping/taxonomy_graph.py +1 -1
  16. megadetector/utils/ct_utils.py +3 -2
  17. megadetector/utils/path_utils.py +75 -29
  18. megadetector/utils/split_locations_into_train_val.py +16 -3
  19. megadetector/utils/wi_utils.py +68 -410
  20. megadetector/visualization/visualization_utils.py +25 -9
  21. megadetector/visualization/visualize_detector_output.py +50 -28
  22. {megadetector-5.0.27.dist-info → megadetector-5.0.28.dist-info}/METADATA +132 -132
  23. {megadetector-5.0.27.dist-info → megadetector-5.0.28.dist-info}/RECORD +26 -25
  24. {megadetector-5.0.27.dist-info → megadetector-5.0.28.dist-info}/WHEEL +1 -1
  25. {megadetector-5.0.27.dist-info → megadetector-5.0.28.dist-info}/licenses/LICENSE +0 -0
  26. {megadetector-5.0.27.dist-info → megadetector-5.0.28.dist-info}/top_level.txt +0 -0
@@ -10,7 +10,6 @@ detector output result file (.json), optionally writing an HTML index file.
10
10
  #%% Imports
11
11
 
12
12
  import argparse
13
- import json
14
13
  import os
15
14
  import random
16
15
  import sys
@@ -21,11 +20,13 @@ from functools import partial
21
20
  from tqdm import tqdm
22
21
 
23
22
  from megadetector.data_management.annotations.annotation_constants import detector_bbox_category_id_to_name
24
- from megadetector.visualization import visualization_utils as vis_utils
25
- from megadetector.visualization.visualization_utils import blur_detections
23
+ from megadetector.detection.run_detector import get_typical_confidence_threshold_from_results
26
24
  from megadetector.utils.ct_utils import get_max_conf
27
25
  from megadetector.utils import write_html_image_list
28
- from megadetector.detection.run_detector import get_typical_confidence_threshold_from_results
26
+ from megadetector.utils.path_utils import path_is_abs
27
+ from megadetector.utils.wi_utils import load_md_or_speciesnet_file
28
+ from megadetector.visualization import visualization_utils as vis_utils
29
+ from megadetector.visualization.visualization_utils import blur_detections
29
30
 
30
31
 
31
32
  #%% Constants
@@ -73,9 +74,16 @@ def _render_image(entry,
73
74
  rendering_result['skipped_image'] = True
74
75
  return rendering_result
75
76
 
76
- image_filename_in_abs = os.path.join(images_dir, image_id)
77
+ if images_dir is None:
78
+ image_filename_in_abs = image_id
79
+ assert path_is_abs(image_filename_in_abs), \
80
+ 'Absolute paths are required when no image base dir is supplied'
81
+ else:
82
+ assert not path_is_abs(image_id), \
83
+ 'Relative paths are required when an image base dir is supplied'
84
+ image_filename_in_abs = os.path.join(images_dir, image_id)
77
85
  if not os.path.exists(image_filename_in_abs):
78
- print(f'Image {image_id} not found in images_dir')
86
+ print(f'Image {image_id} not found')
79
87
  rendering_result['missing_image'] = True
80
88
  return rendering_result
81
89
 
@@ -125,12 +133,14 @@ def _render_image(entry,
125
133
 
126
134
  return rendering_result
127
135
 
136
+ # ...def _render_image(...)
137
+
128
138
 
129
139
  #%% Main function
130
140
 
131
141
  def visualize_detector_output(detector_output_path,
132
142
  out_dir,
133
- images_dir,
143
+ images_dir=None,
134
144
  confidence_threshold=0.15,
135
145
  sample=-1,
136
146
  output_image_width=700,
@@ -153,20 +163,24 @@ def visualize_detector_output(detector_output_path,
153
163
  detector_output_path (str): path to detector output .json file
154
164
  out_dir (str): path to directory for saving annotated images
155
165
  images_dir (str): folder where the images live; filenames in
156
- [detector_output_path] should be relative to [image_dir]
166
+ [detector_output_path] should be relative to [image_dir]. Can be None if paths are
167
+ absolute.
157
168
  confidence_threshold (float, optional): threshold above which detections will be rendered
158
169
  sample (int, optional): maximum number of images to render, -1 for all
159
170
  output_image_width (int, optional): width in pixels to resize images for display,
160
171
  preserving aspect ration; set to -1 to use original image width
161
172
  random_seed (int, optional): seed to use for choosing images when sample != -1
162
- render_detections_only (bool): only render images with above-threshold detections
173
+ render_detections_only (bool): only render images with above-threshold detections. Empty
174
+ images are discarded after sampling, so if you want to see, e.g., 1000 non-empty images,
175
+ you can set [render_detections_only], but you need to sample more than 1000 images.
163
176
  classification_confidence_threshold (float, optional): only show classifications
164
177
  above this threshold; does not impact whether images are rendered, only whether
165
178
  classification labels (not detection categories) are displayed
166
179
  html_output_file (str, optional): output path for an HTML index file (not written
167
180
  if None)
168
181
  html_output_options (dict, optional): HTML formatting options; see write_html_image_list
169
- for details
182
+ for details. The most common option you may want to supply here is
183
+ 'maxFiguresPerHtmlFile'.
170
184
  preserve_path_structure (bool, optional): if False (default), writes images to unique
171
185
  names in a flat structure in the output folder; if True, preserves relative paths
172
186
  within the output folder
@@ -188,25 +202,24 @@ def visualize_detector_output(detector_output_path,
188
202
  assert os.path.exists(detector_output_path), \
189
203
  'Detector output file does not exist at {}'.format(detector_output_path)
190
204
 
191
- assert os.path.isdir(images_dir), \
192
- 'Image folder {} is not available'.format(images_dir)
205
+ if images_dir is not None:
206
+ assert os.path.isdir(images_dir), \
207
+ 'Image folder {} is not available'.format(images_dir)
193
208
 
194
209
  os.makedirs(out_dir, exist_ok=True)
195
210
 
196
211
 
197
212
  ##%% Load detector output
198
213
 
199
- with open(detector_output_path) as f:
200
- detector_output = json.load(f)
201
- assert 'images' in detector_output, (
202
- 'Detector output file should be a json with an "images" field.')
214
+ detector_output = load_md_or_speciesnet_file(detector_output_path)
215
+
203
216
  images = detector_output['images']
204
217
 
205
218
  if confidence_threshold is None:
206
219
  confidence_threshold = get_typical_confidence_threshold_from_results(detector_output)
207
220
 
208
- assert confidence_threshold >= 0 and confidence_threshold <= 1, (
209
- f'Confidence threshold {confidence_threshold} is invalid, must be in (0, 1).')
221
+ assert confidence_threshold >= 0 and confidence_threshold <= 1, \
222
+ f'Confidence threshold {confidence_threshold} is invalid, must be in (0, 1).'
210
223
 
211
224
  if 'detection_categories' in detector_output:
212
225
  detector_label_map = detector_output['detection_categories']
@@ -303,9 +316,12 @@ def visualize_detector_output(detector_output_path,
303
316
  html_dir = os.path.dirname(html_output_file)
304
317
 
305
318
  html_image_info = []
306
-
319
+
307
320
  for r in rendering_results:
308
321
  d = {}
322
+ if r['annotated_image_path'] is None:
323
+ assert r['failed_image'] or r['missing_image'] or r['skipped_image']
324
+ continue
309
325
  annotated_image_path_relative = os.path.relpath(r['annotated_image_path'],html_dir)
310
326
  d['filename'] = annotated_image_path_relative
311
327
  d['textStyle'] = \
@@ -319,6 +335,8 @@ def visualize_detector_output(detector_output_path,
319
335
 
320
336
  return annotated_image_paths
321
337
 
338
+ # ...def visualize_detector_output(...)
339
+
322
340
 
323
341
  #%% Command-line driver
324
342
 
@@ -336,42 +354,45 @@ def main():
336
354
  help='Path to directory where the annotated images will be saved. '
337
355
  'The directory will be created if it does not exist.')
338
356
  parser.add_argument(
339
- '-c', '--confidence', type=float, default=0.15,
357
+ '--confidence', type=float, default=0.15,
340
358
  help='Value between 0 and 1, indicating the confidence threshold '
341
359
  'above which to visualize bounding boxes')
342
360
  parser.add_argument(
343
- '-i', '--images_dir', type=str, default=None,
361
+ '--images_dir', type=str, default=None,
344
362
  help='Path to a local directory where images are stored. This '
345
363
  'serves as the root directory for image paths in '
346
- 'detector_output_path.')
364
+ 'detector_output_path. Omit if image paths are absolute.')
347
365
  parser.add_argument(
348
- '-n', '--sample', type=int, default=-1,
366
+ '--sample', type=int, default=-1,
349
367
  help='Number of images to be annotated and rendered. Set to -1 '
350
368
  '(default) to annotate all images in the detector output file. '
351
369
  'There may be fewer images if some are not found in images_dir.')
352
370
  parser.add_argument(
353
- '-w', '--output_image_width', type=int, default=700,
371
+ '--output_image_width', type=int, default=700,
354
372
  help='Integer, desired width in pixels of the output annotated images. '
355
373
  'Use -1 to not resize. Default: 700.')
356
374
  parser.add_argument(
357
- '-r', '--random_seed', type=int, default=None,
375
+ '--random_seed', type=int, default=None,
358
376
  help='Integer, for deterministic order of image sampling')
359
377
  parser.add_argument(
360
- '-html', '--html_output_file', type=str, default=None,
378
+ '--html_output_file', type=str, default=None,
361
379
  help='Filename to which we should write an HTML image index (off by default)')
362
380
  parser.add_argument(
363
381
  '--open_html_output_file', action='store_true',
364
382
  help='Open the .html output file when done')
365
383
  parser.add_argument(
366
- '-do', '--detections_only', action='store_true',
384
+ '--detections_only', action='store_true',
367
385
  help='Only render images with above-threshold detections (by default, '
368
386
  'both empty and non-empty images are rendered).')
369
387
  parser.add_argument(
370
- '-pps', '--preserve_path_structure', action='store_true',
388
+ '--preserve_path_structure', action='store_true',
371
389
  help='Preserve relative image paths (otherwise flattens and assigns unique file names)')
372
390
  parser.add_argument(
373
391
  '--category_names_to_blur', default=None, type=str,
374
392
  help='Comma-separated list of category names to blur (or a single category name, typically "person")')
393
+ parser.add_argument(
394
+ '--classification_confidence', type=float, default=0.1,
395
+ help='If classification results are present, render results above this threshold')
375
396
 
376
397
  if len(sys.argv[1:]) == 0:
377
398
  parser.print_help()
@@ -392,6 +413,7 @@ def main():
392
413
  output_image_width=args.output_image_width,
393
414
  random_seed=args.random_seed,
394
415
  render_detections_only=args.detections_only,
416
+ classification_confidence_threshold=args.classification_confidence,
395
417
  preserve_path_structure=args.preserve_path_structure,
396
418
  html_output_file=args.html_output_file,
397
419
  category_names_to_blur=category_names_to_blur)
@@ -1,132 +1,132 @@
1
- Metadata-Version: 2.4
2
- Name: megadetector
3
- Version: 5.0.27
4
- Summary: MegaDetector is an AI model that helps conservation folks spend less time doing boring things with camera trap images.
5
- Author-email: Your friendly neighborhood MegaDetector team <cameratraps@lila.science>
6
- Maintainer-email: Your friendly neighborhood MegaDetector team <cameratraps@lila.science>
7
- License: MIT License
8
-
9
- Permission is hereby granted, free of charge, to any person obtaining a copy
10
- of this software and associated documentation files (the "Software"), to deal
11
- in the Software without restriction, including without limitation the rights
12
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
13
- copies of the Software, and to permit persons to whom the Software is
14
- furnished to do so, subject to the following conditions:
15
-
16
- The above copyright notice and this permission notice shall be included in all
17
- copies or substantial portions of the Software.
18
-
19
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
20
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
22
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
23
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
24
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
25
- SOFTWARE.
26
-
27
- Project-URL: Homepage, https://github.com/agentmorris/MegaDetector
28
- Project-URL: Documentation, https://megadetector.readthedocs.io
29
- Project-URL: Bug Reports, https://github.com/agentmorris/MegaDetector/issues
30
- Project-URL: Source, https://github.com/agentmorris/MegaDetector
31
- Keywords: camera traps,conservation,wildlife,ai,megadetector
32
- Classifier: Programming Language :: Python :: 3
33
- Requires-Python: <3.14,>=3.9
34
- Description-Content-Type: text/markdown
35
- License-File: LICENSE
36
- Requires-Dist: mkl==2024.0; sys_platform != "darwin"
37
- Requires-Dist: numpy<2.0,>=1.26.4
38
- Requires-Dist: Pillow>=9.5
39
- Requires-Dist: tqdm>=4.64.0
40
- Requires-Dist: jsonpickle>=3.0.2
41
- Requires-Dist: humanfriendly>=10.0
42
- Requires-Dist: matplotlib>=3.8.0
43
- Requires-Dist: opencv-python>=4.8.0
44
- Requires-Dist: requests>=2.31.0
45
- Requires-Dist: pyqtree>=1.0.0
46
- Requires-Dist: scikit-learn>=1.3.1
47
- Requires-Dist: pandas>=2.1.1
48
- Requires-Dist: python-dateutil
49
- Requires-Dist: send2trash
50
- Requires-Dist: dill
51
- Requires-Dist: ultralytics-yolov5==0.1.1
52
- Requires-Dist: yolov9pip==0.0.4
53
- Requires-Dist: python-dateutil
54
- Dynamic: license-file
55
-
56
- # MegaDetector
57
-
58
- This package is a pip-installable version of the support/inference code for [MegaDetector](https://github.com/agentmorris/MegaDetector/?tab=readme-ov-file#megadetector), an object detection model that helps conservation biologists spend less time doing boring things with camera trap images. Complete documentation for this Python package is available at [megadetector.readthedocs.io](https://megadetector.readthedocs.io).
59
-
60
- If you aren't looking for the Python package specifically, and you just want to learn more about what MegaDetector is all about, head over to the [MegaDetector repo](https://github.com/agentmorris/MegaDetector/?tab=readme-ov-file#megadetector).
61
-
62
- If you don't want to run MegaDetector, and you just want to use the utilities in this package - postprocessing, manipulating large volumes of camera trap images, etc. - you may want to check out the [megadetector-utils](https://pypi.org/project/megadetector-utils/) package, which is identical to this one, but excludes all of the PyTorch/YOLO dependencies, and is thus approximately one zillion times smaller.
63
-
64
- ## Installation
65
-
66
- Install with:
67
-
68
- `pip install megadetector`
69
-
70
- MegaDetector model weights aren't downloaded at the time you install the package, but they will be (optionally) automatically downloaded the first time you run the model.
71
-
72
- ## Package reference
73
-
74
- See [megadetector.readthedocs.io](https://megadetector.readthedocs.io).
75
-
76
-
77
- ## Examples of things you can do with this package
78
-
79
- ### Run MegaDetector on one image and count the number of detections
80
-
81
- ```
82
- from megadetector.utils import url_utils
83
- from megadetector.visualization import visualization_utils as vis_utils
84
- from megadetector.detection import run_detector
85
-
86
- # This is the image at the bottom of this page, it has one animal in it
87
- image_url = 'https://github.com/agentmorris/MegaDetector/raw/main/images/orinoquia-thumb-web.jpg'
88
- temporary_filename = url_utils.download_url(image_url)
89
-
90
- image = vis_utils.load_image(temporary_filename)
91
-
92
- # This will automatically download MDv5a; you can also specify a filename.
93
- model = run_detector.load_detector('MDV5A')
94
-
95
- result = model.generate_detections_one_image(image)
96
-
97
- detections_above_threshold = [d for d in result['detections'] if d['conf'] > 0.2]
98
- print('Found {} detections above threshold'.format(len(detections_above_threshold)))
99
- ```
100
-
101
- ### Run MegaDetector on a folder of images
102
-
103
- ```
104
- from megadetector.detection.run_detector_batch import \
105
- load_and_run_detector_batch, write_results_to_file
106
- from megadetector.utils import path_utils
107
- import os
108
-
109
- # Pick a folder to run MD on recursively, and an output file
110
- image_folder = os.path.expanduser('~/megadetector_test_images')
111
- output_file = os.path.expanduser('~/megadetector_output_test.json')
112
-
113
- # Recursively find images
114
- image_file_names = path_utils.find_images(image_folder,recursive=True)
115
-
116
- # This will automatically download MDv5a; you can also specify a filename.
117
- results = load_and_run_detector_batch('MDV5A', image_file_names)
118
-
119
- # Write results to a format that Timelapse and other downstream tools like.
120
- write_results_to_file(results,
121
- output_file,
122
- relative_path_base=image_folder,
123
- detector_file=detector_filename)
124
- ```
125
-
126
- ## Contact
127
-
128
- Contact <a href="cameratraps@lila.science">cameratraps@lila.science</a> with questions.
129
-
130
- ## Gratuitous animal picture
131
-
132
- <img src="https://github.com/agentmorris/MegaDetector/raw/main/images/orinoquia-thumb-web_detections.jpg"><br/>Image credit University of Minnesota, from the [Orinoquía Camera Traps](http://lila.science/datasets/orinoquia-camera-traps/) data set.
1
+ Metadata-Version: 2.4
2
+ Name: megadetector
3
+ Version: 5.0.28
4
+ Summary: MegaDetector is an AI model that helps conservation folks spend less time doing boring things with camera trap images.
5
+ Author-email: Your friendly neighborhood MegaDetector team <cameratraps@lila.science>
6
+ Maintainer-email: Your friendly neighborhood MegaDetector team <cameratraps@lila.science>
7
+ License: MIT License
8
+
9
+ Permission is hereby granted, free of charge, to any person obtaining a copy
10
+ of this software and associated documentation files (the "Software"), to deal
11
+ in the Software without restriction, including without limitation the rights
12
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
13
+ copies of the Software, and to permit persons to whom the Software is
14
+ furnished to do so, subject to the following conditions:
15
+
16
+ The above copyright notice and this permission notice shall be included in all
17
+ copies or substantial portions of the Software.
18
+
19
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
20
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
22
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
23
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
24
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
25
+ SOFTWARE.
26
+
27
+ Project-URL: Homepage, https://github.com/agentmorris/MegaDetector
28
+ Project-URL: Documentation, https://megadetector.readthedocs.io
29
+ Project-URL: Bug Reports, https://github.com/agentmorris/MegaDetector/issues
30
+ Project-URL: Source, https://github.com/agentmorris/MegaDetector
31
+ Keywords: camera traps,conservation,wildlife,ai,megadetector
32
+ Classifier: Programming Language :: Python :: 3
33
+ Requires-Python: <3.14,>=3.9
34
+ Description-Content-Type: text/markdown
35
+ License-File: LICENSE
36
+ Requires-Dist: mkl==2024.0; sys_platform != "darwin"
37
+ Requires-Dist: numpy>=1.26.4
38
+ Requires-Dist: Pillow>=9.5
39
+ Requires-Dist: tqdm>=4.64.0
40
+ Requires-Dist: jsonpickle>=3.0.2
41
+ Requires-Dist: humanfriendly>=10.0
42
+ Requires-Dist: matplotlib>=3.8.0
43
+ Requires-Dist: opencv-python>=4.8.0
44
+ Requires-Dist: requests>=2.31.0
45
+ Requires-Dist: pyqtree>=1.0.0
46
+ Requires-Dist: scikit-learn>=1.3.1
47
+ Requires-Dist: pandas>=2.1.1
48
+ Requires-Dist: python-dateutil
49
+ Requires-Dist: send2trash
50
+ Requires-Dist: dill
51
+ Requires-Dist: ultralytics-yolov5==0.1.1
52
+ Requires-Dist: yolov9pip==0.0.4
53
+ Requires-Dist: python-dateutil
54
+ Dynamic: license-file
55
+
56
+ # MegaDetector
57
+
58
+ This package is a pip-installable version of the support/inference code for [MegaDetector](https://github.com/agentmorris/MegaDetector/?tab=readme-ov-file#megadetector), an object detection model that helps conservation biologists spend less time doing boring things with camera trap images. Complete documentation for this Python package is available at [megadetector.readthedocs.io](https://megadetector.readthedocs.io).
59
+
60
+ If you aren't looking for the Python package specifically, and you just want to learn more about what MegaDetector is all about, head over to the [MegaDetector repo](https://github.com/agentmorris/MegaDetector/?tab=readme-ov-file#megadetector).
61
+
62
+ If you don't want to run MegaDetector, and you just want to use the utilities in this package - postprocessing, manipulating large volumes of camera trap images, etc. - you may want to check out the [megadetector-utils](https://pypi.org/project/megadetector-utils/) package, which is identical to this one, but excludes all of the PyTorch/YOLO dependencies, and is thus approximately one zillion times smaller.
63
+
64
+ ## Installation
65
+
66
+ Install with:
67
+
68
+ `pip install megadetector`
69
+
70
+ MegaDetector model weights aren't downloaded at the time you install the package, but they will be (optionally) automatically downloaded the first time you run the model.
71
+
72
+ ## Package reference
73
+
74
+ See [megadetector.readthedocs.io](https://megadetector.readthedocs.io).
75
+
76
+
77
+ ## Examples of things you can do with this package
78
+
79
+ ### Run MegaDetector on one image and count the number of detections
80
+
81
+ ```
82
+ from megadetector.utils import url_utils
83
+ from megadetector.visualization import visualization_utils as vis_utils
84
+ from megadetector.detection import run_detector
85
+
86
+ # This is the image at the bottom of this page, it has one animal in it
87
+ image_url = 'https://github.com/agentmorris/MegaDetector/raw/main/images/orinoquia-thumb-web.jpg'
88
+ temporary_filename = url_utils.download_url(image_url)
89
+
90
+ image = vis_utils.load_image(temporary_filename)
91
+
92
+ # This will automatically download MDv5a; you can also specify a filename.
93
+ model = run_detector.load_detector('MDV5A')
94
+
95
+ result = model.generate_detections_one_image(image)
96
+
97
+ detections_above_threshold = [d for d in result['detections'] if d['conf'] > 0.2]
98
+ print('Found {} detections above threshold'.format(len(detections_above_threshold)))
99
+ ```
100
+
101
+ ### Run MegaDetector on a folder of images
102
+
103
+ ```
104
+ from megadetector.detection.run_detector_batch import \
105
+ load_and_run_detector_batch, write_results_to_file
106
+ from megadetector.utils import path_utils
107
+ import os
108
+
109
+ # Pick a folder to run MD on recursively, and an output file
110
+ image_folder = os.path.expanduser('~/megadetector_test_images')
111
+ output_file = os.path.expanduser('~/megadetector_output_test.json')
112
+
113
+ # Recursively find images
114
+ image_file_names = path_utils.find_images(image_folder,recursive=True)
115
+
116
+ # This will automatically download MDv5a; you can also specify a filename.
117
+ results = load_and_run_detector_batch('MDV5A', image_file_names)
118
+
119
+ # Write results to a format that Timelapse and other downstream tools like.
120
+ write_results_to_file(results,
121
+ output_file,
122
+ relative_path_base=image_folder,
123
+ detector_file=detector_filename)
124
+ ```
125
+
126
+ ## Contact
127
+
128
+ Contact <a href="cameratraps@lila.science">cameratraps@lila.science</a> with questions.
129
+
130
+ ## Gratuitous animal picture
131
+
132
+ <img src="https://github.com/agentmorris/MegaDetector/raw/main/images/orinoquia-thumb-web_detections.jpg"><br/>Image credit University of Minnesota, from the [Orinoquía Camera Traps](http://lila.science/datasets/orinoquia-camera-traps/) data set.
@@ -62,9 +62,9 @@ megadetector/data_management/generate_crops_from_cct.py,sha256=Esq2Vlvp1AQvD8bmt
62
62
  megadetector/data_management/get_image_sizes.py,sha256=2b6arj4gvoN-9f61lC3t1zAFFwYFxfb2iL83Tstoiik,6602
63
63
  megadetector/data_management/labelme_to_coco.py,sha256=8RUXALXbLpmS7UYUet4BAe9JVSDW7ojwDDpxYs072ZI,21231
64
64
  megadetector/data_management/labelme_to_yolo.py,sha256=dRePSOwU_jiCr0EakDQCz1Ct-ZHDxDglUk4HbM1LfWc,10034
65
- megadetector/data_management/mewc_to_md.py,sha256=FQ57B0nJ6V0ZxmfvkWUNQ2fY9JZoHNwQ5W0aLwiY-Ds,13398
65
+ megadetector/data_management/mewc_to_md.py,sha256=wZ25oDQ3spdI4a-8uii8F1UFX7JvBatIi1JLGLYPsHE,13399
66
66
  megadetector/data_management/ocr_tools.py,sha256=T9ClY3B-blnK3-UF1vpVdageknYsykm_6FAfqn0kliU,32529
67
- megadetector/data_management/read_exif.py,sha256=TIPf1OHFhuDq7M2H9MxcEEvN17G0dpJTriRTtiqIvxA,30474
67
+ megadetector/data_management/read_exif.py,sha256=aQKkhZ70vs-WT-7mIbujxN44WyuQFP47utZ7azsWQM4,30595
68
68
  megadetector/data_management/remap_coco_categories.py,sha256=xbU3JW6o25YL8vV83KsOzK6_u1gGGbWDo1G0eOj4ncE,5123
69
69
  megadetector/data_management/remove_exif.py,sha256=vIWnJfw1i9JgyQKUDGEzzqkHro4ndykIPFWhtkm6RAU,2502
70
70
  megadetector/data_management/rename_images.py,sha256=ikIj_b5DY1rgaAn9n_IbwsnugAolczFNivh4xzfLPy8,6915
@@ -138,29 +138,30 @@ megadetector/data_management/lila/get_lila_image_counts.py,sha256=UxXS5RDnSA_Wbx
138
138
  megadetector/data_management/lila/lila_common.py,sha256=74ecaGItH4AtCYeY1WSejLIcylhJPCJ1y97gYYL34PM,11080
139
139
  megadetector/data_management/lila/test_lila_metadata_urls.py,sha256=TPNkULZM3zeOLucD-KSGwD8tHsmGY1uHbCBV2_vPpY0,5080
140
140
  megadetector/detection/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
141
- megadetector/detection/process_video.py,sha256=SGCp98nYI-1LZnTwrTOFhiGs1PpFjrebsI078D2KC-Q,54470
142
- megadetector/detection/pytorch_detector.py,sha256=fpeAcWvSUsH4agQp1nq-yD-vtOkbz8b6M2ohvD_AzEs,45331
143
- megadetector/detection/run_detector.py,sha256=7Q6db9HzMLrsYtarR73_JEL9ESNCLtW28JP7cVrtTtw,39242
144
- megadetector/detection/run_detector_batch.py,sha256=2HrzCtQO1abILB_GnqhYiafdzIxW0X339m-ctY1cs_o,73052
141
+ megadetector/detection/process_video.py,sha256=oUF8tzqGmAwUwFKJKnEHQ1hOOtfnn018vWesRUndMGA,54471
142
+ megadetector/detection/pytorch_detector.py,sha256=_ENSlQSE04wvj3J8Bx8W95PCl-vPkuAeBJ29si-LD50,45334
143
+ megadetector/detection/run_detector.py,sha256=zNq90YtuFVcx6zQa4AOO2vK5m1HnSS-H0qxo8kJlLH4,39431
144
+ megadetector/detection/run_detector_batch.py,sha256=hXsib0h_IeA9AF1tkAHiwov8TyUK_1OMUWiVvPiO1lU,73129
145
145
  megadetector/detection/run_inference_with_yolov5_val.py,sha256=Ofu9B4yOmWso-S6JYalK0f_CvsG5tr2gkW_-rDskMD0,55291
146
- megadetector/detection/run_tiled_inference.py,sha256=vw0713eNuMiEOjHfweQl58zPHNxPOMdFWZ8bTDLhlMY,37883
146
+ megadetector/detection/run_tiled_inference.py,sha256=LbBatyumn_0CFv8yaglEvyzaaiSSHyA8s5X0vDbd2gQ,40469
147
147
  megadetector/detection/tf_detector.py,sha256=t9O6J7r1wHOkKbrwchducdJrAHSw38DDA7rF7_0urn0,8522
148
- megadetector/detection/video_utils.py,sha256=XqaaF8YQX-goSzHEoHasmkuNF7DrbFDil0Xd9KjHb5Q,43821
148
+ megadetector/detection/video_utils.py,sha256=UY5MP4PXkoVMTGIAgQqXw9tu-9KWv52KI6OMywO3_a4,43821
149
149
  megadetector/postprocessing/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
150
150
  megadetector/postprocessing/add_max_conf.py,sha256=qTE1_0RwGAy6jLDkHrIo2pS84yNbUV11s4IZuAYGdIU,1514
151
151
  megadetector/postprocessing/categorize_detections_by_size.py,sha256=YdapcvjA6Dz2dPa2AFf1Dwyl7C-OmmP4G4OjhTOuaF4,5797
152
- megadetector/postprocessing/classification_postprocessing.py,sha256=kzTt83ZwqT5J4DxXQLPsgFxjeaRta3Q2rajm-I84uh4,40405
152
+ megadetector/postprocessing/classification_postprocessing.py,sha256=aTSTqFBACR8kjxE-tEQwcpDH8XogzIUj479gcIDgY18,61069
153
153
  megadetector/postprocessing/combine_batch_outputs.py,sha256=va6v1ZZzbQlq16S3gEqHKI5RbBuwRQ6ZoLAdDbIWYOQ,8416
154
154
  megadetector/postprocessing/compare_batch_results.py,sha256=dtRbutrJQNb0e9VO5bOQXMpPTj-rYJqrqrE3AaM6-NU,85613
155
155
  megadetector/postprocessing/convert_output_format.py,sha256=HwThfK76UPEAGa3KQbJ_tMKIrUvJ3JhKoQVWJt9dPBk,15447
156
- megadetector/postprocessing/create_crop_folder.py,sha256=VIjgg_NIS3VkojjdTYFRxSusWDur0F9gr2lgzO4fbiw,16146
156
+ megadetector/postprocessing/create_crop_folder.py,sha256=mnoPDl5_hBVYpzUZeH0IpD3ZY_yHJyROOJi275DHMKg,16146
157
157
  megadetector/postprocessing/detector_calibration.py,sha256=rzAsiUJhw8Y4RxSK1SMnsdjI3MYkFA9NP5vJ7CNsX0I,21820
158
- megadetector/postprocessing/load_api_results.py,sha256=rHH3brs7R2_p5bLcIoryVldRMQ4b32CMK4-0Kiej_SI,6971
158
+ megadetector/postprocessing/generate_csv_report.py,sha256=A2j5FD7PDBVEh2foVEBCdSWzi5KDHoUDE0iwvhEw2Fg,19858
159
+ megadetector/postprocessing/load_api_results.py,sha256=oV9QlqHYhsVUuZJqABWhK9M23q5SGfk2eQjw3JKhaBQ,7046
159
160
  megadetector/postprocessing/md_to_coco.py,sha256=VfAXHSFZsMfzu1ppetZGDEG9ennJouIuUmFHuJdNtQY,15967
160
161
  megadetector/postprocessing/md_to_labelme.py,sha256=DDCsQpxZXQxWjPlsg1DM5yE33Fc_c8KatuDgt66Q8rQ,11696
161
162
  megadetector/postprocessing/md_to_wi.py,sha256=Yq-WdbWPcwkGkF5Iw7c6Ua6Ky723jYwJWY8Kl_KfgRE,1271
162
163
  megadetector/postprocessing/merge_detections.py,sha256=GfoDtDUdOyv9M4p8tTzUuaEPsgnmHu1pgnPsvSUfOq0,17778
163
- megadetector/postprocessing/postprocess_batch_results.py,sha256=uwMhxn6f4lOGg5ibIwV_D6Oam7TH9UIrXrcHxwIMaj4,85469
164
+ megadetector/postprocessing/postprocess_batch_results.py,sha256=BusnOgrFCVv2p6NUd2k-uhiQKWHGXwhtVupUo4TgycE,85582
164
165
  megadetector/postprocessing/remap_detection_categories.py,sha256=d9IYTa0i_KbbrarJc_mczABmdwypscl5-KpK8Hx_z8o,6640
165
166
  megadetector/postprocessing/render_detection_confusion_matrix.py,sha256=_wsk4W0PbNiqmFuHy-EA0Z07B1tQLMsdCTPatnHAdZw,27382
166
167
  megadetector/postprocessing/separate_detections_into_folders.py,sha256=ua7mBe1Vg4-_JC6ZBhqPfv6uMBqfpIR4o_cmZo-2obY,33836
@@ -174,35 +175,35 @@ megadetector/taxonomy_mapping/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5N
174
175
  megadetector/taxonomy_mapping/map_lila_taxonomy_to_wi_taxonomy.py,sha256=6D_YHTeWTs6O8S9ABog2t9-wfQSh9dW2k9XTqXUZKfo,17927
175
176
  megadetector/taxonomy_mapping/map_new_lila_datasets.py,sha256=q6GZ3uUhFaLaGrVPvViZcyzbZJARR3Q557oGV8h0D9Y,4245
176
177
  megadetector/taxonomy_mapping/prepare_lila_taxonomy_release.py,sha256=kemgxFTriz92Z4fJL0FSimmhhLtC3nBZuZ-Cy9cl1kM,4812
177
- megadetector/taxonomy_mapping/preview_lila_taxonomy.py,sha256=X0keNAaM3l22XPf9ohRdYfob539Fnl7X4PeftZNLjXE,17795
178
+ megadetector/taxonomy_mapping/preview_lila_taxonomy.py,sha256=d1m5U0ov6Zdf0Y5SiidqVfqHpMjmWPpliVD5bwMMvQ8,17698
178
179
  megadetector/taxonomy_mapping/retrieve_sample_image.py,sha256=4cfWsLRwS_EwAmQr2p5tA_W6glBK71tSjPfaHxUZQWs,1979
179
180
  megadetector/taxonomy_mapping/simple_image_download.py,sha256=wLhyMSocX_JhDGA6yLbEfpysz8MMI8YFJWaxyA-GZ9c,6932
180
181
  megadetector/taxonomy_mapping/species_lookup.py,sha256=Z7nVoyh7bi8dHT0cJ7U6lEyi2xJOQra_rlv-DREZ_-U,29811
181
182
  megadetector/taxonomy_mapping/taxonomy_csv_checker.py,sha256=A_zPwzY-ERz6xawxgk2Tpfsycl-1sDcjUiuaXXBppi8,4850
182
- megadetector/taxonomy_mapping/taxonomy_graph.py,sha256=ayrTFseVaIMbtMXhnjWCkZdxI5SAVe_BUtnanGewQpU,12263
183
+ megadetector/taxonomy_mapping/taxonomy_graph.py,sha256=fexDfHIqW9mJJ34JPbeW0FWQ56_6lUu1RRoe2B5rQjg,12262
183
184
  megadetector/taxonomy_mapping/validate_lila_category_mappings.py,sha256=1qyZr23bvZSVUYLQnO1XAtIZ4jdpARA5dxt8euKVyOA,2527
184
185
  megadetector/utils/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
185
186
  megadetector/utils/azure_utils.py,sha256=0BdnkG2hW-X0yFpsJqmBhOd2wysz_LvhuyImPJMVPJs,6271
186
- megadetector/utils/ct_utils.py,sha256=Yr8NNg9KWo6dVc1dEMS6rZP0zb-HlqkgfnkxfkARRLE,27366
187
+ megadetector/utils/ct_utils.py,sha256=cR1qbP_h-xh7020nuGrB55TvIytERHQrR6xuSXIkQJQ,27399
187
188
  megadetector/utils/directory_listing.py,sha256=42t8lDz8V3vPkGTGUd-UnSw2xKpqfpvb4BT-6xVAUmY,9689
188
189
  megadetector/utils/gpu_test.py,sha256=1NxvyJrD4mq_uuCysT0q9pSJyR-gpdQogB6O8TP4E2Q,3665
189
190
  megadetector/utils/md_tests.py,sha256=bMloXfts_sxG4vTEZq5pmUJ8-WLnsoU8mYkdz732YrE,75028
190
- megadetector/utils/path_utils.py,sha256=LDnFIbuajlc_iIlG4CzOoFml-RsyqFRBLKdPxvoQJz8,51659
191
+ megadetector/utils/path_utils.py,sha256=nl74fQfhoofE8Qpmb20mkP9xZYFIkNBgV88XvhnIMV0,53155
191
192
  megadetector/utils/process_utils.py,sha256=K7-ZW_bJbMgeDBLDhYHMV84urM8H7L6IddQS5z3UgBw,5824
192
193
  megadetector/utils/sas_blob_utils.py,sha256=k76EcMmJc_otrEHcfV2fxAC6fNhxU88FxM3ddSYrsKU,16917
193
- megadetector/utils/split_locations_into_train_val.py,sha256=jvaDu1xKB51L3Xq2nXQo0XtXRjNRf8RglBApl1g6gHo,10101
194
+ megadetector/utils/split_locations_into_train_val.py,sha256=ldTWD5s8Q14nCGedvL70FAf7W8xZ9cBtTxIWFeI7ehM,10711
194
195
  megadetector/utils/string_utils.py,sha256=ZQapJodzvTDyQhjZgMoMl3-9bqnKAUlORpws8Db9AkA,2050
195
196
  megadetector/utils/url_utils.py,sha256=yybWwJ-vl2A6Fci66i-xt_dl3Uqh72Ylnb8XOT2Grog,14835
196
- megadetector/utils/wi_utils.py,sha256=SNXF2GnBvzKrGw1dUexty9dLIyPBMgeARQb79e5yf7c,115008
197
+ megadetector/utils/wi_utils.py,sha256=OmYSTSCiWIuEnDHcQimPPrsHWPCEL9sMGQn6G8B8XTc,100877
197
198
  megadetector/utils/write_html_image_list.py,sha256=MhVAAv6th9Q2fldtE8hp_hHWFgJ_pcKJEk3YiK6dWY4,9415
198
199
  megadetector/visualization/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
199
200
  megadetector/visualization/plot_utils.py,sha256=lOfU3uPrcuHZagV_1SN8erT8PujIepocgw6KZ17Ej6c,10671
200
201
  megadetector/visualization/render_images_with_thumbnails.py,sha256=kgJYW8BsqRO4C7T3sqItdBuSkZ64I1vOtIWAsVG4XBI,10589
201
- megadetector/visualization/visualization_utils.py,sha256=WU6S8J3be2jmBgEbXsLaX7wtJV6on0YytTLK4xHxoFE,75688
202
+ megadetector/visualization/visualization_utils.py,sha256=5PLL8Wa_TKmrItPH6z_n-b8h5EHn84qxce0VM3paG2k,76276
202
203
  megadetector/visualization/visualize_db.py,sha256=h1NSK_4ZR_NlwBn2JrYyCOv9C7_iqmLWWOk4T6YkyXw,25280
203
- megadetector/visualization/visualize_detector_output.py,sha256=oubAksx2V7YtBC34g5y4UOH0SVnIINGWjuvuacAaUBE,19112
204
- megadetector-5.0.27.dist-info/licenses/LICENSE,sha256=RMa3qq-7Cyk7DdtqRj_bP1oInGFgjyHn9-PZ3PcrqIs,1100
205
- megadetector-5.0.27.dist-info/METADATA,sha256=2IDbeR47q4bzJmiYx2BqnsmZ90_cMNf1hHmGw3tWoJg,6322
206
- megadetector-5.0.27.dist-info/WHEEL,sha256=CmyFI0kx5cdEMTLiONQRbGQwjIoR1aIYB7eCAQ4KPJ0,91
207
- megadetector-5.0.27.dist-info/top_level.txt,sha256=wf9DXa8EwiOSZ4G5IPjakSxBPxTDjhYYnqWRfR-zS4M,13
208
- megadetector-5.0.27.dist-info/RECORD,,
204
+ megadetector/visualization/visualize_detector_output.py,sha256=1zjess07B7FevT7lThNqotdNrMPKdUnPmEu1zyMxci0,20278
205
+ megadetector-5.0.28.dist-info/licenses/LICENSE,sha256=RMa3qq-7Cyk7DdtqRj_bP1oInGFgjyHn9-PZ3PcrqIs,1100
206
+ megadetector-5.0.28.dist-info/METADATA,sha256=9uFX27-meAxvB_zHprROT4U7qhss6MDFYvobGdGjPr8,6449
207
+ megadetector-5.0.28.dist-info/WHEEL,sha256=GHB6lJx2juba1wDgXDNlMTyM13ckjBMKf-OnwgKOCtA,91
208
+ megadetector-5.0.28.dist-info/top_level.txt,sha256=wf9DXa8EwiOSZ4G5IPjakSxBPxTDjhYYnqWRfR-zS4M,13
209
+ megadetector-5.0.28.dist-info/RECORD,,
@@ -1,5 +1,5 @@
1
1
  Wheel-Version: 1.0
2
- Generator: setuptools (78.1.0)
2
+ Generator: setuptools (80.3.0)
3
3
  Root-Is-Purelib: true
4
4
  Tag: py3-none-any
5
5