Chromium Code Reviews| Index: chrome/browser/android/vr_shell/vr_shell_renderer.cc |
| diff --git a/chrome/browser/android/vr_shell/vr_shell_renderer.cc b/chrome/browser/android/vr_shell/vr_shell_renderer.cc |
| index 7fb405fdd5b3717c19ce424240913e5adc7455bb..65bc41bf639e32eb98a8c1f6351b71cfecaa488e 100644 |
| --- a/chrome/browser/android/vr_shell/vr_shell_renderer.cc |
| +++ b/chrome/browser/android/vr_shell/vr_shell_renderer.cc |
| @@ -25,8 +25,22 @@ const float kTexturedQuadTextureCoordinates[12] = { |
| 0.0f, 0.0f, 0.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 1.0f, 1.0f, 0.0f}; |
| const int kTextureCoordinateDataSize = 2; |
| +const float kWebVrVertices[32] = { |
| + // x y u, v |
| + -1.f, 1.f, 0.f, 0.f, // Left Eye |
| + -1.f, -1.f, 0.f, 1.f, |
| + 0.f, -1.f, 1.f, 1.f, |
| + 0.f, 1.f, 1.f, 0.f, |
| + |
| + 0.f, 1.f, 0.f, 0.f, // Right Eye |
| + 0.f, -1.f, 0.f, 1.f, |
| + 1.f, -1.f, 1.f, 1.f, |
| + 1.f, 1.f, 1.f, 0.f }; |
| +const int kWebVrVerticesSize = sizeof(float) * 32; |
| + |
| #define SHADER(Src) #Src |
| #define OEIE_SHADER(Src) "#extension GL_OES_EGL_image_external : require\n" #Src |
| +#define VOID_OFFSET(x) reinterpret_cast<void*>(x) |
| const char* GetShaderSource(ShaderID shader) { |
| switch (shader) { |
| @@ -44,6 +58,26 @@ const char* GetShaderSource(ShaderID shader) { |
| vec4 texture = texture2D(u_Texture, v_TexCoordinate); |
| gl_FragColor = vec4(texture.r, texture.g, texture.b, 1.0); |
| }); |
| + case vr_shell::ShaderID::WEBVR_VERTEX_SHADER: |
| + return SHADER( |
| + attribute vec2 a_Position; |
| + attribute vec2 a_TexCoordinate; |
| + uniform vec4 u_SrcRect; |
| + varying vec2 v_TexCoordinate; |
| + |
| + void main() { |
| + v_TexCoordinate = u_SrcRect.xy + (a_TexCoordinate * u_SrcRect.zw); |
| + gl_Position = vec4(a_Position, 0.0, 1.0); |
| + }); |
| + case vr_shell::ShaderID::WEBVR_FRAGMENT_SHADER: |
| + return OEIE_SHADER( |
| + precision highp float; |
| + uniform samplerExternalOES u_Texture; |
| + varying vec2 v_TexCoordinate; |
| + |
| + void main() { |
| + gl_FragColor = texture2D(u_Texture, v_TexCoordinate); |
| + }); |
| default: |
| LOG(ERROR) << "Shader source requested for unknown shader"; |
| return ""; |
| @@ -118,8 +152,109 @@ TexturedQuadRenderer::~TexturedQuadRenderer() { |
| glDeleteShader(fragment_shader_handle_); |
| } |
| +WebVrRenderer::WebVrRenderer() { |
| + left_bounds_ = { 0.0f, 0.0f, 0.5f, 1.0f }; |
| + right_bounds_ = { 0.5f, 0.0f, 0.5f, 1.0f }; |
| + |
| + std::string error; |
| + GLuint vertex_shader_handle = CompileShader( |
| + GL_VERTEX_SHADER, GetShaderSource(WEBVR_VERTEX_SHADER), error); |
| + if (vertex_shader_handle == 0) { |
| + LOG(ERROR) << error; |
| + exit(1); |
|
David Trainor- moved to gerrit
2016/09/08 06:16:05
Should we just do CHECK_EQ(0, vertex_shader_handle
|
| + } |
| + GLuint fragment_shader_handle = CompileShader( |
| + GL_FRAGMENT_SHADER, GetShaderSource(WEBVR_FRAGMENT_SHADER), error); |
| + if (fragment_shader_handle == 0) { |
| + LOG(ERROR) << error; |
| + exit(1); |
| + } |
| + |
| + program_handle_ = CreateAndLinkProgram( |
| + vertex_shader_handle, fragment_shader_handle, 2, nullptr, error); |
| + if (program_handle_ == 0) { |
| + LOG(ERROR) << error; |
| + exit(1); |
| + } |
| + |
| + // Once the program is linked the shader objects are no longer needed |
| + glDeleteShader(vertex_shader_handle); |
| + glDeleteShader(fragment_shader_handle); |
| + |
| + tex_uniform_handle_ = glGetUniformLocation(program_handle_, "u_Texture"); |
| + src_rect_uniform_handle_ = glGetUniformLocation(program_handle_, "u_SrcRect"); |
| + position_handle_ = glGetAttribLocation(program_handle_, "a_Position"); |
| + texcoord_handle_ = glGetAttribLocation(program_handle_, "a_TexCoordinate"); |
| + |
| + // TODO: Figure out why this need to be restored. |
|
David Trainor- moved to gerrit
2016/09/08 06:16:05
Add ldap?
|
| + GLint old_buffer; |
| + glGetIntegerv(GL_ARRAY_BUFFER_BINDING, &old_buffer); |
| + |
| + glGenBuffersARB(1, &vertex_buffer_); |
| + glBindBuffer(GL_ARRAY_BUFFER, vertex_buffer_); |
| + glBufferData(GL_ARRAY_BUFFER, kWebVrVerticesSize, kWebVrVertices, |
| + GL_STATIC_DRAW); |
| + |
| + glBindBuffer(GL_ARRAY_BUFFER, old_buffer); |
| +} |
| + |
| +/** |
| + * Draw the WebVR frame |
|
David Trainor- moved to gerrit
2016/09/08 06:16:05
// instead of /*? Style guide seems to push for t
|
| + */ |
| +void WebVrRenderer::Draw(int texture_handle) { |
| + // TODO: Figure out why this need to be restored. |
|
David Trainor- moved to gerrit
2016/09/08 06:16:05
ldap, crbug?
|
| + GLint old_buffer; |
|
David Trainor- moved to gerrit
2016/09/08 06:16:05
A ScopedBufferRestore helper would be cool, but if
|
| + glGetIntegerv(GL_ARRAY_BUFFER_BINDING, &old_buffer); |
| + |
| + glUseProgram(program_handle_); |
| + |
| + // Bind vertex attributes |
| + glBindBuffer(GL_ARRAY_BUFFER, vertex_buffer_); |
| + |
| + glEnableVertexAttribArray(position_handle_); |
| + glEnableVertexAttribArray(texcoord_handle_); |
| + |
| + glVertexAttribPointer(position_handle_, POSITION_ELEMENTS, GL_FLOAT, false, |
| + VERTEX_STRIDE, VOID_OFFSET(POSITION_OFFSET)); |
| + glVertexAttribPointer(texcoord_handle_, TEXCOORD_ELEMENTS, GL_FLOAT, false, |
| + VERTEX_STRIDE, VOID_OFFSET(TEXCOORD_OFFSET)); |
| + |
| + // Bind texture. |
| + glActiveTexture(GL_TEXTURE0); |
| + glBindTexture(GL_TEXTURE_EXTERNAL_OES, texture_handle); |
| + glUniform1i(tex_uniform_handle_, 0); |
| + |
| + // TODO: Should be able handle both eyes in a single draw call. |
| + // Left eye |
| + glUniform4fv(src_rect_uniform_handle_, 1, (float*)(&left_bounds_)); |
| + glDrawArrays(GL_TRIANGLE_FAN, 0, 4); |
| + |
| + // Right eye |
| + glUniform4fv(src_rect_uniform_handle_, 1, (float*)(&right_bounds_)); |
| + glDrawArrays(GL_TRIANGLE_FAN, 4, 4); |
| + |
| + glDisableVertexAttribArray(position_handle_); |
| + glDisableVertexAttribArray(texcoord_handle_); |
| + |
| + glBindBuffer(GL_ARRAY_BUFFER, old_buffer); |
| +} |
| + |
| +void WebVrRenderer::UpdateTextureBounds(int eye, const gvr::Rectf& bounds) { |
| + if (eye == 0) { |
| + left_bounds_ = bounds; |
| + } else if (eye == 1) { |
| + right_bounds_ = bounds; |
| + } |
| +} |
| + |
| +WebVrRenderer::~WebVrRenderer() { |
| + glDeleteBuffersARB(1, &vertex_buffer_); |
| + glDeleteProgram(program_handle_); |
| +} |
| + |
| VrShellRenderer::VrShellRenderer() |
| - : textured_quad_renderer_(new TexturedQuadRenderer) {} |
| + : textured_quad_renderer_(new TexturedQuadRenderer), |
| + webvr_renderer_(new WebVrRenderer) {} |
| VrShellRenderer::~VrShellRenderer() {} |