Warm or cool color checker by hue angle
The warm or cool color checker converts a hexadecimal color to its hue angle and compares that angle with fixed warm and cool centers.
Run — free
Red at 0 degrees is the warm center, cyan at 180 degrees is the cool center, and the nearer center determines the result. Exact boundary hues are classified as cool for a stable tie rule. The response includes the normalized color, hue, category, and angular distance, making the decision transparent and repeatable in design tools, tests, and automated color workflows.
How the warm and cool decision is made
This checker uses a geometric definition on the standard RGB hue circle. Red, at 0 degrees, is the center of the warm half; cyan, at 180 degrees, is the center of the cool half. After converting the supplied hexadecimal color to a hue, the calculator measures the shortest angular distance to the warm center. A distance below 90 degrees produces warm, while a distance of 90 degrees or more produces cool. The two dividing hues are therefore 90 and 270 degrees. Because those positions are equally distant from the two centers, the calculator assigns both exact ties to cool. That explicit tie rule prevents different applications from making different choices at a boundary. The output reports the hue and distance used in the decision, so the category is auditable rather than a hidden opinion. This classification is a practical digital-color convention; visual warmth can still shift with surrounding colors, lighting, and cultural context.
Entering a color and reading the result
Enter one hexadecimal RGB color using either the three-digit form, such as #F60, or the six-digit form, such as #FF6600. The leading hash is optional, and letter case does not matter. The response expands shorthand and returns an uppercase six-digit value in the color field. The hue_degrees field gives the calculated position from 0 up to, but not including, 360 degrees. Category is the requested warm or cool label. Distance_from_warm_center shows how far the hue lies from red along the shorter route around the circle, while the two center fields state the reference angles used by the rule. A result near a 90-degree distance is close to the divide and may look context-sensitive even though the computational answer remains stable. Black, white, and every exact gray are rejected: their red, green, and blue channels are equal, so hue is mathematically undefined and a hue-based warm/cool label would be fabricated.
Using deterministic temperature labels in a workflow
A deterministic label is useful when a palette must be filtered, tested, or routed without a person making the same judgment repeatedly. A design-system script can classify candidate accent colors and verify that a warm collection contains only warm results. A catalog pipeline can add a searchable temperature facet to chromatic product swatches. A chart generator can select a contrasting family by checking the category before it chooses supporting colors. The calculation has no network calls, random choices, stored state, or current-time dependency, so identical input always produces identical output. For automation through the API, each request costs $0.002; the browser runner uses the same pure calculation. Treat the label as one measurable property rather than a complete theory of color appearance. Saturation and lightness do not move the hue angle, but they strongly affect how confidently people perceive warmth. For nuanced art direction, review the classified color beside its intended background and neighboring palette after using this result as a consistent first pass.
What you can do with it
Organize a digital palette
Split chromatic hex swatches into stable warm and cool groups before a designer reviews the final combinations.
Test design tokens
Assert that semantic tokens intended for a warm or cool theme remain in the expected hue half after edits.
Tag product colors
Add a deterministic temperature category to chromatic catalog swatches for filtering and merchandising workflows.
FAQ
What angles count as warm?
Hues whose shortest distance from red at 0 degrees is less than 90 degrees are warm. This covers 0 through just under 90 degrees and values above 270 through just under 360 degrees.
What happens exactly on the divide?
Hue angles of exactly 90 or 270 degrees are tied between the warm and cool centers. The deterministic tie rule classifies them as cool.
Why are gray, black, and white rejected?
Their RGB channels are equal, so they have no defined hue angle. Assigning either category would contradict the hue-based rule.
Does saturation or brightness affect the category?
No. They affect appearance, but this capability intentionally classifies only by hue angle.
Which color formats are accepted?
Three-digit and six-digit hexadecimal RGB are accepted, with or without a leading hash. Alpha channels and named colors are not accepted.
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/color/warm-or-cool \
-H "Authorization: Bearer $KIT_KEY" \
-H "Content-Type: application/json" \
-d '{"color":"#E85D04"}'const res = await fetch("https://api.kit.forhosting.com/color/warm-or-cool", {
method: "POST",
headers: {
"Authorization": `Bearer ${process.env.KIT_KEY}`,
"Content-Type": "application/json"
},
body: JSON.stringify({
"color": "#E85D04"
})
});
const { task_id } = await res.json();import os, requests
res = requests.post(
"https://api.kit.forhosting.com/color/warm-or-cool",
headers={"Authorization": f"Bearer {os.environ['KIT_KEY']}"},
json={
"color": "#E85D04"
},
)
task_id = res.json()["task_id"]<?php
$res = file_get_contents("https://api.kit.forhosting.com/color/warm-or-cool", false, stream_context_create([
"http" => [
"method" => "POST",
"header" => "Authorization: Bearer " . getenv("KIT_KEY") . "\r\nContent-Type: application/json",
"content" => '{"color":"#E85D04"}',
],
]));
$task = json_decode($res, true);body := bytes.NewBufferString(`{"color":"#E85D04"}`)
req, _ := http.NewRequest("POST", "https://api.kit.forhosting.com/color/warm-or-cool", body)
req.Header.Set("Authorization", "Bearer "+os.Getenv("KIT_KEY"))
req.Header.Set("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)Example request
{
"color": "#E85D04"
}Example response
{
"task_id": "tsk_a1b2c3d4e5f6a1b2c3d4e5f6",
"type": "color.warm_or_cool",
"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.
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. |