Skip to main content

Blur immodestly dressed people in videos. Video in, video out.

Project description

OCCLUDE

As a muslim, there is content I want to watch and don't. Not because it's bad content (documentaries, lectures, educational videos I'm genuinely curious about), but because they have immodestly dressed people in them, and I'd rather not sit through that. The friction is not the content, it's what's mixed into it.

I went looking for a tool that would just take the video and give me back the same video, with those people blurred. Browser extensions like HaramBlur and PordaAI process in real time, which forces brutal accuracy tradeoffs: flickering, missed frames, false positives. I needed something for offline processing, where you trade interactivity for actually getting it right.

OCCLUDE is what I built. You give it a video file, it gives you back a video file, the immodestly dressed people are blurred according to Islamic modesty rules, and the original audio is intact.

occlude --input documentary.mp4
# → documentary_occluded.mp4

This is not a general people-removal or object-removal tool. The blur logic checks what's visible on each person against specific Islamic modesty criteria, not just whether someone is present. I built it for muslims who run into the same friction. If that's you, you're welcome here.

The modesty rules

The decision is binary: a person either gets fully blurred or they don't. There's no partial blur of a specific body part.

For women, the entire person is blurred if any of the following is visible: uncovered hair, bare arms, bare legs, or exposed neck and chest. Uncovered hair is the primary trigger in practice: if hair is visible, the person is blurred.

For men, the entire person is blurred if any skin in the zone between the navel and the knee is visible. Being shirtless is the primary trigger since it automatically exposes the navel. Shorts or exposed thighs are the secondary case.

People dressed modestly are never blurred: a woman in full hijab and modest clothing, a man in a t-shirt and full-length trousers. Faces of modestly dressed people, backgrounds, objects, animals, and text overlays are not touched.

How it works

 input.mp4 ─▶ frame extraction
                    │
             person detection (YOLOv8)
                    │
          gender classification (per person)
                    │
        body part segmentation (per person crop)
                    │
          modesty rule check (binary decision)
                    │
     blur full bounding box if triggered
                    │
     temporal smoothing (carry flag across frames)
                    │
     video reconstruction (original audio preserved)
                    │
             output_occluded.mp4

YOLOv8 finds the people. A gender classifier determines which rule set applies. A body-part segmentation model identifies what's visible on each crop. The modesty rules run on that output, and if triggered, the full bounding box gets a Gaussian blur. Basic tracking carries a flag forward a few frames so the blur doesn't flicker when detection briefly drops between frames.

Install

pip install occlude

If you have an NVIDIA GPU, install the GPU extra instead. It pulls in onnxruntime-gpu so the face and gender model runs on CUDA along with everything else, which is the difference between a long file finishing overnight and finishing while you sleep badly:

pip install 'occlude[gpu]'

Python 3.10+ required. I develop on macOS with Apple Silicon, and for anything long I run the CUDA path, usually on Google Colab. Plain CPU works but gets slow fast on anything past a short clip.

Usage

occlude --input /path/to/video.mp4

Output is saved in the same directory as the input, named video_occluded.mp4.

Optional flags:

occlude --input video.mp4 --output cleaned.mp4   # custom output path
occlude --input video.mp4 --blur-strength 99     # Gaussian kernel size, odd number (default 199)
occlude --input video.mp4 --frame-stride 3       # run detection every 3rd frame

--frame-stride is the one that matters for long content. On the frames it skips it doesn't re-run detection, it just re-applies the previous frame's blur, so a stride of 3 is roughly three times faster for a small amount of positional lag the soft blur edge hides anyway. I run feature-length files at stride 3 to 6. Leave it at 1 if you want every frame analysed and don't mind the wait.

Running on Google Colab

OCCLUDE is compute-intensive, and where it runs changes the experience a lot. On an NVIDIA GPU every stage runs on CUDA: person detection, body-part segmentation, the per-frame blur, and the face and gender model. On Apple Silicon the detector and segmenter use the GPU through Metal, but the face and gender model still falls back to the CPU, so a feature-length file is slow even there. On a plain CPU it gets painful well before you reach a documentary.

So for anything long, Google Colab with a GPU runtime is the path I actually use. A ready-to-run notebook is at notebooks/occlude_colab.ipynb. Open it in Colab, point it at your video, and run the cells. The notebook installs occlude[gpu], repairs the onnxruntime-gpu install so the face model doesn't silently land on the CPU, and verifies every stage is on the GPU before it starts a multi-hour run.

What OCCLUDE isn't

Before you install it, a few things it doesn't do, so you don't find out the wrong way.

It's not a general people-removal or object-removal tool. If you want to blur all people regardless of dress, or remove specific objects, this is the wrong tool. The blur is tied to the modesty rules above and only triggers when they're violated.

It's not a browser extension and doesn't do real-time processing. OCCLUDE works on local video files only.

It's terminal only. No GUI, no drag-and-drop.

It doesn't take YouTube URLs or download videos. Give it a local file.

Development stage

It works and I use it on real content, but it's still early. The accuracy is reasonable on clear cases: shirtless men, women with uncovered hair and bare arms in decent lighting. Edge cases will give you trouble: unusual angles, partial occlusion, low-resolution video, complex backgrounds.

A long documentary on a machine without GPU acceleration will take a while. Start with a short clip to confirm the output is what you need before committing to a full-length file.

If you find a consistent failure mode, open an issue with a description of the content type. That's more useful than a general accuracy complaint.

Contributing

The parts most worth improving right now: segmentation accuracy, gender classification on difficult crops, and speed on long content. NVIDIA is covered now through the CUDA path; AMD and other accelerators aren't yet. If you want to build a frontend or optimise for a different hardware target, there's room for that too.

Open an issue or PR at https://github.com/anaxoniclabs/OCCLUDE/issues.

If a fellow muslim developer takes this further than I could, that's honestly the outcome I'd be happiest with.

License

MIT

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

occlude-1.2.0.tar.gz (43.5 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

occlude-1.2.0-py3-none-any.whl (34.7 kB view details)

Uploaded Python 3

File details

Details for the file occlude-1.2.0.tar.gz.

File metadata

  • Download URL: occlude-1.2.0.tar.gz
  • Upload date:
  • Size: 43.5 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.13

File hashes

Hashes for occlude-1.2.0.tar.gz
Algorithm Hash digest
SHA256 ebdbf050c0d647030409eef2db420a790aacc2d57a4ede23198f65a1b7cda3b5
MD5 2b5a7d9ccf1ce4a0f7cc522f51043bf2
BLAKE2b-256 0a22738012883d241d53ff873f887f69ca2a2c8c31dca5efd80a49df9a89936e

See more details on using hashes here.

Provenance

The following attestation bundles were made for occlude-1.2.0.tar.gz:

Publisher: publish.yml on anaxoniclabs/OCCLUDE

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file occlude-1.2.0-py3-none-any.whl.

File metadata

  • Download URL: occlude-1.2.0-py3-none-any.whl
  • Upload date:
  • Size: 34.7 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.13

File hashes

Hashes for occlude-1.2.0-py3-none-any.whl
Algorithm Hash digest
SHA256 d8ceaeb511d1ba685b276c9011c0ec8fcfd452a5fcdaa757b0fdc79af9058d0b
MD5 8c1b0b4a40b76dd788350f22634e3c83
BLAKE2b-256 b18fa74e8fdba8fff7193da01e8c2933cac955ab9b47730a8a95724d8648b370

See more details on using hashes here.

Provenance

The following attestation bundles were made for occlude-1.2.0-py3-none-any.whl:

Publisher: publish.yml on anaxoniclabs/OCCLUDE

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page