Replace a specific color in an image
Turn red into green across a list of image pixels. With a tolerance of 32, the pure red and the two near-reds change, so 3 of 5 pixels are replaced. Each channel is compared on its own, which catches edge shading too. Free in your browser.
- Free
- Runs in your browser
- No sign-up
- Your data stays on your device
Run — free
Worked example
- Pixels
- #FF0000, #FF2020, #00FF00, #0000FF, #FE0101
- Target
- #FF0000
- Tolerance
- 32
- Replacement
- #00FF00
- Pixels
- #00FF00, #00FF00, #00FF00, #0000FF, #00FF00
- Replaced count
- 3
- Total count
- 5
A pixel counts as a match when its red, green and blue channels each differ from the target by no more than the tolerance you set: zero replaces only exact matches, while a larger value catches shading and anti-aliasing around the edges. It is the deterministic, offline version of a magic-wand recolor — no image decoding, no AI, just a clean channel-distance rule you can reproduce anywhere.
What replacing a color with tolerance actually means
Real images almost never contain a single flat color. A red logo is surrounded by a halo of pinkish anti-aliasing pixels, and a photograph of a red car holds dozens of reds under changing light. If you only swapped the exact hex value, the result would look patchy and amateur.
A tolerance of 0 is strict equality — useful for icons, sprites and flat UI graphics. Values around 16 to 48 are the usual working range for gradients and photos.
Choosing the target, tolerance and replacement
Start by sampling the color you want gone. The target accepts a standard #RRGGBB hex value; if you are unsure of the exact value, a dominant-color or palette tool will tell you what the image is actually made of. Then pick the tolerance by working from zero upward: run with 0, inspect how many pixels were replaced, and raise it until the halo around your subject is covered without bleeding into neighboring elements.
The replacement is also a hex color, written verbatim into every matching pixel — there is no blending, so the swap is crisp. One guard worth knowing: tolerance must be zero or a positive integer up to 255.
Where it fits in a real workflow
The input and output are lists of pixel colors, not encoded image files, which makes this capability a building block rather than a full photo editor. Typical callers extract the pixels of a small asset — a favicon, a chart series, a game sprite, a QR-style marker — recolor them here, and reassemble the image on their side. Marketing teams use it to generate product-color variants of a single master render.
Chart pipelines use it to re-theme a series color without re-rendering. Accessibility tooling uses it to map problem colors onto compliant ones.
What you can do with it
Recolor product variants
Swap the hero color of a product render to generate every colorway from one master asset, with tolerance catching the shading around the edges.
Re-theme a chart or sprite
Map an old palette color onto the new brand color across every pixel of a small graphic without opening an editor.
Fix a color for accessibility
Replace a non-compliant brand color with its compliant equivalent in icons and UI graphics before shipping.
FAQ
How is a match decided?
A pixel matches when the largest per-channel difference (red, green or blue) against the target color is less than or equal to the tolerance. Tolerance 0 replaces exact matches only.
What happens if the tolerance is negative?
Negative tolerance has no meaning and usually indicates a bug in the calling code.
Does it take an image file?
No. It operates on the pixel colors of the image, given as a list of #RRGGBB hex colors, and returns the recolored list. You decode and reassemble the image on your side.
What tolerance should I use?
Use 0 for icons, sprites and flat graphics, and around 16 to 48 for gradients and photos. Start at zero, check how many pixels changed, and raise it until the halo is covered without spilling onto nearby colors.
Does the new color blend with the old one?
No. The replacement color is written as is into every matching pixel, with no blending, so the swap stays crisp. Shading is handled by the tolerance, which decides which pixels count as a match.
Related tools
For developers — API access
Everything on this page is available programmatically. This section is for teams who want to wire it into their own systems; everyone else can just use the tool above.
API endpoint
Prefer to automate it? One authenticated POST creates the task; the result comes back by webhook or a signed link. The same capability also runs here on the web, by email and from Telegram — and soon from our app too.
Call it from your stack
curl -X POST https://api.kit.forhosting.com/image/color-replace \
-H "Authorization: Bearer $KIT_KEY" \
-H "Content-Type: application/json" \
-d '{"pixels":["#FF0000","#FF2020","#00FF00","#0000FF"],"target":"#FF0000","replacement":"#00FF00"}'const res = await fetch("https://api.kit.forhosting.com/image/color-replace", {
method: "POST",
headers: {
"Authorization": `Bearer ${process.env.KIT_KEY}`,
"Content-Type": "application/json"
},
body: JSON.stringify({
"pixels": [
"#FF0000",
"#FF2020",
"#00FF00",
"#0000FF"
],
"target": "#FF0000",
"replacement": "#00FF00"
})
});
const { task_id } = await res.json();import os, requests
res = requests.post(
"https://api.kit.forhosting.com/image/color-replace",
headers={"Authorization": f"Bearer {os.environ['KIT_KEY']}"},
json={
"pixels": [
"#FF0000",
"#FF2020",
"#00FF00",
"#0000FF"
],
"target": "#FF0000",
"replacement": "#00FF00"
},
)
task_id = res.json()["task_id"]<?php
$res = file_get_contents("https://api.kit.forhosting.com/image/color-replace", false, stream_context_create([
"http" => [
"method" => "POST",
"header" => "Authorization: Bearer " . getenv("KIT_KEY") . "\r\nContent-Type: application/json",
"content" => '{"pixels":["#FF0000","#FF2020","#00FF00","#0000FF"],"target":"#FF0000","replacement":"#00FF00"}',
],
]));
$task = json_decode($res, true);body := bytes.NewBufferString(`{"pixels":["#FF0000","#FF2020","#00FF00","#0000FF"],"target":"#FF0000","replacement":"#00FF00"}`)
req, _ := http.NewRequest("POST", "https://api.kit.forhosting.com/image/color-replace", body)
req.Header.Set("Authorization", "Bearer "+os.Getenv("KIT_KEY"))
req.Header.Set("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)Example request
{
"pixels": [
"#FF0000",
"#FF2020",
"#00FF00",
"#0000FF"
],
"target": "#FF0000",
"replacement": "#00FF00"
}Example response
{
"task_id": "tsk_a1b2c3d4e5f6a1b2c3d4e5f6",
"type": "image.color_replace",
"status": "queued",
"_links": {
"result": "/tasks/tsk_…/result"
}
}The API is asynchronous: the call returns a task_id immediately and the result arrives by webhook. Polling is capped at 1 req/s per task.
Pricing
Published price — no tokens, no invented credits. A failed task is never charged.
Limits
max_pixels | 262144 |
Errors
| HTTP | Code | Meaning |
|---|---|---|
401 | unauthorized | Missing or invalid API key. |
402 | insufficient_balance | Your balance doesn't cover the task price. |
404 | unknown_type | That task type doesn't exist. |
429 | rate_limited | Too many requests. Use the webhook instead of polling. |
Technical notes
The color replacement API takes the pixel colors of an image, a target color, a tolerance and a replacement color, and returns the pixel list with every matching pixel swapped.
What replacing a color with tolerance actually means
Tolerance fixes that by defining a neighborhood around the target: this tool measures, for every pixel, the largest absolute difference across the red, green and blue channels, and replaces the pixel whenever that distance is less than or equal to your tolerance. Because the rule is a plain numeric comparison, the same input always produces the same output: you can test in the browser, then automate the exact same call through the API and get identical results, which is what you want when the recolor feeds a build pipeline or an A/B variant generator.
Choosing the target, tolerance and replacement
A negative tolerance is rejected with an invalid_input error rather than silently clamped, because a negative radius has no meaning and usually signals a bug in the calling code that you would rather see immediately than debug through a subtly wrong image later.
Where it fits in a real workflow
The whole operation is cheap enough to run free in your browser on this page, and costs $0.002 per request through the API when you automate it. No file is uploaded or stored, the math is fully deterministic, and the limit of 262144 pixels per call covers sprites and icons with room to spare.
Technical questions
What does it cost?
$0.002 per request via the API. It is also free to run in your browser on this page.
Is the result deterministic?
Yes. The rule is a plain channel-distance comparison with no randomness, so the same input always produces the same output in the browser and through the API.
Is there a size limit?
Up to 262144 pixels per call, which comfortably covers icons, sprites and small assets.