1/* 2 * Copyright (C) 2011 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17#include "YVURenderer.h" 18 19#include <GLES2/gl2ext.h> 20 21const GLfloat g_vVertices[] = { 22 -1.f, 1.f, 0.0f, 1.0f, // Position 0 23 0.0f, 1.0f, // TexCoord 0 24 1.f, 1.f, 0.0f, 1.0f, // Position 1 25 1.0f, 1.0f, // TexCoord 1 26 -1.f, -1.f, 0.0f, 1.0f, // Position 2 27 0.0f, 0.0f, // TexCoord 2 28 1.f, -1.f, 0.0f, 1.0f, // Position 3 29 1.0f, 0.0f // TexCoord 3 30}; 31 32const int VERTEX_STRIDE = 6 * sizeof(GLfloat); 33 34GLushort g_iIndices3[] = { 0, 1, 2, 3 }; 35 36YVURenderer::YVURenderer() : Renderer() 37 { 38} 39 40YVURenderer::~YVURenderer() { 41} 42 43bool YVURenderer::InitializeGLProgram() 44{ 45 bool succeeded = false; 46 do { 47 GLuint glProgram; 48 glProgram = createProgram(VertexShaderSource(), 49 FragmentShaderSource()); 50 if (!glProgram) { 51 break; 52 } 53 54 glUseProgram(glProgram); 55 if (!checkGlError("glUseProgram")) break; 56 57 // Get attribute locations 58 mPositionLoc = glGetAttribLocation(glProgram, "a_Position"); 59 mTexCoordLoc = glGetAttribLocation(glProgram, "a_texCoord"); 60 61 // Get sampler location 62 mSamplerLoc = glGetUniformLocation(glProgram, "s_texture"); 63 64 mGlProgram = glProgram; 65 succeeded = true; 66 } while (false); 67 68 if (!succeeded && (mGlProgram != 0)) 69 { 70 glDeleteProgram(mGlProgram); 71 checkGlError("glDeleteProgram"); 72 mGlProgram = 0; 73 } 74 return succeeded; 75} 76 77bool YVURenderer::DrawTexture() 78{ 79 bool succeeded = false; 80 do { 81 bool rt = (mFrameBuffer == NULL)? 82 SetupGraphics(mSurfaceWidth, mSurfaceHeight) : 83 SetupGraphics(mFrameBuffer); 84 85 if(!rt) 86 break; 87 88 glDisable(GL_BLEND); 89 90 glActiveTexture(GL_TEXTURE0); 91 if (!checkGlError("glActiveTexture")) break; 92 93 const GLenum texture_type = InputTextureType(); 94 glBindTexture(texture_type, mInputTextureName); 95 if (!checkGlError("glBindTexture")) break; 96 97 // Set the sampler texture unit to 0 98 glUniform1i(mSamplerLoc, 0); 99 100 // Load the vertex position 101 glVertexAttribPointer(mPositionLoc, 4, GL_FLOAT, 102 GL_FALSE, VERTEX_STRIDE, g_vVertices); 103 104 // Load the texture coordinate 105 glVertexAttribPointer(mTexCoordLoc, 2, GL_FLOAT, 106 GL_FALSE, VERTEX_STRIDE, &g_vVertices[4]); 107 108 glEnableVertexAttribArray(mPositionLoc); 109 glEnableVertexAttribArray(mTexCoordLoc); 110 111 // And, finally, execute the GL draw command. 112 glDrawElements(GL_TRIANGLE_STRIP, 4, GL_UNSIGNED_SHORT, g_iIndices3); 113 114 checkGlError("glDrawElements"); 115 116 glBindFramebuffer(GL_FRAMEBUFFER, 0); 117 succeeded = true; 118 } while (false); 119 return succeeded; 120} 121 122const char* YVURenderer::VertexShaderSource() const 123{ 124 // All this really does is copy the coordinates into 125 // variables for the fragment shader to pick up. 126 static const char gVertexShader[] = 127 "attribute vec4 a_Position;\n" 128 "attribute vec2 a_texCoord;\n" 129 "varying vec2 v_texCoord;\n" 130 "void main() {\n" 131 " gl_Position = a_Position;\n" 132 " v_texCoord = a_texCoord;\n" 133 "}\n"; 134 135 return gVertexShader; 136} 137 138const char* YVURenderer::FragmentShaderSource() const 139{ 140 static const char gFragmentShader[] = 141 "precision mediump float;\n" 142 "uniform sampler2D s_texture;\n" 143 "const vec4 coeff_y = vec4(0.257, 0.594, 0.098, 0.063);\n" 144 "const vec4 coeff_v = vec4(0.439, -0.368, -0.071, 0.500);\n" 145 "const vec4 coeff_u = vec4(-0.148, -0.291, 0.439, 0.500);\n" 146 "varying vec2 v_texCoord;\n" 147 "void main() {\n" 148 " vec4 p;\n" 149 " p = texture2D(s_texture, v_texCoord);\n" 150 " gl_FragColor[0] = dot(p, coeff_y);\n" 151 " p = texture2D(s_texture, v_texCoord);\n" 152 " gl_FragColor[1] = dot(p, coeff_v);\n" 153 " p = texture2D(s_texture, v_texCoord);\n" 154 " gl_FragColor[2] = dot(p, coeff_u);\n" 155 " p = texture2D(s_texture, v_texCoord);\n" 156 " gl_FragColor[3] = dot(p, coeff_y);\n" 157 "}\n"; 158 159 return gFragmentShader; 160} 161