megadetector 10.0.6__tar.gz → 10.0.8__tar.gz

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 (153) hide show
  1. {megadetector-10.0.6 → megadetector-10.0.8}/LICENSE +0 -0
  2. {megadetector-10.0.6/megadetector.egg-info → megadetector-10.0.8}/PKG-INFO +134 -134
  3. {megadetector-10.0.6 → megadetector-10.0.8}/README-package.md +0 -0
  4. {megadetector-10.0.6 → megadetector-10.0.8}/README.md +2 -2
  5. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/__init__.py +0 -0
  6. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/api/__init__.py +0 -0
  7. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/api/batch_processing/integration/digiKam/setup.py +0 -0
  8. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/api/batch_processing/integration/digiKam/xmp_integration.py +0 -0
  9. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/api/batch_processing/integration/eMammal/test_scripts/config_template.py +0 -0
  10. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/api/batch_processing/integration/eMammal/test_scripts/push_annotations_to_emammal.py +0 -0
  11. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/api/batch_processing/integration/eMammal/test_scripts/select_images_for_testing.py +0 -0
  12. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/__init__.py +0 -0
  13. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/aggregate_classifier_probs.py +0 -0
  14. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/analyze_failed_images.py +0 -0
  15. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/cache_batchapi_outputs.py +0 -0
  16. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/create_classification_dataset.py +0 -0
  17. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/crop_detections.py +0 -0
  18. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/csv_to_json.py +0 -0
  19. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/detect_and_crop.py +0 -0
  20. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/efficientnet/__init__.py +0 -0
  21. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/efficientnet/model.py +0 -0
  22. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/efficientnet/utils.py +0 -0
  23. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/evaluate_model.py +0 -0
  24. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/identify_mislabeled_candidates.py +0 -0
  25. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/json_to_azcopy_list.py +0 -0
  26. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/json_validator.py +0 -0
  27. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/map_classification_categories.py +0 -0
  28. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/merge_classification_detection_output.py +0 -0
  29. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/prepare_classification_script.py +0 -0
  30. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/prepare_classification_script_mc.py +0 -0
  31. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/run_classifier.py +0 -0
  32. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/save_mislabeled.py +0 -0
  33. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/train_classifier.py +0 -0
  34. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/train_classifier_tf.py +0 -0
  35. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/classification/train_utils.py +0 -0
  36. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/__init__.py +0 -0
  37. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/animl_to_md.py +0 -0
  38. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/annotations/__init__.py +0 -0
  39. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/annotations/annotation_constants.py +0 -0
  40. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/camtrap_dp_to_coco.py +0 -0
  41. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/cct_json_utils.py +16 -6
  42. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/cct_to_md.py +0 -0
  43. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/cct_to_wi.py +0 -0
  44. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/coco_to_labelme.py +0 -0
  45. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/coco_to_yolo.py +0 -0
  46. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/databases/__init__.py +0 -0
  47. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/databases/add_width_and_height_to_db.py +0 -0
  48. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/databases/combine_coco_camera_traps_files.py +0 -0
  49. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/databases/integrity_check_json_db.py +0 -0
  50. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/databases/subset_json_db.py +57 -2
  51. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/generate_crops_from_cct.py +0 -0
  52. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/get_image_sizes.py +0 -0
  53. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/labelme_to_coco.py +0 -0
  54. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/labelme_to_yolo.py +0 -0
  55. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/lila/__init__.py +0 -0
  56. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/lila/create_lila_blank_set.py +0 -0
  57. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/lila/create_lila_test_set.py +0 -0
  58. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/lila/create_links_to_md_results_files.py +0 -0
  59. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/lila/download_lila_subset.py +0 -0
  60. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/lila/generate_lila_per_image_labels.py +0 -0
  61. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/lila/get_lila_annotation_counts.py +0 -0
  62. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/lila/get_lila_image_counts.py +0 -0
  63. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/lila/lila_common.py +0 -0
  64. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/lila/test_lila_metadata_urls.py +0 -0
  65. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/mewc_to_md.py +0 -0
  66. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/ocr_tools.py +0 -0
  67. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/read_exif.py +0 -0
  68. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/remap_coco_categories.py +0 -0
  69. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/remove_exif.py +0 -0
  70. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/rename_images.py +0 -0
  71. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/resize_coco_dataset.py +0 -0
  72. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/speciesnet_to_md.py +0 -0
  73. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/wi_download_csv_to_coco.py +0 -0
  74. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/yolo_output_to_md_output.py +0 -0
  75. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/yolo_to_coco.py +0 -0
  76. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/data_management/zamba_to_md.py +0 -0
  77. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/detection/__init__.py +0 -0
  78. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/detection/change_detection.py +0 -0
  79. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/detection/process_video.py +0 -0
  80. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/detection/pytorch_detector.py +29 -15
  81. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/detection/run_detector.py +0 -0
  82. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/detection/run_detector_batch.py +0 -0
  83. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/detection/run_inference_with_yolov5_val.py +3 -1
  84. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/detection/run_md_and_speciesnet.py +0 -0
  85. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/detection/run_tiled_inference.py +5 -2
  86. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/detection/tf_detector.py +0 -0
  87. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/detection/video_utils.py +23 -7
  88. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/__init__.py +0 -0
  89. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/add_max_conf.py +0 -0
  90. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/categorize_detections_by_size.py +0 -0
  91. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/classification_postprocessing.py +218 -69
  92. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/combine_batch_outputs.py +0 -0
  93. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/compare_batch_results.py +0 -0
  94. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/convert_output_format.py +81 -87
  95. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/create_crop_folder.py +0 -0
  96. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/detector_calibration.py +0 -0
  97. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/generate_csv_report.py +0 -0
  98. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/load_api_results.py +0 -0
  99. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/md_to_coco.py +0 -0
  100. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/md_to_labelme.py +0 -0
  101. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/md_to_wi.py +0 -0
  102. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/merge_detections.py +0 -0
  103. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/postprocess_batch_results.py +0 -0
  104. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/remap_detection_categories.py +0 -0
  105. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/render_detection_confusion_matrix.py +0 -0
  106. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/repeat_detection_elimination/find_repeat_detections.py +0 -0
  107. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/repeat_detection_elimination/remove_repeat_detections.py +0 -0
  108. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/repeat_detection_elimination/repeat_detections_core.py +0 -0
  109. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/separate_detections_into_folders.py +0 -0
  110. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/subset_json_detector_output.py +3 -0
  111. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/top_folders_to_bottom.py +0 -0
  112. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/postprocessing/validate_batch_results.py +0 -0
  113. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/taxonomy_mapping/__init__.py +0 -0
  114. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/taxonomy_mapping/map_lila_taxonomy_to_wi_taxonomy.py +0 -0
  115. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/taxonomy_mapping/map_new_lila_datasets.py +0 -0
  116. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/taxonomy_mapping/prepare_lila_taxonomy_release.py +0 -0
  117. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/taxonomy_mapping/preview_lila_taxonomy.py +0 -0
  118. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/taxonomy_mapping/retrieve_sample_image.py +0 -0
  119. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/taxonomy_mapping/simple_image_download.py +0 -0
  120. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/taxonomy_mapping/species_lookup.py +0 -0
  121. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/taxonomy_mapping/taxonomy_csv_checker.py +0 -0
  122. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/taxonomy_mapping/taxonomy_graph.py +0 -0
  123. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/taxonomy_mapping/validate_lila_category_mappings.py +0 -0
  124. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/tests/__init__.py +0 -0
  125. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/tests/test_nms_synthetic.py +0 -0
  126. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/__init__.py +0 -0
  127. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/ct_utils.py +0 -0
  128. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/directory_listing.py +19 -13
  129. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/extract_frames_from_video.py +0 -0
  130. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/gpu_test.py +0 -0
  131. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/md_tests.py +0 -0
  132. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/path_utils.py +58 -8
  133. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/process_utils.py +0 -0
  134. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/split_locations_into_train_val.py +0 -0
  135. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/string_utils.py +0 -0
  136. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/url_utils.py +91 -1
  137. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/wi_platform_utils.py +0 -0
  138. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/wi_taxonomy_utils.py +44 -26
  139. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/utils/write_html_image_list.py +0 -0
  140. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/visualization/__init__.py +0 -0
  141. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/visualization/plot_utils.py +0 -0
  142. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/visualization/render_images_with_thumbnails.py +0 -0
  143. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/visualization/visualization_utils.py +0 -0
  144. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/visualization/visualize_db.py +0 -0
  145. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/visualization/visualize_detector_output.py +0 -0
  146. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector/visualization/visualize_video_output.py +16 -6
  147. {megadetector-10.0.6 → megadetector-10.0.8/megadetector.egg-info}/PKG-INFO +134 -134
  148. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector.egg-info/SOURCES.txt +0 -0
  149. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector.egg-info/dependency_links.txt +0 -0
  150. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector.egg-info/requires.txt +0 -0
  151. {megadetector-10.0.6 → megadetector-10.0.8}/megadetector.egg-info/top_level.txt +0 -0
  152. {megadetector-10.0.6 → megadetector-10.0.8}/pyproject.toml +2 -2
  153. {megadetector-10.0.6 → megadetector-10.0.8}/setup.cfg +4 -4
File without changes
@@ -1,134 +1,134 @@
1
- Metadata-Version: 2.4
2
- Name: megadetector
3
- Version: 10.0.6
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>=2.1
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: clipboard
51
- Requires-Dist: dill
52
- Requires-Dist: ruff
53
- Requires-Dist: pytest
54
- Requires-Dist: ultralytics-yolov5==0.1.1
55
- Requires-Dist: yolov9pip==0.0.4
56
- Dynamic: license-file
57
-
58
- # MegaDetector
59
-
60
- 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).
61
-
62
- 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).
63
-
64
- 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.
65
-
66
- ## Installation
67
-
68
- Install with:
69
-
70
- `pip install megadetector`
71
-
72
- 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.
73
-
74
- ## Package reference
75
-
76
- See [megadetector.readthedocs.io](https://megadetector.readthedocs.io).
77
-
78
-
79
- ## Examples of things you can do with this package
80
-
81
- ### Run MegaDetector on one image and count the number of detections
82
-
83
- ```
84
- from megadetector.utils import url_utils
85
- from megadetector.visualization import visualization_utils as vis_utils
86
- from megadetector.detection import run_detector
87
-
88
- # This is the image at the bottom of this page, it has one animal in it
89
- image_url = 'https://github.com/agentmorris/MegaDetector/raw/main/images/orinoquia-thumb-web.jpg'
90
- temporary_filename = url_utils.download_url(image_url)
91
-
92
- image = vis_utils.load_image(temporary_filename)
93
-
94
- # This will automatically download MDv5a; you can also specify a filename.
95
- model = run_detector.load_detector('MDV5A')
96
-
97
- result = model.generate_detections_one_image(image)
98
-
99
- detections_above_threshold = [d for d in result['detections'] if d['conf'] > 0.2]
100
- print('Found {} detections above threshold'.format(len(detections_above_threshold)))
101
- ```
102
-
103
- ### Run MegaDetector on a folder of images
104
-
105
- ```
106
- from megadetector.detection.run_detector_batch import \
107
- load_and_run_detector_batch, write_results_to_file
108
- from megadetector.utils import path_utils
109
- import os
110
-
111
- # Pick a folder to run MD on recursively, and an output file
112
- image_folder = os.path.expanduser('~/megadetector_test_images')
113
- output_file = os.path.expanduser('~/megadetector_output_test.json')
114
-
115
- # Recursively find images
116
- image_file_names = path_utils.find_images(image_folder,recursive=True)
117
-
118
- # This will automatically download MDv5a; you can also specify a filename.
119
- results = load_and_run_detector_batch('MDV5A', image_file_names)
120
-
121
- # Write results to a format that Timelapse and other downstream tools like.
122
- write_results_to_file(results,
123
- output_file,
124
- relative_path_base=image_folder,
125
- detector_file=detector_filename)
126
- ```
127
-
128
- ## Contact
129
-
130
- Contact <a href="cameratraps@lila.science">cameratraps@lila.science</a> with questions.
131
-
132
- ## Gratuitous animal picture
133
-
134
- <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: 10.0.8
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>=2.1
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: clipboard
51
+ Requires-Dist: dill
52
+ Requires-Dist: ruff
53
+ Requires-Dist: pytest
54
+ Requires-Dist: ultralytics-yolov5==0.1.1
55
+ Requires-Dist: yolov9pip==0.0.4
56
+ Dynamic: license-file
57
+
58
+ # MegaDetector
59
+
60
+ 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).
61
+
62
+ 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).
63
+
64
+ 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.
65
+
66
+ ## Installation
67
+
68
+ Install with:
69
+
70
+ `pip install megadetector`
71
+
72
+ 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.
73
+
74
+ ## Package reference
75
+
76
+ See [megadetector.readthedocs.io](https://megadetector.readthedocs.io).
77
+
78
+
79
+ ## Examples of things you can do with this package
80
+
81
+ ### Run MegaDetector on one image and count the number of detections
82
+
83
+ ```
84
+ from megadetector.utils import url_utils
85
+ from megadetector.visualization import visualization_utils as vis_utils
86
+ from megadetector.detection import run_detector
87
+
88
+ # This is the image at the bottom of this page, it has one animal in it
89
+ image_url = 'https://github.com/agentmorris/MegaDetector/raw/main/images/orinoquia-thumb-web.jpg'
90
+ temporary_filename = url_utils.download_url(image_url)
91
+
92
+ image = vis_utils.load_image(temporary_filename)
93
+
94
+ # This will automatically download MDv5a; you can also specify a filename.
95
+ model = run_detector.load_detector('MDV5A')
96
+
97
+ result = model.generate_detections_one_image(image)
98
+
99
+ detections_above_threshold = [d for d in result['detections'] if d['conf'] > 0.2]
100
+ print('Found {} detections above threshold'.format(len(detections_above_threshold)))
101
+ ```
102
+
103
+ ### Run MegaDetector on a folder of images
104
+
105
+ ```
106
+ from megadetector.detection.run_detector_batch import \
107
+ load_and_run_detector_batch, write_results_to_file
108
+ from megadetector.utils import path_utils
109
+ import os
110
+
111
+ # Pick a folder to run MD on recursively, and an output file
112
+ image_folder = os.path.expanduser('~/megadetector_test_images')
113
+ output_file = os.path.expanduser('~/megadetector_output_test.json')
114
+
115
+ # Recursively find images
116
+ image_file_names = path_utils.find_images(image_folder,recursive=True)
117
+
118
+ # This will automatically download MDv5a; you can also specify a filename.
119
+ results = load_and_run_detector_batch('MDV5A', image_file_names)
120
+
121
+ # Write results to a format that Timelapse and other downstream tools like.
122
+ write_results_to_file(results,
123
+ output_file,
124
+ relative_path_base=image_folder,
125
+ detector_file=detector_filename)
126
+ ```
127
+
128
+ ## Contact
129
+
130
+ Contact <a href="cameratraps@lila.science">cameratraps@lila.science</a> with questions.
131
+
132
+ ## Gratuitous animal picture
133
+
134
+ <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.
@@ -112,7 +112,6 @@ Here are a few of the organizations that have used MegaDetector... we're only li
112
112
  * [TROPECOLNET project](https://www.anabenitezlopez.com/research/global-change-biology/tropecolnet/), Museo Nacional de Ciencias Naturales
113
113
  * [Wildlife Coexistence Lab](https://wildlife.forestry.ubc.ca/), University of British Columbia
114
114
  * [Wildlife Research](https://www.dfw.state.or.us/wildlife/research/index.asp), Oregon Department of Fish and Wildlife
115
- * [Wildlife Division](https://www.michigan.gov/dnr/about/contact/wildlife), Michigan Department of Natural Resources
116
115
  * [Kohl Wildlife Lab](https://kohlwildlifelab.com/), University of Georgia
117
116
  * [SPEC Lab](https://thespeclab.weebly.com/) and [Cherry Lab](https://www.ckwri.tamuk.edu/about/michael-j-cherry-phd), Caesar Kleberg Wildlife Research Institute, Texas A&M Kingsville
118
117
  * Ecology and Conservation of Amazonian Vertebrates Research Group, Federal University of Amapá
@@ -148,10 +147,11 @@ Here are a few of the organizations that have used MegaDetector... we're only li
148
147
  * [The Nature Conservancy in California](https://www.nature.org/en-us/about-us/where-we-work/united-states/california/) ([Animl platform](https://github.com/tnc-ca-geo/animl-frontend)) ([story](https://www.vision-systems.com/non-factory/environment-agriculture/article/14304433/the-nature-conservancy-brings-cameras-ai-to-invasive-species-prevention))
149
148
  * [San Diego Zoo Wildlife Alliance](https://science.sandiegozoo.org/) ([Animl R package](https://github.com/conservationtechlab/animl))
150
149
  * [TerrOïko](https://www.terroiko.fr/) ([OCAPI platform](https://www.terroiko.fr/ocapi))
150
+ * [Wildlife Division](https://www.michigan.gov/dnr/about/contact/wildlife), Michigan Department of Natural Resources ([blog post](https://www.michigan.gov/dnr/about/newsroom/releases/2025/08/18/dnr-researchers-to-test-trail-cameras-in-elk-survey))
151
151
 
152
152
  Also see:
153
153
 
154
- * The [list of MD-related GUIs, platforms, and GitHub repos](https://github.com/agentmorris/MegaDetector/blob/main/megadetector.md#is-there-a-gui) within the MegaDetector User Guide... although you can never have too many lists, so here they are in a concise comma-separated list: [Wildlife Insights](https://wildlifeinsights.org/), [Animal Detect](https://www.animaldetect.com), [TrapTagger](https://wildeyeconservation.org/trap-tagger-about/), [WildTrax](https://www.wildtrax.ca/), [Agouti](https://agouti.eu/), [Trapper](https://trapper-project.readthedocs.io/en/latest/overview.html), [Camelot](https://camelotproject.org/), [WildePod](https://wildepod.org/), [wpsWatch](https://wildlabs.net/inventory/products/wpswatch), [TNC Animl](https://animl.camera/) ([code](https://github.com/tnc-ca-geo/animl-frontend)), [Wildlife Observer Network](https://roadecology.ucdavis.edu/research/projects/wildlife-observer-network), [Zooniverse ML Subject Assistant](https://subject-assistant.zooniverse.org/#/intro), [Dudek AI Image Toolkit](https://ait.dudek.com), [Zamba Cloud](https://github.com/drivendataorg/zamba), [OCAPI](https://www.terroiko.fr/ocapi/).
154
+ * The [list of MD-related GUIs, platforms, and GitHub repos](https://github.com/agentmorris/MegaDetector/blob/main/megadetector.md#is-there-a-gui) within the MegaDetector User Guide... although you can never have too many lists, so here they are in a concise comma-separated list: [Wildlife Insights](https://wildlifeinsights.org/), [Animal Detect](https://www.animaldetect.com), [TrapTagger](https://wildeyeconservation.org/trap-tagger-about/), [WildTrax](https://www.wildtrax.ca/), [Agouti](https://agouti.eu/), [Trapper](https://trapper-project.readthedocs.io/en/latest/overview.html), [Camelot](https://camelotproject.org/), [WildePod](https://wildepod.org/), [wpsWatch](https://wildlabs.net/inventory/products/wpswatch), [TNC Animl](https://animl.camera/) ([code](https://github.com/tnc-ca-geo/animl-frontend)), [Wildlife Observer Network](https://roadecology.ucdavis.edu/research/projects/wildlife-observer-network), [Zooniverse ML Subject Assistant](https://subject-assistant.zooniverse.org/#/intro), [Dudek AI Image Toolkit](https://ait.dudek.com), [Zamba Cloud](https://github.com/drivendataorg/zamba), [OCAPI](https://www.terroiko.fr/ocapi/), [BoquilaHUB](https://boquila.org/hub)
155
155
 
156
156
  * [Peter's map of AddaxAI (formerly EcoAssist) users](https://addaxdatascience.com/addaxai/) (who are also MegaDetector users!)
157
157
 
@@ -305,6 +305,9 @@ class SequenceOptions:
305
305
  #: How to handle invalid datetimes: 'error' or 'none'
306
306
  self.datetime_conversion_failure_behavior = 'none'
307
307
 
308
+ #: Enable additional debug output
309
+ self.verbose = False
310
+
308
311
 
309
312
  #%% Functions
310
313
 
@@ -331,7 +334,9 @@ def write_object_with_serialized_datetimes(d,json_fn):
331
334
  json.dump(d,f,indent=1,default=json_serialize_datetime)
332
335
 
333
336
 
334
- def parse_datetimes_from_cct_image_list(images,conversion_failure_behavior='error'):
337
+ def parse_datetimes_from_cct_image_list(images,
338
+ conversion_failure_behavior='error',
339
+ verbose=False):
335
340
  """
336
341
  Given the "images" field from a COCO camera traps dictionary, converts all
337
342
  string-formatted datetime fields to Python datetimes, making reasonable assumptions
@@ -342,6 +347,7 @@ def parse_datetimes_from_cct_image_list(images,conversion_failure_behavior='erro
342
347
  conversion_failure_behavior (str, optional): determines what happens on a failed
343
348
  conversion; can be "error" (raise an error), "str" (leave as a string), or
344
349
  "none" (convert to None)
350
+ verbose (bool, optional): enable additional debug output
345
351
 
346
352
  Returns:
347
353
  images: the input list, with datetimes converted (after modifying in place)
@@ -359,14 +365,17 @@ def parse_datetimes_from_cct_image_list(images,conversion_failure_behavior='erro
359
365
  dt = dateutil.parser.parse(im['datetime'])
360
366
  im['datetime'] = dt
361
367
  except Exception as e:
362
- s = 'could not parse datetime {}: {}'.format(str(im['datetime']),str(e))
368
+ s = 'could not parse datetime {} from {}: {}'.format(
369
+ str(im['datetime']),im['file_name'],str(e))
363
370
  if conversion_failure_behavior == 'error':
364
371
  raise ValueError(s)
365
372
  elif conversion_failure_behavior == 'str':
366
- print('Warning: {}'.format(s))
373
+ if verbose:
374
+ print('Warning: {}'.format(s))
367
375
  pass
368
376
  elif conversion_failure_behavior == 'none':
369
- print('Warning: {}'.format(s))
377
+ if verbose:
378
+ print('Warning: {}'.format(s))
370
379
  im['datetime'] = None
371
380
 
372
381
  # ...for each image
@@ -450,7 +459,8 @@ def create_sequences(image_info,options=None):
450
459
 
451
460
  # Modifies the images in place
452
461
  _ = parse_datetimes_from_cct_image_list(image_info,
453
- conversion_failure_behavior=options.datetime_conversion_failure_behavior)
462
+ conversion_failure_behavior=options.datetime_conversion_failure_behavior,
463
+ verbose=options.verbose)
454
464
 
455
465
  n_invalid_datetimes = 0
456
466
  for im in image_info:
@@ -505,7 +515,7 @@ def create_sequences(image_info,options=None):
505
515
  delta = (im['datetime'] - previous_datetime).total_seconds()
506
516
 
507
517
  # Start a new sequence if necessary, including the case where this datetime is invalid
508
- if delta is None or delta > options.episode_interval_seconds or invalid_datetime:
518
+ if (delta is None) or (delta > options.episode_interval_seconds) or (invalid_datetime):
509
519
  next_frame_number = 0
510
520
  current_sequence_id = 'location_{}_sequence_index_{}'.format(
511
521
  location,str(next_sequence_number).zfill(5))
@@ -18,13 +18,20 @@ import json
18
18
  import argparse
19
19
 
20
20
  from tqdm import tqdm
21
- from megadetector.utils import ct_utils
22
21
  from copy import copy
23
22
 
23
+ from megadetector.utils import ct_utils
24
+ from megadetector.utils.ct_utils import sort_list_of_dicts_by_key
25
+
24
26
 
25
27
  #%% Functions
26
28
 
27
- def subset_json_db(input_json, query, output_json=None, ignore_case=False, verbose=False):
29
+ def subset_json_db(input_json,
30
+ query,
31
+ output_json=None,
32
+ ignore_case=False,
33
+ remap_categories=True,
34
+ verbose=False):
28
35
  """
29
36
  Given a json file (or dictionary already loaded from a json file), produce a new
30
37
  database containing only the images whose filenames contain the string 'query',
@@ -36,6 +43,8 @@ def subset_json_db(input_json, query, output_json=None, ignore_case=False, verbo
36
43
  contain this string. If this is a list, test for exact matches.
37
44
  output_json (str, optional): file to write the resulting .json file to
38
45
  ignore_case (bool, optional): whether to perform a case-insensitive search for [query]
46
+ remap_categories (bool, optional): trim the category list to only the categores used
47
+ in the subset
39
48
  verbose (bool, optional): enable additional debug output
40
49
 
41
50
  Returns:
@@ -92,6 +101,52 @@ def subset_json_db(input_json, query, output_json=None, ignore_case=False, verbo
92
101
  output_data['images'] = images
93
102
  output_data['annotations'] = annotations
94
103
 
104
+ # Remap categories if necessary
105
+ if remap_categories:
106
+
107
+ category_ids_used = set()
108
+ for ann in annotations:
109
+ category_ids_used.add(ann['category_id'])
110
+
111
+ if verbose:
112
+ print('Keeping {} of {} categories'.format(
113
+ len(category_ids_used),len(input_data['categories'])))
114
+
115
+ input_category_id_to_output_category_id = {}
116
+
117
+ next_category_id = 0
118
+
119
+ # Build mappings from old to new category IDs
120
+ for input_category_id in category_ids_used:
121
+ assert isinstance(input_category_id,int), \
122
+ 'Illegal category ID {}'.format(input_category_id)
123
+ output_category_id = next_category_id
124
+ next_category_id = next_category_id + 1
125
+ input_category_id_to_output_category_id[input_category_id] = output_category_id
126
+
127
+ # Modify the annotations
128
+ for ann in annotations:
129
+ assert ann['category_id'] in input_category_id_to_output_category_id
130
+ ann['category_id'] = input_category_id_to_output_category_id[ann['category_id']]
131
+
132
+ output_categories = []
133
+
134
+ # Re-write the category table
135
+ for cat in input_data['categories']:
136
+
137
+ if cat['id'] in input_category_id_to_output_category_id:
138
+
139
+ # There may be non-required fields, so don't just create an empty dict
140
+ # and copy the name/id field, keep the original dict other than "id"
141
+ output_category = copy(cat)
142
+ output_category['id'] = input_category_id_to_output_category_id[cat['id']]
143
+ output_categories.append(output_category)
144
+
145
+ output_categories = sort_list_of_dicts_by_key(output_categories,'id')
146
+ output_data['categories'] = output_categories
147
+
148
+ # ...if we need to remap categories
149
+
95
150
  # Write the output file if requested
96
151
  if output_json is not None:
97
152
  if verbose: