sglrShaderProgram.cpp revision 3c827367444ee418f129b2c238299f49d3264554
1/*------------------------------------------------------------------------- 2 * drawElements Quality Program OpenGL ES Utilities 3 * ------------------------------------------------ 4 * 5 * Copyright 2014 The Android Open Source Project 6 * 7 * Licensed under the Apache License, Version 2.0 (the "License"); 8 * you may not use this file except in compliance with the License. 9 * You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, software 14 * distributed under the License is distributed on an "AS IS" BASIS, 15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 16 * See the License for the specific language governing permissions and 17 * limitations under the License. 18 * 19 *//*! 20 * \file 21 * \brief SGLR shader program. 22 *//*--------------------------------------------------------------------*/ 23 24#include "sglrShaderProgram.hpp" 25 26namespace sglr 27{ 28namespace pdec 29{ 30 31ShaderProgramDeclaration::ShaderProgramDeclaration (void) 32 : m_geometryDecl (rr::GEOMETRYSHADERINPUTTYPE_LAST, rr::GEOMETRYSHADEROUTPUTTYPE_LAST, 0, 0) 33 , m_vertexShaderSet (false) 34 , m_fragmentShaderSet (false) 35 , m_geometryShaderSet (false) 36{ 37} 38 39ShaderProgramDeclaration& pdec::ShaderProgramDeclaration::operator<< (const VertexAttribute& v) 40{ 41 m_vertexAttributes.push_back(v); 42 return *this; 43} 44 45ShaderProgramDeclaration& pdec::ShaderProgramDeclaration::operator<< (const VertexToFragmentVarying& v) 46{ 47 m_vertexToFragmentVaryings.push_back(v); 48 return *this; 49} 50 51ShaderProgramDeclaration& pdec::ShaderProgramDeclaration::operator<< (const VertexToGeometryVarying& v) 52{ 53 m_vertexToGeometryVaryings.push_back(v); 54 return *this; 55} 56 57ShaderProgramDeclaration& pdec::ShaderProgramDeclaration::operator<< (const GeometryToFragmentVarying& v) 58{ 59 m_geometryToFragmentVaryings.push_back(v); 60 return *this; 61} 62 63ShaderProgramDeclaration& pdec::ShaderProgramDeclaration::operator<< (const FragmentOutput& v) 64{ 65 m_fragmentOutputs.push_back(v); 66 return *this; 67} 68 69ShaderProgramDeclaration& pdec::ShaderProgramDeclaration::operator<< (const Uniform& v) 70{ 71 m_uniforms.push_back(v); 72 return *this; 73} 74 75ShaderProgramDeclaration& pdec::ShaderProgramDeclaration::operator<< (const VertexSource& c) 76{ 77 DE_ASSERT(!m_vertexShaderSet); 78 m_vertexSource = c.source; 79 m_vertexShaderSet = true; 80 return *this; 81} 82 83ShaderProgramDeclaration& pdec::ShaderProgramDeclaration::operator<< (const FragmentSource& c) 84{ 85 DE_ASSERT(!m_fragmentShaderSet); 86 m_fragmentSource = c.source; 87 m_fragmentShaderSet = true; 88 return *this; 89} 90 91ShaderProgramDeclaration& pdec::ShaderProgramDeclaration::operator<< (const GeometrySource& c) 92{ 93 DE_ASSERT(!m_geometryShaderSet); 94 m_geometrySource = c.source; 95 m_geometryShaderSet = true; 96 return *this; 97} 98 99ShaderProgramDeclaration& pdec::ShaderProgramDeclaration::operator<< (const GeometryShaderDeclaration& c) 100{ 101 m_geometryDecl = c; 102 return *this; 103} 104 105bool ShaderProgramDeclaration::valid (void) const 106{ 107 if (!m_vertexShaderSet || !m_fragmentShaderSet) 108 return false; 109 110 if (m_fragmentOutputs.empty()) 111 return false; 112 113 if (hasGeometryShader()) 114 { 115 if (m_geometryDecl.inputType == rr::GEOMETRYSHADERINPUTTYPE_LAST || 116 m_geometryDecl.outputType == rr::GEOMETRYSHADEROUTPUTTYPE_LAST) 117 return false; 118 } 119 else 120 { 121 if (m_geometryDecl.inputType != rr::GEOMETRYSHADERINPUTTYPE_LAST || 122 m_geometryDecl.outputType != rr::GEOMETRYSHADEROUTPUTTYPE_LAST || 123 m_geometryDecl.numOutputVertices != 0 || 124 m_geometryDecl.numInvocations != 0) 125 return false; 126 } 127 128 return true; 129} 130 131} //pdec 132 133ShaderProgram::ShaderProgram (const pdec::ShaderProgramDeclaration& decl) 134 : rr::VertexShader (decl.getVertexInputCount(), decl.getVertexOutputCount()) 135 , rr::GeometryShader (decl.getGeometryInputCount(), 136 decl.getGeometryOutputCount(), 137 decl.m_geometryDecl.inputType, 138 decl.m_geometryDecl.outputType, 139 decl.m_geometryDecl.numOutputVertices, 140 decl.m_geometryDecl.numInvocations) 141 , rr::FragmentShader (decl.getFragmentInputCount(), decl.getFragmentOutputCount()) 142 , m_attributeNames (decl.getVertexInputCount()) 143 , m_uniforms (decl.m_uniforms.size()) 144 , m_vertSrc (decl.m_vertexSource) 145 , m_fragSrc (decl.m_fragmentSource) 146 , m_geomSrc (decl.hasGeometryShader() ? (decl.m_geometrySource) : ("")) 147 , m_hasGeometryShader (decl.hasGeometryShader()) 148{ 149 DE_ASSERT(decl.valid()); 150 151 // Set up shader IO 152 153 for (size_t ndx = 0; ndx < decl.m_vertexAttributes.size(); ++ndx) 154 { 155 this->rr::VertexShader::m_inputs[ndx].type = decl.m_vertexAttributes[ndx].type; 156 m_attributeNames[ndx] = decl.m_vertexAttributes[ndx].name; 157 } 158 159 if (m_hasGeometryShader) 160 { 161 for (size_t ndx = 0; ndx < decl.m_vertexToGeometryVaryings.size(); ++ndx) 162 { 163 this->rr::VertexShader::m_outputs[ndx].type = decl.m_vertexToGeometryVaryings[ndx].type; 164 this->rr::VertexShader::m_outputs[ndx].flatshade = decl.m_vertexToGeometryVaryings[ndx].flatshade; 165 166 this->rr::GeometryShader::m_inputs[ndx] = this->rr::VertexShader::m_outputs[ndx]; 167 } 168 for (size_t ndx = 0; ndx < decl.m_geometryToFragmentVaryings.size(); ++ndx) 169 { 170 this->rr::GeometryShader::m_outputs[ndx].type = decl.m_geometryToFragmentVaryings[ndx].type; 171 this->rr::GeometryShader::m_outputs[ndx].flatshade = decl.m_geometryToFragmentVaryings[ndx].flatshade; 172 173 this->rr::FragmentShader::m_inputs[ndx] = this->rr::GeometryShader::m_outputs[ndx]; 174 } 175 } 176 else 177 { 178 for (size_t ndx = 0; ndx < decl.m_vertexToFragmentVaryings.size(); ++ndx) 179 { 180 this->rr::VertexShader::m_outputs[ndx].type = decl.m_vertexToFragmentVaryings[ndx].type; 181 this->rr::VertexShader::m_outputs[ndx].flatshade = decl.m_vertexToFragmentVaryings[ndx].flatshade; 182 183 this->rr::FragmentShader::m_inputs[ndx] = this->rr::VertexShader::m_outputs[ndx]; 184 } 185 } 186 187 for (size_t ndx = 0; ndx < decl.m_fragmentOutputs.size(); ++ndx) 188 this->rr::FragmentShader::m_outputs[ndx].type = decl.m_fragmentOutputs[ndx].type; 189 190 // Set up uniforms 191 192 for (size_t ndx = 0; ndx < decl.m_uniforms.size(); ++ndx) 193 { 194 this->m_uniforms[ndx].name = decl.m_uniforms[ndx].name; 195 this->m_uniforms[ndx].type = decl.m_uniforms[ndx].type; 196 } 197} 198 199ShaderProgram::~ShaderProgram (void) 200{ 201} 202 203const UniformSlot& ShaderProgram::getUniformByName (const char* name) const 204{ 205 DE_ASSERT(name); 206 207 for (size_t ndx = 0; ndx < m_uniforms.size(); ++ndx) 208 if (m_uniforms[ndx].name == std::string(name)) 209 return m_uniforms[ndx]; 210 211 DE_ASSERT(!"Invalid uniform name, uniform not found."); 212 return m_uniforms[0]; 213} 214 215void ShaderProgram::shadePrimitives (rr::GeometryEmitter& output, int verticesIn, const rr::PrimitivePacket* packets, const int numPackets, int invocationID) const 216{ 217 DE_UNREF(output); 218 DE_UNREF(verticesIn && packets && numPackets && invocationID); 219 220 // Should never be called. 221 DE_ASSERT(DE_FALSE); 222} 223 224} // sglr 225