| Flutter Impeller |

context.h
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 #ifndef FLUTTER_IMPELLER_RENDERER_CONTEXT_H_
6 #define FLUTTER_IMPELLER_RENDERER_CONTEXT_H_
7
8 #include <memory>
9 #include <string>
10
11 #include "impeller/core/allocator.h"
12 #include "impeller/core/formats.h"
13 #include "impeller/renderer/capabilities.h"
14 #include "impeller/renderer/command_queue.h"
15 #include "impeller/renderer/sampler_library.h"
16
17 namespace impeller {
18
19 class ShaderLibrary;
20 class CommandBuffer;
21 class PipelineLibrary;
22
23 //------------------------------------------------------------------------------
24 /// @brief To do anything rendering related with Impeller, you need a
25 /// context.
26 ///
27 /// Contexts are expensive to construct and typically you only need
28 /// one in the process. The context represents a connection to a
29 /// graphics or compute accelerator on the device.
30 ///
31 /// If there are multiple context in a process, it would typically
32 /// be for separation of concerns (say, use with multiple engines in
33 /// Flutter), talking to multiple accelerators, or talking to the
34 /// same accelerator using different client APIs (Metal, Vulkan,
35 /// OpenGL ES, etc..).
36 ///
37 /// Contexts are thread-safe. They may be created, used, and
38 /// collected (though not from a thread used by an internal pool) on
39 /// any thread. They may also be accessed simultaneously from
40 /// multiple threads.
41 ///
42 /// Contexts are abstract and a concrete instance must be created
43 /// using one of the subclasses of `Context` in
44 /// `//impeller/renderer/backend`.
45 class Context {
46 public:
47 enum class BackendType {
48 kMetal,
49 kOpenGLES,
50 kVulkan,
51 };
52
53 /// The maximum number of tasks that should ever be stored for
54 /// `StoreTaskForGPU`.
55 ///
56 /// This number was arbitrarily chosen. The idea is that this is a somewhat
57 /// rare situation where tasks happen to get executed in that tiny amount of
58 /// time while an app is being backgrounded but still executing.
59 static constexpr int32_t kMaxTasksAwaitingGPU = 10;
60
61 //----------------------------------------------------------------------------
62 /// @brief Destroys an Impeller context.
63 ///
64 virtual ~Context();
65
66 //----------------------------------------------------------------------------
67 /// @brief Get the graphics backend of an Impeller context.
68 ///
69 /// This is useful for cases where a renderer needs to track and
70 /// lookup backend-specific resources, like shaders or uniform
71 /// layout information.
72 ///
73 /// It's not recommended to use this as a substitute for
74 /// per-backend capability checking. Instead, check for specific
75 /// capabilities via `GetCapabilities()`.
76 ///
77 /// @return The graphics backend of the `Context`.
78 ///
79 virtual BackendType GetBackendType() const = 0;
80
81 // TODO(129920): Refactor and move to capabilities.
82 virtual std::string DescribeGpuModel() const = 0;
83
84 //----------------------------------------------------------------------------
85 /// @brief Determines if a context is valid. If the caller ever receives
86 /// an invalid context, they must discard it and construct a new
87 /// context. There is no recovery mechanism to repair a bad
88 /// context.
89 ///
90 /// It is convention in Impeller to never return an invalid
91 /// context from a call that returns an pointer to a context. The
92 /// call implementation performs validity checks itself and return
93 /// a null context instead of a pointer to an invalid context.
94 ///
95 /// How a context goes invalid is backend specific. It could
96 /// happen due to device loss, or any other unrecoverable error.
97 ///
98 /// @return If the context is valid.
99 ///
100 virtual bool IsValid() const = 0;
101
102 //----------------------------------------------------------------------------
103 /// @brief Get the capabilities of Impeller context. All optionally
104 /// supported feature of the platform, client-rendering API, and
105 /// device can be queried using the `Capabilities`.
106 ///
107 /// @return The capabilities. Can never be `nullptr` for a valid context.
108 ///
109 virtual const std::shared_ptr<const Capabilities>& GetCapabilities()
110 const = 0;
111
112 // TODO(129920): Refactor and move to capabilities.
113 virtual bool UpdateOffscreenLayerPixelFormat(PixelFormat format);
114
115 //----------------------------------------------------------------------------
116 /// @brief Returns the allocator used to create textures and buffers on
117 /// the device.
118 ///
119 /// @return The resource allocator. Can never be `nullptr` for a valid
120 /// context.
121 ///
122 virtual std::shared_ptr<Allocator> GetResourceAllocator() const = 0;
123
124 //----------------------------------------------------------------------------
125 /// @brief Returns the library of shaders used to specify the
126 /// programmable stages of a pipeline.
127 ///
128 /// @return The shader library. Can never be `nullptr` for a valid
129 /// context.
130 ///
131 virtual std::shared_ptr<ShaderLibrary> GetShaderLibrary() const = 0;
132
133 //----------------------------------------------------------------------------
134 /// @brief Returns the library of combined image samplers used in
135 /// shaders.
136 ///
137 /// @return The sampler library. Can never be `nullptr` for a valid
138 /// context.
139 ///
140 virtual std::shared_ptr<SamplerLibrary> GetSamplerLibrary() const = 0;
141
142 //----------------------------------------------------------------------------
143 /// @brief Returns the library of pipelines used by render or compute
144 /// commands.
145 ///
146 /// @return The pipeline library. Can never be `nullptr` for a valid
147 /// context.
148 ///
149 virtual std::shared_ptr<PipelineLibrary> GetPipelineLibrary() const = 0;
150
151 //----------------------------------------------------------------------------
152 /// @brief Create a new command buffer. Command buffers can be used to
153 /// encode graphics, blit, or compute commands to be submitted to
154 /// the device.
155 ///
156 /// A command buffer can only be used on a single thread.
157 /// Multi-threaded render, blit, or compute passes must create a
158 /// new command buffer on each thread.
159 ///
160 /// @return A new command buffer.
161 ///
162 virtual std::shared_ptr<CommandBuffer> CreateCommandBuffer() const = 0;
163
164 /// @brief Return the graphics queue for submitting command buffers.
165 virtual std::shared_ptr<CommandQueue> GetCommandQueue() const = 0;
166
167 //----------------------------------------------------------------------------
168 /// @brief Force all pending asynchronous work to finish. This is
169 /// achieved by deleting all owned concurrent message loops.
170 ///
171 virtual void Shutdown() = 0;
172
173 /// Stores a task on the `ContextMTL` that is awaiting access for the GPU.
174 ///
175 /// The task will be executed in the event that the GPU access has changed to
176 /// being available or that the task has been canceled. The task should
177 /// operate with the `SyncSwitch` to make sure the GPU is accessible.
178 ///
179 /// Threadsafe.
180 ///
181 /// `task` will be executed on the platform thread.
182 virtual void StoreTaskForGPU(const std::function<void()>& task) {
183 FML_CHECK(false && "not supported in this context");
184 }
185
186 /// Run backend specific additional setup and create common shader variants.
187 ///
188 /// This bootstrap is intended to improve the performance of several
189 /// first frame benchmarks that are tracked in the flutter device lab.
190 /// The workload includes initializing commonly used but not default
191 /// shader variants, as well as forcing driver initialization.
192 virtual void InitializeCommonlyUsedShadersIfNeeded() const {}
193
194 protected:
195 Context();
196
197 std::vector<std::function<void()>> per_frame_task_;
198
199 private:
200 Context(const Context&) = delete;
201
202 Context& operator=(const Context&) = delete;
203 };
204
205 } // namespace impeller
206
207 #endif // FLUTTER_IMPELLER_RENDERER_CONTEXT_H_
impeller::Context::GetPipelineLibrary
virtual std::shared_ptr< PipelineLibrary > GetPipelineLibrary() const =0
Returns the library of pipelines used by render or compute commands.
impeller::Context::~Context
virtual ~Context()
Destroys an Impeller context.
impeller::Context::BackendType
BackendType
Definition: context.h:47
sampler_library.h
impeller::Context::GetCapabilities
virtual const std::shared_ptr< const Capabilities > & GetCapabilities() const =0
Get the capabilities of Impeller context. All optionally supported feature of the platform,...
command_queue.h
impeller::Context::GetShaderLibrary
virtual std::shared_ptr< ShaderLibrary > GetShaderLibrary() const =0
Returns the library of shaders used to specify the programmable stages of a pipeline.
formats.h
impeller::PixelFormat
PixelFormat
The Pixel formats supported by Impeller. The naming convention denotes the usage of the component,...
Definition: formats.h:99
impeller::Context::GetBackendType
virtual BackendType GetBackendType() const =0
Get the graphics backend of an Impeller context.
impeller::Context::BackendType::kOpenGLES
@ kOpenGLES
impeller::Context::InitializeCommonlyUsedShadersIfNeeded
virtual void InitializeCommonlyUsedShadersIfNeeded() const
Definition: context.h:192
impeller::Context::Context
Context()
capabilities.h
impeller::Context::GetSamplerLibrary
virtual std::shared_ptr< SamplerLibrary > GetSamplerLibrary() const =0
Returns the library of combined image samplers used in shaders.
impeller::Context::StoreTaskForGPU
virtual void StoreTaskForGPU(const std::function< void()> &task)
Definition: context.h:182
impeller::Context::CreateCommandBuffer
virtual std::shared_ptr< CommandBuffer > CreateCommandBuffer() const =0
Create a new command buffer. Command buffers can be used to encode graphics, blit,...
impeller::Context::GetCommandQueue
virtual std::shared_ptr< CommandQueue > GetCommandQueue() const =0
Return the graphics queue for submitting command buffers.
impeller::Context::IsValid
virtual bool IsValid() const =0
Determines if a context is valid. If the caller ever receives an invalid context, they must discard i...
allocator.h
impeller::Context::BackendType::kVulkan
@ kVulkan
impeller::Context::BackendType::kMetal
@ kMetal
impeller::Context
To do anything rendering related with Impeller, you need a context.
Definition: context.h:45
impeller::Context::Shutdown
virtual void Shutdown()=0
Force all pending asynchronous work to finish. This is achieved by deleting all owned concurrent mess...
impeller::Context::per_frame_task_
std::vector< std::function< void()> > per_frame_task_
Definition: context.h:197
impeller::Context::DescribeGpuModel
virtual std::string DescribeGpuModel() const =0
impeller
Definition: aiks_blend_unittests.cc:18
impeller::Context::GetResourceAllocator
virtual std::shared_ptr< Allocator > GetResourceAllocator() const =0
Returns the allocator used to create textures and buffers on the device.
impeller::Context::UpdateOffscreenLayerPixelFormat
virtual bool UpdateOffscreenLayerPixelFormat(PixelFormat format)
Definition: context.cc:13
impeller::Context::kMaxTasksAwaitingGPU
static constexpr int32_t kMaxTasksAwaitingGPU
Definition: context.h:59