8eeb0b8bc7fdde8833b1d4b1ec763b96c0ec4b31
[blender.git] / source / blender / draw / engines / gpencil / shaders / gpencil_blend_frag.glsl
1 in vec4 uvcoordsvar;
2
3 out vec4 FragColor;
4
5 uniform sampler2D strokeColor;
6 uniform sampler2D strokeDepth;
7 uniform sampler2D blendColor;
8 uniform sampler2D blendDepth;
9 uniform int mode;
10 uniform int clamp_layer;
11 uniform float blend_opacity;
12
13 #define ON 1
14 #define OFF 0
15
16 #define MODE_NORMAL   0
17 #define MODE_OVERLAY  1
18 #define MODE_ADD      2
19 #define MODE_SUB      3
20 #define MODE_MULTIPLY 4
21 #define MODE_DIVIDE   5
22
23 float overlay_color(float a, float b)
24 {
25         float rtn;
26                 if (a < 0.5) {
27                         rtn = 2.0 * a * b;
28                 }
29                 else {
30                         rtn = 1.0 - 2.0 * (1.0 - a) * (1.0 - b);
31                 }
32
33         return rtn;
34 }
35
36 vec4 get_blend_color(int mode, vec4 src_color, vec4 blend_color)
37 {
38         vec4 mix_color = blend_color;
39         vec4 outcolor;
40
41     if (mix_color.a == 0) {
42                 outcolor = src_color;
43         }
44         else if (mode == MODE_OVERLAY) {
45                 mix_color.rgb = mix_color.rgb * mix_color.a * blend_opacity;
46                 outcolor.r = overlay_color(src_color.r, mix_color.r);
47                 outcolor.g = overlay_color(src_color.g, mix_color.g);
48                 outcolor.b = overlay_color(src_color.b, mix_color.b);
49                 outcolor.a = src_color.a;
50         }
51         else if (mode == MODE_ADD){
52                 mix_color.rgb = mix_color.rgb * mix_color.a * blend_opacity;
53                 outcolor = src_color + mix_color;
54                 outcolor.a = src_color.a;
55         }
56         else if (mode == MODE_SUB){
57                 outcolor = src_color - mix_color;
58                 outcolor.a = clamp(src_color.a - (mix_color.a * blend_opacity), 0.0, 1.0);
59         }
60         else if (mode == MODE_MULTIPLY) {
61                 /* interpolate between 1 and color using opacity */
62                 mix_color.rgb = mix(vec3(1,1,1), mix_color.rgb * mix_color.a, blend_opacity);
63                 outcolor = src_color * mix_color;
64                 outcolor.a = src_color.a;
65         }
66         else if (mode == MODE_DIVIDE) {
67                 mix_color.rgb = mix_color.rgb * mix_color.a * blend_opacity;
68                 outcolor = src_color / mix_color;
69                 outcolor.a = src_color.a;
70         }
71         else {
72                 outcolor = mix_color * blend_opacity;;
73                 outcolor.a = src_color.a;
74         }
75         
76         return outcolor;
77 }
78
79 void main()
80 {
81         vec4 outcolor;
82         ivec2 uv = ivec2(gl_FragCoord.xy);
83         vec4 stroke_color =  texelFetch(strokeColor, uv, 0).rgba;
84         float stroke_depth = texelFetch(strokeDepth, uv, 0).r;
85         
86         vec4 mix_color =  texelFetch(blendColor, uv, 0).rgba;
87         float mix_depth = texelFetch(blendDepth, uv, 0).r;
88
89         /* premult alpha factor to remove double blend effects */
90         if (stroke_color.a > 0) {
91                 stroke_color = vec4(vec3(stroke_color.rgb / stroke_color.a), stroke_color.a);
92         }
93         if (mix_color.a > 0) {
94                 mix_color = vec4(vec3(mix_color.rgb / mix_color.a), mix_color.a);
95         }
96         
97         /* Normal mode */
98         if (mode == MODE_NORMAL) {
99                 if (stroke_color.a > 0) {
100                         if (mix_color.a > 0) {
101                                 FragColor = vec4(mix(stroke_color.rgb, mix_color.rgb, mix_color.a), stroke_color.a);
102                                 gl_FragDepth = mix_depth;
103                         }
104                         else {
105                                 FragColor = stroke_color;
106                                 gl_FragDepth = stroke_depth;
107                         }
108                 }
109                 else {
110                         if (clamp_layer == ON) {
111                                 discard;
112                         }
113                         else {
114                                 FragColor = mix_color;
115                                 gl_FragDepth = mix_depth;
116                         }
117                 }
118                 return;
119         }
120         
121         /* if not using mask, return mix color */
122         if ((stroke_color.a == 0) && (clamp_layer == OFF)) {
123                 FragColor = mix_color;
124                 gl_FragDepth = mix_depth;
125                 return;
126         }
127
128         /* apply blend mode */
129         FragColor = get_blend_color(mode, stroke_color, mix_color);
130         gl_FragDepth = stroke_depth;
131 }