YUVUtils.cpp 2.6 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788
  1. /*
  2. * Copyright 2019 Google Inc.
  3. *
  4. * Use of this source code is governed by a BSD-style license that can be
  5. * found in the LICENSE file.
  6. */
  7. #include "tools/gpu/YUVUtils.h"
  8. #include "include/core/SkData.h"
  9. #include "include/gpu/GrContext.h"
  10. #include "src/codec/SkCodecImageGenerator.h"
  11. #include "src/gpu/GrContextPriv.h"
  12. namespace sk_gpu_test {
  13. std::unique_ptr<LazyYUVImage> LazyYUVImage::Make(sk_sp<SkData> data) {
  14. std::unique_ptr<LazyYUVImage> image(new LazyYUVImage());
  15. if (image->reset(std::move(data))) {
  16. return image;
  17. } else {
  18. return nullptr;
  19. }
  20. }
  21. sk_sp<SkImage> LazyYUVImage::refImage(GrContext* context) {
  22. if (this->ensureYUVImage(context)) {
  23. return fYUVImage;
  24. } else {
  25. return nullptr;
  26. }
  27. }
  28. const SkImage* LazyYUVImage::getImage(GrContext* context) {
  29. if (this->ensureYUVImage(context)) {
  30. return fYUVImage.get();
  31. } else {
  32. return nullptr;
  33. }
  34. }
  35. bool LazyYUVImage::reset(sk_sp<SkData> data) {
  36. auto codec = SkCodecImageGenerator::MakeFromEncodedCodec(data);
  37. if (!codec) {
  38. return false;
  39. }
  40. if (!codec->queryYUVA8(&fSizeInfo, fComponents, &fColorSpace)) {
  41. return false;
  42. }
  43. fPlaneData.reset(fSizeInfo.computeTotalBytes());
  44. void* planes[SkYUVASizeInfo::kMaxCount];
  45. fSizeInfo.computePlanes(fPlaneData.get(), planes);
  46. if (!codec->getYUVA8Planes(fSizeInfo, fComponents, planes)) {
  47. return false;
  48. }
  49. for (int i = 0; i < SkYUVASizeInfo::kMaxCount; ++i) {
  50. if (fSizeInfo.fSizes[i].isEmpty()) {
  51. fPlanes[i].reset();
  52. } else {
  53. SkASSERT(planes[i]);
  54. auto planeInfo = SkImageInfo::Make(fSizeInfo.fSizes[i].fWidth,
  55. fSizeInfo.fSizes[i].fHeight,
  56. kGray_8_SkColorType, kOpaque_SkAlphaType, nullptr);
  57. fPlanes[i].reset(planeInfo, planes[i], fSizeInfo.fWidthBytes[i]);
  58. }
  59. }
  60. // The SkPixmap data is fully configured now for MakeFromYUVAPixmaps once we get a GrContext
  61. return true;
  62. }
  63. bool LazyYUVImage::ensureYUVImage(GrContext* context) {
  64. if (!context) {
  65. return false; // Cannot make a YUV image from planes
  66. }
  67. if (context->priv().contextID() == fOwningContextID) {
  68. return fYUVImage != nullptr; // Have already made a YUV image (or tried and failed)
  69. }
  70. // Must make a new YUV image
  71. fYUVImage = SkImage::MakeFromYUVAPixmaps(context, fColorSpace, fPlanes, fComponents,
  72. fSizeInfo.fSizes[0], kTopLeft_GrSurfaceOrigin, false, false);
  73. fOwningContextID = context->priv().contextID();
  74. return fYUVImage != nullptr;
  75. }
  76. } // namespace sk_gpu_test