[go: nahoru, domu]

blob: 1072361ca658da82300b526ce6b34f1b590869b8 [file] [log] [blame]
Avi Drissman3f7a9d82022-09-08 20:55:421// Copyright 2015 The Chromium Authors
loysobb93bef2015-07-03 00:19:502// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "cc/animation/animation_timeline.h"
6
7#include <algorithm>
Peter Kastingb4ee3372021-07-06 23:02:298#include <utility>
9#include <vector>
loysobb93bef2015-07-03 00:19:5010
Peter Kastingb4ee3372021-07-06 23:02:2911#include "base/time/time.h"
Yi Guaa830ff2018-02-22 03:09:1112#include "cc/animation/animation.h"
loyso0bc588b2016-09-08 00:33:4513#include "cc/animation/animation_host.h"
Robert Flackf2d37b02023-06-06 18:25:4814#include "cc/animation/keyframe_effect.h"
Yi Guad72f3b2020-04-28 21:35:5915#include "cc/trees/property_tree.h"
loysobb93bef2015-07-03 00:19:5016
17namespace cc {
18
Kevin Ellis8bc26acd2023-02-07 17:52:4419scoped_refptr<AnimationTimeline> AnimationTimeline::Create(int id,
20 bool impl_only) {
21 return base::WrapRefCounted(new AnimationTimeline(id, impl_only));
loysobb93bef2015-07-03 00:19:5022}
23
Kevin Ellis8bc26acd2023-02-07 17:52:4424AnimationTimeline::AnimationTimeline(int id, bool is_impl_only)
loyso0bc588b2016-09-08 00:33:4525 : id_(id),
26 animation_host_(),
27 needs_push_properties_(false),
Kevin Ellis8bc26acd2023-02-07 17:52:4428 is_impl_only_(is_impl_only) {}
loysobb93bef2015-07-03 00:19:5029
30AnimationTimeline::~AnimationTimeline() {
Kevin Ellis8bc26acd2023-02-07 17:52:4431 for (auto& kv : id_to_animation_map_.Read(*this)) {
loyso10d62672016-02-09 06:48:2132 kv.second->SetAnimationTimeline(nullptr);
Kevin Ellis8bc26acd2023-02-07 17:52:4433 }
loysobb93bef2015-07-03 00:19:5034}
35
36scoped_refptr<AnimationTimeline> AnimationTimeline::CreateImplInstance() const {
37 scoped_refptr<AnimationTimeline> timeline = AnimationTimeline::Create(id());
38 return timeline;
39}
40
41void AnimationTimeline::SetAnimationHost(AnimationHost* animation_host) {
Kevin Ellis8bc26acd2023-02-07 17:52:4442 DCHECK(!animation_host || animation_host->IsOwnerThread());
43
loyso0bc588b2016-09-08 00:33:4544 if (animation_host_ == animation_host)
45 return;
46
Kevin Ellis8bc26acd2023-02-07 17:52:4447 WaitForProtectedSequenceCompletion();
48
loysobb93bef2015-07-03 00:19:5049 animation_host_ = animation_host;
Kevin Ellis8bc26acd2023-02-07 17:52:4450 for (auto& kv : id_to_animation_map_.Write(*this)) {
loyso10d62672016-02-09 06:48:2151 kv.second->SetAnimationHost(animation_host);
Kevin Ellis8bc26acd2023-02-07 17:52:4452 }
loyso0bc588b2016-09-08 00:33:4553
54 SetNeedsPushProperties();
loysobb93bef2015-07-03 00:19:5055}
56
Yi Guaa830ff2018-02-22 03:09:1157void AnimationTimeline::AttachAnimation(scoped_refptr<Animation> animation) {
58 DCHECK(animation->id());
Kevin Ellis8bc26acd2023-02-07 17:52:4459 animation->SetAnimationHost(animation_host());
Yi Guaa830ff2018-02-22 03:09:1160 animation->SetAnimationTimeline(this);
Kevin Ellis8bc26acd2023-02-07 17:52:4461 id_to_animation_map_.Write(*this).insert(
Yi Guaa830ff2018-02-22 03:09:1162 std::make_pair(animation->id(), std::move(animation)));
loyso0bc588b2016-09-08 00:33:4563
64 SetNeedsPushProperties();
loysobb93bef2015-07-03 00:19:5065}
66
Yi Guaa830ff2018-02-22 03:09:1167void AnimationTimeline::DetachAnimation(scoped_refptr<Animation> animation) {
68 DCHECK(animation->id());
69 EraseAnimation(animation);
Kevin Ellis8bc26acd2023-02-07 17:52:4470 id_to_animation_map_.Write(*this).erase(animation->id());
loyso0bc588b2016-09-08 00:33:4571
72 SetNeedsPushProperties();
loysobb93bef2015-07-03 00:19:5073}
74
Yi Guaa830ff2018-02-22 03:09:1175Animation* AnimationTimeline::GetAnimationById(int animation_id) const {
Kevin Ellis8bc26acd2023-02-07 17:52:4476 auto f = id_to_animation_map_.Read(*this).find(animation_id);
77 return f == id_to_animation_map_.Read(*this).end() ? nullptr
78 : f->second.get();
loysobb93bef2015-07-03 00:19:5079}
80
Yi Guaa830ff2018-02-22 03:09:1181void AnimationTimeline::ClearAnimations() {
Kevin Ellis8bc26acd2023-02-07 17:52:4482 for (auto& kv : id_to_animation_map_.Write(*this)) {
Yi Guaa830ff2018-02-22 03:09:1183 EraseAnimation(kv.second);
Kevin Ellis8bc26acd2023-02-07 17:52:4484 }
85 id_to_animation_map_.Write(*this).clear();
loyso0bc588b2016-09-08 00:33:4586
87 SetNeedsPushProperties();
88}
89
Yi Guad72f3b2020-04-28 21:35:5990bool AnimationTimeline::TickTimeLinkedAnimations(
91 const std::vector<scoped_refptr<Animation>>& ticking_animations,
Robert Flackf2d37b02023-06-06 18:25:4892 base::TimeTicks monotonic_time,
93 bool tick_finished) {
Yi Guad72f3b2020-04-28 21:35:5994 DCHECK(!IsScrollTimeline());
95
96 bool animated = false;
97 for (auto& animation : ticking_animations) {
98 if (animation->animation_timeline() != this)
99 continue;
100 // Worklet animations are ticked separately by AnimationHost.
101 if (animation->IsWorkletAnimation())
102 continue;
103
104 // Scroll-linked animations are ticked separately.
105 if (animation->IsScrollLinkedAnimation())
106 continue;
107
Robert Flackf2d37b02023-06-06 18:25:48108 if (!tick_finished && animation->keyframe_effect()->awaiting_deletion()) {
109 continue;
110 }
111
112 animated |= animation->Tick(monotonic_time);
Yi Guad72f3b2020-04-28 21:35:59113 }
114 return animated;
115}
116
117bool AnimationTimeline::TickScrollLinkedAnimations(
118 const std::vector<scoped_refptr<Animation>>& ticking_animations,
119 const ScrollTree& scroll_tree,
120 bool is_active_tree) {
121 return false;
122}
123
loyso0bc588b2016-09-08 00:33:45124void AnimationTimeline::SetNeedsPushProperties() {
Kevin Ellis8bc26acd2023-02-07 17:52:44125 needs_push_properties_.Write(*this) = true;
126 if (animation_host()) {
127 animation_host()->SetNeedsPushProperties();
128 }
loysobb93bef2015-07-03 00:19:50129}
130
131void AnimationTimeline::PushPropertiesTo(AnimationTimeline* timeline_impl) {
Kevin Ellis8bc26acd2023-02-07 17:52:44132 if (needs_push_properties_.Read(*this)) {
133 needs_push_properties_.Write(*this) = false;
Yi Guaa830ff2018-02-22 03:09:11134 PushAttachedAnimationsToImplThread(timeline_impl);
135 RemoveDetachedAnimationsFromImplThread(timeline_impl);
loyso0bc588b2016-09-08 00:33:45136 PushPropertiesToImplThread(timeline_impl);
137 }
loysobb93bef2015-07-03 00:19:50138}
139
Yi Guaa830ff2018-02-22 03:09:11140void AnimationTimeline::PushAttachedAnimationsToImplThread(
loysobb93bef2015-07-03 00:19:50141 AnimationTimeline* timeline_impl) const {
Kevin Ellis8bc26acd2023-02-07 17:52:44142 for (auto& kv : id_to_animation_map_.Read(*this)) {
Yi Guaa830ff2018-02-22 03:09:11143 auto& animation = kv.second;
144 Animation* animation_impl =
145 timeline_impl->GetAnimationById(animation->id());
146 if (animation_impl)
loysobb93bef2015-07-03 00:19:50147 continue;
148
Yi Guaa830ff2018-02-22 03:09:11149 scoped_refptr<Animation> to_add = animation->CreateImplInstance();
150 timeline_impl->AttachAnimation(to_add.get());
loysobb93bef2015-07-03 00:19:50151 }
152}
153
Yi Guaa830ff2018-02-22 03:09:11154void AnimationTimeline::RemoveDetachedAnimationsFromImplThread(
loysobb93bef2015-07-03 00:19:50155 AnimationTimeline* timeline_impl) const {
Kevin Ellis8bc26acd2023-02-07 17:52:44156 IdToAnimationMap& animations_impl =
157 timeline_impl->id_to_animation_map_.Write(*this);
loysobb93bef2015-07-03 00:19:50158
Yi Guaa830ff2018-02-22 03:09:11159 // Erase all the impl animations which |this| doesn't have.
160 for (auto it = animations_impl.begin(); it != animations_impl.end();) {
161 if (GetAnimationById(it->second->id())) {
loyso10d62672016-02-09 06:48:21162 ++it;
163 } else {
Yi Guaa830ff2018-02-22 03:09:11164 timeline_impl->EraseAnimation(it->second);
165 it = animations_impl.erase(it);
loyso10d62672016-02-09 06:48:21166 }
167 }
loysobb93bef2015-07-03 00:19:50168}
169
Yi Guaa830ff2018-02-22 03:09:11170void AnimationTimeline::EraseAnimation(scoped_refptr<Animation> animation) {
Yi Gub0422c42020-01-13 17:00:36171 if (animation->element_animations())
Yi Guaa830ff2018-02-22 03:09:11172 animation->DetachElement();
Robert Flackca12161ac2022-03-14 18:09:19173 animation->SetAnimationHost(nullptr);
Robert Flack670a727d2022-03-17 01:13:15174 animation->SetAnimationTimeline(nullptr);
loysobb93bef2015-07-03 00:19:50175}
176
177void AnimationTimeline::PushPropertiesToImplThread(
178 AnimationTimeline* timeline_impl) {
Kevin Ellis8bc26acd2023-02-07 17:52:44179 for (auto& kv : id_to_animation_map_.Read(*this)) {
Yi Guaa830ff2018-02-22 03:09:11180 Animation* animation = kv.second.get();
181 if (Animation* animation_impl =
182 timeline_impl->GetAnimationById(animation->id())) {
183 animation->PushPropertiesTo(animation_impl);
loyso0bc588b2016-09-08 00:33:45184 }
loysobb93bef2015-07-03 00:19:50185 }
186}
187
Yi Gu352fe2a42020-01-21 17:38:10188bool AnimationTimeline::IsScrollTimeline() const {
189 return false;
190}
191
Steve Kobes5aa845c2023-04-24 15:01:50192bool AnimationTimeline::IsLinkedToScroller(ElementId scroller) const {
193 return false;
194}
195
Kevin Ellis8bc26acd2023-02-07 17:52:44196bool AnimationTimeline::IsOwnerThread() const {
197 return !animation_host_ || animation_host_->IsOwnerThread();
198}
199
200bool AnimationTimeline::InProtectedSequence() const {
201 return !animation_host_ || animation_host_->InProtectedSequence();
202}
203
204void AnimationTimeline::WaitForProtectedSequenceCompletion() const {
205 if (animation_host_) {
206 animation_host_->WaitForProtectedSequenceCompletion();
207 }
208}
209
loysobb93bef2015-07-03 00:19:50210} // namespace cc