colour
colour copied to clipboard
[FEATURE]: Add colourspace XYB from JPEG-XL
Description
Hi!
Please add support for colour space XYB. There is two variants of XYB, one defined in Google/Butteraugli and the other in JPEG-XL (and PIK)
Here is numpy code to convert to and fro from XYZ and Jpeg-XL's XYB. I'll create a pull request after 20th March if no one has done so by then :)
def xyz_to_xyb(xyz):
mat_xyz_to_lms = np.matrix([
[ 0.3739, 0.6896, -0.0413],
[ 0.0792, 0.9286, -0.0035],
[ 0.6212, -0.1027, 0.4704]
])
mat_lms_to_xyb = np.matrix([
[ 0.5, -0.5, 0.0],
[ 0.5, 0.5, 0.0],
[ 0.0, 0.0, 1.0],
])
xyb_bias = 0.00379307
xyb_bias_cbrt = pow(xyb_bias, 1/3)
lmslin = np.inner(mat_xyz_to_lms, xyz).T
lms = np.cbrt(lmslin + xyb_bias) - xyb_bias_cbrt
return np.inner(mat_lms_to_xyb, lms).T
def xyb_to_xyz(xyb):
mat_lms_to_xyz = np.matrix([
[ 2.7253, -1.9993, 0.2245],
[-0.2462, 1.2585, -0.0122],
[-3.6527, 2.9148, 1.8268]
])
mat_xyb_to_lms = np.matrix([
[ 1.0, 1.0, 0.0],
[ -1.0, 1.0, 0.0],
[ 0.0, 0.0, 1.0],
])
xyb_bias = 0.00379307
xyb_bias_cbrt = pow(xyb_bias, 1/3)
lms = np.inner(mat_xyb_to_lms, xyb).T
lmslin = np.power(lms + xyb_bias_cbrt, 3) - xyb_bias
return np.inner(mat_lms_to_xyz, lmslin).T
xyz= np.array([
[1, 2, 3],
[10, 20, 30]
])
xyb = xyz_to_xyb(xyz)
Credits to Raph Levien for the original code in JS which I ported to Python/Numpy.
Hi @zeroby0,
Thank you, great idea! This seems to follow the typical IPT-like colour model structure, which we generalise:
- https://github.com/colour-science/colour/blob/develop/colour/models/ipt.py
- https://github.com/colour-science/colour/blob/develop/colour/models/common.py#L287
Cheers,
Thomas
Awesome!
Once I figure out how to do that, I'll add the procedure here and close the issue. Thank you for the links!
This seems to be kind of obscure and not documented well, but this tweet seems to indicate the default format of the color space subtracts Y from B to make X = B = 0 for achromatic colors: https://twitter.com/jonsneyers/status/1605321352143331328
You can achieve this by just adjusting the matrix:
[
[0.5, -0.5, 0.0],
[0.5, 0.5, 0.0],
[0.0, -1.0, 1.0],
]
This gives the color space a more practical Lab-like orientation where Y operates as your lightness and X and B change the hue and contrast.

I guess there are a lot of people implementing it without this adjustment. Anyways, hope this helps.