{"id":13586151,"url":"https://github.com/LJMUAstroecology/flirpy","last_synced_at":"2025-04-07T14:33:53.113Z","repository":{"id":41228688,"uuid":"146534780","full_name":"LJMUAstroecology/flirpy","owner":"LJMUAstroecology","description":"Python library to interact with FLIR camera cores","archived":false,"fork":false,"pushed_at":"2024-07-27T00:46:14.000Z","size":13337,"stargazers_count":189,"open_issues_count":35,"forks_count":54,"subscribers_count":18,"default_branch":"main","last_synced_at":"2024-08-02T16:02:53.012Z","etag":null,"topics":["cameras","flir-camera-cores","flir-cameras","python","thermal","thermal-camera","thermal-imaging"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"other","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/LJMUAstroecology.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE.md","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2018-08-29T02:38:04.000Z","updated_at":"2024-07-31T17:02:05.000Z","dependencies_parsed_at":"2024-01-06T01:03:45.417Z","dependency_job_id":"e90a027d-321e-4bf0-b8f0-c09ed35f5596","html_url":"https://github.com/LJMUAstroecology/flirpy","commit_stats":null,"previous_names":[],"tags_count":17,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/LJMUAstroecology%2Fflirpy","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/LJMUAstroecology%2Fflirpy/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/LJMUAstroecology%2Fflirpy/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/LJMUAstroecology%2Fflirpy/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/LJMUAstroecology","download_url":"https://codeload.github.com/LJMUAstroecology/flirpy/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":223285144,"owners_count":17119843,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["cameras","flir-camera-cores","flir-cameras","python","thermal","thermal-camera","thermal-imaging"],"created_at":"2024-08-01T15:05:21.438Z","updated_at":"2024-11-06T04:31:09.552Z","avatar_url":"https://github.com/LJMUAstroecology.png","language":"Python","funding_links":[],"categories":["Python","Network and Middleware"],"sub_categories":["Sensor and Acuator Interfaces"],"readme":"# ![logo](logo.png)\n\n![coverage](coverage.svg) [![Documentation Status](https://readthedocs.org/projects/flirpy/badge/?version=latest)](https://flirpy.readthedocs.io/en/latest/?badge=latest)\n\n[![DOI](https://zenodo.org/badge/146534780.svg)](https://zenodo.org/badge/latestdoi/146534780)\n\n## Introduction\n\nflirpy is a Python library to interact with FLIR thermal imaging cameras and images. If you use flirpy for a research or other publishable application, please cite it using the Zenodo DOI.\n\nIt aims to be a one-stop-shop to:\n\n* Interact and query cameras via serial\n* Capture raw images\n* Convert FLIR file formats (e.g. seq, fff) to geotagged readable images\n* Convert raw images to radiometric images\n\nThe library has been tested with:\n\n* FLIR Tau 2 (serial)\n* TeAx ThermalCapture Grabber USB (image capture and Tau2 serial)\n* FLIR Boson (serial and image capture)\n* FLIR Duo Pro R (image post-processing)\n* TeAx Fusion Zoom (image post-processing)\n* FLIR Lepton (PureThermal board, capture+telemetry only)\n\n**If your camera is not on this list and it does not produce SEQ files, then flirpy probably does not support it. Many of FLIR's cameras use proprietary bluetooth interfaces for control and there are no APIs available.**\n\nComing soon\n\n* FLIR Lepton low level (SPI)\n* Documentation...\n\n**It is strongly recommended that you use Python 3**. I have tried to ensure that certain functions are portable between Python 2 and 3, mainly those involved with camera communication (for example if you want to use flirpy with ROS, most of the important stuff works). However, some file IO is hit and miss on Python 2 due to differences in regexes. Python 2 is effectively end of life and while I'd like to support both, it's a low priority. Submit a PR if you like!\n\n## Library organisation\n\nThe library is organised into logical sections:\n\n* `flirpy.camera` contains classes to communicate with FLIR camera cores directly\n* `flirpy.io` contains claseses to deal with thermal image formats\n* `flirpy.util` contains helper functions e.g. raw conversion\n\n## Utilities\n\nFlirpy includes a convenience utility `split_seqs` for splitting FLIR sequence (SEQ) files.\n\nOnce installed, you can run:\n\n``` bash\npython .\\scripts\\split_seqs -h\nusage: split_seqs [-h] [-o OUTPUT] [-i INPUT] [-v VERBOSITY]\n                  [--preview_format PREVIEW_FORMAT] [--rgb RGB]\n                  [--jpeg_quality JPEG_QUALITY] [--use_gstreamer] [--copy]\n                  [--width WIDTH] [--height HEIGHT]\n                  [--merge_folders | --no_merge_folders]\n                  [--split_filetypes | --no_split_filetypes]\n                  [--export_meta | --no_export_meta]\n                  [--export_tiff | --no_export_tiff]\n                  [--export_raw | --no_export_raw]\n                  [--export_preview | --no_export_preview]\n                  [--skip_thermal | --no_skip_thermal]\n                  [--sync_rgb | --no_sync_rgb]\n\nSplit all files in folder\n\noptional arguments:\n  -h, --help            show this help message and exit\n  -o OUTPUT, --output OUTPUT\n                        Output folder (default: ./)\n  -i INPUT, --input INPUT\n                        Input file mask, e.g. \"/path/*.SEQ\" (default: *.SEQ)\n  -v VERBOSITY, --verbosity VERBOSITY\n                        Logging level (default: info)\n  --preview_format PREVIEW_FORMAT\n                        Output preview format (png, jpg, tiff) (default: jpg)\n  --rgb RGB             If provided, split videos too e.g. \"/path/*.MOV\"\n                        (default: )\n  --jpeg_quality JPEG_QUALITY\n                        RGB Output quality (0-100) (default: 80)\n  --use_gstreamer       Use Gstreamer for video decoding (default: False)\n  --copy                Copy first, instead of move after split (default:\n                        False)\n  --width WIDTH         Image width (if unspecified flirpy will attempt to\n                        infer from FFF files) (default: None)\n  --height HEIGHT       Image height (default: None)\n  --merge_folders       Merge output folders (and remove intermediates\n                        afterwards) (default: True)\n  --no_merge_folders    Merge output folders (and remove intermediates\n                        afterwards) (default: True)\n  --split_filetypes     Split output files by type (make\n                        raw/preview/radiometric folders) (default: True)\n  --no_split_filetypes  Split output files by type (make\n                        raw/preview/radiometric folders) (default: True)\n  --export_meta         Export meta information files (also for geotagging)\n                        (default: True)\n  --no_export_meta      Export meta information files (also for geotagging)\n                        (default: True)\n  --export_tiff         Export radiometric tiff files (default: True)\n  --no_export_tiff      Export radiometric tiff files (default: True)\n  --export_raw          Leave raw files (by default copy meta to radiometric)\n                        (default: False)\n  --no_export_raw       Leave raw files (by default copy meta to radiometric)\n                        (default: False)\n  --export_preview      Export 8-bit preview png files (default: True)\n  --no_export_preview   Export 8-bit preview png files (default: True)\n  --skip_thermal        Skip thermal processing (default: False)\n  --no_skip_thermal     Skip thermal processing (default: False)\n  --sync_rgb            Attempt to synchronise RGB/IR streams (default: False)\n  --no_sync_rgb         Attempt to synchronise RGB/IR streams (default: False)\n```\n\n**Flirpy includes an experimental FFF interpreter that attempts to load metadata and other information directly from the file headers. If you have trouble splitting your SEQ files, then specify the `width` and `height` parameters in this script and it will fall back to using Exiftool.**\n\n`split_seqs` accepts either a directory, a specific filename, or a wildcard string (e.g. `\"./my/data/flight_*.SEQ\"`). If you use wildcards, be sure to enclose the argument in quotes, otherwise your shell will expand the wildcard before running the program and confuse it. If you specify a directoy, all SEQ files in that diretory will be used.\n\nFiles will be extracted to folders with the same base name as the SEQ file, for example `20180101_1030.SEQ` will be extracted to `20180101_1030`, etc. By default the splitter will three kinds of files, separated by subfolder.\n\n* Raw (FFF) files with metadata text files\n* Radiometric 16-bit tiff images\n* Preview 8-bit RGB representations of the radiometric data\n\nBy default, the raw folder will be deleted and all the metadata files will be copied to the radiometric folder. This is mostly to save disk space as it's unlikely you need the raw files hanging around. If you do need raw counts for some reason, you can use the `--no_export_radiometric` flag.\n\nThe tiff images will be geotagged if GPS information is present in the raw data.\n\nOutput images are numbered sequentially. If SEQ file 1 contains 1800 frames, the first frame from SEQ file 2 will be numbered 1800.\n\nRGB extraction options are experimental. Generally it's difficult to sync the two streams because they do not start simultaneously and when the IR camera flat fields, it can cause odd discontinuities in the data. If you are familiar with multi-modal video synchronisation, we'd love to hear from you!\n## Installation\n\nFlirpy has been tested with Python 3 and _may_ work on Python 2. It is always recommended that you install packages inside a virtualenv or Conda environment.\n\nSimply install using `pip`:\n\n``` bash\npip install flirpy\n```\n\nOr you can clone the repository and run:\n\n``` bash\npip install .\n```\n\nOr:\n\n``` bash\npython setup.py install\n```\n\nUsing `pip` is preferable, as it will let you uninstall the package if you need.\n\nflirpy is distributed with a copy of [Exiftool](https://sno.phy.queensu.ca/~phil/exiftool/) which is used to extract metadata from certain file formats.\n\nFor a fast local pip install, e.g. from the repository:\n\n``` bash\npython setup.py bdist_wheel\npip install flirpy --no-index --find-links ./dist\n```\n\nThis will disable pip looking up stuff online and tell it to look in the dist folder for wheels. This is a useful command for testing!\n\n### Installation on ARM (e.g. Raspberry Pi)\n\nFlirpy mostly works well, and has been tested, on the Raspberry Pi. If you're building from scratch, you need to install a few things manually. Try to use Python 3 if you can.\n\nIt's recommended that you first install the Python dependencies using `pip` in combination with [piwheels](https://www.piwheels.org/). For whatever reason, `setuptools` does not find these files, so it will fail if e.g. OpenCV isn't installed already. Once you've set up piwheels (it should be automatic on Raspbian if you've installed pip3) run:\n\n``` bash\npip3 install -r requirements.txt\n```\n\nYou may need to install some dependencies for OpenCV, for example `libjasper-dev`.\n\nYou should also install Exiftool manually with `sudo apt install exiftool`.\n\nNowadays `opencv-python-headless` should exist on most ARM platforms, including `aarch64`.\n\n## Grab images\n\nHere's a very simple example of grabbing an image using a Boson or Lepton:\n    \n``` python\nfrom flirpy.camera.lepton import Lepton\n\ncamera = Lepton()\nimage = camera.grab()\ncamera.close()\n```\n\nIf you're using a PureThermal Lepton you can also check frame telemetry if enabled:\n\n```python\ncamera.major_version\ncamera.minor_version\ncamera.uptime_ms\ncamera.status # see datasheet\ncamera.revision\ncamera.frame_count\ncamera.frame_mean # too low?\ncamera.fpa_temp_k\ncamera.ffc_temp_k\ncamera.ffc_elapsed_ms\ncamera.agc_roi\ncamera.clip_high\ncamera.clip_low\ncamera.video_format\n```\n\nFlirpy automatically locates your camera and captures a 16-bit (raw) image:\n\n``` python\nfrom flirpy.camera.boson import Boson\n\ncamera = Boson()\nimage = camera.grab()\ncamera.close()\n```\n\nIf you have a Tau with TeAx's USB grabbing back, then you can grab radiometric images directly:\n\n``` python\nfrom flirpy.camera.tau import TeaxGrabber\n\ncamera = TeaxGrabber()\nimage = camera.grab()\ncamera.close()\n```\n\nThese radiometric images are returned as 64-bit Numpy arrays in units of Celsius. This assumes a conversion factor of 0.04 K per count.\n\nConveniently, `TeaxGrabber` subclasses the `Tau` driver so you also have access to all the internal information from the camera, for example:\n\n```python\ncamera = TeaxGrabber()\ncamera.get_fpa_temperature()\n```\n\nCameras support the Python `with` interface to ensure that interfaces are properly closed when the resource is no longer needed (swap in Lepton or TeaxGraber):\n\n```python\nimport cv2\nfrom flirpy.camera.boson import Boson\n\nwith Boson() as camera:\n    while True:\n        img = camera.grab().astype(np.float32)\n\n        # Rescale to 8 bit\n        img = 255*(img - img.min())/(img.max()-img.min())\n        \n        # Apply colourmap - try COLORMAP_JET if INFERNO doesn't work.\n        # You can also try PLASMA or MAGMA\n        img_col = cv2.applyColorMap(img.astype(np.uint8), cv2.COLORMAP_INFERNO)\n\n        cv2.imshow('Boson', img_col)\n        if cv2.waitKey(1) == 27:\n            break  # esc to quit\n        \ncv2.destroyAllWindows()\n```\n\n## Driver problems on Windows\n\nOccasionally Windows can do some bizarre things and forget that USB devices are cameras. This will stop the camera from being discoverable by flirpy (and usable by software including OpenCV).\n\nYou can solve this by going to device manager, right clicking on the USB device and selecting \"Update Driver\". Choose \"Browse my computer ... \" and then \"Let me pick ... \". Choose the \"USB Video Device\" driver.\n\n\n## Tests\n\nTo run the test suite:\n\n``` bash\npip install pytest pytest-cov\npython -m pytest --cov=flirpy\n```\n\nSome tests are hardware dependent, e.g. for cameras, so expect them to fail unless you own and have a camera to try them with. Hardware tests are skipped by default if the requisite camera is not plugged in.\n\nThe repository includes some small representative examples of image files (e.g. SEQ). It is tested and is routinely used with flight data from FLIR Duo cameras, so larger files aren't a problem, but they're too large to include in the repository.\n\nIf you're testing on Python 2:\n```bash\npip install pytest pytest-cov backports.tempfile\npytest --cov=flirpy test\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2FLJMUAstroecology%2Fflirpy","html_url":"https://awesome.ecosyste.ms/projects/github.com%2FLJMUAstroecology%2Fflirpy","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2FLJMUAstroecology%2Fflirpy/lists"}