6

I have two cv::Scalar objects and I want to calculate the color difference.

I came up with this code:

cv::Scalar a(255, 128, 255); // color 1
cv::Scalar b(100, 100, 100); // color 2

cv::Scalar d = b - a;
double distance = sqrtl(d[0]*d[0] + d[1]*d[1] + d[2]*d[2]);

This looks rather clumsy. Is there a simpler way to express this or another metric, e.g. a way to express the dot product d*d, or a way to say directly distance of two cv::Scalar, or cv::Vec4i, to which it can be casted afaik?

Daniel S.
  • 6,458
  • 4
  • 35
  • 78
  • 2
    The difference between two colours is in fact a complicated topic. Are you sure you're looking for the Euclidean distance between two (RGB) colours? If you're actually looking for the perceptual difference (the difference in colour as perceived by a human), a better solution for you would be to convert your colours to the CIE Lab colour space, which is designed s.t. the Euclidean distance between two colours is better correlated to the actual perceptual distance. – Iwillnotexist Idonotexist Oct 01 '14 at 00:46
  • @IwillnotexistIdonotexist thank you for the hint. I will consider CIE Lab if I do not get good results with RGB. Meanwhile, it's more about writing the formula. Once I've converted to Lab space, will I have to calculate an euclidean distance in the Lab space or is there another formula? – Daniel S. Oct 01 '14 at 01:06
  • I believe it is indeed the Euclidean distance. [Wikipedia](http://en.wikipedia.org/wiki/Color_difference) claims that a Euclidean distance of approximately 2.3 constitutes a JND (Just-Noticeable Difference). – Iwillnotexist Idonotexist Oct 01 '14 at 01:21
  • 2
    The documentation for OpenCV alleges the existence of a `norm()` function for `Vec`'s.... http://docs.opencv.org/modules/core/doc/basic_structures.html#vec – Iwillnotexist Idonotexist Oct 01 '14 at 01:34
  • 1
    For the benefit of other people - those looking for a ***complicated*** metric for color difference, the following Wikipedia articles will be useful: (1) [Color difference](https://en.wikipedia.org/wiki/Color_difference) (2) [MacAdam ellipse](https://en.wikipedia.org/wiki/MacAdam_ellipse). – rwong May 09 '16 at 18:49

1 Answers1

8

As suggested by @IwillnotexistIdonotexist, you can use the Vec class and according norm():

cv::Vec4d d = a-b;
double distance = cv::norm(d);
herohuyongtao
  • 49,413
  • 29
  • 133
  • 174