Product shadow
Give a cutout product a soft shadow that follows its own contours, not a generic blurred oval, so it looks like it rests on a surface under real light. Make a whole catalog look shot in one studio session. You pay per use, with no subscription.
This task is not available right now, so it cannot be purchased. Nothing is charged for it.
How it works & APIA clean cutout floating on white looks unfinished the moment it sits next to a photograph with real light in it — nothing grounds it to a surface.
The tell that gives away a cutout
Remove a background and what's left is technically correct but visually dishonest: an object with no contact point, no weight, floating in a void. Human vision reads shadows before it reads almost anything else in a scene to judge depth and grounding, so a shadowless product photo registers as fake even to viewers who couldn't say why. Adding one back is less a decorative flourish than a repair to that missing depth cue.
Why shadows in photography aren't arbitrary
Studio photographers spend real budget on light tables, reflectors and diffusion precisely to get a shadow that reads as natural rather than harsh or fake — a shadow that's too dark, too sharp-edged or pointed the wrong way is as suspicious to a shopper's eye as no shadow at all. This task aims for that same soft, plausible falloff, the kind that suggests an object actually rests on a surface under real light rather than sitting on a layer in an editor.
What you can do with it
Marketplace listing photos
A seller uploads cutout product shots and casts a consistent shadow on all of them so the catalog looks shot in one studio session instead of assembled from mismatched sources.
Ad creative production
A performance marketing team drops a shadowed product onto seasonal backgrounds for dozens of ad variants without re-shooting anything.
Print and packaging mockups
A design team building packaging mockups adds a grounded shadow so a rendered product sits convincingly on a mockup surface.
FAQ
Is the shadow generic or shaped to the object?
The shadow follows the object's actual contours rather than dropping a generic blurred oval underneath, which is what keeps it looking physically plausible.
What happens if shadow generation fails?
The task retries automatically up to three times before returning a clear error, and a failed request is never charged.
Why does a product photo need a shadow at all?
A cutout on white has no contact point and seems to float. People judge depth and grounding from shadows before almost anything else, so a shadowless product looks fake even to viewers who could not say why.
Should I remove the background before adding the shadow?
Yes, ideally send a cutout with a transparent or already removed background. Most teams strip the background first, then cast the shadow, then place the result on whatever backdrop the listing needs.
What makes a shadow look natural rather than fake?
A soft, plausible falloff. A shadow that is too dark, too sharp-edged or pointing the wrong way looks as suspicious to a shopper as no shadow at all, which is why the shadow follows the shape of the object.
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
One authenticated POST creates the task; the result comes back by webhook or a signed link. This capability is currently available through the API, not as an interactive Web tool.
Call it from your stack
curl -X POST https://api.kit.forhosting.com/image/shadow \
-H "Authorization: Bearer $KIT_KEY" \
-H "Content-Type: application/json" \
-d '{"image":"https://example.com/photo.jpg"}'const res = await fetch("https://api.kit.forhosting.com/image/shadow", {
method: "POST",
headers: {
"Authorization": `Bearer ${process.env.KIT_KEY}`,
"Content-Type": "application/json"
},
body: JSON.stringify({
"image": "https://example.com/photo.jpg"
})
});
const { task_id } = await res.json();import os, requests
res = requests.post(
"https://api.kit.forhosting.com/image/shadow",
headers={"Authorization": f"Bearer {os.environ['KIT_KEY']}"},
json={
"image": "https://example.com/photo.jpg"
},
)
task_id = res.json()["task_id"]<?php
$res = file_get_contents("https://api.kit.forhosting.com/image/shadow", false, stream_context_create([
"http" => [
"method" => "POST",
"header" => "Authorization: Bearer " . getenv("KIT_KEY") . "\r\nContent-Type: application/json",
"content" => '{"image":"https://example.com/photo.jpg"}',
],
]));
$task = json_decode($res, true);body := bytes.NewBufferString(`{"image":"https://example.com/photo.jpg"}`)
req, _ := http.NewRequest("POST", "https://api.kit.forhosting.com/image/shadow", body)
req.Header.Set("Authorization", "Bearer "+os.Getenv("KIT_KEY"))
req.Header.Set("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)Example request
{
"image": "https://example.com/photo.jpg"
}Example response
{
"task_id": "tsk_a1b2c3d4e5f6a1b2c3d4e5f6",
"type": "image.shadow",
"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_mb | 15 |
max_megapixels | 12 |
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
This endpoint studies the shape of a cutout and casts a soft, directionally consistent shadow beneath it, the kind a photographer would have captured on a light table instead of a flat product shot.
What the endpoint actually does
The result comes back as an image with the shadow composited in, ready to drop straight onto a white background, a lifestyle scene, or a marketplace listing template. POST a cutout image to /image/shadow — ideally one with a transparent or already-removed background — and the task analyzes the silhouette to build a shadow shape that follows the object's contours rather than a generic blurred oval underneath it.
Fitting into a catalog pipeline
Most teams reach this endpoint right after a background removal step: strip the background, then cast the shadow, then composite onto whatever backdrop the listing needs. Because it's asynchronous, a batch of a few images and a batch of ten thousand SKUs both submit the same way — send each image, collect a task_id, and let results land by webhook as they finish, or pull them from a signed link if a script prefers to poll.
Pricing and what happens on failure
If a shadow can't be generated the task retries automatically up to three times before returning a clear error, and a request that never succeeds is never billed — so a large batch only costs what actually completed. The cost is a small flat fee per request plus a per-image rate, published and predictable whether you're finishing one hero shot or an entire catalog refresh.
Integration use cases
E-commerce catalog refresh
A retailer migrating to a new template pipes existing cutouts through the endpoint to add depth before placing them on the new page backgrounds.
Technical questions
How do I add a shadow to a product photo with this API?
POST a cutout image, ideally with a transparent background, to /image/shadow and the task returns the same image composited with a natural drop shadow beneath the object.
Does the input need a transparent background first?
A background-removed cutout gives the cleanest result since the endpoint works from the object's silhouette; pair it with a background removal endpoint if your source images still have a background.
Is the shadow API free to use?
There's no free tier — free tiers get abused and slow everyone down. Access runs on a prepaid ForHosting KIT balance: top up from $10.00 (it never expires) and each request is charged at its published price, so a call with no balance returns HTTP 402. No subscription, no tokens, no invented credits, and a failed task is never charged.
How do I get the result back?
The task returns a task_id immediately and processes asynchronously; collect the shadowed image via signed webhook, or from a signed link valid for 24 hours.
Can I process a whole catalog in bulk?
Yes, each image is submitted as its own request and the endpoint is fully asynchronous, so a script can queue thousands of cutouts and collect results as each one finishes.
Is this endpoint available now?
It's in final deployment and will be accepting jobs soon; the endpoint and pricing on this page are the ones that will go live.