Blur Image
Blur any image right in your browser. Soften the whole picture or just one rectangle, choose a Gaussian blur or a pixelate mode, drag the strength slider, and download. Nothing is uploaded.
- Free, no account
- No watermark
- No usage limit
About the Blur Image
Until this week this tool handed back part of your original picture, and not a subtle part. A mark sitting against the edge of the frame kept 62.4 percent of its contrast at a blur strength of 8, and 51.4 percent at 64, and pushing the slider up made the weak band wider instead of narrower. On a page whose entire job is hiding a face or a numberplate, that was the worst bug it could have had, and it is now fixed: the same measurement reads 29.4 percent and 3.9 percent, and it improves as you push the slider rather than getting worse. Everything below is what I measured proving it, including the repair I tried first that turned out to be the bug wearing a different hat.
Load a picture, pick Gaussian blur or a chunky pixelate, and drag the strength while the preview updates. Blur the whole frame, or draw a box around one face or plate and leave the rest of the shot sharp. No account, no watermark, and the file never leaves your machine.
How to use
- Choose an image. Click the box or drag a file in. The size limit is exactly 40 MB, and it is a hard edge, not a rough guide. A file one byte over comes back with "is bigger than the 40 MB limit, so it was left out" and nothing loads.
- Pick the effect. Gaussian is the smooth, out of focus look. Pixelate breaks the area into flat blocks, the mosaic censor style.
- Choose the scope. Whole image blurs everything. Just a rectangle blurs a box you draw and leaves the rest exactly as it was.
- Draw the box (rectangle mode). Drag on the preview. It starts centered at half the width and half the height of your image, and you can redraw as often as you like. Only the last box counts.
- Set the strength. For Gaussian the number is a pixel radius and it runs from 0 to 200. For pixelate it is a percentage from 1 to 100 that gets turned into a block size scaled to the area you covered, so slider 25 on a full 4032 by 3024 phone photo gives you 126 pixel blocks, and the same 25 on a 300 by 300 box gives you 13 pixel ones.
- Download. JPG, PNG and WebP come back as themselves. Everything else (GIF, BMP, TIFF, AVIF, HEIC, SVG) comes back as PNG.
Hit Clear to start over. Nothing is final until you download, and there is no un-blur once it is.
The border bug, what caused it, and the fix that did not work
This is the finding I would most want you to take away, because the cause has nothing to do with this page in particular and everything to do with what a blur does at the edge of any picture at all.
A blur works by averaging each pixel with its neighbors. At the edge of a picture half those neighbors do not exist, so the blurred layer comes out partly see-through there. Measured on the old code, the blurred layer's coverage in the very first column was 128 to 134 out of 255, and it did not reach full coverage until 2.38 to 2.44 times the blur radius inward. The old renderer dealt with that by painting the sharp original underneath as a backing, with a comment in the code explaining that this stopped the edges going transparent. It did stop the edges going transparent, by filling the gap with the one thing that must never be in a redaction.
Here is the measurement. A 3 pixel black bar in a 1200 by 400 white frame, moved inward one step at a time, blurred whole. Each cell is how much of the bar's original contrast survived, before this week and after.
| bar position | strength 8 | strength 16 | strength 24 | strength 40 | strength 64 |
|---|---|---|---|---|---|
| touching the edge | 62.4% to 29.4% | 56.1% to 14.9% | 54.1% to 9.8% | 52.5% to 5.9% | 51.4% to 3.9% |
| 12 px in | 19.6% to 14.9% | 28.6% to 11.0% | 34.9% to 8.6% | 40.8% to 5.9% | 43.9% to 3.5% |
| 32 px in | 14.9% to 14.9% | 8.6% to 7.5% | 12.9% to 5.1% | 23.1% to 4.3% | 32.2% to 3.5% |
| 96 px in | 14.9% to 14.9% | 7.5% to 7.5% | 5.1% to 5.1% | 3.1% to 3.1% | 7.5% to 2.0% |
| dead center | no change at any strength |
Read the second row rather than the first, because it is the one that gives the cause away. Twelve pixels from the edge, the old blur got worse as you turned it up, from 19.6 percent to 43.9 percent, which is the opposite of what a blur slider is supposed to do. The weak band was exactly as wide as the blur reached, so a stronger blur meant a wider band of picture that had not really been blurred. Corners were the worst of it, because the effect stacks on both axes: a 3 pixel dot in the top left corner survived at 73.3 percent and now measures 0.8 percent.
Now the part I did not expect. The standard repair for this is to pad the picture before blurring it, stretching the edge pixels outward so the average has something real to work with. I built that first and it changed nothing. Not "not much". The border reading was identical to the bug at every strength I tried, and once I wrote out the arithmetic it was obvious why: stretching means every invented pixel equals the edge pixel, so the average at the border is half that one original pixel and half the honest answer, which is the same equation as the bug. What actually works is reflecting the picture outward instead, so that every added pixel is a real neighbor from further in, and that turned out to be the whole fix.
Rectangle mode leaked the same way when the box you drew touched the frame. A box at x equals 0 now measures 9.8 percent at strength 24 against 5.1 percent for the same box moved 100 pixels inward, which is close enough to call the same. Pixelate never had the problem at all: it measured 0.0 percent at the border before any of this work and it still does, because a block average has no soft falloff to lose.
One side effect worth knowing about, because it is a good way to see how much picture was leaking. Blurring the same 1440 by 1080 photo and saving it as a PNG, the file came out 9.6 percent smaller at strength 8, 32.4 percent smaller at strength 24, and 70.0 percent smaller at strength 64 than the old code produced. Most of what those old files were spending their bytes on was unblurred detail around the border.
I measured all of this in Node against Skia, the same drawing engine Chromium uses, driving this page's own code. I have not confirmed it in a real browser, and I am not going to pretend otherwise.
How much blur it actually takes to erase text
Here is the second measurement, and the honest headline is that there is no single multiplier, which is what I would have told you if you had asked me before I ran it.
One line of bold Arial in the middle of a white frame, blurred whole, then read back for the strongest light to dark difference left inside the text. It starts at 255 levels and below about 2 there is no shape left in the file at all. "Ink height" is the height of the actual marks in the picture, which for Arial runs at roughly three quarters of the font size.
| font size | ink height | faint smudge | nothing left | ratio to ink height |
|---|---|---|---|---|
| 10 px | 7 px | 6 | 20 | 2.86 |
| 14 px | 11 px | 9 | 28 | 2.55 |
| 20 px | 15 px | 13 | 40 | 2.67 |
| 28 px | 20 px | 17 | 56 | 2.80 |
| 40 px | 28 px | 25 | 80 | 2.86 |
| 55 px | 39 px | 34 | 109 | 2.79 |
| 60 px | 43 px | 38 | 126 | 2.93 |
| 90 px | 67 px | 59 | 184 | 2.75 |
That looks beautifully consistent at about 2.8 times the ink height, and then you change what is written on the line and it falls apart. Same 40 pixel font, same frame, same threshold:
| what is on the line | strength to erase it | ratio to ink height |
|---|---|---|
a single 8 |
28 | 1.00 |
a single W |
37 | 1.32 |
B8 4RG |
80 | 2.86 |
Ashworth |
92 | 3.29 |
ACCOUNT BALANCE 12,480.55 |
192 | 5.65 |
A long line of text is far harder to erase than a short one at the same height. It makes sense once you see it: a run of dark characters is one big dark region as well as a lot of small ones, and a blur is much better at destroying the small ones. So the useful rule is not a number, it is look at how much text there is, not just how tall it is. Six characters want roughly 3 times their ink height. A whole line of a bank statement wants nearer 6.
The slider used to stop at 100 and it now stops at 200, which was a measured decision rather than a generous one. At 100, a 60 pixel line of plate characters was still carrying 4 levels of contrast, and at 90 pixels that rose to 12. Pushing the same two lines to 200 takes them to 0 and 2. The cost of the higher ceiling turned out to be nothing worth reporting in time (a 12 megapixel photo redraws in 304 ms at strength 200 against 292 ms at 100), because the drawing engine switches to a cheaper approximation as the radius grows. What it does cost is memory, since a stronger blur needs a bigger padded copy to work from, and if your device will not give the page one the tool says so on screen and names how wide a border it could not treat.
Pixelate still gets there faster and with room to spare. On that same 2400 by 1600 frame, 40 pixel text disappears at slider 12, which is a 32 pixel block, 60 pixel text at slider 20, and 90 pixel text at slider 24 on a control that runs to 100.
If you are hiding something rather than styling something, use pixelate and push the blocks past the size of the letters. That was my recommendation before I fixed the border bug and it still is, for a reason that has not changed: a block is one flat color, so the only question is whether the block is bigger than the letter, and the block size scales with the area you covered so it can always get big enough.
What the amber warning is scored against
When the strength is too low, this page shows an amber note saying the detail underneath is still readable. It had two problems and both are fixed, but the honest version is smaller than you might want.
It used to be impossible to satisfy. The rule asks for a blur radius of one twenty-fourth of the short side of whatever you covered. On a whole 4032 by 3024 phone photo that is 126, and the slider stopped at 100. So on the commonest image anybody loads, the warning could never go away no matter what you did, while telling you to push a control that had nothing left to give. A warning nobody can satisfy is worse than no warning, because it teaches you to ignore the one that matters. The slider now reaches 200, the note names the number it wants instead of saying "well up", and when a Gaussian genuinely cannot get there it says so and points at pixelate rather than repeating itself.
It still cannot see what is inside your box, and I have stopped pretending otherwise. The rule is scored against the area you covered. It has no idea how tall the characters on a plate are. Draw a tight 240 by 80 box around a numberplate and the warning clears at strength 8, while the characters on that plate are around 40 pixels tall and want something near 115. That gap is not fixable by being cleverer, because the size of the thing you are hiding is simply not in the data the page has. So the tool now says that next to the slider, in as many words: clearing the check means the setting is not obviously useless, and it is not a verdict that the plate is gone.
| what you covered | warning clears at | text that strength erases |
|---|---|---|
| a whole 4032 by 3024 phone photo | 126 | about 45 px of ink |
| a whole 1920 by 1080 screenshot | 45 | about 16 px |
| a whole 1200 by 800 photo | 33 | about 12 px |
| a 300 by 300 box on a face | 13 | about 5 px |
| a 240 by 80 box on a plate | 8 | about 3 px |
Treat it as a check that catches the obviously useless settings, which is what it is, and use the tables further up for the real number.
What is actually in the file you download
Three things I checked, because a blurred face shipped with the GPS tag still attached is a real failure and nobody talks about it.
Metadata is gone. I built a JPG carrying a 406 byte block with a camera make, a model, a software string, a timestamp and GPS coordinates, ran it through the blur, and read the output. Camera, timestamp, coordinates, all absent from the JPG, the PNG and the WebP. None of the original text strings survived anywhere in the bytes. What comes out is pixels, plus a 456 byte color profile on the JPG and WebP that the encoder writes itself.
Outside the box really is untouched. On a 1440 by 1080 photo with a 500 by 400 box drawn at (400, 300), exactly zero pixels outside that box changed, in either mode. Inside it, the Gaussian at strength 24 altered 199,991 of the 200,000 pixels and pixelate at slider 50 altered 199,952, the nine and the forty-eight it left alone being places where the average happened to land on the value already there. That only holds if you save as PNG, which is why the Save as box starts there when you load a JPG.
File size goes whichever way your particular picture pushes it, and I would not promise you a direction. Starting from a 698,309 byte JPG of a grainy photograph, a strength 24 blur saved back as JPG gives 62,693 bytes, 91 percent smaller, because the grain is what the encoder was spending its bytes on and the blur ate it. The same blur saved as PNG gives 573,829 bytes, still smaller than the source. Take a flat interface screenshot instead and it can go the other way, since a blur replaces uniform runs with gradients. What is consistent across everything I threw at it is pixelate: on that photo it came back at 9,986 bytes, and on the screenshot at 6,074 bytes against the original 162,605. So pixelate saved as PNG is both the strongest redaction here and by a wide margin the smallest file.
Frequently asked questions
Can a blurred image be un-blurred?
Sometimes, and I can show you the ceiling rather than guess at it. I ran a template attack against this tool's own output: seven characters of 28 pixel bold Arial, and an attacker handed the font, the size, the exact pixel position and the identity of every other character, re-rendering all 36 candidates and blurring each one identically to see which matched. It read 7 of 7 characters at every strength I tried, against a 2.8 percent chance baseline for a single guess.
The uncomfortable detail is what that means at the top of the slider. Fixing the border bug took the contrast left inside those characters at strength 100 from 8 levels down to 1, and at strength 200 there is nothing measurable left inside them at all. The attack still read all seven, because it compares the whole picture and the faint smear spreading out around the text still carries enough.
Now the honest framing, because that number is easy to misread. What I built is an upper bound on what anybody could ever extract, and no real person has those advantages. It worked on a clean file with no photo grain and no compression noise, knowing the exact typeface and the exact alignment. Someone working from a photograph has none of that. What the result does prove is that a Gaussian blur attenuates information rather than deleting it, so I will not tell you any strength on this slider is irreversible. I have not run a real deblurring attack on a real photo and my evidence stops there. For anything with genuine stakes, an ID, a legal document, a bank balance, cover the area with a solid opaque box in an editor instead. That is the only method with nothing left to recover.
Blur or pixelate, if I only care about hiding something?
Pixelate, at a block size bigger than the letters or features you are covering. It has three measured advantages here. A block collapses to one flat color, so on a 2400 by 1600 frame a 90 pixel line of text is gone at slider 24 while the blur needs 184 of its 200. It never had the border weakness the Gaussian had, measuring 0.0 percent survival at the frame edge on the day the blur was measuring 51.4 percent there. And it produced the smallest file of anything tested, by a factor of about 70 against the source photo.
The Gaussian is the better looking of the two and it is fine for style, backgrounds, and anything you are softening rather than hiding.
Which formats can I load, and what comes back?
The box says PNG, JPG, WebP and GIF, and that is what it is built around. What it actually accepts is anything your system labels as an image, which I checked one file type at a time: HEIC, AVIF, SVG, TIFF and BMP all get past the gate. Whether they then open is your browser's decision, not this page's, and an iPhone HEIC often will not. A PDF or a camera raw file is refused by name before it gets that far.
On the way out, JPG stays JPG and WebP stays WebP. Everything else comes back as PNG, which is lossless and keeps transparency.
What happens with an animated GIF?
You get the first frame, and what downloads is a still PNG. There is no way to keep the animation, so if the motion matters this is the wrong tool.
Where does it get slow?
Slower than it used to be, and I want to correct something this page said before I explain why.
The old version of this section claimed the redraw took 26.7 milliseconds on a 12 megapixel photo and did not care what strength you picked. That was a measurement of the wrong thing. Asking a browser to draw does not make it draw, it queues the work, so timing the call and not the result measures how fast you can ask. Forcing the drawing to actually finish before stopping the clock, the code that shipped took 185 to 197 milliseconds on the same photo, and it was never strength independent either.
Measured properly, today, on a 12 megapixel photo: a whole image blur is 265 ms at strength 8, 276 at 24, 292 at 100 and 304 at 200. The old renderer was 188, 191 and 197 at the first three, so the repair costs between 1.41 and 1.48 times the redraw. That is the price of the padded copy the blur now works from, and I think it is worth it for a tool that is supposed to hide things. At strength 0 the new code is actually faster, 41 ms against 54, because a whole image blur no longer needs the sharp backing layer that caused the bug.
Two other things worth knowing. A rectangle is now genuinely cheaper than the whole frame, 147 ms against 272 at strength 24, where before they cost the same. And pixelate is the fast one at 55 ms. Writing the file is the other big cost: a PNG off that 12 megapixel picture took 351 ms against 67 ms for a JPG, so if you are working with something large and do not need the untouched pixels kept exact, switch the Save as box.
Those timings are from Node on one desktop, not from a browser on your phone, so read them as the shape of the curve rather than as your numbers.
Is there a size limit?
Yes, 40 MB, and I tested the edge rather than trusting the label. Exactly 40 MB loads. One byte more is refused with a sentence naming the limit. A zero byte file gets past that check and then fails to open, which is a slightly odd two step way of being told no, but you do get told.