OLD | NEW |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
| 5 #include <GLES2/gl2.h> |
| 6 #include <GLES2/gl2ext.h> |
| 7 #include <string.h> |
| 8 |
5 #include <vector> | 9 #include <vector> |
6 | 10 |
7 #include "ppapi/c/pp_errors.h" | 11 #include "ppapi/c/pp_errors.h" |
8 #include "ppapi/c/ppb_opengles2.h" | 12 #include "ppapi/c/ppb_opengles2.h" |
9 #include "ppapi/cpp/completion_callback.h" | 13 #include "ppapi/cpp/completion_callback.h" |
10 #include "ppapi/cpp/graphics_3d.h" | 14 #include "ppapi/cpp/graphics_3d.h" |
11 #include "ppapi/cpp/graphics_3d_client.h" | 15 #include "ppapi/cpp/graphics_3d_client.h" |
12 #include "ppapi/cpp/instance.h" | 16 #include "ppapi/cpp/instance.h" |
13 #include "ppapi/cpp/media_stream_video_track.h" | 17 #include "ppapi/cpp/media_stream_video_track.h" |
14 #include "ppapi/cpp/module.h" | 18 #include "ppapi/cpp/module.h" |
15 #include "ppapi/cpp/rect.h" | 19 #include "ppapi/cpp/rect.h" |
16 #include "ppapi/cpp/var.h" | 20 #include "ppapi/cpp/var.h" |
17 #include "ppapi/cpp/video_frame.h" | 21 #include "ppapi/cpp/video_frame.h" |
18 #include "ppapi/lib/gl/include/GLES2/gl2.h" | 22 #include "ppapi/lib/gl/gles2/gl2ext_ppapi.h" |
19 #include "ppapi/lib/gl/include/GLES2/gl2ext.h" | |
20 #include "ppapi/utility/completion_callback_factory.h" | 23 #include "ppapi/utility/completion_callback_factory.h" |
21 | 24 |
22 // When compiling natively on Windows, PostMessage can be #define-d to | 25 // When compiling natively on Windows, PostMessage can be #define-d to |
23 // something else. | 26 // something else. |
24 #ifdef PostMessage | 27 #ifdef PostMessage |
25 #undef PostMessage | 28 #undef PostMessage |
26 #endif | 29 #endif |
27 | 30 |
28 // Assert |context_| isn't holding any GL Errors. Done as a macro instead of a | 31 // Assert |context_| isn't holding any GL Errors. Done as a macro instead of a |
29 // function to preserve line number information in the failure message. | 32 // function to preserve line number information in the failure message. |
30 #define AssertNoGLError() \ | 33 #define AssertNoGLError() \ |
31 PP_DCHECK(!gles2_if_->GetError(context_->pp_resource())); | 34 PP_DCHECK(!glGetError()); |
32 | 35 |
33 namespace { | 36 namespace { |
34 | 37 |
35 // This object is the global object representing this plugin library as long | 38 // This object is the global object representing this plugin library as long |
36 // as it is loaded. | 39 // as it is loaded. |
37 class MediaStreamVideoModule : public pp::Module { | 40 class MediaStreamVideoModule : public pp::Module { |
38 public: | 41 public: |
39 MediaStreamVideoModule() : pp::Module() {} | 42 MediaStreamVideoModule() : pp::Module() {} |
40 virtual ~MediaStreamVideoModule() {} | 43 virtual ~MediaStreamVideoModule() {} |
41 | 44 |
(...skipping 20 matching lines...) Expand all Loading... |
62 | 65 |
63 private: | 66 private: |
64 void DrawYUV(); | 67 void DrawYUV(); |
65 void DrawRGB(); | 68 void DrawRGB(); |
66 void Render(); | 69 void Render(); |
67 | 70 |
68 // GL-related functions. | 71 // GL-related functions. |
69 void InitGL(); | 72 void InitGL(); |
70 GLuint CreateTexture(int32_t width, int32_t height, int unit, bool rgba); | 73 GLuint CreateTexture(int32_t width, int32_t height, int unit, bool rgba); |
71 void CreateGLObjects(); | 74 void CreateGLObjects(); |
72 void CreateShader(GLuint program, GLenum type, const char* source, int size); | 75 void CreateShader(GLuint program, GLenum type, const char* source); |
73 void PaintFinished(int32_t result); | 76 void PaintFinished(int32_t result); |
74 void CreateTextures(); | 77 void CreateTextures(); |
75 void ConfigureTrack(); | 78 void ConfigureTrack(); |
76 | 79 |
77 | 80 |
78 // MediaStreamVideoTrack callbacks. | 81 // MediaStreamVideoTrack callbacks. |
79 void OnConfigure(int32_t result); | 82 void OnConfigure(int32_t result); |
80 void OnGetFrame(int32_t result, pp::VideoFrame frame); | 83 void OnGetFrame(int32_t result, pp::VideoFrame frame); |
81 | 84 |
82 pp::Size position_size_; | 85 pp::Size position_size_; |
(...skipping 10 matching lines...) Expand all Loading... |
93 pp::MediaStreamVideoTrack video_track_; | 96 pp::MediaStreamVideoTrack video_track_; |
94 pp::CompletionCallbackFactory<MediaStreamVideoDemoInstance> callback_factory_; | 97 pp::CompletionCallbackFactory<MediaStreamVideoDemoInstance> callback_factory_; |
95 std::vector<int32_t> attrib_list_; | 98 std::vector<int32_t> attrib_list_; |
96 | 99 |
97 // MediaStreamVideoTrack attributes: | 100 // MediaStreamVideoTrack attributes: |
98 bool need_config_; | 101 bool need_config_; |
99 PP_VideoFrame_Format attrib_format_; | 102 PP_VideoFrame_Format attrib_format_; |
100 int32_t attrib_width_; | 103 int32_t attrib_width_; |
101 int32_t attrib_height_; | 104 int32_t attrib_height_; |
102 | 105 |
103 // Unowned pointers. | |
104 const struct PPB_OpenGLES2* gles2_if_; | |
105 | |
106 // Owned data. | 106 // Owned data. |
107 pp::Graphics3D* context_; | 107 pp::Graphics3D* context_; |
108 | 108 |
109 pp::Size frame_size_; | 109 pp::Size frame_size_; |
110 }; | 110 }; |
111 | 111 |
112 MediaStreamVideoDemoInstance::MediaStreamVideoDemoInstance( | 112 MediaStreamVideoDemoInstance::MediaStreamVideoDemoInstance( |
113 PP_Instance instance, pp::Module* module) | 113 PP_Instance instance, pp::Module* module) |
114 : pp::Instance(instance), | 114 : pp::Instance(instance), |
115 pp::Graphics3DClient(this), | 115 pp::Graphics3DClient(this), |
116 is_painting_(false), | 116 is_painting_(false), |
117 needs_paint_(false), | 117 needs_paint_(false), |
118 is_bgra_(false), | 118 is_bgra_(false), |
119 texture_y_(0), | 119 texture_y_(0), |
120 texture_u_(0), | 120 texture_u_(0), |
121 texture_v_(0), | 121 texture_v_(0), |
122 texture_rgb_(0), | 122 texture_rgb_(0), |
123 callback_factory_(this), | 123 callback_factory_(this), |
124 need_config_(false), | 124 need_config_(false), |
125 attrib_format_(PP_VIDEOFRAME_FORMAT_I420), | 125 attrib_format_(PP_VIDEOFRAME_FORMAT_I420), |
126 attrib_width_(0), | 126 attrib_width_(0), |
127 attrib_height_(0), | 127 attrib_height_(0), |
128 context_(NULL) { | 128 context_(NULL) { |
129 gles2_if_ = static_cast<const struct PPB_OpenGLES2*>( | 129 if (!glInitializePPAPI(pp::Module::Get()->get_browser_interface())) { |
130 module->GetBrowserInterface(PPB_OPENGLES2_INTERFACE)); | 130 LogToConsole(PP_LOGLEVEL_ERROR, pp::Var("Unable to initialize GL PPAPI!")); |
131 PP_DCHECK(gles2_if_); | 131 assert(false); |
| 132 } |
132 } | 133 } |
133 | 134 |
134 MediaStreamVideoDemoInstance::~MediaStreamVideoDemoInstance() { | 135 MediaStreamVideoDemoInstance::~MediaStreamVideoDemoInstance() { |
135 delete context_; | 136 delete context_; |
136 } | 137 } |
137 | 138 |
138 void MediaStreamVideoDemoInstance::DidChangeView( | 139 void MediaStreamVideoDemoInstance::DidChangeView( |
139 const pp::Rect& position, const pp::Rect& clip_ignored) { | 140 const pp::Rect& position, const pp::Rect& clip_ignored) { |
140 if (position.width() == 0 || position.height() == 0) | 141 if (position.width() == 0 || position.height() == 0) |
141 return; | 142 return; |
142 if (position.size() == position_size_) | 143 if (position.size() == position_size_) |
143 return; | 144 return; |
144 | 145 |
145 position_size_ = position.size(); | 146 position_size_ = position.size(); |
146 | 147 |
147 // Initialize graphics. | 148 // Initialize graphics. |
148 InitGL(); | 149 InitGL(); |
149 Render(); | 150 Render(); |
150 } | 151 } |
151 | 152 |
152 void MediaStreamVideoDemoInstance::HandleMessage(const pp::Var& var_message) { | 153 void MediaStreamVideoDemoInstance::HandleMessage(const pp::Var& var_message) { |
153 if (!var_message.is_dictionary()) | 154 if (!var_message.is_dictionary()) { |
| 155 LogToConsole(PP_LOGLEVEL_ERROR, pp::Var("Invalid message!")); |
154 return; | 156 return; |
| 157 } |
155 | 158 |
156 pp::VarDictionary var_dictionary_message(var_message); | 159 pp::VarDictionary var_dictionary_message(var_message); |
157 std::string command = var_dictionary_message.Get("command").AsString(); | 160 std::string command = var_dictionary_message.Get("command").AsString(); |
158 | 161 |
159 if (command == "init") { | 162 if (command == "init") { |
160 pp::Var var_track = var_dictionary_message.Get("track"); | 163 pp::Var var_track = var_dictionary_message.Get("track"); |
161 if (!var_track.is_resource()) | 164 if (!var_track.is_resource()) |
162 return; | 165 return; |
163 pp::Resource resource_track = var_track.AsResource(); | 166 pp::Resource resource_track = var_track.AsResource(); |
164 video_track_ = pp::MediaStreamVideoTrack(resource_track); | 167 video_track_ = pp::MediaStreamVideoTrack(resource_track); |
165 ConfigureTrack(); | 168 ConfigureTrack(); |
166 } else if (command == "format") { | 169 } else if (command == "format") { |
167 std::string str_format = var_dictionary_message.Get("format").AsString(); | 170 std::string str_format = var_dictionary_message.Get("format").AsString(); |
168 if (str_format == "YV12") { | 171 if (str_format == "YV12") { |
169 attrib_format_ = PP_VIDEOFRAME_FORMAT_YV12; | 172 attrib_format_ = PP_VIDEOFRAME_FORMAT_YV12; |
170 } else if (str_format == "I420") { | 173 } else if (str_format == "I420") { |
171 attrib_format_ = PP_VIDEOFRAME_FORMAT_I420; | 174 attrib_format_ = PP_VIDEOFRAME_FORMAT_I420; |
172 } else if (str_format == "BGRA") { | 175 } else if (str_format == "BGRA") { |
173 attrib_format_ = PP_VIDEOFRAME_FORMAT_BGRA; | 176 attrib_format_ = PP_VIDEOFRAME_FORMAT_BGRA; |
174 } else { | 177 } else { |
175 attrib_format_ = PP_VIDEOFRAME_FORMAT_UNKNOWN; | 178 attrib_format_ = PP_VIDEOFRAME_FORMAT_UNKNOWN; |
176 } | 179 } |
177 need_config_ = true; | 180 need_config_ = true; |
178 } else if (command == "size") { | 181 } else if (command == "size") { |
179 attrib_width_ = var_dictionary_message.Get("width").AsInt(); | 182 attrib_width_ = var_dictionary_message.Get("width").AsInt(); |
180 attrib_height_ = var_dictionary_message.Get("height").AsInt(); | 183 attrib_height_ = var_dictionary_message.Get("height").AsInt(); |
181 need_config_ = true; | 184 need_config_ = true; |
| 185 } else { |
| 186 LogToConsole(PP_LOGLEVEL_ERROR, pp::Var("Invalid command!")); |
182 } | 187 } |
183 } | 188 } |
184 | 189 |
185 void MediaStreamVideoDemoInstance::InitGL() { | 190 void MediaStreamVideoDemoInstance::InitGL() { |
186 PP_DCHECK(position_size_.width() && position_size_.height()); | 191 PP_DCHECK(position_size_.width() && position_size_.height()); |
187 is_painting_ = false; | 192 is_painting_ = false; |
188 | 193 |
189 delete context_; | 194 delete context_; |
190 int32_t attributes[] = { | 195 int32_t attributes[] = { |
191 PP_GRAPHICS3DATTRIB_ALPHA_SIZE, 0, | 196 PP_GRAPHICS3DATTRIB_ALPHA_SIZE, 0, |
192 PP_GRAPHICS3DATTRIB_BLUE_SIZE, 8, | 197 PP_GRAPHICS3DATTRIB_BLUE_SIZE, 8, |
193 PP_GRAPHICS3DATTRIB_GREEN_SIZE, 8, | 198 PP_GRAPHICS3DATTRIB_GREEN_SIZE, 8, |
194 PP_GRAPHICS3DATTRIB_RED_SIZE, 8, | 199 PP_GRAPHICS3DATTRIB_RED_SIZE, 8, |
195 PP_GRAPHICS3DATTRIB_DEPTH_SIZE, 0, | 200 PP_GRAPHICS3DATTRIB_DEPTH_SIZE, 0, |
196 PP_GRAPHICS3DATTRIB_STENCIL_SIZE, 0, | 201 PP_GRAPHICS3DATTRIB_STENCIL_SIZE, 0, |
197 PP_GRAPHICS3DATTRIB_SAMPLES, 0, | 202 PP_GRAPHICS3DATTRIB_SAMPLES, 0, |
198 PP_GRAPHICS3DATTRIB_SAMPLE_BUFFERS, 0, | 203 PP_GRAPHICS3DATTRIB_SAMPLE_BUFFERS, 0, |
199 PP_GRAPHICS3DATTRIB_WIDTH, position_size_.width(), | 204 PP_GRAPHICS3DATTRIB_WIDTH, position_size_.width(), |
200 PP_GRAPHICS3DATTRIB_HEIGHT, position_size_.height(), | 205 PP_GRAPHICS3DATTRIB_HEIGHT, position_size_.height(), |
201 PP_GRAPHICS3DATTRIB_NONE, | 206 PP_GRAPHICS3DATTRIB_NONE, |
202 }; | 207 }; |
203 context_ = new pp::Graphics3D(this, attributes); | 208 context_ = new pp::Graphics3D(this, attributes); |
204 PP_DCHECK(!context_->is_null()); | 209 PP_DCHECK(!context_->is_null()); |
205 | 210 |
| 211 glSetCurrentContextPPAPI(context_->pp_resource()); |
| 212 |
206 // Set viewport window size and clear color bit. | 213 // Set viewport window size and clear color bit. |
207 gles2_if_->ClearColor(context_->pp_resource(), 1, 0, 0, 1); | 214 glClearColor(1, 0, 0, 1); |
208 gles2_if_->Clear(context_->pp_resource(), GL_COLOR_BUFFER_BIT); | 215 glClear(GL_COLOR_BUFFER_BIT); |
209 gles2_if_->Viewport(context_->pp_resource(), 0, 0, | 216 glViewport(0, 0, position_size_.width(), position_size_.height()); |
210 position_size_.width(), position_size_.height()); | |
211 | 217 |
212 BindGraphics(*context_); | 218 BindGraphics(*context_); |
213 AssertNoGLError(); | 219 AssertNoGLError(); |
214 | 220 |
215 CreateGLObjects(); | 221 CreateGLObjects(); |
216 } | 222 } |
217 | 223 |
218 void MediaStreamVideoDemoInstance::DrawYUV() { | 224 void MediaStreamVideoDemoInstance::DrawYUV() { |
219 PP_Resource context = context_->pp_resource(); | |
220 static const float kColorMatrix[9] = { | 225 static const float kColorMatrix[9] = { |
221 1.1643828125f, 1.1643828125f, 1.1643828125f, | 226 1.1643828125f, 1.1643828125f, 1.1643828125f, |
222 0.0f, -0.39176171875f, 2.017234375f, | 227 0.0f, -0.39176171875f, 2.017234375f, |
223 1.59602734375f, -0.81296875f, 0.0f | 228 1.59602734375f, -0.81296875f, 0.0f |
224 }; | 229 }; |
225 | 230 |
226 gles2_if_->UseProgram(context, program_yuv_); | 231 glUseProgram(program_yuv_); |
227 gles2_if_->Uniform1i(context, gles2_if_->GetUniformLocation( | 232 glUniform1i(glGetUniformLocation(program_yuv_, "y_texture"), 0); |
228 context, program_yuv_, "y_texture"), 0); | 233 glUniform1i(glGetUniformLocation(program_yuv_, "u_texture"), 1); |
229 gles2_if_->Uniform1i(context, gles2_if_->GetUniformLocation( | 234 glUniform1i(glGetUniformLocation(program_yuv_, "v_texture"), 2); |
230 context, program_yuv_, "u_texture"), 1); | 235 glUniformMatrix3fv(glGetUniformLocation(program_yuv_, "color_matrix"), |
231 gles2_if_->Uniform1i(context, gles2_if_->GetUniformLocation( | |
232 context, program_yuv_, "v_texture"), 2); | |
233 gles2_if_->UniformMatrix3fv( | |
234 context, | |
235 gles2_if_->GetUniformLocation(context, program_yuv_, "color_matrix"), | |
236 1, GL_FALSE, kColorMatrix); | 236 1, GL_FALSE, kColorMatrix); |
237 AssertNoGLError(); | 237 AssertNoGLError(); |
238 | 238 |
239 GLint pos_location = gles2_if_->GetAttribLocation( | 239 GLint pos_location = glGetAttribLocation(program_yuv_, "a_position"); |
240 context, program_yuv_, "a_position"); | 240 GLint tc_location = glGetAttribLocation(program_yuv_, "a_texCoord"); |
241 GLint tc_location = gles2_if_->GetAttribLocation( | |
242 context, program_yuv_, "a_texCoord"); | |
243 AssertNoGLError(); | 241 AssertNoGLError(); |
244 gles2_if_->EnableVertexAttribArray(context, pos_location); | 242 glEnableVertexAttribArray(pos_location); |
245 gles2_if_->VertexAttribPointer(context, pos_location, 2, | 243 glVertexAttribPointer(pos_location, 2, GL_FLOAT, GL_FALSE, 0, 0); |
246 GL_FLOAT, GL_FALSE, 0, 0); | 244 glEnableVertexAttribArray(tc_location); |
247 gles2_if_->EnableVertexAttribArray(context, tc_location); | 245 glVertexAttribPointer(tc_location, 2, GL_FLOAT, GL_FALSE, 0, |
248 gles2_if_->VertexAttribPointer( | |
249 context, tc_location, 2, GL_FLOAT, GL_FALSE, 0, | |
250 static_cast<float*>(0) + 16); // Skip position coordinates. | 246 static_cast<float*>(0) + 16); // Skip position coordinates. |
251 AssertNoGLError(); | 247 AssertNoGLError(); |
252 | 248 |
253 gles2_if_->DrawArrays(context, GL_TRIANGLE_STRIP, 0, 4); | 249 glDrawArrays(GL_TRIANGLE_STRIP, 0, 4); |
254 AssertNoGLError(); | 250 AssertNoGLError(); |
255 } | 251 } |
256 | 252 |
257 void MediaStreamVideoDemoInstance::DrawRGB() { | 253 void MediaStreamVideoDemoInstance::DrawRGB() { |
258 PP_Resource context = context_->pp_resource(); | 254 glUseProgram(program_rgb_); |
259 gles2_if_->UseProgram(context, program_rgb_); | 255 glUniform1i(glGetUniformLocation(program_rgb_, "rgb_texture"), 3); |
260 gles2_if_->Uniform1i(context, | |
261 gles2_if_->GetUniformLocation(context, program_rgb_, "rgb_texture"), 3); | |
262 AssertNoGLError(); | 256 AssertNoGLError(); |
263 | 257 |
264 GLint pos_location = gles2_if_->GetAttribLocation( | 258 GLint pos_location = glGetAttribLocation(program_rgb_, "a_position"); |
265 context, program_rgb_, "a_position"); | 259 GLint tc_location = glGetAttribLocation(program_rgb_, "a_texCoord"); |
266 GLint tc_location = gles2_if_->GetAttribLocation( | |
267 context, program_rgb_, "a_texCoord"); | |
268 AssertNoGLError(); | 260 AssertNoGLError(); |
269 gles2_if_->EnableVertexAttribArray(context, pos_location); | 261 glEnableVertexAttribArray(pos_location); |
270 gles2_if_->VertexAttribPointer(context, pos_location, 2, | 262 glVertexAttribPointer(pos_location, 2, GL_FLOAT, GL_FALSE, 0, 0); |
271 GL_FLOAT, GL_FALSE, 0, 0); | 263 glEnableVertexAttribArray(tc_location); |
272 gles2_if_->EnableVertexAttribArray(context, tc_location); | 264 glVertexAttribPointer(tc_location, 2, GL_FLOAT, GL_FALSE, 0, |
273 gles2_if_->VertexAttribPointer( | |
274 context, tc_location, 2, GL_FLOAT, GL_FALSE, 0, | |
275 static_cast<float*>(0) + 16); // Skip position coordinates. | 265 static_cast<float*>(0) + 16); // Skip position coordinates. |
276 AssertNoGLError(); | 266 AssertNoGLError(); |
277 | 267 |
278 gles2_if_->DrawArrays(context, GL_TRIANGLE_STRIP, 4, 4); | 268 glDrawArrays(GL_TRIANGLE_STRIP, 4, 4); |
279 } | 269 } |
280 | 270 |
281 void MediaStreamVideoDemoInstance::Render() { | 271 void MediaStreamVideoDemoInstance::Render() { |
282 PP_DCHECK(!is_painting_); | 272 PP_DCHECK(!is_painting_); |
283 is_painting_ = true; | 273 is_painting_ = true; |
284 needs_paint_ = false; | 274 needs_paint_ = false; |
285 | 275 |
286 if (texture_y_) { | 276 if (texture_y_) { |
287 DrawRGB(); | 277 DrawRGB(); |
288 DrawYUV(); | 278 DrawYUV(); |
289 } else { | 279 } else { |
290 gles2_if_->Clear(context_->pp_resource(), GL_COLOR_BUFFER_BIT); | 280 glClear(GL_COLOR_BUFFER_BIT); |
291 } | 281 } |
292 pp::CompletionCallback cb = callback_factory_.NewCallback( | 282 pp::CompletionCallback cb = callback_factory_.NewCallback( |
293 &MediaStreamVideoDemoInstance::PaintFinished); | 283 &MediaStreamVideoDemoInstance::PaintFinished); |
294 context_->SwapBuffers(cb); | 284 context_->SwapBuffers(cb); |
295 } | 285 } |
296 | 286 |
297 void MediaStreamVideoDemoInstance::PaintFinished(int32_t result) { | 287 void MediaStreamVideoDemoInstance::PaintFinished(int32_t result) { |
298 is_painting_ = false; | 288 is_painting_ = false; |
299 if (needs_paint_) | 289 if (needs_paint_) |
300 Render(); | 290 Render(); |
301 } | 291 } |
302 | 292 |
303 GLuint MediaStreamVideoDemoInstance::CreateTexture( | 293 GLuint MediaStreamVideoDemoInstance::CreateTexture( |
304 int32_t width, int32_t height, int unit, bool rgba) { | 294 int32_t width, int32_t height, int unit, bool rgba) { |
305 GLuint texture_id; | 295 GLuint texture_id; |
306 gles2_if_->GenTextures(context_->pp_resource(), 1, &texture_id); | 296 glGenTextures(1, &texture_id); |
307 AssertNoGLError(); | 297 AssertNoGLError(); |
308 | 298 |
309 // Assign parameters. | 299 // Assign parameters. |
310 gles2_if_->ActiveTexture(context_->pp_resource(), GL_TEXTURE0 + unit); | 300 glActiveTexture(GL_TEXTURE0 + unit); |
311 gles2_if_->BindTexture(context_->pp_resource(), GL_TEXTURE_2D, texture_id); | 301 glBindTexture(GL_TEXTURE_2D, texture_id); |
312 gles2_if_->TexParameteri( | 302 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); |
313 context_->pp_resource(), GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, | 303 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); |
314 GL_NEAREST); | 304 glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); |
315 gles2_if_->TexParameteri( | 305 glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); |
316 context_->pp_resource(), GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, | |
317 GL_NEAREST); | |
318 gles2_if_->TexParameterf( | |
319 context_->pp_resource(), GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, | |
320 GL_CLAMP_TO_EDGE); | |
321 gles2_if_->TexParameterf( | |
322 context_->pp_resource(), GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, | |
323 GL_CLAMP_TO_EDGE); | |
324 // Allocate texture. | 306 // Allocate texture. |
325 gles2_if_->TexImage2D( | 307 glTexImage2D(GL_TEXTURE_2D, 0, |
326 context_->pp_resource(), GL_TEXTURE_2D, 0, | 308 rgba ? GL_BGRA_EXT : GL_LUMINANCE, |
327 rgba ? GL_BGRA_EXT : GL_LUMINANCE, | 309 width, height, 0, |
328 width, height, 0, | 310 rgba ? GL_BGRA_EXT : GL_LUMINANCE, GL_UNSIGNED_BYTE, NULL); |
329 rgba ? GL_BGRA_EXT : GL_LUMINANCE, GL_UNSIGNED_BYTE, NULL); | |
330 AssertNoGLError(); | 311 AssertNoGLError(); |
331 return texture_id; | 312 return texture_id; |
332 } | 313 } |
333 | 314 |
334 void MediaStreamVideoDemoInstance::CreateGLObjects() { | 315 void MediaStreamVideoDemoInstance::CreateGLObjects() { |
335 // Code and constants for shader. | 316 // Code and constants for shader. |
336 static const char kVertexShader[] = | 317 static const char kVertexShader[] = |
337 "varying vec2 v_texCoord; \n" | 318 "varying vec2 v_texCoord; \n" |
338 "attribute vec4 a_position; \n" | 319 "attribute vec4 a_position; \n" |
339 "attribute vec2 a_texCoord; \n" | 320 "attribute vec2 a_texCoord; \n" |
(...skipping 22 matching lines...) Expand all Loading... |
362 | 343 |
363 static const char kFragmentShaderRGB[] = | 344 static const char kFragmentShaderRGB[] = |
364 "precision mediump float; \n" | 345 "precision mediump float; \n" |
365 "varying vec2 v_texCoord; \n" | 346 "varying vec2 v_texCoord; \n" |
366 "uniform sampler2D rgb_texture; \n" | 347 "uniform sampler2D rgb_texture; \n" |
367 "void main() \n" | 348 "void main() \n" |
368 "{ \n" | 349 "{ \n" |
369 " gl_FragColor = texture2D(rgb_texture, v_texCoord); \n" | 350 " gl_FragColor = texture2D(rgb_texture, v_texCoord); \n" |
370 "}"; | 351 "}"; |
371 | 352 |
372 PP_Resource context = context_->pp_resource(); | |
373 | |
374 // Create shader programs. | 353 // Create shader programs. |
375 program_yuv_ = gles2_if_->CreateProgram(context); | 354 program_yuv_ = glCreateProgram(); |
376 CreateShader(program_yuv_, GL_VERTEX_SHADER, | 355 CreateShader(program_yuv_, GL_VERTEX_SHADER, kVertexShader); |
377 kVertexShader, sizeof(kVertexShader)); | 356 CreateShader(program_yuv_, GL_FRAGMENT_SHADER, kFragmentShaderYUV); |
378 CreateShader(program_yuv_, GL_FRAGMENT_SHADER, | 357 glLinkProgram(program_yuv_); |
379 kFragmentShaderYUV, sizeof(kFragmentShaderYUV)); | |
380 gles2_if_->LinkProgram(context, program_yuv_); | |
381 AssertNoGLError(); | 358 AssertNoGLError(); |
382 | 359 |
383 program_rgb_ = gles2_if_->CreateProgram(context); | 360 program_rgb_ = glCreateProgram(); |
384 CreateShader(program_rgb_, GL_VERTEX_SHADER, | 361 CreateShader(program_rgb_, GL_VERTEX_SHADER, kVertexShader); |
385 kVertexShader, sizeof(kVertexShader)); | 362 CreateShader(program_rgb_, GL_FRAGMENT_SHADER, kFragmentShaderRGB); |
386 CreateShader(program_rgb_, GL_FRAGMENT_SHADER, | 363 glLinkProgram(program_rgb_); |
387 kFragmentShaderRGB, sizeof(kFragmentShaderRGB)); | |
388 gles2_if_->LinkProgram(context, program_rgb_); | |
389 AssertNoGLError(); | 364 AssertNoGLError(); |
390 | 365 |
391 // Assign vertex positions and texture coordinates to buffers for use in | 366 // Assign vertex positions and texture coordinates to buffers for use in |
392 // shader program. | 367 // shader program. |
393 static const float kVertices[] = { | 368 static const float kVertices[] = { |
394 -1, 1, -1, -1, 0, 1, 0, -1, // Position coordinates. | 369 -1, 1, -1, -1, 0, 1, 0, -1, // Position coordinates. |
395 0, 1, 0, -1, 1, 1, 1, -1, // Position coordinates. | 370 0, 1, 0, -1, 1, 1, 1, -1, // Position coordinates. |
396 0, 0, 0, 1, 1, 0, 1, 1, // Texture coordinates. | 371 0, 0, 0, 1, 1, 0, 1, 1, // Texture coordinates. |
397 0, 0, 0, 1, 1, 0, 1, 1, // Texture coordinates. | 372 0, 0, 0, 1, 1, 0, 1, 1, // Texture coordinates. |
398 }; | 373 }; |
399 | 374 |
400 gles2_if_->GenBuffers(context, 1, &buffer_); | 375 glGenBuffers(1, &buffer_); |
401 gles2_if_->BindBuffer(context, GL_ARRAY_BUFFER, buffer_); | 376 glBindBuffer(GL_ARRAY_BUFFER, buffer_); |
402 gles2_if_->BufferData(context, GL_ARRAY_BUFFER, | 377 glBufferData(GL_ARRAY_BUFFER, sizeof(kVertices), kVertices, GL_STATIC_DRAW); |
403 sizeof(kVertices), kVertices, GL_STATIC_DRAW); | |
404 AssertNoGLError(); | 378 AssertNoGLError(); |
405 } | 379 } |
406 | 380 |
407 void MediaStreamVideoDemoInstance::CreateShader( | 381 void MediaStreamVideoDemoInstance::CreateShader( |
408 GLuint program, GLenum type, const char* source, int size) { | 382 GLuint program, GLenum type, const char* source) { |
409 PP_Resource context = context_->pp_resource(); | 383 GLuint shader = glCreateShader(type); |
410 GLuint shader = gles2_if_->CreateShader(context, type); | 384 GLint length = strlen(source) + 1; |
411 gles2_if_->ShaderSource(context, shader, 1, &source, &size); | 385 glShaderSource(shader, 1, &source, &length); |
412 gles2_if_->CompileShader(context, shader); | 386 glCompileShader(shader); |
413 gles2_if_->AttachShader(context, program, shader); | 387 glAttachShader(program, shader); |
414 gles2_if_->DeleteShader(context, shader); | 388 glDeleteShader(shader); |
415 } | 389 } |
416 | 390 |
417 void MediaStreamVideoDemoInstance::CreateTextures() { | 391 void MediaStreamVideoDemoInstance::CreateTextures() { |
418 int32_t width = frame_size_.width(); | 392 int32_t width = frame_size_.width(); |
419 int32_t height = frame_size_.height(); | 393 int32_t height = frame_size_.height(); |
420 if (width == 0 || height == 0) | 394 if (width == 0 || height == 0) |
421 return; | 395 return; |
422 if (texture_y_) | 396 if (texture_y_) |
423 gles2_if_->DeleteTextures(context_->pp_resource(), 1, &texture_y_); | 397 glDeleteTextures(1, &texture_y_); |
424 if (texture_u_) | 398 if (texture_u_) |
425 gles2_if_->DeleteTextures(context_->pp_resource(), 1, &texture_u_); | 399 glDeleteTextures(1, &texture_u_); |
426 if (texture_v_) | 400 if (texture_v_) |
427 gles2_if_->DeleteTextures(context_->pp_resource(), 1, &texture_v_); | 401 glDeleteTextures(1, &texture_v_); |
428 if (texture_rgb_) | 402 if (texture_rgb_) |
429 gles2_if_->DeleteTextures(context_->pp_resource(), 1, &texture_rgb_); | 403 glDeleteTextures(1, &texture_rgb_); |
430 texture_y_ = CreateTexture(width, height, 0, false); | 404 texture_y_ = CreateTexture(width, height, 0, false); |
431 | 405 |
432 texture_u_ = CreateTexture(width / 2, height / 2, 1, false); | 406 texture_u_ = CreateTexture(width / 2, height / 2, 1, false); |
433 texture_v_ = CreateTexture(width / 2, height / 2, 2, false); | 407 texture_v_ = CreateTexture(width / 2, height / 2, 2, false); |
434 texture_rgb_ = CreateTexture(width, height, 3, true); | 408 texture_rgb_ = CreateTexture(width, height, 3, true); |
435 } | 409 } |
436 | 410 |
437 void MediaStreamVideoDemoInstance::ConfigureTrack() { | 411 void MediaStreamVideoDemoInstance::ConfigureTrack() { |
438 const int32_t attrib_list[] = { | 412 const int32_t attrib_list[] = { |
439 PP_MEDIASTREAMVIDEOTRACK_ATTRIB_FORMAT, attrib_format_, | 413 PP_MEDIASTREAMVIDEOTRACK_ATTRIB_FORMAT, attrib_format_, |
(...skipping 21 matching lines...) Expand all Loading... |
461 if (size != frame_size_) { | 435 if (size != frame_size_) { |
462 frame_size_ = size; | 436 frame_size_ = size; |
463 CreateTextures(); | 437 CreateTextures(); |
464 } | 438 } |
465 | 439 |
466 is_bgra_ = (frame.GetFormat() == PP_VIDEOFRAME_FORMAT_BGRA); | 440 is_bgra_ = (frame.GetFormat() == PP_VIDEOFRAME_FORMAT_BGRA); |
467 | 441 |
468 int32_t width = frame_size_.width(); | 442 int32_t width = frame_size_.width(); |
469 int32_t height = frame_size_.height(); | 443 int32_t height = frame_size_.height(); |
470 if (!is_bgra_) { | 444 if (!is_bgra_) { |
471 gles2_if_->ActiveTexture(context_->pp_resource(), GL_TEXTURE0); | 445 glActiveTexture(GL_TEXTURE0); |
472 gles2_if_->TexSubImage2D( | 446 glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, width, height, |
473 context_->pp_resource(), GL_TEXTURE_2D, 0, 0, 0, width, height, | 447 GL_LUMINANCE, GL_UNSIGNED_BYTE, data); |
474 GL_LUMINANCE, GL_UNSIGNED_BYTE, data); | |
475 | 448 |
476 data += width * height; | 449 data += width * height; |
477 width /= 2; | 450 width /= 2; |
478 height /= 2; | 451 height /= 2; |
479 | 452 |
480 gles2_if_->ActiveTexture(context_->pp_resource(), GL_TEXTURE1); | 453 glActiveTexture(GL_TEXTURE1); |
481 gles2_if_->TexSubImage2D( | 454 glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, width, height, |
482 context_->pp_resource(), GL_TEXTURE_2D, 0, 0, 0, width, height, | 455 GL_LUMINANCE, GL_UNSIGNED_BYTE, data); |
483 GL_LUMINANCE, GL_UNSIGNED_BYTE, data); | |
484 | 456 |
485 data += width * height; | 457 data += width * height; |
486 gles2_if_->ActiveTexture(context_->pp_resource(), GL_TEXTURE2); | 458 glActiveTexture(GL_TEXTURE2); |
487 gles2_if_->TexSubImage2D( | 459 glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, width, height, |
488 context_->pp_resource(), GL_TEXTURE_2D, 0, 0, 0, width, height, | 460 GL_LUMINANCE, GL_UNSIGNED_BYTE, data); |
489 GL_LUMINANCE, GL_UNSIGNED_BYTE, data); | |
490 } else { | 461 } else { |
491 gles2_if_->ActiveTexture(context_->pp_resource(), GL_TEXTURE3); | 462 glActiveTexture(GL_TEXTURE3); |
492 gles2_if_->TexSubImage2D( | 463 glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, width, height, |
493 context_->pp_resource(), GL_TEXTURE_2D, 0, 0, 0, width, height, | 464 GL_BGRA_EXT, GL_UNSIGNED_BYTE, data); |
494 GL_BGRA_EXT, GL_UNSIGNED_BYTE, data); | |
495 } | 465 } |
496 | 466 |
497 if (is_painting_) | 467 if (is_painting_) |
498 needs_paint_ = true; | 468 needs_paint_ = true; |
499 else | 469 else |
500 Render(); | 470 Render(); |
501 | 471 |
502 video_track_.RecycleFrame(frame); | 472 video_track_.RecycleFrame(frame); |
503 if (need_config_) { | 473 if (need_config_) { |
504 ConfigureTrack(); | 474 ConfigureTrack(); |
505 need_config_ = false; | 475 need_config_ = false; |
506 } else { | 476 } else { |
507 video_track_.GetFrame(callback_factory_.NewCallbackWithOutput( | 477 video_track_.GetFrame(callback_factory_.NewCallbackWithOutput( |
508 &MediaStreamVideoDemoInstance::OnGetFrame)); | 478 &MediaStreamVideoDemoInstance::OnGetFrame)); |
509 } | 479 } |
510 } | 480 } |
511 | 481 |
512 pp::Instance* MediaStreamVideoModule::CreateInstance(PP_Instance instance) { | 482 pp::Instance* MediaStreamVideoModule::CreateInstance(PP_Instance instance) { |
513 return new MediaStreamVideoDemoInstance(instance, this); | 483 return new MediaStreamVideoDemoInstance(instance, this); |
514 } | 484 } |
515 | 485 |
516 } // anonymous namespace | 486 } // anonymous namespace |
517 | 487 |
518 namespace pp { | 488 namespace pp { |
519 // Factory function for your specialization of the Module object. | 489 // Factory function for your specialization of the Module object. |
520 Module* CreateModule() { | 490 Module* CreateModule() { |
521 return new MediaStreamVideoModule(); | 491 return new MediaStreamVideoModule(); |
522 } | 492 } |
523 } // namespace pp | 493 } // namespace pp |
OLD | NEW |