| 1 | // Aseprite | 
|---|
| 2 | // Copyright (C) 2022  Igara Studio S.A. | 
|---|
| 3 | // | 
|---|
| 4 | // This program is distributed under the terms of | 
|---|
| 5 | // the End-User License Agreement for Aseprite. | 
|---|
| 6 |  | 
|---|
| 7 | #ifndef APP_UTIL_SHADER_HELPERS_H_INCLUDED | 
|---|
| 8 | #define APP_UTIL_SHADER_HELPERS_H_INCLUDED | 
|---|
| 9 | #pragma once | 
|---|
| 10 |  | 
|---|
| 11 | #if SK_ENABLE_SKSL | 
|---|
| 12 |  | 
|---|
| 13 | #include "app/color.h" | 
|---|
| 14 | #include "gfx/color.h" | 
|---|
| 15 |  | 
|---|
| 16 | #include "include/core/SkM44.h" | 
|---|
| 17 |  | 
|---|
| 18 | // To include kRGB_to_HSL_sksl and kHSL_to_RGB_sksl | 
|---|
| 19 | #include "src/core/SkRuntimeEffectPriv.h" | 
|---|
| 20 |  | 
|---|
| 21 | namespace app { | 
|---|
| 22 |  | 
|---|
| 23 | // rgb_to_hsl() and hsv_to_hsl() functions by Sam Hocevar licensed | 
|---|
| 24 | // under WTFPL (https://en.wikipedia.org/wiki/WTFPL) | 
|---|
| 25 | // Source: | 
|---|
| 26 | //   http://lolengine.net/blog/2013/07/27/rgb-to-hsv-in-glsl | 
|---|
| 27 | //   https://stackoverflow.com/a/17897228/408239 | 
|---|
| 28 |  | 
|---|
| 29 | inline constexpr char kRGB_to_HSV_sksl[] = R"( | 
|---|
| 30 | half3 rgb_to_hsv(half3 c) { | 
|---|
| 31 |  half4 K = half4(0.0, -1.0 / 3.0, 2.0 / 3.0, -1.0); | 
|---|
| 32 |  half4 p = mix(half4(c.bg, K.wz), half4(c.gb, K.xy), step(c.b, c.g)); | 
|---|
| 33 |  half4 q = mix(half4(p.xyw, c.r), half4(c.r, p.yzx), step(p.x, c.r)); | 
|---|
| 34 |  | 
|---|
| 35 |  float d = q.x - min(q.w, q.y); | 
|---|
| 36 |  float e = 1.0e-10; | 
|---|
| 37 |  return half3(abs(q.z + (q.w - q.y) / (6.0 * d + e)), d / (q.x + e), q.x); | 
|---|
| 38 | } | 
|---|
| 39 | )"; | 
|---|
| 40 |  | 
|---|
| 41 | inline constexpr char kHSV_to_RGB_sksl[] = R"( | 
|---|
| 42 | half3 hsv_to_rgb(half3 c) { | 
|---|
| 43 |  half4 K = half4(1.0, 2.0 / 3.0, 1.0 / 3.0, 3.0); | 
|---|
| 44 |  half3 p = abs(fract(c.xxx + K.xyz) * 6.0 - K.www); | 
|---|
| 45 |  return c.z * mix(K.xxx, clamp(p - K.xxx, 0.0, 1.0), c.y); | 
|---|
| 46 | } | 
|---|
| 47 | )"; | 
|---|
| 48 |  | 
|---|
| 49 | inline SkV4 gfxColor_to_SkV4(gfx::Color color) { | 
|---|
| 50 | return SkV4{float(gfx::getr(color) / 255.0), | 
|---|
| 51 | float(gfx::getg(color) / 255.0), | 
|---|
| 52 | float(gfx::getb(color) / 255.0), | 
|---|
| 53 | float(gfx::geta(color) / 255.0)}; | 
|---|
| 54 | } | 
|---|
| 55 |  | 
|---|
| 56 | inline SkV4 appColor_to_SkV4(const app::Color& color) { | 
|---|
| 57 | return SkV4{float(color.getRed() / 255.0), | 
|---|
| 58 | float(color.getGreen() / 255.0), | 
|---|
| 59 | float(color.getBlue() / 255.0), | 
|---|
| 60 | float(color.getAlpha() / 255.0)}; | 
|---|
| 61 | } | 
|---|
| 62 |  | 
|---|
| 63 | inline SkV4 appColorHsv_to_SkV4(const app::Color& color) { | 
|---|
| 64 | return SkV4{float(color.getHsvHue() / 360.0), | 
|---|
| 65 | float(color.getHsvSaturation()), | 
|---|
| 66 | float(color.getHsvValue()), | 
|---|
| 67 | float(color.getAlpha() / 255.0)}; | 
|---|
| 68 | } | 
|---|
| 69 |  | 
|---|
| 70 | inline SkV4 appColorHsl_to_SkV4(const app::Color& color) { | 
|---|
| 71 | return SkV4{float(color.getHslHue() / 360.0), | 
|---|
| 72 | float(color.getHslSaturation()), | 
|---|
| 73 | float(color.getHslLightness()), | 
|---|
| 74 | float(color.getAlpha() / 255.0)}; | 
|---|
| 75 | } | 
|---|
| 76 |  | 
|---|
| 77 | } // namespace app | 
|---|
| 78 |  | 
|---|
| 79 | #endif | 
|---|
| 80 |  | 
|---|
| 81 | #endif | 
|---|
| 82 |  | 
|---|