Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(51)

Side by Side Diff: cc/page_scale_animation.cc

Issue 11364189: cc: Clean up PageScaleAnimation for readability. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Rename targetPosition to targetOffset Created 8 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « cc/page_scale_animation.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2012 The Chromium Authors. All rights reserved. 1 // Copyright 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "cc/page_scale_animation.h" 5 #include "cc/page_scale_animation.h"
6 6
7 #include "base/logging.h"
7 #include "cc/geometry.h" 8 #include "cc/geometry.h"
8 #include "ui/gfx/point_f.h" 9 #include "ui/gfx/point_f.h"
9 #include "ui/gfx/rect_f.h" 10 #include "ui/gfx/rect_f.h"
11 #include "ui/gfx/vector2d_conversions.h"
10 12
11 #include <math.h> 13 #include <math.h>
12 14
13 namespace { 15 namespace {
14 16
15 gfx::PointF toPointF(const gfx::Vector2dF& vector)
16 {
17 return gfx::PointF(vector.x(), vector.y());
18 }
19
20 // This takes a viewport-relative vector and returns a vector whose values are 17 // This takes a viewport-relative vector and returns a vector whose values are
21 // between 0 and 1, representing the percentage position within the viewport. 18 // between 0 and 1, representing the percentage position within the viewport.
22 gfx::Vector2dF normalizeFromViewport(const gfx::Vector2dF& denormalized, const g fx::SizeF& viewportSize) 19 gfx::Vector2dF normalizeFromViewport(const gfx::Vector2dF& denormalized, const g fx::SizeF& viewportSize)
23 { 20 {
24 return gfx::ScaleVector2d(denormalized, 1 / viewportSize.width(), 1 / viewpo rtSize.height()); 21 return gfx::ScaleVector2d(denormalized, 1 / viewportSize.width(), 1 / viewpo rtSize.height());
25 } 22 }
26 23
27 gfx::Vector2dF denormalizeToViewport(const gfx::Vector2dF& normalized, const gfx ::SizeF& viewportSize) 24 gfx::Vector2dF denormalizeToViewport(const gfx::Vector2dF& normalized, const gfx ::SizeF& viewportSize)
28 { 25 {
29 return gfx::ScaleVector2d(normalized, viewportSize.width(), viewportSize.hei ght()); 26 return gfx::ScaleVector2d(normalized, viewportSize.width(), viewportSize.hei ght());
30 } 27 }
31 28
32 gfx::Vector2dF interpolateBetween(const gfx::Vector2dF& start, const gfx::Vector 2dF end, float interp) 29 gfx::Vector2dF interpolateBetween(const gfx::Vector2dF& start, const gfx::Vector 2dF end, float interp)
33 { 30 {
34 gfx::Vector2dF result; 31 return start + gfx::ScaleVector2d(end - start, interp);
35 result.set_x(start.x() + interp * (end.x() - start.x()));
36 result.set_y(start.y() + interp * (end.y() - start.y()));
37 return result;
38 } 32 }
39 33
40 } 34 }
41 35
42 namespace cc { 36 namespace cc {
43 37
44 scoped_ptr<PageScaleAnimation> PageScaleAnimation::create(const gfx::Vector2dF& startScrollOffset, float startPageScaleFactor, const gfx::SizeF& viewportSize, c onst gfx::SizeF& rootLayerSize, double startTime) 38 scoped_ptr<PageScaleAnimation> PageScaleAnimation::create(const gfx::Vector2dF& startScrollOffset, float startPageScaleFactor, const gfx::SizeF& viewportSize, c onst gfx::SizeF& rootLayerSize, double startTime)
45 { 39 {
46 return make_scoped_ptr(new PageScaleAnimation(startScrollOffset, startPageSc aleFactor, viewportSize, rootLayerSize, startTime)); 40 return make_scoped_ptr(new PageScaleAnimation(startScrollOffset, startPageSc aleFactor, viewportSize, rootLayerSize, startTime));
47 } 41 }
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after
90 84
91 // We start zooming out from the anchor tapped by the user. But if 85 // We start zooming out from the anchor tapped by the user. But if
92 // the target scale is impossible to attain without hitting the root layer 86 // the target scale is impossible to attain without hitting the root layer
93 // edges, then infer an anchor that doesn't collide with the edges. 87 // edges, then infer an anchor that doesn't collide with the edges.
94 // We will interpolate between the two anchors during the animation. 88 // We will interpolate between the two anchors during the animation.
95 inferTargetScrollOffsetFromStartAnchor(); 89 inferTargetScrollOffsetFromStartAnchor();
96 clampTargetScrollOffset(); 90 clampTargetScrollOffset();
97 inferTargetAnchorFromScrollOffsets(); 91 inferTargetAnchorFromScrollOffsets();
98 } 92 }
99 93
100 gfx::SizeF PageScaleAnimation::viewportSizeAtScale(float pageScaleFactor) const
101 {
102 return gfx::ScaleSize(m_viewportSize, 1 / pageScaleFactor);
103 }
104
105 void PageScaleAnimation::inferTargetScrollOffsetFromStartAnchor() 94 void PageScaleAnimation::inferTargetScrollOffsetFromStartAnchor()
106 { 95 {
107 gfx::Vector2dF anchorRelativeToStartViewport = m_startAnchor - m_startScroll Offset; 96 gfx::Vector2dF normalized = normalizeFromViewport(m_startAnchor - m_startScr ollOffset, startViewportSize());
108 gfx::Vector2dF normalized = normalizeFromViewport(anchorRelativeToStartViewp ort, viewportSizeAtScale(m_startPageScaleFactor)); 97 m_targetScrollOffset = m_startAnchor - denormalizeToViewport(normalized, tar getViewportSize());
109 m_targetScrollOffset = m_startAnchor - denormalizeToViewport(normalized, vie wportSizeAtScale(m_targetPageScaleFactor));
110 } 98 }
111 99
112 void PageScaleAnimation::inferTargetAnchorFromScrollOffsets() 100 void PageScaleAnimation::inferTargetAnchorFromScrollOffsets()
113 { 101 {
114 gfx::RectF startRect(toPointF(m_startScrollOffset), viewportSizeAtScale(m_st artPageScaleFactor));
115 gfx::RectF targetRect(toPointF(m_targetScrollOffset), viewportSizeAtScale(m_ targetPageScaleFactor));
116
117 // The anchor is the point which is at the same normalized relative position 102 // The anchor is the point which is at the same normalized relative position
118 // within both startRect and endRect. For example, a zoom-in double-tap to a 103 // within both start viewport rect and target viewport rect. For example, a
119 // perfectly centered rect will have normalized anchor (0.5, 0.5), while one 104 // zoom-in double-tap to a perfectly centered rect will have normalized
120 // to a rect touching the bottom-right of the screen will have normalized 105 // anchor (0.5, 0.5), while one to a rect touching the bottom-right of the
121 // anchor (1.0, 1.0). In other words, it obeys the equations: 106 // screen will have normalized anchor (1.0, 1.0). In other words, it obeys
122 // anchorX = start_width * normalizedX + start_x 107 // the equations:
123 // anchorX = target_width * normalizedX + target_x 108 // anchor = start_size * normalized + start_offset
124 // anchorY = start_height * normalizedY + start_y 109 // anchor = target_size * normalized + target_offset
125 // anchorY = target_height * normalizedY + target_y 110 // where both anchor and normalized begin as unknowns. Solving
126 // where both anchor{x,y} and normalized{x,y} begin as unknowns. Solving 111 // for the normalized, we get the following:
127 // for the normalized, we get the following formulas: 112 float widthScale = 1 / (targetViewportSize().width() - startViewportSize().w idth());
128 gfx::Vector2dF normalized; 113 float heightScale = 1 / (targetViewportSize().height() - startViewportSize() .height());
129 normalized.set_x((startRect.x() - targetRect.x()) / (targetRect.width() - st artRect.width())); 114 gfx::Vector2dF normalized = ScaleVector2d(m_startScrollOffset - m_targetScro llOffset, widthScale, heightScale);
danakj 2012/11/14 00:47:23 nit: gfx::ScaleVector2d
aelias_OOO_until_Jul13 2012/11/14 02:26:51 Done.
130 normalized.set_y((startRect.y() - targetRect.y()) / (targetRect.height() - s tartRect.height())); 115 m_targetAnchor = m_targetScrollOffset + denormalizeToViewport(normalized, ta rgetViewportSize());
131 m_targetAnchor = m_targetScrollOffset + denormalizeToViewport(normalized, vi ewportSizeAtScale(m_targetPageScaleFactor));
132 } 116 }
133 117
134 void PageScaleAnimation::clampTargetScrollOffset() 118 void PageScaleAnimation::clampTargetScrollOffset()
135 { 119 {
136 gfx::Vector2dF maxScrollOffset = BottomRight(gfx::RectF(m_rootLayerSize)) - BottomRight(gfx::RectF(viewportSizeAtScale(m_targetPageScaleFactor))); 120 gfx::Vector2dF maxScrollOffset = BottomRight(gfx::RectF(m_rootLayerSize)) - BottomRight(gfx::RectF(targetViewportSize()));
137 m_targetScrollOffset.ClampToMin(gfx::Vector2dF()); 121 m_targetScrollOffset.ClampToMin(gfx::Vector2dF());
138 m_targetScrollOffset.ClampToMax(maxScrollOffset); 122 m_targetScrollOffset.ClampToMax(maxScrollOffset);
139 } 123 }
140 124
125 gfx::SizeF PageScaleAnimation::startViewportSize() const
126 {
127 return gfx::ScaleSize(m_viewportSize, 1 / m_startPageScaleFactor);
128 }
129
130 gfx::SizeF PageScaleAnimation::targetViewportSize() const
131 {
132 return gfx::ScaleSize(m_viewportSize, 1 / m_targetPageScaleFactor);
133 }
134
135 gfx::SizeF PageScaleAnimation::viewportSizeAt(float interp) const
136 {
137 return gfx::ScaleSize(m_viewportSize, 1 / pageScaleFactorAt(interp));
138 }
139
141 gfx::Vector2dF PageScaleAnimation::scrollOffsetAtTime(double time) const 140 gfx::Vector2dF PageScaleAnimation::scrollOffsetAtTime(double time) const
142 { 141 {
143 return scrollOffsetAt(interpAtTime(time)); 142 return scrollOffsetAt(interpAtTime(time));
144 } 143 }
145 144
146 float PageScaleAnimation::pageScaleFactorAtTime(double time) const 145 float PageScaleAnimation::pageScaleFactorAtTime(double time) const
147 { 146 {
148 return pageScaleFactorAt(interpAtTime(time)); 147 return pageScaleFactorAt(interpAtTime(time));
149 } 148 }
150 149
151 bool PageScaleAnimation::isAnimationCompleteAtTime(double time) const 150 bool PageScaleAnimation::isAnimationCompleteAtTime(double time) const
152 { 151 {
153 return time >= endTime(); 152 return time >= endTime();
154 } 153 }
155 154
156 float PageScaleAnimation::interpAtTime(double time) const 155 float PageScaleAnimation::interpAtTime(double time) const
157 { 156 {
157 DCHECK_GE(time, m_startTime);
158 if (isAnimationCompleteAtTime(time)) 158 if (isAnimationCompleteAtTime(time))
159 return 1; 159 return 1;
160 160
161 return (time - m_startTime) / m_duration; 161 return (time - m_startTime) / m_duration;
162 } 162 }
163 163
164 gfx::Vector2dF PageScaleAnimation::scrollOffsetAt(float interp) const 164 gfx::Vector2dF PageScaleAnimation::scrollOffsetAt(float interp) const
165 { 165 {
166 if (interp <= 0) 166 if (interp <= 0)
167 return m_startScrollOffset; 167 return m_startScrollOffset;
168 if (interp >= 1) 168 if (interp >= 1)
169 return m_targetScrollOffset; 169 return m_targetScrollOffset;
170 170
171 return anchorAt(interp) - viewportRelativeAnchorAt(interp); 171 return anchorAt(interp) - viewportRelativeAnchorAt(interp);
172 } 172 }
173 173
174 gfx::Vector2dF PageScaleAnimation::anchorAt(float interp) const 174 gfx::Vector2dF PageScaleAnimation::anchorAt(float interp) const
175 { 175 {
176 // Interpolate from start to target anchor in absolute space. 176 // Interpolate from start to target anchor in absolute space.
177 gfx::Vector2dF delta = gfx::ScaleVector2d(m_targetAnchor - m_startAnchor, in terp); 177 return interpolateBetween(m_startAnchor, m_targetAnchor, interp);
178 return m_startAnchor + delta;
179 } 178 }
180 179
181 gfx::Vector2dF PageScaleAnimation::viewportRelativeAnchorAt(float interp) const 180 gfx::Vector2dF PageScaleAnimation::viewportRelativeAnchorAt(float interp) const
182 { 181 {
183 // Interpolate from start to target anchor in the space relative to the 182 // Interpolate from start to target anchor in normalized space.
184 // viewport at its current scale level. 183 gfx::Vector2dF startNormalized = normalizeFromViewport(m_startAnchor - m_sta rtScrollOffset, startViewportSize());
185 gfx::Vector2dF anchorRelativeToStartViewport = m_startAnchor - m_startScroll Offset; 184 gfx::Vector2dF targetNormalized = normalizeFromViewport(m_targetAnchor - m_t argetScrollOffset, targetViewportSize());
186 gfx::Vector2dF anchorRelativeToTargetViewport = m_targetAnchor - m_targetScr ollOffset;
187
188 gfx::Vector2dF startNormalized = normalizeFromViewport(anchorRelativeToStart Viewport, viewportSizeAtScale(m_startPageScaleFactor));
189 gfx::Vector2dF targetNormalized = normalizeFromViewport(anchorRelativeToTarg etViewport, viewportSizeAtScale(m_targetPageScaleFactor));
190 gfx::Vector2dF interpNormalized = interpolateBetween(startNormalized, target Normalized, interp); 185 gfx::Vector2dF interpNormalized = interpolateBetween(startNormalized, target Normalized, interp);
191 186
192 gfx::SizeF currentViewportSize = viewportSizeAtScale(pageScaleFactorAt(inter p)); 187 return denormalizeToViewport(interpNormalized, viewportSizeAt(interp));
193 return denormalizeToViewport(interpNormalized, currentViewportSize);
194 } 188 }
195 189
196 float PageScaleAnimation::pageScaleFactorAt(float interp) const 190 float PageScaleAnimation::pageScaleFactorAt(float interp) const
197 { 191 {
198 if (interp <= 0) 192 if (interp <= 0)
199 return m_startPageScaleFactor; 193 return m_startPageScaleFactor;
200 if (interp >= 1) 194 if (interp >= 1)
201 return m_targetPageScaleFactor; 195 return m_targetPageScaleFactor;
202 196
203 // Linearly interpolate the magnitude in log scale. 197 // Linearly interpolate the magnitude in log scale.
204 float diff = m_targetPageScaleFactor / m_startPageScaleFactor; 198 float diff = m_targetPageScaleFactor / m_startPageScaleFactor;
205 float logDiff = log(diff); 199 float logDiff = log(diff);
206 logDiff *= interp; 200 logDiff *= interp;
207 diff = exp(logDiff); 201 diff = exp(logDiff);
208 return m_startPageScaleFactor * diff; 202 return m_startPageScaleFactor * diff;
209 } 203 }
210 204
211 } // namespace cc 205 } // namespace cc
OLDNEW
« no previous file with comments | « cc/page_scale_animation.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698