| OLD | NEW |
| 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 "cc/resources/video_resource_updater.h" | 5 #include "cc/resources/video_resource_updater.h" |
| 6 | 6 |
| 7 #include <stddef.h> | 7 #include <stddef.h> |
| 8 #include <stdint.h> | 8 #include <stdint.h> |
| 9 | 9 |
| 10 #include <algorithm> | 10 #include <algorithm> |
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 60 switch (video_frame->mailbox_holder(0).texture_target) { | 60 switch (video_frame->mailbox_holder(0).texture_target) { |
| 61 case GL_TEXTURE_EXTERNAL_OES: | 61 case GL_TEXTURE_EXTERNAL_OES: |
| 62 return VideoFrameExternalResources::YUV_RESOURCE; | 62 return VideoFrameExternalResources::YUV_RESOURCE; |
| 63 case GL_TEXTURE_RECTANGLE_ARB: | 63 case GL_TEXTURE_RECTANGLE_ARB: |
| 64 return VideoFrameExternalResources::RGB_RESOURCE; | 64 return VideoFrameExternalResources::RGB_RESOURCE; |
| 65 default: | 65 default: |
| 66 NOTREACHED(); | 66 NOTREACHED(); |
| 67 break; | 67 break; |
| 68 } | 68 } |
| 69 break; | 69 break; |
| 70 case media::PIXEL_FORMAT_Y8: |
| 71 case media::PIXEL_FORMAT_Y16: |
| 72 return VideoFrameExternalResources::Y_RESOURCE; |
| 73 break; |
| 70 case media::PIXEL_FORMAT_YV12: | 74 case media::PIXEL_FORMAT_YV12: |
| 71 case media::PIXEL_FORMAT_YV16: | 75 case media::PIXEL_FORMAT_YV16: |
| 72 case media::PIXEL_FORMAT_YV24: | 76 case media::PIXEL_FORMAT_YV24: |
| 73 case media::PIXEL_FORMAT_YV12A: | 77 case media::PIXEL_FORMAT_YV12A: |
| 74 case media::PIXEL_FORMAT_NV21: | 78 case media::PIXEL_FORMAT_NV21: |
| 75 case media::PIXEL_FORMAT_YUY2: | 79 case media::PIXEL_FORMAT_YUY2: |
| 76 case media::PIXEL_FORMAT_RGB24: | 80 case media::PIXEL_FORMAT_RGB24: |
| 77 case media::PIXEL_FORMAT_RGB32: | 81 case media::PIXEL_FORMAT_RGB32: |
| 78 case media::PIXEL_FORMAT_MJPEG: | 82 case media::PIXEL_FORMAT_MJPEG: |
| 79 case media::PIXEL_FORMAT_MT21: | 83 case media::PIXEL_FORMAT_MT21: |
| (...skipping 182 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 262 case media::PIXEL_FORMAT_NV12: | 266 case media::PIXEL_FORMAT_NV12: |
| 263 case media::PIXEL_FORMAT_NV21: | 267 case media::PIXEL_FORMAT_NV21: |
| 264 case media::PIXEL_FORMAT_UYVY: | 268 case media::PIXEL_FORMAT_UYVY: |
| 265 case media::PIXEL_FORMAT_YUY2: | 269 case media::PIXEL_FORMAT_YUY2: |
| 266 case media::PIXEL_FORMAT_ARGB: | 270 case media::PIXEL_FORMAT_ARGB: |
| 267 case media::PIXEL_FORMAT_XRGB: | 271 case media::PIXEL_FORMAT_XRGB: |
| 268 case media::PIXEL_FORMAT_RGB24: | 272 case media::PIXEL_FORMAT_RGB24: |
| 269 case media::PIXEL_FORMAT_RGB32: | 273 case media::PIXEL_FORMAT_RGB32: |
| 270 case media::PIXEL_FORMAT_MJPEG: | 274 case media::PIXEL_FORMAT_MJPEG: |
| 271 case media::PIXEL_FORMAT_MT21: | 275 case media::PIXEL_FORMAT_MT21: |
| 276 case media::PIXEL_FORMAT_Y8: |
| 272 bits_per_channel = 8; | 277 bits_per_channel = 8; |
| 273 break; | 278 break; |
| 274 case media::PIXEL_FORMAT_YUV420P9: | 279 case media::PIXEL_FORMAT_YUV420P9: |
| 275 case media::PIXEL_FORMAT_YUV422P9: | 280 case media::PIXEL_FORMAT_YUV422P9: |
| 276 case media::PIXEL_FORMAT_YUV444P9: | 281 case media::PIXEL_FORMAT_YUV444P9: |
| 277 bits_per_channel = 9; | 282 bits_per_channel = 9; |
| 278 break; | 283 break; |
| 279 case media::PIXEL_FORMAT_YUV420P10: | 284 case media::PIXEL_FORMAT_YUV420P10: |
| 280 case media::PIXEL_FORMAT_YUV422P10: | 285 case media::PIXEL_FORMAT_YUV422P10: |
| 281 case media::PIXEL_FORMAT_YUV444P10: | 286 case media::PIXEL_FORMAT_YUV444P10: |
| 282 bits_per_channel = 10; | 287 bits_per_channel = 10; |
| 283 break; | 288 break; |
| 289 case media::PIXEL_FORMAT_Y16: |
| 290 bits_per_channel = 16; |
| 291 break; |
| 284 } | 292 } |
| 285 | 293 |
| 286 // Only YUV software video frames are supported. | 294 // Only YUV, Y8 and Y16 software video frames are supported. |
| 287 if (!media::IsYuvPlanar(input_frame_format)) { | 295 const bool isYuvPlanar = media::IsYuvPlanar(input_frame_format); |
| 296 if (!(isYuvPlanar || input_frame_format == media::PIXEL_FORMAT_Y16 || |
| 297 input_frame_format == media::PIXEL_FORMAT_Y8)) { |
| 288 NOTREACHED() << media::VideoPixelFormatToString(input_frame_format); | 298 NOTREACHED() << media::VideoPixelFormatToString(input_frame_format); |
| 289 return VideoFrameExternalResources(); | 299 return VideoFrameExternalResources(); |
| 290 } | 300 } |
| 291 | 301 |
| 292 const bool software_compositor = context_provider_ == NULL; | 302 const bool software_compositor = context_provider_ == NULL; |
| 293 | 303 |
| 304 if ((input_frame_format == media::PIXEL_FORMAT_Y8 || |
| 305 input_frame_format == media::PIXEL_FORMAT_Y16) && |
| 306 software_compositor) { |
| 307 // TODO(astojilj) Y8 and Y16 software compositor support. |
| 308 NOTREACHED() << "Software compositor doesn't support PIXEL_FORMAT_Y8/Y16"; |
| 309 return VideoFrameExternalResources(); |
| 310 } |
| 311 |
| 294 ResourceFormat output_resource_format = | 312 ResourceFormat output_resource_format = |
| 295 resource_provider_->YuvResourceFormat(bits_per_channel); | 313 (input_frame_format == media::PIXEL_FORMAT_Y16) |
| 314 ? resource_provider_->Y16ResourceFormat(bits_per_channel) |
| 315 : resource_provider_->YuvResourceFormat(bits_per_channel); |
| 296 | 316 |
| 297 size_t output_plane_count = media::VideoFrame::NumPlanes(input_frame_format); | 317 size_t output_plane_count = media::VideoFrame::NumPlanes(input_frame_format); |
| 298 | 318 |
| 299 // TODO(skaslev): If we're in software compositing mode, we do the YUV -> RGB | 319 // TODO(skaslev): If we're in software compositing mode, we do the YUV -> RGB |
| 300 // conversion here. That involves an extra copy of each frame to a bitmap. | 320 // conversion here. That involves an extra copy of each frame to a bitmap. |
| 301 // Obviously, this is suboptimal and should be addressed once ubercompositor | 321 // Obviously, this is suboptimal and should be addressed once ubercompositor |
| 302 // starts shaping up. | 322 // starts shaping up. |
| 303 if (software_compositor) { | 323 if (software_compositor) { |
| 304 output_resource_format = kRGBResourceFormat; | 324 output_resource_format = kRGBResourceFormat; |
| 305 output_plane_count = 1; | 325 output_plane_count = 1; |
| (...skipping 122 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 428 | 448 |
| 429 bool needs_conversion = false; | 449 bool needs_conversion = false; |
| 430 int shift = 0; | 450 int shift = 0; |
| 431 | 451 |
| 432 // LUMINANCE_F16 uses half-floats, so we always need a conversion step. | 452 // LUMINANCE_F16 uses half-floats, so we always need a conversion step. |
| 433 if (plane_resource.resource_format() == LUMINANCE_F16) { | 453 if (plane_resource.resource_format() == LUMINANCE_F16) { |
| 434 needs_conversion = true; | 454 needs_conversion = true; |
| 435 // Note that the current method of converting integers to half-floats | 455 // Note that the current method of converting integers to half-floats |
| 436 // stops working if you have more than 10 bits of data. | 456 // stops working if you have more than 10 bits of data. |
| 437 DCHECK_LE(bits_per_channel, 10); | 457 DCHECK_LE(bits_per_channel, 10); |
| 458 } else if (plane_resource.resource_format() == RG_88) { |
| 459 DCHECK_EQ(bits_per_channel, 16); |
| 438 } else if (bits_per_channel > 8) { | 460 } else if (bits_per_channel > 8) { |
| 439 // If bits_per_channel > 8 and we can't use LUMINANCE_F16, we need to | 461 // If bits_per_channel > 8 and we can't use LUMINANCE_F16, we need to |
| 440 // shift the data down and create an 8-bit texture. | 462 // shift the data down and create an 8-bit texture. |
| 441 needs_conversion = true; | 463 needs_conversion = true; |
| 442 shift = bits_per_channel - 8; | 464 shift = bits_per_channel - 8; |
| 443 } | 465 } |
| 444 const uint8_t* pixels; | 466 const uint8_t* pixels; |
| 445 if (static_cast<int>(upload_image_stride) == video_stride_bytes && | 467 if (static_cast<int>(upload_image_stride) == video_stride_bytes && |
| 446 !needs_conversion) { | 468 !needs_conversion) { |
| 447 pixels = video_frame->data(i); | 469 pixels = video_frame->data(i); |
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 484 } | 506 } |
| 485 pixels = &upload_pixels_[0]; | 507 pixels = &upload_pixels_[0]; |
| 486 } | 508 } |
| 487 | 509 |
| 488 resource_provider_->CopyToResource(plane_resource.resource_id(), pixels, | 510 resource_provider_->CopyToResource(plane_resource.resource_id(), pixels, |
| 489 resource_size_pixels); | 511 resource_size_pixels); |
| 490 plane_resource.SetUniqueId(video_frame->unique_id(), i); | 512 plane_resource.SetUniqueId(video_frame->unique_id(), i); |
| 491 } | 513 } |
| 492 | 514 |
| 493 if (plane_resource.resource_format() == LUMINANCE_F16) { | 515 if (plane_resource.resource_format() == LUMINANCE_F16) { |
| 516 DCHECK(isYuvPlanar); |
| 494 // By OR-ing with 0x3800, 10-bit numbers become half-floats in the | 517 // By OR-ing with 0x3800, 10-bit numbers become half-floats in the |
| 495 // range [0.5..1) and 9-bit numbers get the range [0.5..0.75). | 518 // range [0.5..1) and 9-bit numbers get the range [0.5..0.75). |
| 496 // | 519 // |
| 497 // Half-floats are evaluated as: | 520 // Half-floats are evaluated as: |
| 498 // float value = pow(2.0, exponent - 25) * (0x400 + fraction); | 521 // float value = pow(2.0, exponent - 25) * (0x400 + fraction); |
| 499 // | 522 // |
| 500 // In our case the exponent is 14 (since we or with 0x3800) and | 523 // In our case the exponent is 14 (since we or with 0x3800) and |
| 501 // pow(2.0, 14-25) * 0x400 evaluates to 0.5 (our offset) and | 524 // pow(2.0, 14-25) * 0x400 evaluates to 0.5 (our offset) and |
| 502 // pow(2.0, 14-25) * fraction is [0..0.49951171875] for 10-bit and | 525 // pow(2.0, 14-25) * fraction is [0..0.49951171875] for 10-bit and |
| 503 // [0..0.24951171875] for 9-bit. | 526 // [0..0.24951171875] for 9-bit. |
| (...skipping 10 matching lines...) Expand all Loading... |
| 514 } | 537 } |
| 515 | 538 |
| 516 external_resources.mailboxes.push_back( | 539 external_resources.mailboxes.push_back( |
| 517 TextureMailbox(plane_resource.mailbox(), gpu::SyncToken(), | 540 TextureMailbox(plane_resource.mailbox(), gpu::SyncToken(), |
| 518 resource_provider_->GetResourceTextureTarget( | 541 resource_provider_->GetResourceTextureTarget( |
| 519 plane_resource.resource_id()))); | 542 plane_resource.resource_id()))); |
| 520 external_resources.release_callbacks.push_back(base::Bind( | 543 external_resources.release_callbacks.push_back(base::Bind( |
| 521 &RecycleResource, AsWeakPtr(), plane_resource.resource_id())); | 544 &RecycleResource, AsWeakPtr(), plane_resource.resource_id())); |
| 522 } | 545 } |
| 523 | 546 |
| 524 external_resources.type = VideoFrameExternalResources::YUV_RESOURCE; | 547 external_resources.type = (input_frame_format == media::PIXEL_FORMAT_Y16 || |
| 548 input_frame_format == media::PIXEL_FORMAT_Y8) |
| 549 ? VideoFrameExternalResources::Y_RESOURCE |
| 550 : VideoFrameExternalResources::YUV_RESOURCE; |
| 525 return external_resources; | 551 return external_resources; |
| 526 } | 552 } |
| 527 | 553 |
| 528 // static | 554 // static |
| 529 void VideoResourceUpdater::ReturnTexture( | 555 void VideoResourceUpdater::ReturnTexture( |
| 530 base::WeakPtr<VideoResourceUpdater> updater, | 556 base::WeakPtr<VideoResourceUpdater> updater, |
| 531 const scoped_refptr<media::VideoFrame>& video_frame, | 557 const scoped_refptr<media::VideoFrame>& video_frame, |
| 532 const gpu::SyncToken& sync_token, | 558 const gpu::SyncToken& sync_token, |
| 533 bool lost_resource, | 559 bool lost_resource, |
| 534 BlockingTaskRunner* main_thread_task_runner) { | 560 BlockingTaskRunner* main_thread_task_runner) { |
| (...skipping 156 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 691 if (lost_resource) { | 717 if (lost_resource) { |
| 692 resource_it->clear_refs(); | 718 resource_it->clear_refs(); |
| 693 updater->DeleteResource(resource_it); | 719 updater->DeleteResource(resource_it); |
| 694 return; | 720 return; |
| 695 } | 721 } |
| 696 | 722 |
| 697 resource_it->remove_ref(); | 723 resource_it->remove_ref(); |
| 698 } | 724 } |
| 699 | 725 |
| 700 } // namespace cc | 726 } // namespace cc |
| OLD | NEW |