mirror of
https://github.com/flutter/flutter.git
synced 2026-02-20 02:29:02 +08:00
EndFrame should be always called by rasterizer (flutter/engine#19257)
This commit is contained in:
parent
c467c00208
commit
910b7ed0df
@ -287,16 +287,16 @@ class ExternalViewEmbedder {
|
||||
virtual bool SubmitFrame(GrContext* context,
|
||||
std::unique_ptr<SurfaceFrame> frame);
|
||||
|
||||
// This should only be called after |SubmitFrame|.
|
||||
// This method provides the embedder a way to do additional tasks after
|
||||
// |SubmitFrame|. After invoking this method, the current task on the
|
||||
// TaskRunner should end immediately.
|
||||
// |SubmitFrame|. For example, merge task runners if `should_resubmit_frame`
|
||||
// is true.
|
||||
//
|
||||
// For example on the iOS embedder, threads are merged in this call.
|
||||
// A new frame on the platform thread starts immediately. If the GPU thread
|
||||
// still has some task running, there could be two frames being rendered
|
||||
// concurrently, which causes undefined behaviors.
|
||||
virtual void EndFrame(
|
||||
bool should_resubmit_frame,
|
||||
fml::RefPtr<fml::RasterThreadMerger> raster_thread_merger) {}
|
||||
|
||||
FML_DISALLOW_COPY_AND_ASSIGN(ExternalViewEmbedder);
|
||||
|
||||
@ -151,12 +151,10 @@ void Rasterizer::Draw(fml::RefPtr<Pipeline<flutter::LayerTree>> pipeline) {
|
||||
|
||||
// Merging the thread as we know the next `Draw` should be run on the platform
|
||||
// thread.
|
||||
if (raster_status == RasterStatus::kResubmit) {
|
||||
auto* external_view_embedder = surface_->GetExternalViewEmbedder();
|
||||
// We know only the `external_view_embedder` can
|
||||
// causes|RasterStatus::kResubmit|. Check to make sure.
|
||||
FML_DCHECK(external_view_embedder != nullptr);
|
||||
external_view_embedder->EndFrame(raster_thread_merger_);
|
||||
if (surface_ != nullptr && surface_->GetExternalViewEmbedder() != nullptr) {
|
||||
auto should_resubmit_frame = raster_status == RasterStatus::kResubmit;
|
||||
surface_->GetExternalViewEmbedder()->EndFrame(should_resubmit_frame,
|
||||
raster_thread_merger_);
|
||||
}
|
||||
|
||||
// Consume as many pipeline items as possible. But yield the event loop
|
||||
|
||||
@ -43,8 +43,9 @@ bool ShellTestExternalViewEmbedder::SubmitFrame(
|
||||
|
||||
// |ExternalViewEmbedder|
|
||||
void ShellTestExternalViewEmbedder::EndFrame(
|
||||
bool should_resubmit_frame,
|
||||
fml::RefPtr<fml::RasterThreadMerger> raster_thread_merger) {
|
||||
end_frame_call_back_();
|
||||
end_frame_call_back_(should_resubmit_frame);
|
||||
}
|
||||
|
||||
// |ExternalViewEmbedder|
|
||||
|
||||
@ -15,7 +15,7 @@ namespace flutter {
|
||||
///
|
||||
class ShellTestExternalViewEmbedder final : public ExternalViewEmbedder {
|
||||
public:
|
||||
using EndFrameCallBack = std::function<void(void)>;
|
||||
using EndFrameCallBack = std::function<void(bool)>;
|
||||
|
||||
ShellTestExternalViewEmbedder(const EndFrameCallBack& end_frame_call_back,
|
||||
PostPrerollResult post_preroll_result)
|
||||
@ -56,6 +56,7 @@ class ShellTestExternalViewEmbedder final : public ExternalViewEmbedder {
|
||||
|
||||
// |ExternalViewEmbedder|
|
||||
void EndFrame(
|
||||
bool should_resubmit_frame,
|
||||
fml::RefPtr<fml::RasterThreadMerger> raster_thread_merger) override;
|
||||
|
||||
// |ExternalViewEmbedder|
|
||||
|
||||
@ -474,7 +474,8 @@ TEST_F(ShellTest,
|
||||
auto settings = CreateSettingsForFixture();
|
||||
fml::AutoResetWaitableEvent endFrameLatch;
|
||||
bool end_frame_called = false;
|
||||
auto end_frame_callback = [&] {
|
||||
auto end_frame_callback = [&](bool should_resubmit_frame) {
|
||||
ASSERT_TRUE(should_resubmit_frame);
|
||||
end_frame_called = true;
|
||||
endFrameLatch.Signal();
|
||||
};
|
||||
|
||||
@ -254,8 +254,9 @@ void AndroidExternalViewEmbedder::CancelFrame() {
|
||||
|
||||
// |ExternalViewEmbedder|
|
||||
void AndroidExternalViewEmbedder::EndFrame(
|
||||
bool should_resubmit_frame,
|
||||
fml::RefPtr<fml::RasterThreadMerger> raster_thread_merger) {
|
||||
if (should_run_rasterizer_on_platform_thread_) {
|
||||
if (should_resubmit_frame && should_run_rasterizer_on_platform_thread_) {
|
||||
raster_thread_merger->MergeWithLease(kDefaultMergedLeaseDuration);
|
||||
should_run_rasterizer_on_platform_thread_ = false;
|
||||
}
|
||||
|
||||
@ -65,6 +65,7 @@ class AndroidExternalViewEmbedder final : public ExternalViewEmbedder {
|
||||
|
||||
// |ExternalViewEmbedder|
|
||||
void EndFrame(
|
||||
bool should_resubmit_frame,
|
||||
fml::RefPtr<fml::RasterThreadMerger> raster_thread_merger) override;
|
||||
|
||||
// Gets the rect based on the device pixel ratio of a platform view displayed
|
||||
|
||||
@ -158,7 +158,7 @@ TEST(AndroidExternalViewEmbedder, RasterizerRunsOnPlatformThread) {
|
||||
ASSERT_TRUE(embedder->SubmitFrame(nullptr, nullptr));
|
||||
|
||||
EXPECT_CALL(*jni_mock, FlutterViewEndFrame());
|
||||
embedder->EndFrame(raster_thread_merger);
|
||||
embedder->EndFrame(/*should_resubmit_frame=*/true, raster_thread_merger);
|
||||
|
||||
ASSERT_TRUE(raster_thread_merger->IsMerged());
|
||||
|
||||
@ -182,7 +182,7 @@ TEST(AndroidExternalViewEmbedder, RasterizerRunsOnRasterizerThread) {
|
||||
ASSERT_EQ(PostPrerollResult::kSuccess, result);
|
||||
|
||||
EXPECT_CALL(*jni_mock, FlutterViewEndFrame());
|
||||
embedder->EndFrame(raster_thread_merger);
|
||||
embedder->EndFrame(/*should_resubmit_frame=*/true, raster_thread_merger);
|
||||
|
||||
ASSERT_FALSE(raster_thread_merger->IsMerged());
|
||||
}
|
||||
@ -332,7 +332,7 @@ TEST(AndroidExternalViewEmbedder, SubmitFrame__RecycleSurfaces) {
|
||||
embedder->SubmitFrame(gr_context.get(), std::move(surface_frame));
|
||||
|
||||
EXPECT_CALL(*jni_mock, FlutterViewEndFrame());
|
||||
embedder->EndFrame(raster_thread_merger);
|
||||
embedder->EndFrame(/*should_resubmit_frame=*/false, raster_thread_merger);
|
||||
}
|
||||
|
||||
// ------------------ Second frame ------------------ //
|
||||
@ -380,7 +380,7 @@ TEST(AndroidExternalViewEmbedder, SubmitFrame__RecycleSurfaces) {
|
||||
embedder->SubmitFrame(gr_context.get(), std::move(surface_frame));
|
||||
|
||||
EXPECT_CALL(*jni_mock, FlutterViewEndFrame());
|
||||
embedder->EndFrame(raster_thread_merger);
|
||||
embedder->EndFrame(/*should_resubmit_frame=*/false, raster_thread_merger);
|
||||
}
|
||||
}
|
||||
|
||||
@ -399,7 +399,7 @@ TEST(AndroidExternalViewEmbedder, DoesNotCallJNIPlatformThreadOnlyMethods) {
|
||||
raster_thread_merger);
|
||||
|
||||
EXPECT_CALL(*jni_mock, FlutterViewEndFrame()).Times(0);
|
||||
embedder->EndFrame(raster_thread_merger);
|
||||
embedder->EndFrame(/*should_resubmit_frame=*/false, raster_thread_merger);
|
||||
}
|
||||
|
||||
} // namespace testing
|
||||
|
||||
@ -604,8 +604,9 @@ void FlutterPlatformViewsController::BringLayersIntoView(LayersMap layer_map) {
|
||||
}
|
||||
|
||||
void FlutterPlatformViewsController::EndFrame(
|
||||
bool should_resubmit_frame,
|
||||
fml::RefPtr<fml::RasterThreadMerger> raster_thread_merger) {
|
||||
if (merge_threads_) {
|
||||
if (should_resubmit_frame && merge_threads_) {
|
||||
raster_thread_merger->MergeWithLease(kDefaultMergedLeaseDuration);
|
||||
merge_threads_ = false;
|
||||
}
|
||||
|
||||
@ -168,7 +168,8 @@ class FlutterPlatformViewsController {
|
||||
// Invoked at the very end of a frame.
|
||||
// After invoking this method, nothing should happen on the current TaskRunner during the same
|
||||
// frame.
|
||||
void EndFrame(fml::RefPtr<fml::RasterThreadMerger> raster_thread_merger);
|
||||
void EndFrame(bool should_resubmit_frame,
|
||||
fml::RefPtr<fml::RasterThreadMerger> raster_thread_merger);
|
||||
|
||||
void OnMethodCall(FlutterMethodCall* call, FlutterResult& result);
|
||||
|
||||
|
||||
@ -85,7 +85,8 @@ class IOSSurface : public ExternalViewEmbedder {
|
||||
bool SubmitFrame(GrContext* context, std::unique_ptr<SurfaceFrame> frame) override;
|
||||
|
||||
// |ExternalViewEmbedder|
|
||||
void EndFrame(fml::RefPtr<fml::RasterThreadMerger> raster_thread_merger) override;
|
||||
void EndFrame(bool should_resubmit_frame,
|
||||
fml::RefPtr<fml::RasterThreadMerger> raster_thread_merger) override;
|
||||
|
||||
public:
|
||||
FML_DISALLOW_COPY_AND_ASSIGN(IOSSurface);
|
||||
|
||||
@ -149,10 +149,11 @@ bool IOSSurface::SubmitFrame(GrContext* context, std::unique_ptr<SurfaceFrame> f
|
||||
}
|
||||
|
||||
// |ExternalViewEmbedder|
|
||||
void IOSSurface::EndFrame(fml::RefPtr<fml::RasterThreadMerger> raster_thread_merger) {
|
||||
void IOSSurface::EndFrame(bool should_resubmit_frame,
|
||||
fml::RefPtr<fml::RasterThreadMerger> raster_thread_merger) {
|
||||
TRACE_EVENT0("flutter", "IOSSurface::EndFrame");
|
||||
FML_CHECK(platform_views_controller_ != nullptr);
|
||||
return platform_views_controller_->EndFrame(raster_thread_merger);
|
||||
return platform_views_controller_->EndFrame(should_resubmit_frame, raster_thread_merger);
|
||||
}
|
||||
|
||||
} // namespace flutter
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user