Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(460)

Side by Side Diff: content/common/gpu/media/rendering_helper.cc

Issue 940903002: video_decode_accelerator_unittest: enable test on ozone surfaceless (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Use GpuMemoryBufferFactory instead of GpuMemoryBufferFactoryOzoneNativeBuffer Created 5 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2013 The Chromium Authors. All rights reserved. 1 // Copyright 2013 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 "content/common/gpu/media/rendering_helper.h" 5 #include "content/common/gpu/media/rendering_helper.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <numeric> 8 #include <numeric>
9 #include <vector> 9 #include <vector>
10 10
11 #include "base/bind.h" 11 #include "base/bind.h"
12 #include "base/callback_helpers.h" 12 #include "base/callback_helpers.h"
13 #include "base/command_line.h" 13 #include "base/command_line.h"
14 #include "base/mac/scoped_nsautorelease_pool.h" 14 #include "base/mac/scoped_nsautorelease_pool.h"
15 #include "base/message_loop/message_loop.h" 15 #include "base/message_loop/message_loop.h"
16 #include "base/run_loop.h" 16 #include "base/run_loop.h"
17 #include "base/strings/stringize_macros.h" 17 #include "base/strings/stringize_macros.h"
18 #include "base/synchronization/waitable_event.h" 18 #include "base/synchronization/waitable_event.h"
19 #include "base/time/time.h" 19 #include "base/time/time.h"
20 #include "content/common/gpu/media/gl_renderer.h"
21 #include "content/common/gpu/media/surfaceless_gl_renderer.h"
20 #include "ui/gl/gl_context.h" 22 #include "ui/gl/gl_context.h"
21 #include "ui/gl/gl_implementation.h" 23 #include "ui/gl/gl_implementation.h"
22 #include "ui/gl/gl_surface.h" 24 #include "ui/gl/gl_surface.h"
23
24 #if defined(OS_WIN) 25 #if defined(OS_WIN)
25 #include <windows.h> 26 #include <windows.h>
26 #endif 27 #endif
27 28
28 #if defined(USE_X11) 29 #if defined(USE_X11)
29 #include "ui/gfx/x/x11_types.h" 30 #include "ui/gfx/x/x11_types.h"
30 #endif 31 #endif
31 32
32 #if defined(ARCH_CPU_X86_FAMILY) && defined(USE_X11) 33 #if defined(ARCH_CPU_X86_FAMILY) && defined(USE_X11)
33 #include "ui/gl/gl_surface_glx.h" 34 #include "ui/gl/gl_surface_glx.h"
34 #define GL_VARIANT_GLX 1 35 #define GL_VARIANT_GLX 1
35 #else 36 #else
36 #include "ui/gl/gl_surface_egl.h" 37 #include "ui/gl/gl_surface_egl.h"
37 #define GL_VARIANT_EGL 1 38 #define GL_VARIANT_EGL 1
38 #endif 39 #endif
39 40
40 #if defined(USE_OZONE) 41 #if defined(USE_OZONE)
41 #if defined(OS_CHROMEOS) 42 #if defined(OS_CHROMEOS)
42 #include "ui/display/chromeos/display_configurator.h" 43 #include "ui/display/chromeos/display_configurator.h"
43 #endif // defined(OS_CHROMEOS) 44 #endif // defined(OS_CHROMEOS)
44 #include "ui/ozone/public/ozone_platform.h" 45 #include "ui/ozone/public/ozone_platform.h"
46 #include "ui/ozone/public/ozone_switches.h"
45 #include "ui/platform_window/platform_window.h" 47 #include "ui/platform_window/platform_window.h"
46 #include "ui/platform_window/platform_window_delegate.h" 48 #include "ui/platform_window/platform_window_delegate.h"
47 #endif // defined(USE_OZONE) 49 #endif // defined(USE_OZONE)
48 50
49 // Helper for Shader creation. 51 // Helper for Shader creation.
50 static void CreateShader(GLuint program, 52 static void CreateShader(GLuint program,
51 GLenum type, 53 GLenum type,
52 const char* source, 54 const char* source,
53 int size) { 55 int size) {
54 GLuint shader = glCreateShader(type); 56 GLuint shader = glCreateShader(type);
(...skipping 125 matching lines...) Expand 10 before | Expand all | Expand 10 after
180 done->Signal(); 182 done->Signal();
181 } 183 }
182 184
183 RenderingHelper::RenderingHelper() { 185 RenderingHelper::RenderingHelper() {
184 window_ = gfx::kNullAcceleratedWidget; 186 window_ = gfx::kNullAcceleratedWidget;
185 Clear(); 187 Clear();
186 } 188 }
187 189
188 RenderingHelper::~RenderingHelper() { 190 RenderingHelper::~RenderingHelper() {
189 CHECK_EQ(videos_.size(), 0U) << "Must call UnInitialize before dtor."; 191 CHECK_EQ(videos_.size(), 0U) << "Must call UnInitialize before dtor.";
190 Clear(); 192 CHECK(!gl_renderer_);
191 } 193 }
192 194
193 void RenderingHelper::Setup() { 195 void RenderingHelper::Setup() {
194 #if defined(OS_WIN) 196 #if defined(OS_WIN)
197 screen_size_ = gfx::Size(GetSystemMetrics(SM_CXSCREEN),
198 GetSystemMetrics(SM_CYSCREEN));
195 window_ = CreateWindowEx(0, 199 window_ = CreateWindowEx(0,
196 L"Static", 200 L"Static",
197 L"VideoDecodeAcceleratorTest", 201 L"VideoDecodeAcceleratorTest",
198 WS_OVERLAPPEDWINDOW | WS_VISIBLE, 202 WS_OVERLAPPEDWINDOW | WS_VISIBLE,
199 0, 203 0,
200 0, 204 0,
201 GetSystemMetrics(SM_CXSCREEN), 205 screen_size_.width(),
202 GetSystemMetrics(SM_CYSCREEN), 206 screen_size_.height(),
203 NULL, 207 NULL,
204 NULL, 208 NULL,
205 NULL, 209 NULL,
206 NULL); 210 NULL);
207 #elif defined(USE_X11) 211 #elif defined(USE_X11)
208 Display* display = gfx::GetXDisplay(); 212 Display* display = gfx::GetXDisplay();
209 Screen* screen = DefaultScreenOfDisplay(display); 213 Screen* screen = DefaultScreenOfDisplay(display);
210 214
211 CHECK(display); 215 CHECK(display);
212 216
213 XSetWindowAttributes window_attributes; 217 XSetWindowAttributes window_attributes;
214 memset(&window_attributes, 0, sizeof(window_attributes)); 218 memset(&window_attributes, 0, sizeof(window_attributes));
215 window_attributes.background_pixel = 219 window_attributes.background_pixel =
216 BlackPixel(display, DefaultScreen(display)); 220 BlackPixel(display, DefaultScreen(display));
217 window_attributes.override_redirect = true; 221 window_attributes.override_redirect = true;
218 int depth = DefaultDepth(display, DefaultScreen(display)); 222 int depth = DefaultDepth(display, DefaultScreen(display));
219 223
224 screen_size_ = gfx::Size(XWidthOfScreen(screen), XHeightOfScreen(screen));
225
220 window_ = XCreateWindow(display, 226 window_ = XCreateWindow(display,
221 DefaultRootWindow(display), 227 DefaultRootWindow(display),
222 0, 228 0,
223 0, 229 0,
224 XWidthOfScreen(screen), 230 screen_size_.width(),
225 XHeightOfScreen(screen), 231 screen_size_.height(),
226 0 /* border width */, 232 0 /* border width */,
227 depth, 233 depth,
228 CopyFromParent /* class */, 234 CopyFromParent /* class */,
229 CopyFromParent /* visual */, 235 CopyFromParent /* visual */,
230 (CWBackPixel | CWOverrideRedirect), 236 (CWBackPixel | CWOverrideRedirect),
231 &window_attributes); 237 &window_attributes);
232 XStoreName(display, window_, "VideoDecodeAcceleratorTest"); 238 XStoreName(display, window_, "VideoDecodeAcceleratorTest");
233 XSelectInput(display, window_, ExposureMask); 239 XSelectInput(display, window_, ExposureMask);
234 XMapWindow(display, window_); 240 XMapWindow(display, window_);
235 #elif defined(USE_OZONE) 241 #elif defined(USE_OZONE)
(...skipping 10 matching lines...) Expand all
246 base::RunLoop wait_display_setup; 252 base::RunLoop wait_display_setup;
247 DisplayConfiguratorObserver display_setup_observer(&wait_display_setup); 253 DisplayConfiguratorObserver display_setup_observer(&wait_display_setup);
248 display_configurator_.reset(new ui::DisplayConfigurator()); 254 display_configurator_.reset(new ui::DisplayConfigurator());
249 display_configurator_->AddObserver(&display_setup_observer); 255 display_configurator_->AddObserver(&display_setup_observer);
250 display_configurator_->Init(true); 256 display_configurator_->Init(true);
251 display_configurator_->ForceInitialConfigure(0); 257 display_configurator_->ForceInitialConfigure(0);
252 // Make sure all the display configuration is applied. 258 // Make sure all the display configuration is applied.
253 wait_display_setup.Run(); 259 wait_display_setup.Run();
254 display_configurator_->RemoveObserver(&display_setup_observer); 260 display_configurator_->RemoveObserver(&display_setup_observer);
255 261
262 screen_size_ = display_configurator_->framebuffer_size();
263 #else
264 screen_size_ = gfx::Size(800, 600));
265 #endif
256 platform_window_delegate_->platform_window()->SetBounds( 266 platform_window_delegate_->platform_window()->SetBounds(
257 gfx::Rect(display_configurator_->framebuffer_size())); 267 gfx::Rect(screen_size_));
258 #else
259 platform_window_delegate_->platform_window()->SetBounds(gfx::Rect(800, 600));
260 #endif
261 268
262 // On Ozone/DRI, platform windows are associated with the physical 269 // On Ozone/DRI, platform windows are associated with the physical
263 // outputs. Association is achieved by matching the bounds of the 270 // outputs. Association is achieved by matching the bounds of the
264 // window with the origin & modeset of the display output. Until a 271 // window with the origin & modeset of the display output. Until a
265 // window is associated with a display output, we cannot get vsync 272 // window is associated with a display output, we cannot get vsync
266 // events, because there is no hardware to get events from. Here we 273 // events, because there is no hardware to get events from. Here we
267 // wait for the window to resized and therefore associated with 274 // wait for the window to resized and therefore associated with
268 // display output to be sure that we will get such events. 275 // display output to be sure that we will get such events.
269 wait_window_resize.RunUntilIdle(); 276 wait_window_resize.RunUntilIdle();
270 #else 277 #else
(...skipping 25 matching lines...) Expand all
296 void RenderingHelper::Initialize(const RenderingHelperParams& params, 303 void RenderingHelper::Initialize(const RenderingHelperParams& params,
297 base::WaitableEvent* done) { 304 base::WaitableEvent* done) {
298 // Use videos_.size() != 0 as a proxy for the class having already been 305 // Use videos_.size() != 0 as a proxy for the class having already been
299 // Initialize()'d, and UnInitialize() before continuing. 306 // Initialize()'d, and UnInitialize() before continuing.
300 if (videos_.size()) { 307 if (videos_.size()) {
301 base::WaitableEvent done(false, false); 308 base::WaitableEvent done(false, false);
302 UnInitialize(&done); 309 UnInitialize(&done);
303 done.Wait(); 310 done.Wait();
304 } 311 }
305 312
313 #if defined(USE_OZONE)
314 base::CommandLine* command_line = base::CommandLine::ForCurrentProcess();
315 if (command_line->HasSwitch(switches::kOzoneUseSurfaceless))
316 gl_renderer_.reset(new SurfacelessGlRenderer(window_, screen_size_));
317 else
318 gl_renderer_.reset(new GlRenderer(window_, screen_size_));
319 #else
320 gl_renderer_.reset(new GlRenderer(window_, screen_size_));
321 #endif
322
323 CHECK(gl_renderer_->Initialize());
324
306 render_task_.Reset( 325 render_task_.Reset(
307 base::Bind(&RenderingHelper::RenderContent, base::Unretained(this))); 326 base::Bind(&RenderingHelper::RenderContent, base::Unretained(this)));
308 327
309 frame_duration_ = params.rendering_fps > 0 328 frame_duration_ = params.rendering_fps > 0
310 ? base::TimeDelta::FromSeconds(1) / params.rendering_fps 329 ? base::TimeDelta::FromSeconds(1) / params.rendering_fps
311 : base::TimeDelta(); 330 : base::TimeDelta();
312 331
313 render_as_thumbnails_ = params.render_as_thumbnails; 332 render_as_thumbnails_ = params.render_as_thumbnails;
314 message_loop_ = base::MessageLoop::current(); 333 message_loop_ = base::MessageLoop::current();
315 334
316 gl_surface_ = gfx::GLSurface::CreateViewGLSurface(window_); 335 CHECK(gl_renderer_->MakeCurrent());
317 screen_size_ = gl_surface_->GetSize();
318
319 gl_context_ = gfx::GLContext::CreateGLContext(
320 NULL, gl_surface_.get(), gfx::PreferIntegratedGpu);
321 CHECK(gl_context_->MakeCurrent(gl_surface_.get()));
322 336
323 CHECK_GT(params.window_sizes.size(), 0U); 337 CHECK_GT(params.window_sizes.size(), 0U);
324 videos_.resize(params.window_sizes.size()); 338 videos_.resize(params.window_sizes.size());
325 LayoutRenderingAreas(params.window_sizes); 339 LayoutRenderingAreas(params.window_sizes);
326 340
327 if (render_as_thumbnails_) { 341 if (render_as_thumbnails_) {
328 CHECK_EQ(videos_.size(), 1U); 342 CHECK_EQ(videos_.size(), 1U);
329 343
330 GLint max_texture_size; 344 GLint max_texture_size;
331 glGetIntegerv(GL_MAX_TEXTURE_SIZE, &max_texture_size); 345 glGetIntegerv(GL_MAX_TEXTURE_SIZE, &max_texture_size);
(...skipping 14 matching lines...) Expand all
346 0, 360 0,
347 GL_RGB, 361 GL_RGB,
348 GL_UNSIGNED_SHORT_5_6_5, 362 GL_UNSIGNED_SHORT_5_6_5,
349 NULL); 363 NULL);
350 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); 364 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
351 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); 365 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
352 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 366 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
353 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 367 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
354 glBindTexture(GL_TEXTURE_2D, 0); 368 glBindTexture(GL_TEXTURE_2D, 0);
355 369
356 glBindFramebufferEXT(GL_FRAMEBUFFER, thumbnails_fbo_id_); 370 gl_renderer_->BindFramebuffer(thumbnails_fbo_id_);
357 glFramebufferTexture2DEXT(GL_FRAMEBUFFER, 371 glFramebufferTexture2DEXT(GL_FRAMEBUFFER,
358 GL_COLOR_ATTACHMENT0, 372 GL_COLOR_ATTACHMENT0,
359 GL_TEXTURE_2D, 373 GL_TEXTURE_2D,
360 thumbnails_texture_id_, 374 thumbnails_texture_id_,
361 0); 375 0);
362 376
363 GLenum fb_status = glCheckFramebufferStatusEXT(GL_FRAMEBUFFER); 377 GLenum fb_status = glCheckFramebufferStatusEXT(GL_FRAMEBUFFER);
364 CHECK(fb_status == GL_FRAMEBUFFER_COMPLETE) << fb_status; 378 CHECK(fb_status == GL_FRAMEBUFFER_COMPLETE) << fb_status;
365 glClearColor(0.0f, 0.0f, 0.0f, 1.0f); 379 glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
366 glClear(GL_COLOR_BUFFER_BIT); 380 glClear(GL_COLOR_BUFFER_BIT);
367 glBindFramebufferEXT(GL_FRAMEBUFFER, 0); 381 gl_renderer_->UnbindFramebuffer();
368 } 382 }
369 383
370 // These vertices and texture coords. map (0,0) in the texture to the 384 // These vertices and texture coords. map (0,0) in the texture to the
371 // bottom left of the viewport. Since we get the video frames with the 385 // bottom left of the viewport. Since we get the video frames with the
372 // the top left at (0,0) we need to flip the texture y coordinate 386 // the top left at (0,0) we need to flip the texture y coordinate
373 // in the vertex shader for this to be rendered the right way up. 387 // in the vertex shader for this to be rendered the right way up.
374 // In the case of thumbnail rendering we use the same vertex shader 388 // In the case of thumbnail rendering we use the same vertex shader
375 // to render the FBO the screen, where we do not want this flipping. 389 // to render the FBO the screen, where we do not want this flipping.
376 static const float kVertices[] = 390 static const float kVertices[] =
377 { -1.f, 1.f, -1.f, -1.f, 1.f, 1.f, 1.f, -1.f, }; 391 { -1.f, 1.f, -1.f, -1.f, 1.f, 1.f, 1.f, -1.f, };
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after
424 int result = GL_FALSE; 438 int result = GL_FALSE;
425 glGetProgramiv(program_, GL_LINK_STATUS, &result); 439 glGetProgramiv(program_, GL_LINK_STATUS, &result);
426 if (!result) { 440 if (!result) {
427 char log[4096]; 441 char log[4096];
428 glGetShaderInfoLog(program_, arraysize(log), NULL, log); 442 glGetShaderInfoLog(program_, arraysize(log), NULL, log);
429 LOG(FATAL) << log; 443 LOG(FATAL) << log;
430 } 444 }
431 glUseProgram(program_); 445 glUseProgram(program_);
432 glDeleteProgram(program_); 446 glDeleteProgram(program_);
433 447
434 glUniform1i(glGetUniformLocation(program_, "tex_flip"), 0); 448 glUniform1i(glGetUniformLocation(program_, "tex_flip"),
449 gl_renderer_->IsFlipped() ? 0 : 1);
435 glUniform1i(glGetUniformLocation(program_, "tex"), 0); 450 glUniform1i(glGetUniformLocation(program_, "tex"), 0);
436 GLint tex_external = glGetUniformLocation(program_, "tex_external"); 451 GLint tex_external = glGetUniformLocation(program_, "tex_external");
437 if (tex_external != -1) { 452 if (tex_external != -1) {
438 glUniform1i(tex_external, 1); 453 glUniform1i(tex_external, 1);
439 } 454 }
440 int pos_location = glGetAttribLocation(program_, "in_pos"); 455 int pos_location = glGetAttribLocation(program_, "in_pos");
441 glEnableVertexAttribArray(pos_location); 456 glEnableVertexAttribArray(pos_location);
442 glVertexAttribPointer(pos_location, 2, GL_FLOAT, GL_FALSE, 0, kVertices); 457 glVertexAttribPointer(pos_location, 2, GL_FLOAT, GL_FALSE, 0, kVertices);
443 int tc_location = glGetAttribLocation(program_, "in_tc"); 458 int tc_location = glGetAttribLocation(program_, "in_tc");
444 glEnableVertexAttribArray(tc_location); 459 glEnableVertexAttribArray(tc_location);
(...skipping 10 matching lines...) Expand all
455 // test's last frames, so we set warm up iterations to 2, to clear 470 // test's last frames, so we set warm up iterations to 2, to clear
456 // the front and back buffers. 471 // the front and back buffers.
457 warm_up_iterations = std::max(2, warm_up_iterations); 472 warm_up_iterations = std::max(2, warm_up_iterations);
458 #endif 473 #endif
459 WarmUpRendering(warm_up_iterations); 474 WarmUpRendering(warm_up_iterations);
460 } 475 }
461 476
462 // It's safe to use Unretained here since |rendering_thread_| will be stopped 477 // It's safe to use Unretained here since |rendering_thread_| will be stopped
463 // in VideoDecodeAcceleratorTest.TearDown(), while the |rendering_helper_| is 478 // in VideoDecodeAcceleratorTest.TearDown(), while the |rendering_helper_| is
464 // a member of that class. (See video_decode_accelerator_unittest.cc.) 479 // a member of that class. (See video_decode_accelerator_unittest.cc.)
465 gfx::VSyncProvider* vsync_provider = gl_surface_->GetVSyncProvider(); 480 gfx::VSyncProvider* vsync_provider =
481 gl_renderer_->gl_surface()->GetVSyncProvider();
466 if (vsync_provider && frame_duration_ != base::TimeDelta()) 482 if (vsync_provider && frame_duration_ != base::TimeDelta())
467 vsync_provider->GetVSyncParameters(base::Bind( 483 vsync_provider->GetVSyncParameters(base::Bind(
468 &RenderingHelper::UpdateVSyncParameters, base::Unretained(this), done)); 484 &RenderingHelper::UpdateVSyncParameters, base::Unretained(this), done));
469 else 485 else
470 done->Signal(); 486 done->Signal();
471 } 487 }
472 488
473 // The rendering for the first few frames is slow (e.g., 100ms on Peach Pit). 489 // The rendering for the first few frames is slow (e.g., 100ms on Peach Pit).
474 // This affects the numbers measured in the performance test. We try to render 490 // This affects the numbers measured in the performance test. We try to render
475 // several frames here to warm up the rendering. 491 // several frames here to warm up the rendering.
476 void RenderingHelper::WarmUpRendering(int warm_up_iterations) { 492 void RenderingHelper::WarmUpRendering(int warm_up_iterations) {
477 unsigned int texture_id; 493 unsigned int texture_id;
478 scoped_ptr<GLubyte[]> emptyData(new GLubyte[screen_size_.GetArea() * 2]()); 494 scoped_ptr<GLubyte[]> emptyData(new GLubyte[screen_size_.GetArea() * 2]());
479 glGenTextures(1, &texture_id); 495 glGenTextures(1, &texture_id);
480 glBindTexture(GL_TEXTURE_2D, texture_id); 496 glBindTexture(GL_TEXTURE_2D, texture_id);
481 glTexImage2D(GL_TEXTURE_2D, 497 glTexImage2D(GL_TEXTURE_2D,
482 0, 498 0,
483 GL_RGB, 499 GL_RGB,
484 screen_size_.width(), 500 screen_size_.width(),
485 screen_size_.height(), 501 screen_size_.height(),
486 0, 502 0,
487 GL_RGB, 503 GL_RGB,
488 GL_UNSIGNED_SHORT_5_6_5, 504 GL_UNSIGNED_SHORT_5_6_5,
489 emptyData.get()); 505 emptyData.get());
490 for (int i = 0; i < warm_up_iterations; ++i) { 506 for (int i = 0; i < warm_up_iterations; ++i) {
491 RenderTexture(GL_TEXTURE_2D, texture_id); 507 RenderTexture(GL_TEXTURE_2D, texture_id);
492 gl_surface_->SwapBuffers(); 508 gl_renderer_->SwapBuffers();
493 } 509 }
494 glDeleteTextures(1, &texture_id); 510 glDeleteTextures(1, &texture_id);
495 } 511 }
496 512
497 void RenderingHelper::UnInitialize(base::WaitableEvent* done) { 513 void RenderingHelper::UnInitialize(base::WaitableEvent* done) {
498 CHECK_EQ(base::MessageLoop::current(), message_loop_); 514 CHECK_EQ(base::MessageLoop::current(), message_loop_);
499 515
500 render_task_.Cancel(); 516 render_task_.Cancel();
501 517
502 if (render_as_thumbnails_) { 518 if (render_as_thumbnails_) {
503 glDeleteTextures(1, &thumbnails_texture_id_); 519 glDeleteTextures(1, &thumbnails_texture_id_);
504 glDeleteFramebuffersEXT(1, &thumbnails_fbo_id_); 520 glDeleteFramebuffersEXT(1, &thumbnails_fbo_id_);
505 } 521 }
506 522
507 gl_context_->ReleaseCurrent(gl_surface_.get()); 523 Clear();
508 gl_context_ = NULL;
509 gl_surface_ = NULL;
510 524
511 Clear();
512 done->Signal(); 525 done->Signal();
513 } 526 }
514 527
515 void RenderingHelper::CreateTexture(uint32 texture_target, 528 void RenderingHelper::CreateTexture(uint32 texture_target,
516 uint32* texture_id, 529 uint32* texture_id,
517 const gfx::Size& size, 530 const gfx::Size& size,
518 base::WaitableEvent* done) { 531 base::WaitableEvent* done) {
519 if (base::MessageLoop::current() != message_loop_) { 532 if (base::MessageLoop::current() != message_loop_) {
520 message_loop_->PostTask(FROM_HERE, 533 message_loop_->PostTask(FROM_HERE,
521 base::Bind(&RenderingHelper::CreateTexture, 534 base::Bind(&RenderingHelper::CreateTexture,
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
560 const int width = thumbnail_size_.width(); 573 const int width = thumbnail_size_.width();
561 const int height = thumbnail_size_.height(); 574 const int height = thumbnail_size_.height();
562 const int thumbnails_in_row = thumbnails_fbo_size_.width() / width; 575 const int thumbnails_in_row = thumbnails_fbo_size_.width() / width;
563 const int thumbnails_in_column = thumbnails_fbo_size_.height() / height; 576 const int thumbnails_in_column = thumbnails_fbo_size_.height() / height;
564 const int row = (frame_count_ / thumbnails_in_row) % thumbnails_in_column; 577 const int row = (frame_count_ / thumbnails_in_row) % thumbnails_in_column;
565 const int col = frame_count_ % thumbnails_in_row; 578 const int col = frame_count_ % thumbnails_in_row;
566 579
567 gfx::Rect area(col * width, row * height, width, height); 580 gfx::Rect area(col * width, row * height, width, height);
568 581
569 glUniform1i(glGetUniformLocation(program_, "tex_flip"), 0); 582 glUniform1i(glGetUniformLocation(program_, "tex_flip"), 0);
570 glBindFramebufferEXT(GL_FRAMEBUFFER, thumbnails_fbo_id_); 583 gl_renderer_->BindFramebuffer(thumbnails_fbo_id_);
571 GLSetViewPort(area); 584 GLSetViewPort(area);
572 RenderTexture(texture_target, texture_id); 585 RenderTexture(texture_target, texture_id);
573 glBindFramebufferEXT(GL_FRAMEBUFFER, 0); 586 gl_renderer_->UnbindFramebuffer();
574 587
575 // Need to flush the GL commands before we return the tnumbnail texture to 588 // Need to flush the GL commands before we return the tnumbnail texture to
576 // the decoder. 589 // the decoder.
577 glFlush(); 590 glFlush();
578 ++frame_count_; 591 ++frame_count_;
579 } 592 }
580 593
581 void RenderingHelper::QueueVideoFrame( 594 void RenderingHelper::QueueVideoFrame(
582 size_t window_id, 595 size_t window_id,
583 scoped_refptr<VideoFrameTexture> video_frame) { 596 scoped_refptr<VideoFrameTexture> video_frame) {
(...skipping 29 matching lines...) Expand all
613 CHECK_EQ(static_cast<int>(glGetError()), GL_NO_ERROR); 626 CHECK_EQ(static_cast<int>(glGetError()), GL_NO_ERROR);
614 } 627 }
615 628
616 void RenderingHelper::DeleteTexture(uint32 texture_id) { 629 void RenderingHelper::DeleteTexture(uint32 texture_id) {
617 CHECK_EQ(base::MessageLoop::current(), message_loop_); 630 CHECK_EQ(base::MessageLoop::current(), message_loop_);
618 glDeleteTextures(1, &texture_id); 631 glDeleteTextures(1, &texture_id);
619 CHECK_EQ(static_cast<int>(glGetError()), GL_NO_ERROR); 632 CHECK_EQ(static_cast<int>(glGetError()), GL_NO_ERROR);
620 } 633 }
621 634
622 scoped_refptr<gfx::GLContext> RenderingHelper::GetGLContext() { 635 scoped_refptr<gfx::GLContext> RenderingHelper::GetGLContext() {
623 return gl_context_; 636 return gl_renderer_->gl_context();
624 } 637 }
625 638
626 void* RenderingHelper::GetGLContextHandle() { 639 void* RenderingHelper::GetGLContextHandle() {
627 return gl_context_->GetHandle(); 640 return gl_renderer_->gl_context()->GetHandle();
628 } 641 }
629 642
630 void* RenderingHelper::GetGLDisplay() { 643 void* RenderingHelper::GetGLDisplay() {
631 return gl_surface_->GetDisplay(); 644 return gl_renderer_->gl_surface()->GetDisplay();
632 } 645 }
633 646
634 void RenderingHelper::Clear() { 647 void RenderingHelper::Clear() {
635 videos_.clear(); 648 videos_.clear();
636 message_loop_ = NULL; 649 message_loop_ = NULL;
637 gl_context_ = NULL;
638 gl_surface_ = NULL;
639 650
640 render_as_thumbnails_ = false; 651 render_as_thumbnails_ = false;
641 frame_count_ = 0; 652 frame_count_ = 0;
642 thumbnails_fbo_id_ = 0; 653 thumbnails_fbo_id_ = 0;
643 thumbnails_texture_id_ = 0; 654 thumbnails_texture_id_ = 0;
655
656 gl_renderer_.reset();
644 } 657 }
645 658
646 void RenderingHelper::GetThumbnailsAsRGB(std::vector<unsigned char>* rgb, 659 void RenderingHelper::GetThumbnailsAsRGB(std::vector<unsigned char>* rgb,
647 bool* alpha_solid, 660 bool* alpha_solid,
648 base::WaitableEvent* done) { 661 base::WaitableEvent* done) {
649 CHECK(render_as_thumbnails_); 662 CHECK(render_as_thumbnails_);
650 663
651 const size_t num_pixels = thumbnails_fbo_size_.GetArea(); 664 const size_t num_pixels = thumbnails_fbo_size_.GetArea();
652 std::vector<unsigned char> rgba; 665 std::vector<unsigned char> rgba;
653 rgba.resize(num_pixels * 4); 666 rgba.resize(num_pixels * 4);
654 glBindFramebufferEXT(GL_FRAMEBUFFER, thumbnails_fbo_id_); 667 gl_renderer_->BindFramebuffer(thumbnails_fbo_id_);
655 glPixelStorei(GL_PACK_ALIGNMENT, 1); 668 glPixelStorei(GL_PACK_ALIGNMENT, 1);
656 // We can only count on GL_RGBA/GL_UNSIGNED_BYTE support. 669 // We can only count on GL_RGBA/GL_UNSIGNED_BYTE support.
657 glReadPixels(0, 670 glReadPixels(0,
658 0, 671 0,
659 thumbnails_fbo_size_.width(), 672 thumbnails_fbo_size_.width(),
660 thumbnails_fbo_size_.height(), 673 thumbnails_fbo_size_.height(),
661 GL_RGBA, 674 GL_RGBA,
662 GL_UNSIGNED_BYTE, 675 GL_UNSIGNED_BYTE,
663 &rgba[0]); 676 &rgba[0]);
664 glBindFramebufferEXT(GL_FRAMEBUFFER, 0); 677 gl_renderer_->UnbindFramebuffer();
665 rgb->resize(num_pixels * 3); 678 rgb->resize(num_pixels * 3);
666 // Drop the alpha channel, but check as we go that it is all 0xff. 679 // Drop the alpha channel, but check as we go that it is all 0xff.
667 bool solid = true; 680 bool solid = true;
668 unsigned char* rgb_ptr = &((*rgb)[0]); 681 unsigned char* rgb_ptr = &((*rgb)[0]);
669 unsigned char* rgba_ptr = &rgba[0]; 682 unsigned char* rgba_ptr = &rgba[0];
670 for (size_t i = 0; i < num_pixels; ++i) { 683 for (size_t i = 0; i < num_pixels; ++i) {
671 *rgb_ptr++ = *rgba_ptr++; 684 *rgb_ptr++ = *rgba_ptr++;
672 *rgb_ptr++ = *rgba_ptr++; 685 *rgb_ptr++ = *rgba_ptr++;
673 *rgb_ptr++ = *rgba_ptr++; 686 *rgb_ptr++ = *rgba_ptr++;
674 solid = solid && (*rgba_ptr == 0xff); 687 solid = solid && (*rgba_ptr == 0xff);
675 rgba_ptr++; 688 rgba_ptr++;
676 } 689 }
677 *alpha_solid = solid; 690 *alpha_solid = solid;
678 691
679 done->Signal(); 692 done->Signal();
680 } 693 }
681 694
682 void RenderingHelper::Flush(size_t window_id) { 695 void RenderingHelper::Flush(size_t window_id) {
683 videos_[window_id].is_flushing = true; 696 videos_[window_id].is_flushing = true;
684 } 697 }
685 698
686 void RenderingHelper::RenderContent() { 699 void RenderingHelper::RenderContent() {
687 CHECK_EQ(base::MessageLoop::current(), message_loop_); 700 CHECK_EQ(base::MessageLoop::current(), message_loop_);
688 701
689 // Update the VSync params. 702 // Update the VSync params.
690 // 703 //
691 // It's safe to use Unretained here since |rendering_thread_| will be stopped 704 // It's safe to use Unretained here since |rendering_thread_| will be stopped
692 // in VideoDecodeAcceleratorTest.TearDown(), while the |rendering_helper_| is 705 // in VideoDecodeAcceleratorTest.TearDown(), while the |rendering_helper_| is
693 // a member of that class. (See video_decode_accelerator_unittest.cc.) 706 // a member of that class. (See video_decode_accelerator_unittest.cc.)
694 gfx::VSyncProvider* vsync_provider = gl_surface_->GetVSyncProvider(); 707 gfx::VSyncProvider* vsync_provider =
708 gl_renderer_->gl_surface()->GetVSyncProvider();
695 if (vsync_provider) { 709 if (vsync_provider) {
696 vsync_provider->GetVSyncParameters(base::Bind( 710 vsync_provider->GetVSyncParameters(base::Bind(
697 &RenderingHelper::UpdateVSyncParameters, base::Unretained(this), 711 &RenderingHelper::UpdateVSyncParameters, base::Unretained(this),
698 static_cast<base::WaitableEvent*>(NULL))); 712 static_cast<base::WaitableEvent*>(NULL)));
699 } 713 }
700 714
701 glUniform1i(glGetUniformLocation(program_, "tex_flip"), 1); 715 glUniform1i(glGetUniformLocation(program_, "tex_flip"),
716 gl_renderer_->IsFlipped() ? 0 : 1);
702 717
703 // Frames that will be returned to the client (via the no_longer_needed_cb) 718 // Frames that will be returned to the client (via the no_longer_needed_cb)
704 // after this vector falls out of scope at the end of this method. We need 719 // after this vector falls out of scope at the end of this method. We need
705 // to keep references to them until after SwapBuffers() call below. 720 // to keep references to them until after SwapBuffers() call below.
706 std::vector<scoped_refptr<VideoFrameTexture> > frames_to_be_returned; 721 std::vector<scoped_refptr<VideoFrameTexture> > frames_to_be_returned;
707 bool need_swap_buffer = false; 722 bool need_swap_buffer = false;
708 if (render_as_thumbnails_) { 723 if (render_as_thumbnails_) {
709 // In render_as_thumbnails_ mode, we render the FBO content on the 724 // In render_as_thumbnails_ mode, we render the FBO content on the
710 // screen instead of the decoded textures. 725 // screen instead of the decoded textures.
711 GLSetViewPort(videos_[0].render_area); 726 GLSetViewPort(videos_[0].render_area);
(...skipping 11 matching lines...) Expand all
723 if (video.pending_frames.size() > 1 || video.is_flushing) { 738 if (video.pending_frames.size() > 1 || video.is_flushing) {
724 frames_to_be_returned.push_back(video.pending_frames.front()); 739 frames_to_be_returned.push_back(video.pending_frames.front());
725 video.pending_frames.pop(); 740 video.pending_frames.pop();
726 } else { 741 } else {
727 ++video.frames_to_drop; 742 ++video.frames_to_drop;
728 } 743 }
729 } 744 }
730 } 745 }
731 746
732 if (need_swap_buffer) 747 if (need_swap_buffer)
733 gl_surface_->SwapBuffers(); 748 gl_renderer_->SwapBuffers();
734 749
735 ScheduleNextRenderContent(); 750 ScheduleNextRenderContent();
736 } 751 }
737 752
738 // Helper function for the LayoutRenderingAreas(). The |lengths| are the 753 // Helper function for the LayoutRenderingAreas(). The |lengths| are the
739 // heights(widths) of the rows(columns). It scales the elements in 754 // heights(widths) of the rows(columns). It scales the elements in
740 // |lengths| proportionally so that the sum of them equal to |total_length|. 755 // |lengths| proportionally so that the sum of them equal to |total_length|.
741 // It also outputs the coordinates of the rows(columns) to |offsets|. 756 // It also outputs the coordinates of the rows(columns) to |offsets|.
742 static void ScaleAndCalculateOffsets(std::vector<int>* lengths, 757 static void ScaleAndCalculateOffsets(std::vector<int>* lengths,
743 std::vector<int>* offsets, 758 std::vector<int>* offsets,
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after
831 // When the rendering falls behind, drops frames. 846 // When the rendering falls behind, drops frames.
832 while (scheduled_render_time_ < target) { 847 while (scheduled_render_time_ < target) {
833 scheduled_render_time_ += frame_duration_; 848 scheduled_render_time_ += frame_duration_;
834 DropOneFrameForAllVideos(); 849 DropOneFrameForAllVideos();
835 } 850 }
836 851
837 message_loop_->PostDelayedTask( 852 message_loop_->PostDelayedTask(
838 FROM_HERE, render_task_.callback(), target - now); 853 FROM_HERE, render_task_.callback(), target - now);
839 } 854 }
840 } // namespace content 855 } // namespace content
OLDNEW
« no previous file with comments | « content/common/gpu/media/rendering_helper.h ('k') | content/common/gpu/media/surfaceless_gl_renderer.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698