thomasp85 / farver

High Performance Colourspace Manipulation in R
https://farver.data-imaginist.com
Other
125 stars 14 forks source link

comparison between vectors / matrix give different results #18

Closed dylanbeaudette closed 4 years ago

dylanbeaudette commented 4 years ago

First off, thank you for the excellent package.

I'd like to replace [some functionality](, using functionality from the {aqp} package.) in the {aqp} package with farver::compare_colour(..., method = 'CIE2000'). Currently, the conversion from sRGB -> closest Munsell chip is done via Euclidean distance in the CIE LAB color space. This is very close to what I need, but dE00 is better.

I've noticed something odd when comparing a single color to a matrix of colors (bottom row). This does not happen when comparing pairs of colors (top row). Is this a bug or am I missing something?

image

Here is some code for testing.

library(aqp)
library(grDevices)
library(farver)

# number of closest colors to keep
nClosest <- 8

# convert Munsell notation to sRGB (D65)
this.color <- parseMunsell('10YR 3/4', return_triplets=TRUE)

# full LUT of Munsell chips
load(system.file("data/munsell.rda", package="aqp")[1])

# convert sRGB to LAB
# this appears give visually closer results than the conversion done by farver::convert_colour
this.color.lab <- convertColor(this.color, from='sRGB', to='Lab', from.ref.white='D65', to.ref.white = 'D65')
dimnames(this.color.lab)[[2]] <- c('L', 'A', 'B')

# CIE dE00 1-to-1 comparisons, quite slow
sigma <- list()
for(i in 1:nrow(munsell)){
  sigma[i] <- compare_colour(this.color.lab, munsell[i, 7:9], from_space='lab', method = 'CIE2000', white_from = 'D65')
}
sigma <- unlist(sigma)

## this is correct
# return the closest n-matches
idx <- order(sigma)[1:nClosest]
(res <- data.frame(munsell[idx, 1:3], sigma=sigma[idx]))

# CIE dE00 via vector to matrix comparison
sigma <- compare_colour(this.color.lab, munsell[, 7:9], from_space='lab', method = 'CIE2000', white_from = 'D65')
sigma <- as.vector(sigma)

## this is wrong
# return the closest n-matches
idx <- order(sigma)[1:nClosest]
(res.wrong <- data.frame(munsell[idx, 1:3], sigma=sigma[idx]))

## quick visualization
cols <- munsell2rgb(res$hue, res$value, res$chroma)
cols.lab <- sprintf("%s %s/%s\ndE00: %s", res$hue, res$value, res$chroma, round(res$sigma, 2))

cols.wrong <- munsell2rgb(res.wrong$hue, res.wrong$value, res.wrong$chroma)
cols.wrong.lab <- sprintf("%s %s/%s\ndE00: %s", res.wrong$hue, res.wrong$value, res.wrong$chroma, round(res.wrong$sigma, 2))

par(mfrow=c(2,1), mar=c(0.25, 4, 0.25, 0.25))
soilPalette(cols, lab = cols.lab)
mtext('Correct', side = 2)
soilPalette(cols.wrong, lab = cols.wrong.lab)
mtext('Wrong', side = 2)
thomasp85 commented 4 years ago

Wow... what an embarrassing bug that was 😬

dylanbeaudette commented 4 years ago

Howdy! Thanks for fixing that so quickly, off by one letter... I've done that before.

I'm stuck on a Windoze build here: any idea on when the new binaries will be available for testing?

thomasp85 commented 4 years ago

I’m planning on doing a cran release tomorrow

dylanbeaudette commented 4 years ago

Tested and works as expected. Thank you!

thomasp85 commented 4 years ago

An unfortunate setback: farver has been rolled back to last release on CRAN due to some unforeseen issues. I’ll try to get a new version on CRAN next week