roboflow/supervision · error · ValueError
Could not resolve color by class because Detections do not h
Error message
Could not resolve color by class because Detections do not have class_id. If using an annotator, try setting color_lookup to sv.ColorLookup.INDEX or sv.ColorLookup.TRACK.
What it means
Raised by `resolve_color_idx` when the color lookup strategy is the default `ColorLookup.CLASS` but `detections.class_id` is None. Mapping colors by class requires class ids; without them the palette cannot be indexed, so the annotator refuses to pick a color rather than guessing.
Source
Thrown at src/supervision/annotators/utils.py:60
) -> int:
if detection_idx >= len(detections):
raise ValueError(
f"Detection index {detection_idx} "
f"is out of bounds for detections of length {len(detections)}"
)
if isinstance(color_lookup, np.ndarray):
if len(color_lookup) != len(detections):
raise ValueError(
f"Length of color lookup {len(color_lookup)} "
f"does not match length of detections {len(detections)}"
)
return int(color_lookup[detection_idx])
elif color_lookup == ColorLookup.INDEX:
return detection_idx
elif color_lookup == ColorLookup.CLASS:
if detections.class_id is None:
raise ValueError(
"Could not resolve color by class because "
"Detections do not have class_id. If using an annotator, "
"try setting color_lookup to sv.ColorLookup.INDEX or "
"sv.ColorLookup.TRACK."
)
return int(detections.class_id[detection_idx])
elif color_lookup == ColorLookup.TRACK:
if detections.tracker_id is None:
raise ValueError(
"Could not resolve color by track because "
"Detections do not have tracker_id. Did you call "
"tracker.update_with_detections(...) before annotating?"
)
return int(detections.tracker_id[detection_idx])
raise ValueError(f"Unsupported color lookup strategy: {color_lookup}")
def resolve_text_background_xyxy(View on GitHub (pinned to 7f254d9784)
Solutions
- Pass `color_lookup=sv.ColorLookup.INDEX` to the annotator constructor so colors are assigned per detection index.
- Populate `class_id` on the Detections (even a zeros array for single-class use).
- If you track, `ColorLookup.TRACK` works once tracker ids exist — but class_id or INDEX is simpler.
Example fix
# before annotator = sv.BoxAnnotator() # default ColorLookup.CLASS annotator.annotate(scene, sv.Detections(xyxy=boxes)) # no class_id -> ValueError # after annotator = sv.BoxAnnotator(color_lookup=sv.ColorLookup.INDEX) annotator.annotate(scene, sv.Detections(xyxy=boxes))
Defensive patterns
Strategy: type-guard
Validate before calling
lookup = (
sv.ColorLookup.CLASS if detections.class_id is not None
else sv.ColorLookup.INDEX
)
annotator = sv.BoxAnnotator(color_lookup=lookup) Type guard
def color_lookup_for(detections) -> sv.ColorLookup:
if detections.tracker_id is not None:
return sv.ColorLookup.TRACK
if detections.class_id is not None:
return sv.ColorLookup.CLASS
return sv.ColorLookup.INDEX Prevention
- Default to ColorLookup.INDEX when building Detections without class_id.
- Check detections.class_id is not None before using default annotator settings.
When it happens
Trigger: Constructing `Detections(xyxy=..., confidence=...)` with no `class_id` and annotating with any default-configured annotator (BoxAnnotator, LabelAnnotator, etc. all default to `ColorLookup.CLASS`); using a connector or model output that omits class labels (e.g. class-agnostic detection); zero-row detections do not trigger this — only None class_id does.
Common situations: Quick prototypes with hand-built Detections fixtures that skip class_id; class-agnostic models (single-class heads that return boxes only); switching from a classifier-equipped model to a raw head while keeping the same annotation code.
Related errors
- Unsupported color lookup strategy: {color_lookup}
- max_line_length must be a positive integer
- Invalid hex color format: {hex_color}
- RGBA must be a 4-tuple with values between 0-255.
- Length of color lookup {len(color_lookup)} does not match le
AI-assisted analysis of roboflow/supervision@7f254d9784 (2026-08-15).
Data as JSON: /api/errors/bf8ccd7bc665dab2.
Report an issue: GitHub.