// // Copyright (C) Pixar. All rights reserved. // // This license governs use of the accompanying software. If you // use the software, you accept this license. If you do not accept // the license, do not use the software. // // 1. Definitions // The terms "reproduce," "reproduction," "derivative works," and // "distribution" have the same meaning here as under U.S. // copyright law. A "contribution" is the original software, or // any additions or changes to the software. // A "contributor" is any person or entity that distributes its // contribution under this license. // "Licensed patents" are a contributor's patent claims that read // directly on its contribution. // // 2. Grant of Rights // (A) Copyright Grant- Subject to the terms of this license, // including the license conditions and limitations in section 3, // each contributor grants you a non-exclusive, worldwide, // royalty-free copyright license to reproduce its contribution, // prepare derivative works of its contribution, and distribute // its contribution or any derivative works that you create. // (B) Patent Grant- Subject to the terms of this license, // including the license conditions and limitations in section 3, // each contributor grants you a non-exclusive, worldwide, // royalty-free license under its licensed patents to make, have // made, use, sell, offer for sale, import, and/or otherwise // dispose of its contribution in the software or derivative works // of the contribution in the software. // // 3. Conditions and Limitations // (A) No Trademark License- This license does not grant you // rights to use any contributor's name, logo, or trademarks. // (B) If you bring a patent claim against any contributor over // patents that you claim are infringed by the software, your // patent license from such contributor to the software ends // automatically. // (C) If you distribute any portion of the software, you must // retain all copyright, patent, trademark, and attribution // notices that are present in the software. // (D) If you distribute any portion of the software in source // code form, you may do so only under this license by including a // complete copy of this license with your distribution. If you // distribute any portion of the software in compiled or object // code form, you may only do so under a license that complies // with this license. // (E) The software is licensed "as-is." You bear the risk of // using it. The contributors give no express warranties, // guarantees or conditions. You may have additional consumer // rights under your local laws which this license cannot change. // To the extent permitted under your local laws, the contributors // exclude the implied warranties of merchantability, fitness for // a particular purpose and non-infringement. // #if defined(VARYING_COLOR) || defined(FACEVARYING_COLOR) #undef OSD_USER_VARYING_DECLARE #define OSD_USER_VARYING_DECLARE \ vec3 color; #undef OSD_USER_VARYING_ATTRIBUTE_DECLARE #define OSD_USER_VARYING_ATTRIBUTE_DECLARE \ layout(location = 1) in vec3 color; #undef OSD_USER_VARYING_PER_VERTEX #define OSD_USER_VARYING_PER_VERTEX() \ outpt.color = color #undef OSD_USER_VARYING_PER_CONTROL_POINT #define OSD_USER_VARYING_PER_CONTROL_POINT(ID_OUT, ID_IN) \ outpt[ID_OUT].color = inpt[ID_IN].color #undef OSD_USER_VARYING_PER_EVAL_POINT #define OSD_USER_VARYING_PER_EVAL_POINT(UV, a, b, c, d) \ outpt.color = \ mix(mix(inpt[a].color, inpt[b].color, UV.x), \ mix(inpt[c].color, inpt[d].color, UV.x), UV.y) #else #define OSD_USER_VARYING_DECLARE #define OSD_USER_VARYING_ATTRIBUTE_DECLARE #define OSD_USER_VARYING_PER_VERTEX() #define OSD_USER_VARYING_PER_CONTROL_POINT(ID_OUT, ID_IN) #define OSD_USER_VARYING_PER_EVAL_POINT(UV, a, b, c, d) #endif //-------------------------------------------------------------- // Vertex Shader //-------------------------------------------------------------- #ifdef VERTEX_SHADER layout (location=0) in vec4 position; OSD_USER_VARYING_ATTRIBUTE_DECLARE out block { OutputVertex v; OSD_USER_VARYING_DECLARE } outpt; void main() { outpt.v.position = ModelViewMatrix * position; OSD_USER_VARYING_PER_VERTEX(); } #endif //-------------------------------------------------------------- // Geometry Shader //-------------------------------------------------------------- #ifdef GEOMETRY_SHADER #ifdef PRIM_QUAD layout(lines_adjacency) in; #define EDGE_VERTS 4 #endif // PRIM_QUAD #ifdef PRIM_TRI layout(triangles) in; #define EDGE_VERTS 3 #endif // PRIM_TRI uniform samplerBuffer g_uvFVarBuffer; layout(triangle_strip, max_vertices = EDGE_VERTS) out; in block { OutputVertex v; OSD_USER_VARYING_DECLARE } inpt[EDGE_VERTS]; out block { OutputVertex v; noperspective out vec4 edgeDistance; OSD_USER_VARYING_DECLARE } outpt; void emit(int index, vec3 normal, vec2 uvs[4]) { outpt.v.position = inpt[index].v.position; #ifdef SMOOTH_NORMALS outpt.v.normal = inpt[index].v.normal; #else outpt.v.normal = normal; #endif #ifdef VARYING_COLOR outpt.color = inpt[index].color; #endif #ifdef FACEVARYING_COLOR #ifdef UNIFORM_SUBDIVISION vec2 quadst[4] = vec2[](vec2(0,0), vec2(1,0), vec2(1,1), vec2(0,1)); vec2 st = quadst[index]; #else vec2 st = inpt[index].v.tessCoord; #endif outpt.color = vec3(mix(mix(uvs[0], uvs[1], st.s), mix(uvs[3], uvs[2], st.s), st.t), 0); #endif gl_Position = ProjectionMatrix * inpt[index].v.position; EmitVertex(); } #if defined(GEOMETRY_OUT_WIRE) || defined(GEOMETRY_OUT_LINE) const float VIEWPORT_SCALE = 1024.0; // XXXdyu float edgeDistance(vec4 p, vec4 p0, vec4 p1) { return VIEWPORT_SCALE * abs((p.x - p0.x) * (p1.y - p0.y) - (p.y - p0.y) * (p1.x - p0.x)) / length(p1.xy - p0.xy); } void emit(int index, vec3 normal, vec2 uvs[4], vec4 edgeVerts[EDGE_VERTS]) { outpt.edgeDistance[0] = edgeDistance(edgeVerts[index], edgeVerts[0], edgeVerts[1]); outpt.edgeDistance[1] = edgeDistance(edgeVerts[index], edgeVerts[1], edgeVerts[2]); #ifdef PRIM_TRI outpt.edgeDistance[2] = edgeDistance(edgeVerts[index], edgeVerts[2], edgeVerts[0]); #endif #ifdef PRIM_QUAD outpt.edgeDistance[2] = edgeDistance(edgeVerts[index], edgeVerts[2], edgeVerts[3]); outpt.edgeDistance[3] = edgeDistance(edgeVerts[index], edgeVerts[3], edgeVerts[0]); #endif emit(index, normal, uvs); } #endif void main() { gl_PrimitiveID = gl_PrimitiveIDIn; vec2 uvs[4]; #ifdef FACEVARYING_COLOR // Offset based on prim id and offset into patch-type fvar data table int uvOffset = (gl_PrimitiveID+LevelBase) * 4; uvs[0] = vec2( texelFetch( g_uvFVarBuffer, (uvOffset+0)*2 ).s, texelFetch( g_uvFVarBuffer, (uvOffset+0)*2+1 ).s ); uvs[1] = vec2( texelFetch( g_uvFVarBuffer, (uvOffset+1)*2 ).s, texelFetch( g_uvFVarBuffer, (uvOffset+1)*2+1 ).s ); uvs[2] = vec2( texelFetch( g_uvFVarBuffer, (uvOffset+2)*2 ).s, texelFetch( g_uvFVarBuffer, (uvOffset+2)*2+1 ).s ); uvs[3] = vec2( texelFetch( g_uvFVarBuffer, (uvOffset+3)*2 ).s, texelFetch( g_uvFVarBuffer, (uvOffset+3)*2+1 ).s ); #endif #ifdef PRIM_QUAD vec3 A = (inpt[0].v.position - inpt[1].v.position).xyz; vec3 B = (inpt[3].v.position - inpt[1].v.position).xyz; vec3 C = (inpt[2].v.position - inpt[1].v.position).xyz; vec3 n0 = normalize(cross(B, A)); #if defined(GEOMETRY_OUT_WIRE) || defined(GEOMETRY_OUT_LINE) vec4 edgeVerts[EDGE_VERTS]; edgeVerts[0] = ProjectionMatrix * inpt[0].v.position; edgeVerts[1] = ProjectionMatrix * inpt[1].v.position; edgeVerts[2] = ProjectionMatrix * inpt[2].v.position; edgeVerts[3] = ProjectionMatrix * inpt[3].v.position; edgeVerts[0].xy /= edgeVerts[0].w; edgeVerts[1].xy /= edgeVerts[1].w; edgeVerts[2].xy /= edgeVerts[2].w; edgeVerts[3].xy /= edgeVerts[3].w; emit(0, n0, uvs, edgeVerts); emit(1, n0, uvs, edgeVerts); emit(3, n0, uvs, edgeVerts); emit(2, n0, uvs, edgeVerts); #else emit(0, n0, uvs); emit(1, n0, uvs); emit(3, n0, uvs); emit(2, n0, uvs); #endif #endif // PRIM_QUAD #ifdef PRIM_TRI vec3 A = (inpt[1].v.position - inpt[0].v.position).xyz; vec3 B = (inpt[2].v.position - inpt[0].v.position).xyz; vec3 n0 = normalize(cross(B, A)); #if defined(GEOMETRY_OUT_WIRE) || defined(GEOMETRY_OUT_LINE) vec4 edgeVerts[EDGE_VERTS]; edgeVerts[0] = ProjectionMatrix * inpt[0].v.position; edgeVerts[1] = ProjectionMatrix * inpt[1].v.position; edgeVerts[2] = ProjectionMatrix * inpt[2].v.position; edgeVerts[0].xy /= edgeVerts[0].w; edgeVerts[1].xy /= edgeVerts[1].w; edgeVerts[2].xy /= edgeVerts[2].w; emit(0, n0, uvs, edgeVerts); emit(1, n0, uvs, edgeVerts); emit(2, n0, uvs, edgeVerts); #else emit(0, n0, uvs); emit(1, n0, uvs); emit(2, n0, uvs); #endif #endif // PRIM_TRI EndPrimitive(); } #endif //-------------------------------------------------------------- // Fragment Shader //-------------------------------------------------------------- #ifdef FRAGMENT_SHADER in block { OutputVertex v; noperspective in vec4 edgeDistance; OSD_USER_VARYING_DECLARE } inpt; out vec4 outColor; #define NUM_LIGHTS 2 struct LightSource { vec4 position; vec4 ambient; vec4 diffuse; vec4 specular; }; layout(std140) uniform Lighting { LightSource lightSource[NUM_LIGHTS]; }; uniform vec4 diffuseColor = vec4(1); uniform vec4 ambientColor = vec4(1); vec4 lighting(vec4 diffuse, vec3 Peye, vec3 Neye) { vec4 color = vec4(0); for (int i = 0; i < NUM_LIGHTS; ++i) { vec4 Plight = lightSource[i].position; vec3 l = (Plight.w == 0.0) ? normalize(Plight.xyz) : normalize(Plight.xyz - Peye); vec3 n = normalize(Neye); vec3 h = normalize(l + vec3(0,0,1)); // directional viewer float d = max(0.0, dot(n, l)); float s = pow(max(0.0, dot(n, h)), 500.0f); color += lightSource[i].ambient * ambientColor + d * lightSource[i].diffuse * diffuse + s * lightSource[i].specular; } color.a = 1; return color; } vec4 edgeColor(vec4 Cfill, vec4 edgeDistance) { #if defined(GEOMETRY_OUT_WIRE) || defined(GEOMETRY_OUT_LINE) #ifdef PRIM_TRI float d = min(inpt.edgeDistance[0], min(inpt.edgeDistance[1], inpt.edgeDistance[2])); #endif #ifdef PRIM_QUAD float d = min(min(inpt.edgeDistance[0], inpt.edgeDistance[1]), min(inpt.edgeDistance[2], inpt.edgeDistance[3])); #endif vec4 Cedge = vec4(1.0, 1.0, 0.0, 1.0); float p = exp2(-2 * d * d); #if defined(GEOMETRY_OUT_WIRE) if (p < 0.25) discard; #endif Cfill.rgb = mix(Cfill.rgb, Cedge.rgb, p); #endif return Cfill; } #if defined(PRIM_QUAD) || defined(PRIM_TRI) void main() { vec3 N = (gl_FrontFacing ? inpt.v.normal : -inpt.v.normal); #if defined(VARYING_COLOR) vec4 color = vec4(inpt.color, 1); #elif defined(FACEVARYING_COLOR) vec4 color = vec4(inpt.color.rg, int(floor(20*inpt.color.r)+floor(20*inpt.color.g))&1, 1); #else vec4 color = diffuseColor; #endif vec4 Cf = lighting(color, inpt.v.position.xyz, N); #if defined(GEOMETRY_OUT_WIRE) || defined(GEOMETRY_OUT_LINE) Cf = edgeColor(Cf, inpt.edgeDistance); #endif outColor = Cf; } #endif #endif