{"id":46343934,"url":"https://github.com/awxkee/libblur","last_synced_at":"2026-04-02T18:02:31.658Z","repository":{"id":235610623,"uuid":"791001101","full_name":"awxkee/libblur","owner":"awxkee","description":"High performance blur in pure Rust using SIMD","archived":false,"fork":false,"pushed_at":"2026-03-29T13:48:58.000Z","size":23982,"stargazers_count":81,"open_issues_count":0,"forks_count":5,"subscribers_count":1,"default_branch":"master","last_synced_at":"2026-03-29T14:35:56.706Z","etag":null,"topics":["blur","box-blur","gauss-blur","gaussian-filter","median-blur","median-filter","neon","rust","simd","sse","sse41","stack-blur","wasm"],"latest_commit_sha":null,"homepage":"","language":"Rust","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"bsd-3-clause","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/awxkee.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":".github/FUNDING.yml","license":"LICENSE-APACHE.md","code_of_conduct":"CODE_OF_CONDUCT.md","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,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null},"funding":{"github":"awxkee"}},"created_at":"2024-04-23T23:11:10.000Z","updated_at":"2026-03-29T13:35:24.000Z","dependencies_parsed_at":"2024-04-24T00:27:06.843Z","dependency_job_id":"75721667-804c-4da3-af91-d5a571dc186c","html_url":"https://github.com/awxkee/libblur","commit_stats":null,"previous_names":["awxkee/fastblur"],"tags_count":67,"template":false,"template_full_name":null,"purl":"pkg:github/awxkee/libblur","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/awxkee%2Flibblur","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/awxkee%2Flibblur/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/awxkee%2Flibblur/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/awxkee%2Flibblur/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/awxkee","download_url":"https://codeload.github.com/awxkee/libblur/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/awxkee%2Flibblur/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":31312744,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-02T12:59:32.332Z","status":"ssl_error","status_checked_at":"2026-04-02T12:54:48.875Z","response_time":89,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.5:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"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":["blur","box-blur","gauss-blur","gaussian-filter","median-blur","median-filter","neon","rust","simd","sse","sse41","stack-blur","wasm"],"created_at":"2026-03-04T21:02:41.707Z","updated_at":"2026-04-02T18:02:31.602Z","avatar_url":"https://github.com/awxkee.png","language":"Rust","funding_links":["https://github.com/sponsors/awxkee"],"categories":[],"sub_categories":[],"readme":"# Fast blur algorithms library for Rust\n\nThere are some very good and blazing fast algorithms that do blurring images.\nAlso providing convenient api for doing convolution and some edge detection filters.\\\nBest optimized for NEON, SSE and AVX, partially done WASM.\n\nYou may receive gaussian blur in 100 FPS for 4K photo.\n\nMuch faster than `image` default blur.\n\nWhen 4-channels mode is in use that always considered that alpha channel is the last.\n\nAlso there are some available options to perform blurring in linear colorspace, or if methods do not fit you `f32`\noptions also available\n\n# Performance\n\nMost blur algorithms done very good and works at excellent speed. Where appropriate comparison with OpenCV is available.\n\n# Usage\n\n```\ncargo add libblur\n```\n\n#### Usage with image feature\n\n```rust\nlet blurred = gaussian_blur_image(\n    img,\n    GaussianBlurParams::new_from_kernel(61.),\n    EdgeMode2D::new(EdgeMode::Clamp),\n    ConvolutionMode::FixedPoint,\n    ThreadingPolicy::Adaptive,\n)\n.unwrap();\n\nblurred\n.save_with_format(\"blurred.jpg\", ImageFormat::Jpeg)\n.unwrap();\n```\n\n### Transfer function\n\nAll blur methods assume that data is already linearized.\nIf additional linearization is needed use API:\n\n```rust\nlet cvt = BlurImage::borrow(\n    \u0026v_vec,\n    dyn_image.width(),\n    dyn_image.height(),\n    FastBlurChannels::Channels4,\n);\nlet image = cvt\n    .linearize(libblur::TransferFunction::Srgb, true)\n    .unwrap();\n// perform blur\nlet dst_ref = dst_image.to_immutable_ref();\nlet back_in_gamma = dst_ref.gamma8(libblur::TransferFunction::Srgb, true);\n```\n\n### Gaussian blur\n\nExcellent results. Have significant improvements, however, much slower than any approximations. Use when use need gaussian\nmethods - smoothing, FFT, advanced analysis etc.\nThere are two methods of convolution, fixed point approximation and exact,\napproximation in fixed point adds 1-3% of error. However, it is about two times faster.\n\nKernel size must be odd. Will panic if kernel size is not odd.\n\nO(R) complexity.\n\n```rust\nlibblur::gaussian_blur( \u0026 bytes, src_stride, \u0026 mut dst_bytes, dst_stride, width, height, kernel_size, sigma, FastBlurChannels::Channels3, GaussianPreciseLevel::EXACT);\n```\n\nExample comparison time for blurring image 3000x4000 RGB 8-bit in multithreaded mode with 151 kernel size.\n\n|                     | Time(NEON) | Time(AVX) | \n|---------------------|:----------:|:---------:| \n| libblur(Exact)      |  49.40ms   |  43.41ms  | \n| libblur(FixedPoint) |  26.68ms   |  30.72ms  | \n| OpenCV              |  180.56ms  | 182.44ms  | \n\nExample comparison time for blurring image 2828x4242 RGBA 8-bit in multithreaded mode with 151 kernel size.\n\n|                     | time(NEON) | Time(AVX) |\n|---------------------|:----------:|:---------:|\n| libblur(Exact)      |  65.13ms   |  51.40ms  |\n| libblur(FixedPoint) |  33.99ms   |  38.91ms  |\n| OpenCV              |  134.60ms  | 185.30ms  |\n\nExample comparison time for blurring image 3000x4000 single plane 8-bit in multithreaded mode with 151 kernel size.\n\n|                     | time(NEON) | Time(SSE/AVX) |\n|---------------------|:----------:|:-------------:|\n| libblur(Exact)      |  17.59ms   |    15.51ms    |\n| libblur(FixedPoint) |   8.50ms   |    11.45ms    |\n| OpenCV              |  74.73ms   |    64.20ms    |\n\n### Stack blur\n\nThe fastest with acceptable results. Result are quite close to gaussian and look good. Sometimes noticeable changes\nmay be\nobserved. However, if you'll use advanced analysis algorithms non gaussian methods will be detected. Not suitable for\nadvanced analysis. Results just a little worse than in 'fast gaussian', however it's faster.\n\nO(1) complexity.\n\n```rust\nlet mut dst_image = BlurImageMut::borrow(\u0026mut src_bytes, dyn_image.width(), dyn_image.height(), FastBlurChannels::Channels3)\nlibblur::stack_blur( \u0026mut dst_image, 10, ThreadingPolicy::Single).unwrap();\n```\n\nExample comparison time for blurring image 3000x4000 RGB 8-bit in multithreaded mode with 77 radius.\n\n|         | time(NEON) | time(SSE) |\n|---------|:----------:|:---------:|\n| libblur |   4.95ms   |  5.30ms   |\n| OpenCV  |   8.43ms   |  10.36ms  |\n\nExample comparison time for blurring image 2828x4242 RGBA 8-bit in multithreaded mode with 77 radius.\n\n|         | time(NEON) | time(SSE) |\n|---------|:----------:|:---------:|\n| libblur |   4.97ms   |  5.48ms   |\n| OpenCV  |   8.00ms   |  8.55ms   |\n\n### Fast gaussian\n\nVery fast. Result are quite close to gaussian and look good. Sometimes noticeable changes\nmay be\nobserved. However, if you'll use advanced analysis algorithms non gaussian methods will be detected. Not suitable for\nadvanced analysis.\nDo not use when you need gaussian. Based on binomial filter, generally speed close, might be a little faster than stack\nblur , however results are better.\n\nO(log R) complexity.\n\n```rust\nlet mut dst_image = BlurImageMut::borrow(\u0026mut src_bytes, dyn_image.width(), dyn_image.height(), FastBlurChannels::Channels3)\nlibblur::fast_gaussian(\u0026mut dst_image, 10, ThreadingPolicy::Single, EdgeMode::Wrap).unwrap();\n```\n\nExample comparison time for blurring image 3000x4000 RGB 8-bit in multithreaded mode with 77 radius.\n\n|         | time(NEON) | time(SSE) | \n|---------|:----------:|:---------:| \n| libblur |   5.72ms   |  6.42ms   | \n| OpenCV  |     -      |     -     | \n\nExample comparison time for blurring image 2828x4242 RGBA 8-bit in multithreaded mode with 77 radius.\n\n|         | time(NEON) | time(SSE) |\n|---------|:----------:|:---------:|\n| libblur |   5.49ms   |  5.77ms   |\n| OpenCV  |     --     |    --     |\n\n### Fast gaussian next\n\nVery fast.\nProduces very pleasant results close to gaussian. Max radius ~150-180 for u8, for u16 will be less.\n\nO(log R) complexity.\n\n```rust\nlet mut dst_image = BlurImageMut::borrow(\u0026mut src_bytes, dyn_image.width(), dyn_image.height(), FastBlurChannels::Channels3)\nlibblur::fast_gaussian_next(\u0026mut dst_image, 10, ThreadingPolicy::Single, EdgeMode::Wrap).unwrap();\n```\n\nExample comparison time for blurring image 2828x4242 RGBA 8-bit in multithreaded mode with 35 radius.\n\n|         | time(NEON) | time(SSE) |\n|---------|:----------:|:---------:| \n| libblur |   4.07ms   |  6.08ms   | \n| OpenCV  |     -      |     -     | \n\nExample comparison time for blurring image 3000x4000 RGB 8-bit in multithreaded mode with 77 radius.\n\n|         | time(NEON) | time(SSE) |\n|---------|:----------:|:---------:|\n| libblur |   4.71ms   |  6.15ms   |\n| OpenCV  |     -      |     -     |\n\n### Tent blur\n\n2 sequential box blur ( [theory](https://en.wikipedia.org/wiki/Central_limit_theorem) ) that produces a tent filter.\nMedium speed, good-looking results with large radius `tents` becoming more noticeable\n\nO(1) complexity.\n\n```rust\nlet image = BlurImage::borrow(\n    \u0026src_bytes,\n    dyn_image.width(),\n    dyn_image.height(),\n    FastBlurChannels::Channels3,\n);\nlet mut dst_image = BlurImageMut::default();\nlibblur::tent_blur(\u0026image, \u0026mut dst_image,10f32, ThreadingPolicy::Single).unwrap();\n```\n\n### Median blur\n\nMedian blur ( median filter ). Implementation is fast enough.\n\nO(log R) complexity.\n\n```rust\nlet image = BlurImage::borrow(\n    \u0026src_bytes,\n    dyn_image.width(),\n    dyn_image.height(),\n    FastBlurChannels::Channels3,\n);\nlet mut dst_image = BlurImageMut::default();\nlibblur::median_blur(\u0026image, \u0026mut dst_image,10, ThreadingPolicy::Single).unwrap();\n```\n\nExample comparison time for blurring image 3000x4000 RGB 8-bit in multithreaded mode with 35 radius.\n\n|         | time(NEON) | time(SSE) |\n|---------|:----------:|:---------:|\n| libblur |  603.51ms  | 872.03ms  |\n| OpenCV  |  637.83ms  | 959.07ms  |\n\nExample comparison time for blurring image 2828x4242 RGBA 8-bit in multithreaded mode with 35 radius.\n\n|         | time(NEON) | time(SSE) |\n|---------|:----------:|:---------:|\n| libblur |  643.22ms  | 695.75ms  |\n| OpenCV  |  664.22ms  | 808.21ms  |\n\n### Gaussian box blur\n\nGenerally 3 sequential box blurs it is almost gaussian\nblur ( [theory](https://en.wikipedia.org/wiki/Central_limit_theorem) ), slow, really pleasant results.\nMedium speed.\n\nO(1) complexity.\n\n```rust\nlet image = BlurImage::borrow(\n    \u0026src_bytes,\n    dyn_image.width(),\n    dyn_image.height(),\n    FastBlurChannels::Channels3,\n);\nlet mut dst_image = BlurImageMut::default();\nlibblur::gaussian_box_blur(\u0026image, \u0026mut dst_image, 10f32, ThreadingPolicy::Single).unwrap();\n```\n\n### Box blur\n\nBox blur. Compromise speed with bad looking results.\nMedium speed.\n\nO(1) complexity.\n\n```rust\nlet image = BlurImage::borrow(\n    \u0026src_bytes,\n    dyn_image.width(),\n    dyn_image.height(),\n    FastBlurChannels::Channels3,\n);\nlet mut dst_image = BlurImageMut::default();\nlibblur::box_blur(\u0026image, \u0026mut dst_image,10, ThreadingPolicy::Single).unwrap();\n```\n\nExample comparison time for blurring image 3000x4000 RGB 8-bit in multithreaded mode with 77 radius.\n\n|         | time(NEON) | time(SSE) |\n|---------|:----------:|:---------:|\n| libblur |   3.71ms   |  6.08ms   |\n| OpenCV  |  15.73ms   |  43.59ms  |\n\nExample comparison time for blurring image 2828x4242 RGBA 8-bit in multithreaded mode with 77 radius.\n\n|         | Time(NEON) | Time(SSE) |\n|---------|:----------:|:---------:|\n| libblur |   3.56ms   |  6.16ms   |\n| OpenCV  |  15.77ms   |  31.29ms  |\n\nExample comparison time for blurring image 2828x4242 RGBA 8-bit in single-thread mode with 15 radius on MacOS.\n\n|                  | Time(NEON) |\n|------------------|:----------:|\n| libblur          |  11.46ms   |\n| Apple Accelerate |  11.65ms   |\n\n### Fast bilateral blur\n\nThis is fast bilateral approximation, note this behaviour significantly differs from OpenCV.\nThis method has high convergence and will completely blur an image very fast with increasing spatial sigma.\nBy the nature of this filter the more spatial sigma are the faster method is.\n\n```rust\nlet image = BlurImage::borrow(\n    \u0026src_bytes,\n    dyn_image.width(),\n    dyn_image.height(),\n    FastBlurChannels::Channels3,\n);\nlet mut dst_image = BlurImageMut::default();\nlibblur::fast_bilateral_filter(\u0026image, \u0026mut dst_image, 25, 7f32, 7f32).unwrap();\n```\n\n### Common speed chain\n\nThis is arbitrary example for blurring speed for all methods in descending order. \n\nbox_blur -\u003e stack_blur -\u003e fast_gaussian_next -\u003e fast_gaussian -\u003e fast_gaussian_superior -\u003e tent_blur -\u003e gaussian_box_blur -\u003e gaussian_blur -\u003e bilateral -\u003e median\n\nThis project is licensed under either of\n\n- BSD-3-Clause License (see [LICENSE](LICENSE.md))\n- Apache License, Version 2.0 (see [LICENSE](LICENSE-APACHE.md))\n\nat your option.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fawxkee%2Flibblur","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fawxkee%2Flibblur","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fawxkee%2Flibblur/lists"}