mirror of
https://github.com/flutter/flutter.git
synced 2026-02-20 02:29:02 +08:00
SkiaUnrefQueue should be empty at destruction time. If the queue is nonempty, then there will be a pending drain task that will hold a reference to the queue. The queue can only be destructed after the drain completes and the reference is dropped. Drains must only be done on the queue's task runner thread, which may not be the thread where the queue is destructed.
45 lines
1.1 KiB
C++
45 lines
1.1 KiB
C++
// Copyright 2013 The Flutter Authors. All rights reserved.
|
|
// Use of this source code is governed by a BSD-style license that can be
|
|
// found in the LICENSE file.
|
|
|
|
#include "flutter/flow/skia_gpu_object.h"
|
|
|
|
#include "flutter/fml/message_loop.h"
|
|
|
|
namespace flutter {
|
|
|
|
SkiaUnrefQueue::SkiaUnrefQueue(fml::RefPtr<fml::TaskRunner> task_runner,
|
|
fml::TimeDelta delay)
|
|
: task_runner_(std::move(task_runner)),
|
|
drain_delay_(delay),
|
|
drain_pending_(false) {}
|
|
|
|
SkiaUnrefQueue::~SkiaUnrefQueue() {
|
|
FML_DCHECK(objects_.empty());
|
|
}
|
|
|
|
void SkiaUnrefQueue::Unref(SkRefCnt* object) {
|
|
std::scoped_lock lock(mutex_);
|
|
objects_.push_back(object);
|
|
if (!drain_pending_) {
|
|
drain_pending_ = true;
|
|
task_runner_->PostDelayedTask(
|
|
[strong = fml::Ref(this)]() { strong->Drain(); }, drain_delay_);
|
|
}
|
|
}
|
|
|
|
void SkiaUnrefQueue::Drain() {
|
|
std::deque<SkRefCnt*> skia_objects;
|
|
{
|
|
std::scoped_lock lock(mutex_);
|
|
objects_.swap(skia_objects);
|
|
drain_pending_ = false;
|
|
}
|
|
|
|
for (SkRefCnt* skia_object : skia_objects) {
|
|
skia_object->unref();
|
|
}
|
|
}
|
|
|
|
} // namespace flutter
|