Skip to content
This repository was archived by the owner on Feb 25, 2025. It is now read-only.

Commit 1de265f

Browse files
committed
[embedder] Compositor can specify that no backing stores be cached
1 parent dbd1abe commit 1de265f

7 files changed

+70
-6
lines changed

shell/platform/embedder/embedder.cc

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -542,6 +542,8 @@ InferExternalViewEmbedderFromArgs(const FlutterCompositor* compositor) {
542542
SAFE_ACCESS(compositor, collect_backing_store_callback, nullptr);
543543
auto c_present_callback =
544544
SAFE_ACCESS(compositor, present_layers_callback, nullptr);
545+
bool avoid_backing_store_cache =
546+
SAFE_ACCESS(compositor, avoid_backing_store_cache, false);
545547

546548
// Make sure the required callbacks are present
547549
if (!c_create_callback || !c_collect_callback || !c_present_callback) {
@@ -568,7 +570,8 @@ InferExternalViewEmbedderFromArgs(const FlutterCompositor* compositor) {
568570
};
569571

570572
return {std::make_unique<flutter::EmbedderExternalViewEmbedder>(
571-
create_render_target_callback, present_callback),
573+
avoid_backing_store_cache, create_render_target_callback,
574+
present_callback),
572575
false};
573576
}
574577

shell/platform/embedder/embedder.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -937,6 +937,8 @@ typedef struct {
937937
/// Callback invoked by the engine to composite the contents of each layer
938938
/// onto the screen.
939939
FlutterLayersPresentCallback present_layers_callback;
940+
/// Avoid caching backing stores provided by this compositor.
941+
bool avoid_backing_store_cache;
940942
} FlutterCompositor;
941943

942944
typedef struct {

shell/platform/embedder/embedder_external_view_embedder.cc

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,11 @@
1313
namespace flutter {
1414

1515
EmbedderExternalViewEmbedder::EmbedderExternalViewEmbedder(
16+
bool avoid_backing_store_cache,
1617
const CreateRenderTargetCallback& create_render_target_callback,
1718
const PresentCallback& present_callback)
18-
: create_render_target_callback_(create_render_target_callback),
19+
: avoid_backing_store_cache_(avoid_backing_store_cache),
20+
create_render_target_callback_(create_render_target_callback),
1921
present_callback_(present_callback) {
2022
FML_DCHECK(create_render_target_callback_);
2123
FML_DCHECK(present_callback_);
@@ -263,8 +265,10 @@ void EmbedderExternalViewEmbedder::SubmitFrame(
263265
// Hold all rendered layers in the render target cache for one frame to
264266
// see if they may be reused next frame.
265267
for (auto& render_target : matched_render_targets) {
266-
render_target_cache_.CacheRenderTarget(render_target.first,
267-
std::move(render_target.second));
268+
if (!avoid_backing_store_cache_) {
269+
render_target_cache_.CacheRenderTarget(render_target.first,
270+
std::move(render_target.second));
271+
}
268272
}
269273

270274
frame->Submit();

shell/platform/embedder/embedder_external_view_embedder.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,11 @@ class EmbedderExternalViewEmbedder final : public ExternalViewEmbedder {
4040
/// @brief Creates an external view embedder used by the generic embedder
4141
/// API.
4242
///
43+
/// @param[in] avoid_backing_store_cache If set, create_render_target callback
44+
/// will beinvoked every frame for every
45+
/// engine composited layer. The result
46+
/// will not cached.
47+
///
4348
/// @param[in] create_render_target_callback
4449
/// The render target callback used to
4550
/// request the render target for a layer.
@@ -49,6 +54,7 @@ class EmbedderExternalViewEmbedder final : public ExternalViewEmbedder {
4954
/// embedder for presentation.
5055
///
5156
EmbedderExternalViewEmbedder(
57+
bool avoid_backing_store_cache,
5258
const CreateRenderTargetCallback& create_render_target_callback,
5359
const PresentCallback& present_callback);
5460

@@ -100,6 +106,7 @@ class EmbedderExternalViewEmbedder final : public ExternalViewEmbedder {
100106
SkCanvas* GetRootCanvas() override;
101107

102108
private:
109+
const bool avoid_backing_store_cache_;
103110
const CreateRenderTargetCallback create_render_target_callback_;
104111
const PresentCallback present_callback_;
105112
SurfaceTransformationCallback surface_transformation_callback_;

shell/platform/embedder/tests/embedder_config_builder.cc

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -249,7 +249,7 @@ void EmbedderConfigBuilder::SetPlatformMessageCallback(
249249
context_.SetPlatformMessageCallback(callback);
250250
}
251251

252-
void EmbedderConfigBuilder::SetCompositor() {
252+
void EmbedderConfigBuilder::SetCompositor(bool avoid_backing_store_cache) {
253253
context_.SetupCompositor();
254254
auto& compositor = context_.GetCompositor();
255255
compositor_.struct_size = sizeof(compositor_);
@@ -279,6 +279,7 @@ void EmbedderConfigBuilder::SetCompositor() {
279279

280280
);
281281
};
282+
compositor_.avoid_backing_store_cache = avoid_backing_store_cache;
282283
project_args_.compositor = &compositor_;
283284
}
284285

shell/platform/embedder/tests/embedder_config_builder.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,7 @@ class EmbedderConfigBuilder {
8585
void SetPlatformMessageCallback(
8686
const std::function<void(const FlutterPlatformMessage*)>& callback);
8787

88-
void SetCompositor();
88+
void SetCompositor(bool avoid_backing_store_cache = false);
8989

9090
FlutterCompositor& GetCompositor();
9191

shell/platform/embedder/tests/embedder_unittests_gl.cc

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3352,5 +3352,52 @@ TEST_F(EmbedderTest, MultipleDisplaysWithSameDisplayIdIsInvalid) {
33523352
latch.Wait();
33533353
}
33543354

3355+
TEST_F(EmbedderTest, CompositorRenderTargetsNotRecycledWhenAvoidsCacheSet) {
3356+
auto& context = GetEmbedderContext(ContextType::kOpenGLContext);
3357+
3358+
EmbedderConfigBuilder builder(context);
3359+
builder.SetOpenGLRendererConfig(SkISize::Make(300, 200));
3360+
builder.SetCompositor(/*avoid_backing_store_cache=*/true);
3361+
builder.SetDartEntrypoint("render_targets_are_recycled");
3362+
builder.SetRenderTargetType(
3363+
EmbedderTestBackingStoreProducer::RenderTargetType::kOpenGLTexture);
3364+
3365+
const unsigned num_frames = 8;
3366+
const unsigned num_engine_layers = 10;
3367+
const unsigned num_backing_stores = num_frames * num_engine_layers;
3368+
fml::CountDownLatch latch(1 + num_frames); // 1 for native test signal.
3369+
3370+
context.AddNativeCallback("SignalNativeTest",
3371+
CREATE_NATIVE_ENTRY([&](Dart_NativeArguments args) {
3372+
latch.CountDown();
3373+
}));
3374+
3375+
context.GetCompositor().SetPresentCallback(
3376+
[&](const FlutterLayer** layers, size_t layers_count) {
3377+
ASSERT_EQ(layers_count, 20u);
3378+
latch.CountDown();
3379+
},
3380+
/*one_shot=*/false);
3381+
3382+
auto engine = builder.LaunchEngine();
3383+
ASSERT_TRUE(engine.is_valid());
3384+
3385+
FlutterWindowMetricsEvent event = {};
3386+
event.struct_size = sizeof(event);
3387+
event.width = 300;
3388+
event.height = 200;
3389+
event.pixel_ratio = 1.0;
3390+
ASSERT_EQ(FlutterEngineSendWindowMetricsEvent(engine.get(), &event),
3391+
kSuccess);
3392+
3393+
latch.Wait();
3394+
3395+
ASSERT_EQ(context.GetCompositor().GetBackingStoresCreatedCount(),
3396+
num_backing_stores);
3397+
// Killing the engine should collect all the frames.
3398+
engine.reset();
3399+
ASSERT_EQ(context.GetCompositor().GetPendingBackingStoresCount(), 0u);
3400+
}
3401+
33553402
} // namespace testing
33563403
} // namespace flutter

0 commit comments

Comments
 (0)