mx_hsv.js 1.7 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556
  1. import { glslFn } from '../../code/FunctionNode.js';
  2. // Original shader code from:
  3. // https://github.com/AcademySoftwareFoundation/MaterialX/blob/main/libraries/stdlib/genglsl/lib/mx_hsv.glsl
  4. export const mx_hsvtorgb = glslFn( `vec3 mx_hsvtorgb(vec3 hsv)
  5. {
  6. // Reference for this technique: Foley & van Dam
  7. float h = hsv.x; float s = hsv.y; float v = hsv.z;
  8. if (s < 0.0001f) {
  9. return vec3 (v, v, v);
  10. } else {
  11. h = 6.0f * (h - floor(h)); // expand to [0..6)
  12. int hi = int(trunc(h));
  13. float f = h - float(hi);
  14. float p = v * (1.0f-s);
  15. float q = v * (1.0f-s*f);
  16. float t = v * (1.0f-s*(1.0f-f));
  17. if (hi == 0)
  18. return vec3 (v, t, p);
  19. else if (hi == 1)
  20. return vec3 (q, v, p);
  21. else if (hi == 2)
  22. return vec3 (p, v, t);
  23. else if (hi == 3)
  24. return vec3 (p, q, v);
  25. else if (hi == 4)
  26. return vec3 (t, p, v);
  27. return vec3 (v, p, q);
  28. }
  29. }` );
  30. export const mx_rgbtohsv = glslFn( `vec3 mx_rgbtohsv(vec3 c)
  31. {
  32. // See Foley & van Dam
  33. float r = c.x; float g = c.y; float b = c.z;
  34. float mincomp = min (r, min(g, b));
  35. float maxcomp = max (r, max(g, b));
  36. float delta = maxcomp - mincomp; // chroma
  37. float h, s, v;
  38. v = maxcomp;
  39. if (maxcomp > 0.0f)
  40. s = delta / maxcomp;
  41. else s = 0.0f;
  42. if (s <= 0.0f)
  43. h = 0.0f;
  44. else {
  45. if (r >= maxcomp) h = (g-b) / delta;
  46. else if (g >= maxcomp) h = 2.0f + (b-r) / delta;
  47. else h = 4.0f + (r-g) / delta;
  48. h *= (1.0f/6.0f);
  49. if (h < 0.0f)
  50. h += 1.0f;
  51. }
  52. return vec3(h, s, v);
  53. }` );