| Flutter Impeller |

picture.cc
Go to the documentation of this file.
1 // Copyright 2013 The Flutter Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "impeller/aiks/picture.h"
6
7 #include <memory>
8 #include <optional>
9
10 #include "impeller/base/validation.h"
11 #include "impeller/entity/entity.h"
12 #include "impeller/renderer/render_target.h"
13 #include "impeller/renderer/snapshot.h"
14
15 namespace impeller {
16
17 std::optional<Snapshot> Picture::Snapshot(AiksContext& context) {
18 auto coverage = pass->GetElementsCoverage(std::nullopt);
19 if (!coverage.has_value() || coverage->IsEmpty()) {
20 return std::nullopt;
21 }
22
23 const auto translate = Matrix::MakeTranslation(-coverage.value().origin);
24 auto texture =
25 RenderToTexture(context, ISize(coverage.value().size), translate);
26 return impeller::Snapshot{
27 .texture = std::move(texture),
28 .transform = Matrix::MakeTranslation(coverage.value().origin)};
29 }
30
31 std::shared_ptr<Image> Picture::ToImage(AiksContext& context,
32 ISize size) const {
33 if (size.IsEmpty()) {
34 return nullptr;
35 }
36 auto texture = RenderToTexture(context, size);
37 return texture ? std::make_shared<Image>(texture) : nullptr;
38 }
39
40 std::shared_ptr<Texture> Picture::RenderToTexture(
41 AiksContext& context,
42 ISize size,
43 std::optional<const Matrix> translate) const {
44 FML_DCHECK(!size.IsEmpty());
45
46 pass->IterateAllEntities([&translate](auto& entity) -> bool {
47 auto matrix = translate.has_value()
48 ? translate.value() * entity.GetTransformation()
49 : entity.GetTransformation();
50 entity.SetTransformation(matrix);
51 return true;
52 });
53
54 // This texture isn't host visible, but we might want to add host visible
55 // features to Image someday.
56 auto impeller_context = context.GetContext();
57 // Do not use the render target cache as the lifecycle of this texture
58 // will outlive a particular frame.
59 RenderTargetAllocator render_target_allocator =
60 RenderTargetAllocator(impeller_context->GetResourceAllocator());
61 RenderTarget target;
62 if (impeller_context->GetCapabilities()->SupportsOffscreenMSAA()) {
63 target = RenderTarget::CreateOffscreenMSAA(
64 *impeller_context, // context
65 render_target_allocator, // allocator
66 size, // size
67 "Picture Snapshot MSAA", // label
68 RenderTarget::
69 kDefaultColorAttachmentConfigMSAA // color_attachment_config
70 #ifndef FML_OS_ANDROID // Reduce PSO variants for Vulkan.
71 ,
72 std::nullopt // stencil_attachment_config
73 #endif // FML_OS_ANDROID
74 );
75 } else {
76 target = RenderTarget::CreateOffscreen(
77 *impeller_context, // context
78 render_target_allocator, // allocator
79 size, // size
80 "Picture Snapshot", // label
81 RenderTarget::kDefaultColorAttachmentConfig // color_attachment_config
82 #ifndef FML_OS_ANDROID // Reduce PSO variants for Vulkan.
83 ,
84 std::nullopt // stencil_attachment_config
85 #endif // FML_OS_ANDROID
86 );
87 }
88 if (!target.IsValid()) {
89 VALIDATION_LOG << "Could not create valid RenderTarget.";
90 return nullptr;
91 }
92
93 if (!context.Render(*this, target)) {
94 VALIDATION_LOG << "Could not render Picture to Texture.";
95 return nullptr;
96 }
97
98 auto texture = target.GetRenderTargetTexture();
99 if (!texture) {
100 VALIDATION_LOG << "RenderTarget has no target texture.";
101 return nullptr;
102 }
103
104 return texture;
105 }
106
107 } // namespace impeller
impeller::Picture::pass
std::unique_ptr< EntityPass > pass
Definition: picture.h:20
impeller::AiksContext
Definition: aiks_context.h:20
impeller::RenderTarget::kDefaultColorAttachmentConfig
static constexpr AttachmentConfig kDefaultColorAttachmentConfig
Definition: render_target.h:65
entity.h
picture.h
impeller::Matrix::MakeTranslation
static constexpr Matrix MakeTranslation(const Vector3 &t)
Definition: matrix.h:94
validation.h
impeller::TSize< int64_t >
impeller::Picture::Snapshot
std::optional< Snapshot > Snapshot(AiksContext &context)
Definition: picture.cc:17
impeller::Snapshot
Represents a texture and its intended draw transform/sampler configuration.
Definition: snapshot.h:24
impeller::ISize
TSize< int64_t > ISize
Definition: size.h:136
impeller::AiksContext::GetContext
std::shared_ptr< Context > GetContext() const
Definition: aiks_context.cc:35
impeller::RenderTarget::CreateOffscreen
static RenderTarget CreateOffscreen(const Context &context, RenderTargetAllocator &allocator, ISize size, const std::string &label="Offscreen", AttachmentConfig color_attachment_config=kDefaultColorAttachmentConfig, std::optional< AttachmentConfig > stencil_attachment_config=kDefaultStencilAttachmentConfig)
Definition: render_target.cc:223
impeller::Picture::ToImage
std::shared_ptr< Image > ToImage(AiksContext &context, ISize size) const
Definition: picture.cc:31
impeller::AiksContext::Render
bool Render(const Picture &picture, RenderTarget &render_target)
Definition: aiks_context.cc:43
VALIDATION_LOG
#define VALIDATION_LOG
Definition: validation.h:60
snapshot.h
impeller::TSize::IsEmpty
constexpr bool IsEmpty() const
Definition: size.h:105
impeller::Snapshot::texture
std::shared_ptr< Texture > texture
Definition: snapshot.h:25
render_target.h
impeller
Definition: aiks_context.cc:10
impeller::RenderTarget::CreateOffscreenMSAA
static RenderTarget CreateOffscreenMSAA(const Context &context, RenderTargetAllocator &allocator, ISize size, const std::string &label="Offscreen MSAA", AttachmentConfigMSAA color_attachment_config=kDefaultColorAttachmentConfigMSAA, std::optional< AttachmentConfig > stencil_attachment_config=kDefaultStencilAttachmentConfig)
Definition: render_target.cc:270