Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2017 The Chromium Authors. All rights reserved. | 1 // Copyright 2017 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 "gpu/ipc/service/direct_composition_surface_win.h" | 5 #include "gpu/ipc/service/direct_composition_surface_win.h" |
| 6 | 6 |
| 7 #include <d3d11_1.h> | 7 #include <d3d11_1.h> |
| 8 #include <dcomptypes.h> | 8 #include <dcomptypes.h> |
| 9 | 9 |
| 10 #include <deque> | |
| 11 | |
| 10 #include "base/feature_list.h" | 12 #include "base/feature_list.h" |
| 11 #include "base/memory/ptr_util.h" | 13 #include "base/memory/ptr_util.h" |
| 12 #include "base/metrics/histogram_macros.h" | 14 #include "base/metrics/histogram_macros.h" |
| 13 #include "base/optional.h" | 15 #include "base/optional.h" |
| 14 #include "base/synchronization/waitable_event.h" | 16 #include "base/synchronization/waitable_event.h" |
| 15 #include "base/trace_event/trace_event.h" | 17 #include "base/trace_event/trace_event.h" |
| 16 #include "base/win/scoped_handle.h" | 18 #include "base/win/scoped_handle.h" |
| 17 #include "base/win/windows_version.h" | 19 #include "base/win/windows_version.h" |
| 18 #include "gpu/ipc/service/gpu_channel_manager.h" | 20 #include "gpu/ipc/service/gpu_channel_manager.h" |
| 19 #include "gpu/ipc/service/gpu_channel_manager_delegate.h" | 21 #include "gpu/ipc/service/gpu_channel_manager_delegate.h" |
| (...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 64 } | 66 } |
| 65 | 67 |
| 66 private: | 68 private: |
| 67 base::Optional<ui::ScopedMakeCurrent> make_current_; | 69 base::Optional<ui::ScopedMakeCurrent> make_current_; |
| 68 }; | 70 }; |
| 69 | 71 |
| 70 bool SizeContains(const gfx::Size& a, const gfx::Size& b) { | 72 bool SizeContains(const gfx::Size& a, const gfx::Size& b) { |
| 71 return gfx::Rect(a).Contains(gfx::Rect(b)); | 73 return gfx::Rect(a).Contains(gfx::Rect(b)); |
| 72 } | 74 } |
| 73 | 75 |
| 76 // This keeps track of whether the previous 30 frames used Overlays or GPU | |
| 77 // composition to present. | |
| 78 class PresentationHistory { | |
| 79 public: | |
| 80 static const int kPresentsToStore = 30; | |
| 81 | |
| 82 PresentationHistory() {} | |
| 83 | |
| 84 void AddSample(DXGI_FRAME_PRESENTATION_MODE mode) { | |
| 85 if (mode == DXGI_FRAME_PRESENTATION_MODE_COMPOSED) | |
| 86 composed_count_++; | |
| 87 | |
| 88 presents_.push_back(mode); | |
| 89 if (presents_.size() > kPresentsToStore) { | |
| 90 DXGI_FRAME_PRESENTATION_MODE first_mode = presents_.front(); | |
| 91 if (first_mode == DXGI_FRAME_PRESENTATION_MODE_COMPOSED) | |
| 92 composed_count_--; | |
| 93 presents_.pop_front(); | |
| 94 } | |
| 95 } | |
| 96 | |
| 97 bool valid() const { return presents_.size() >= kPresentsToStore; } | |
| 98 int composed_count() const { return composed_count_; } | |
| 99 | |
| 100 private: | |
| 101 std::deque<DXGI_FRAME_PRESENTATION_MODE> presents_; | |
| 102 int composed_count_ = 0; | |
| 103 | |
| 104 DISALLOW_COPY_AND_ASSIGN(PresentationHistory); | |
| 105 }; | |
| 106 | |
| 74 // Only one DirectComposition surface can be rendered into at a time. Track | 107 // Only one DirectComposition surface can be rendered into at a time. Track |
| 75 // here which IDCompositionSurface is being rendered into. If another context | 108 // here which IDCompositionSurface is being rendered into. If another context |
| 76 // is made current, then this surface will be suspended. | 109 // is made current, then this surface will be suspended. |
| 77 IDCompositionSurface* g_current_surface; | 110 IDCompositionSurface* g_current_surface; |
| 78 | 111 |
| 79 } // namespace | 112 } // namespace |
| 80 | 113 |
| 81 class DCLayerTree { | 114 class DCLayerTree { |
| 82 public: | 115 public: |
| 83 DCLayerTree(DirectCompositionSurfaceWin* surface, | 116 DCLayerTree(DirectCompositionSurfaceWin* surface, |
| (...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 171 return swap_chain_; | 204 return swap_chain_; |
| 172 } | 205 } |
| 173 | 206 |
| 174 private: | 207 private: |
| 175 using PFN_DCOMPOSITION_CREATE_SURFACE_HANDLE = | 208 using PFN_DCOMPOSITION_CREATE_SURFACE_HANDLE = |
| 176 HRESULT(WINAPI*)(DWORD, SECURITY_ATTRIBUTES*, HANDLE*); | 209 HRESULT(WINAPI*)(DWORD, SECURITY_ATTRIBUTES*, HANDLE*); |
| 177 | 210 |
| 178 // Returns true if the video processor changed. | 211 // Returns true if the video processor changed. |
| 179 bool InitializeVideoProcessor(const gfx::Size& in_size, | 212 bool InitializeVideoProcessor(const gfx::Size& in_size, |
| 180 const gfx::Size& out_size); | 213 const gfx::Size& out_size); |
| 181 void ReallocateSwapChain(); | 214 void ReallocateSwapChain(bool yuy2); |
| 215 bool ShouldBeYUY2(); | |
| 182 | 216 |
| 183 DCLayerTree* surface_; | 217 DCLayerTree* surface_; |
| 184 PFN_DCOMPOSITION_CREATE_SURFACE_HANDLE create_surface_handle_function_; | 218 PFN_DCOMPOSITION_CREATE_SURFACE_HANDLE create_surface_handle_function_; |
| 185 | 219 |
| 186 gfx::Size swap_chain_size_; | 220 gfx::Size swap_chain_size_; |
| 187 gfx::Size processor_input_size_; | 221 gfx::Size processor_input_size_; |
| 188 gfx::Size processor_output_size_; | 222 gfx::Size processor_output_size_; |
| 189 bool is_yuy2_swapchain_ = false; | 223 bool is_yuy2_swapchain_ = false; |
| 190 | 224 |
| 191 // This is the scale from the swapchain size to the size of the contents | 225 // This is the scale from the swapchain size to the size of the contents |
| 192 // onscreen. | 226 // onscreen. |
| 193 float swap_chain_scale_x_ = 0.0f; | 227 float swap_chain_scale_x_ = 0.0f; |
| 194 float swap_chain_scale_y_ = 0.0f; | 228 float swap_chain_scale_y_ = 0.0f; |
| 195 | 229 |
| 230 PresentationHistory history_; | |
|
sunnyps
2017/04/11 23:19:29
nit: presentation_history_
| |
| 231 bool failed_to_create_yuy2_swapchain_ = false; | |
| 232 int frames_since_color_space_change_ = 0; | |
| 233 | |
| 196 // This is the GLImage that was presented in the last frame. | 234 // This is the GLImage that was presented in the last frame. |
| 197 scoped_refptr<gl::GLImageDXGI> last_gl_image_; | 235 scoped_refptr<gl::GLImageDXGI> last_gl_image_; |
| 198 | 236 |
| 199 base::win::ScopedComPtr<ID3D11Device> d3d11_device_; | 237 base::win::ScopedComPtr<ID3D11Device> d3d11_device_; |
| 200 base::win::ScopedComPtr<IDXGISwapChain1> swap_chain_; | 238 base::win::ScopedComPtr<IDXGISwapChain1> swap_chain_; |
| 201 base::win::ScopedComPtr<ID3D11VideoProcessorOutputView> out_view_; | 239 base::win::ScopedComPtr<ID3D11VideoProcessorOutputView> out_view_; |
| 202 base::win::ScopedComPtr<ID3D11VideoProcessor> video_processor_; | 240 base::win::ScopedComPtr<ID3D11VideoProcessor> video_processor_; |
| 203 base::win::ScopedComPtr<ID3D11VideoProcessorEnumerator> | 241 base::win::ScopedComPtr<ID3D11VideoProcessorEnumerator> |
| 204 video_processor_enumerator_; | 242 video_processor_enumerator_; |
| 205 base::win::ScopedComPtr<ID3D11VideoDevice> video_device_; | 243 base::win::ScopedComPtr<ID3D11VideoDevice> video_device_; |
| (...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 280 HMODULE dcomp = ::GetModuleHandleA("dcomp.dll"); | 318 HMODULE dcomp = ::GetModuleHandleA("dcomp.dll"); |
| 281 CHECK(dcomp); | 319 CHECK(dcomp); |
| 282 create_surface_handle_function_ = | 320 create_surface_handle_function_ = |
| 283 reinterpret_cast<PFN_DCOMPOSITION_CREATE_SURFACE_HANDLE>( | 321 reinterpret_cast<PFN_DCOMPOSITION_CREATE_SURFACE_HANDLE>( |
| 284 GetProcAddress(dcomp, "DCompositionCreateSurfaceHandle")); | 322 GetProcAddress(dcomp, "DCompositionCreateSurfaceHandle")); |
| 285 CHECK(create_surface_handle_function_); | 323 CHECK(create_surface_handle_function_); |
| 286 } | 324 } |
| 287 | 325 |
| 288 DCLayerTree::SwapChainPresenter::~SwapChainPresenter() {} | 326 DCLayerTree::SwapChainPresenter::~SwapChainPresenter() {} |
| 289 | 327 |
| 328 bool DCLayerTree::SwapChainPresenter::ShouldBeYUY2() { | |
| 329 // Start out as YUY2. | |
| 330 if (!history_.valid()) | |
| 331 return true; | |
| 332 int composition_count = history_.composed_count(); | |
| 333 | |
| 334 // It's more efficient to use a BGRA backbuffer instead of YUY2 if overlays | |
| 335 // aren't being used, as otherwise DWM will use the video processor a second | |
| 336 // time to convert it to BGRA before displaying it on screen. | |
| 337 | |
| 338 if (is_yuy2_swapchain_) { | |
| 339 // Switch to BGRA once 3/4 of presents are composed. | |
| 340 return composition_count < (PresentationHistory::kPresentsToStore * 3 / 4); | |
| 341 } else { | |
| 342 // Switch to YUY2 once 3/4 are using overlays (or unknown). | |
| 343 return composition_count < (PresentationHistory::kPresentsToStore / 4); | |
| 344 } | |
| 345 } | |
| 346 | |
| 290 void DCLayerTree::SwapChainPresenter::PresentToSwapChain( | 347 void DCLayerTree::SwapChainPresenter::PresentToSwapChain( |
| 291 const ui::DCRendererLayerParams& params) { | 348 const ui::DCRendererLayerParams& params) { |
| 292 gl::GLImageDXGI* image_dxgi = | 349 gl::GLImageDXGI* image_dxgi = |
| 293 gl::GLImageDXGI::FromGLImage(params.image.get()); | 350 gl::GLImageDXGI::FromGLImage(params.image.get()); |
| 294 DCHECK(image_dxgi); | 351 DCHECK(image_dxgi); |
| 295 | 352 |
| 296 // Swap chain size is the minimum of the on-screen size and the source | 353 // Swap chain size is the minimum of the on-screen size and the source |
| 297 // size so the video processor can do the minimal amount of work and | 354 // size so the video processor can do the minimal amount of work and |
| 298 // the overlay has to read the minimal amount of data. | 355 // the overlay has to read the minimal amount of data. |
| 299 // DWM is also less likely to promote a surface to an overlay if it's | 356 // DWM is also less likely to promote a surface to an overlay if it's |
| 300 // much larger than its area on-screen. | 357 // much larger than its area on-screen. |
| 301 gfx::Rect bounds_rect = params.rect; | 358 gfx::Rect bounds_rect = params.rect; |
| 302 gfx::Size ceiled_input_size = gfx::ToCeiledSize(params.contents_rect.size()); | 359 gfx::Size ceiled_input_size = gfx::ToCeiledSize(params.contents_rect.size()); |
| 303 gfx::Size swap_chain_size = bounds_rect.size(); | 360 gfx::Size swap_chain_size = bounds_rect.size(); |
| 304 swap_chain_size.SetToMin(ceiled_input_size); | 361 swap_chain_size.SetToMin(ceiled_input_size); |
| 305 | 362 |
| 306 // YUY2 surfaces must have an even width. | 363 // YUY2 surfaces must have an even width. |
| 307 if (swap_chain_size.width() % 2 == 1) | 364 if (swap_chain_size.width() % 2 == 1) |
| 308 swap_chain_size.set_width(swap_chain_size.width() + 1); | 365 swap_chain_size.set_width(swap_chain_size.width() + 1); |
| 309 | 366 |
| 310 InitializeVideoProcessor(ceiled_input_size, swap_chain_size); | 367 InitializeVideoProcessor(ceiled_input_size, swap_chain_size); |
| 311 | 368 |
| 369 bool yuy2_swapchain = ShouldBeYUY2(); | |
| 312 bool first_present = false; | 370 bool first_present = false; |
| 313 if (!swap_chain_ || swap_chain_size_ != swap_chain_size) { | 371 if (!swap_chain_ || swap_chain_size_ != swap_chain_size || |
| 372 ((yuy2_swapchain != is_yuy2_swapchain_) && | |
| 373 !failed_to_create_yuy2_swapchain_)) { | |
| 314 first_present = true; | 374 first_present = true; |
| 315 swap_chain_size_ = swap_chain_size; | 375 swap_chain_size_ = swap_chain_size; |
| 316 swap_chain_.Reset(); | 376 swap_chain_.Reset(); |
| 317 ReallocateSwapChain(); | 377 ReallocateSwapChain(yuy2_swapchain); |
| 318 } else if (last_gl_image_ == image_dxgi) { | 378 } else if (last_gl_image_ == image_dxgi) { |
| 319 // The swap chain is presenting the same image as last swap, which means | 379 // The swap chain is presenting the same image as last swap, which means |
| 320 // that the image was never returned to the video decoder and should have | 380 // that the image was never returned to the video decoder and should have |
| 321 // the same contents as last time. It shouldn't need to be redrawn. | 381 // the same contents as last time. It shouldn't need to be redrawn. |
| 322 return; | 382 return; |
| 323 } | 383 } |
| 324 | 384 |
| 325 last_gl_image_ = image_dxgi; | 385 last_gl_image_ = image_dxgi; |
| 326 | 386 |
| 327 if (!out_view_) { | 387 if (!out_view_) { |
| (...skipping 78 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 406 hr = video_context_->VideoProcessorBlt(video_processor_.get(), | 466 hr = video_context_->VideoProcessorBlt(video_processor_.get(), |
| 407 out_view_.get(), 0, 1, &stream); | 467 out_view_.get(), 0, 1, &stream); |
| 408 CHECK(SUCCEEDED(hr)); | 468 CHECK(SUCCEEDED(hr)); |
| 409 } | 469 } |
| 410 | 470 |
| 411 swap_chain_scale_x_ = bounds_rect.width() * 1.0f / swap_chain_size.width(); | 471 swap_chain_scale_x_ = bounds_rect.width() * 1.0f / swap_chain_size.width(); |
| 412 swap_chain_scale_y_ = bounds_rect.height() * 1.0f / swap_chain_size.height(); | 472 swap_chain_scale_y_ = bounds_rect.height() * 1.0f / swap_chain_size.height(); |
| 413 | 473 |
| 414 swap_chain_->Present(first_present ? 0 : 1, 0); | 474 swap_chain_->Present(first_present ? 0 : 1, 0); |
| 415 | 475 |
| 476 frames_since_color_space_change_++; | |
| 477 | |
| 416 base::win::ScopedComPtr<IDXGISwapChainMedia> swap_chain_media; | 478 base::win::ScopedComPtr<IDXGISwapChainMedia> swap_chain_media; |
| 417 if (SUCCEEDED(swap_chain_.QueryInterface(swap_chain_media.Receive()))) { | 479 if (SUCCEEDED(swap_chain_.QueryInterface(swap_chain_media.Receive()))) { |
| 418 DXGI_FRAME_STATISTICS_MEDIA stats = {}; | 480 DXGI_FRAME_STATISTICS_MEDIA stats = {}; |
| 419 if (SUCCEEDED(swap_chain_media->GetFrameStatisticsMedia(&stats))) { | 481 if (SUCCEEDED(swap_chain_media->GetFrameStatisticsMedia(&stats))) { |
| 420 UMA_HISTOGRAM_SPARSE_SLOWLY("GPU.DirectComposition.CompositionMode", | 482 UMA_HISTOGRAM_SPARSE_SLOWLY("GPU.DirectComposition.CompositionMode", |
| 421 stats.CompositionMode); | 483 stats.CompositionMode); |
| 484 history_.AddSample(stats.CompositionMode); | |
| 422 } | 485 } |
| 423 } | 486 } |
| 424 } | 487 } |
| 425 | 488 |
| 426 bool DCLayerTree::SwapChainPresenter::InitializeVideoProcessor( | 489 bool DCLayerTree::SwapChainPresenter::InitializeVideoProcessor( |
| 427 const gfx::Size& in_size, | 490 const gfx::Size& in_size, |
| 428 const gfx::Size& out_size) { | 491 const gfx::Size& out_size) { |
| 429 if (video_processor_ && SizeContains(processor_input_size_, in_size) && | 492 if (video_processor_ && SizeContains(processor_input_size_, in_size) && |
| 430 SizeContains(processor_output_size_, out_size)) | 493 SizeContains(processor_output_size_, out_size)) |
| 431 return false; | 494 return false; |
| 432 processor_input_size_ = in_size; | 495 processor_input_size_ = in_size; |
| 433 processor_output_size_ = out_size; | 496 processor_output_size_ = out_size; |
| 434 surface_->InitializeVideoProcessor(in_size, out_size); | 497 surface_->InitializeVideoProcessor(in_size, out_size); |
| 435 | 498 |
| 436 video_processor_enumerator_ = surface_->video_processor_enumerator(); | 499 video_processor_enumerator_ = surface_->video_processor_enumerator(); |
| 437 video_processor_ = surface_->video_processor(); | 500 video_processor_ = surface_->video_processor(); |
| 438 // out_view_ depends on video_processor_enumerator_, so ensure it's | 501 // out_view_ depends on video_processor_enumerator_, so ensure it's |
| 439 // recreated if the enumerator is. | 502 // recreated if the enumerator is. |
| 440 out_view_.Reset(); | 503 out_view_.Reset(); |
| 441 return true; | 504 return true; |
| 442 } | 505 } |
| 443 | 506 |
| 444 void DCLayerTree::SwapChainPresenter::ReallocateSwapChain() { | 507 void DCLayerTree::SwapChainPresenter::ReallocateSwapChain(bool yuy2) { |
| 445 TRACE_EVENT0("gpu", "DCLayerTree::SwapChainPresenter::ReallocateSwapChain"); | 508 TRACE_EVENT0("gpu", "DCLayerTree::SwapChainPresenter::ReallocateSwapChain"); |
| 446 DCHECK(!swap_chain_); | 509 DCHECK(!swap_chain_); |
| 447 | 510 |
| 448 base::win::ScopedComPtr<IDXGIDevice> dxgi_device; | 511 base::win::ScopedComPtr<IDXGIDevice> dxgi_device; |
| 449 d3d11_device_.QueryInterface(dxgi_device.Receive()); | 512 d3d11_device_.QueryInterface(dxgi_device.Receive()); |
| 450 base::win::ScopedComPtr<IDXGIAdapter> dxgi_adapter; | 513 base::win::ScopedComPtr<IDXGIAdapter> dxgi_adapter; |
| 451 dxgi_device->GetAdapter(dxgi_adapter.Receive()); | 514 dxgi_device->GetAdapter(dxgi_adapter.Receive()); |
| 452 base::win::ScopedComPtr<IDXGIFactory2> dxgi_factory; | 515 base::win::ScopedComPtr<IDXGIFactory2> dxgi_factory; |
| 453 dxgi_adapter->GetParent(IID_PPV_ARGS(dxgi_factory.Receive())); | 516 dxgi_adapter->GetParent(IID_PPV_ARGS(dxgi_factory.Receive())); |
| 454 | 517 |
| (...skipping 11 matching lines...) Expand all Loading... | |
| 466 desc.SwapEffect = DXGI_SWAP_EFFECT_FLIP_SEQUENTIAL; | 529 desc.SwapEffect = DXGI_SWAP_EFFECT_FLIP_SEQUENTIAL; |
| 467 desc.AlphaMode = DXGI_ALPHA_MODE_IGNORE; | 530 desc.AlphaMode = DXGI_ALPHA_MODE_IGNORE; |
| 468 desc.Flags = | 531 desc.Flags = |
| 469 DXGI_SWAP_CHAIN_FLAG_YUV_VIDEO | DXGI_SWAP_CHAIN_FLAG_FULLSCREEN_VIDEO; | 532 DXGI_SWAP_CHAIN_FLAG_YUV_VIDEO | DXGI_SWAP_CHAIN_FLAG_FULLSCREEN_VIDEO; |
| 470 | 533 |
| 471 HANDLE handle; | 534 HANDLE handle; |
| 472 create_surface_handle_function_(COMPOSITIONOBJECT_ALL_ACCESS, nullptr, | 535 create_surface_handle_function_(COMPOSITIONOBJECT_ALL_ACCESS, nullptr, |
| 473 &handle); | 536 &handle); |
| 474 swap_chain_handle_.Set(handle); | 537 swap_chain_handle_.Set(handle); |
| 475 | 538 |
| 539 if (is_yuy2_swapchain_ != yuy2) { | |
| 540 UMA_HISTOGRAM_COUNTS_1000( | |
| 541 "GPU.DirectComposition.FramesSinceColorSpaceChange", | |
| 542 frames_since_color_space_change_); | |
| 543 } | |
| 544 | |
| 545 frames_since_color_space_change_ = 0; | |
| 546 | |
| 476 is_yuy2_swapchain_ = true; | 547 is_yuy2_swapchain_ = true; |
| 477 // The composition surface handle isn't actually used, but | 548 // The composition surface handle isn't actually used, but |
| 478 // CreateSwapChainForComposition can't create YUY2 swapchains. | 549 // CreateSwapChainForComposition can't create YUY2 swapchains. |
| 479 HRESULT hr = media_factory->CreateSwapChainForCompositionSurfaceHandle( | 550 HRESULT hr = E_FAIL; |
|
sunnyps
2017/04/11 23:19:30
nit: can you rewrite to something like this:
is_y
| |
| 480 d3d11_device_.get(), swap_chain_handle_.Get(), &desc, nullptr, | 551 if (yuy2) { |
| 481 swap_chain_.Receive()); | 552 hr = media_factory->CreateSwapChainForCompositionSurfaceHandle( |
| 553 d3d11_device_.get(), swap_chain_handle_.Get(), &desc, nullptr, | |
| 554 swap_chain_.Receive()); | |
| 555 failed_to_create_yuy2_swapchain_ = FAILED(hr); | |
| 556 } | |
| 482 | 557 |
| 483 if (FAILED(hr)) { | 558 if (FAILED(hr)) { |
| 484 // This should not be hit in production but is a simple fallback for | 559 // This should not be hit in production but is a simple fallback for |
|
sunnyps
2017/04/11 23:19:30
nit: This comment needs to be updated.
| |
| 485 // testing on systems without YUY2 swapchain support. | 560 // testing on systems without YUY2 swapchain support. |
| 486 DLOG(ERROR) << "YUY2 creation failed with " << std::hex << hr | 561 DLOG(ERROR) << "YUY2 creation failed with " << std::hex << hr |
| 487 << ". Falling back to BGRA"; | 562 << ". Falling back to BGRA"; |
| 488 is_yuy2_swapchain_ = false; | 563 is_yuy2_swapchain_ = false; |
| 489 desc.Format = DXGI_FORMAT_B8G8R8A8_UNORM; | 564 desc.Format = DXGI_FORMAT_B8G8R8A8_UNORM; |
| 490 desc.Flags = 0; | 565 desc.Flags = 0; |
| 491 hr = media_factory->CreateSwapChainForCompositionSurfaceHandle( | 566 hr = media_factory->CreateSwapChainForCompositionSurfaceHandle( |
| 492 d3d11_device_.get(), swap_chain_handle_.Get(), &desc, nullptr, | 567 d3d11_device_.get(), swap_chain_handle_.Get(), &desc, nullptr, |
| 493 swap_chain_.Receive()); | 568 swap_chain_.Receive()); |
| 494 CHECK(SUCCEEDED(hr)); | 569 CHECK(SUCCEEDED(hr)); |
| (...skipping 567 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1062 DirectCompositionSurfaceWin::GetWindowTaskRunnerForTesting() { | 1137 DirectCompositionSurfaceWin::GetWindowTaskRunnerForTesting() { |
| 1063 return child_window_.GetTaskRunnerForTesting(); | 1138 return child_window_.GetTaskRunnerForTesting(); |
| 1064 } | 1139 } |
| 1065 | 1140 |
| 1066 base::win::ScopedComPtr<IDXGISwapChain1> | 1141 base::win::ScopedComPtr<IDXGISwapChain1> |
| 1067 DirectCompositionSurfaceWin::GetLayerSwapChainForTesting(size_t index) const { | 1142 DirectCompositionSurfaceWin::GetLayerSwapChainForTesting(size_t index) const { |
| 1068 return layer_tree_->GetLayerSwapChainForTesting(index); | 1143 return layer_tree_->GetLayerSwapChainForTesting(index); |
| 1069 } | 1144 } |
| 1070 | 1145 |
| 1071 } // namespace gpu | 1146 } // namespace gpu |
| OLD | NEW |