Quelques usages non conventionnels de ce puissant outil que sont les courbes pour le traitement d'image (et pour faire suite à cet article). L'interface de courbe est un portage canvas / JS de ce projet, merci à l'auteur !
Le classique de Photoshop consistant à appliquer cette fonction de transfert sur les 3 couches RVB simultanément mène à des "problèmes" comme la modification de la saturation : les zones assombries deviennent trop saturées, les zones éclaircies trop pâles. (Je ne parle pas ici de leur application couche par couche.)
On peut contourner ce problème (et en créer d'autres ?) par l'application cette fonction sur la luminosité uniquement. Ceci est certes possible à réaliser dans Photoshop. Les résultats sont à mon avis nettement plus naturels et agréables que l'action sur les couches RVB (dans la limites de modifications légères, cela va de soi). Ceci suppose une conversion RVB vers HSL et réciproquement via des fonctions rapportées ci-après. Travailler sur cette couche de luminosité permet en outre des traitement assez peu intuitifs comme par exemple réaliser une inversion (négatif) des valeurs sans inversion des teintes.
Pourquoi s'arrêter en si bon chemin et ne pas poursuivre cette approche en travaillant sur la couche de saturation ou de teinte ? Voici de quoi expérimenter ces traitements quelques peu extravagants :-).
Si l'action sur la couche de teinte rappelle beaucoup ce que l'on peut obtenir avec l'outil teinte/saturation, l'action sur la couche de saturation seule est elle assez inédite. Par exemple, augmenter le contraste de cette couche va entraîner une baisse de saturation sur les zones peu saturées et renforcer la saturation sur les tons déjà saturés, et vice-versa. Étonnant non ?
// Converts an HSL color value to RGB. Conversion formula
// adapted from http://en.wikipedia.org/wiki/HSL_color_space.
// Assumes h, s, and l are contained in the set [0, 1] and
// returns r, g, and b in the set [0, 255].
function hslToRgb(h, s, l) {
var r, g, b;
if(s == 0) {
r = g = b = l; // achromatic
} else {
var hue2rgb = function hue2rgb(p, q, t) {
if(t < 0) t += 1;
if(t > 1) t -= 1;
if(t < 1/6) return p + (q - p) * 6 * t;
if(t < 1/2) return q;
if(t < 2/3) return p + (q - p) * (2/3 - t) * 6;
return p;
}
var q = l < 0.5 ? l * (1 + s) : l + s - l * s;
var p = 2 * l - q;
r = hue2rgb(p, q, h + 1/3);
g = hue2rgb(p, q, h);
b = hue2rgb(p, q, h - 1/3);
}
return [Math.round(r * 255), Math.round(g * 255), Math.round(b * 255)];
}
// Converts an RGB color value to HSL. Conversion formula
// adapted from http://en.wikipedia.org/wiki/HSL_color_space.
// Assumes r, g, and b are contained in the set [0, 255] and
// returns h, s, and l in the set [0, 1].
function rgbToHsl(r, g, b) {
r /= 255, g /= 255, b /= 255;
var max = Math.max(r, g, b), min = Math.min(r, g, b);
var h, s, l = (max + min) / 2;
if(max == min) {
h = s = 0; // achromatic
} else {
var d = max - min;
s = l > 0.5 ? d / (2 - max - min) : d / (max + min);
switch(max){
case r: h = (g - b) / d + (g < b ? 6 : 0); break;
case g: h = (b - r) / d + 2; break;
case b: h = (r - g) / d + 4; break;
}
h /= 6;
}
return [h, s, l];
}