1 // Copyright (c) 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
7 tvcm.require('tvcm.utils');
8 tvcm.require('tvcm.ui.animation');
10 tvcm.exportTo('tracing', function() {
11 var kDefaultPanAnimatoinDurationMs = 100.0;
14 * Pans a TimelineDisplayTransform by a given amount.
16 * @extends {tvcm.ui.Animation}
17 * @param {Number} deltaX The total amount of change to the transform's panX.
18 * @param {Number} deltaY The total amount of change to the transform's panY.
19 * @param {Number=} opt_durationMs How long the pan animation should run.
20 * Defaults to kDefaultPanAnimatoinDurationMs.
22 function TimelineDisplayTransformPanAnimation(
23 deltaX, deltaY, opt_durationMs) {
26 if (opt_durationMs === undefined)
27 this.durationMs = kDefaultPanAnimatoinDurationMs;
29 this.durationMs = opt_durationMs;
31 this.startPanX = undefined;
32 this.startPanY = undefined;
33 this.startTimeMs = undefined;
36 TimelineDisplayTransformPanAnimation.prototype = {
37 __proto__: tvcm.ui.Animation.prototype,
40 return this.deltaY !== 0;
43 canTakeOverFor: function(existingAnimation) {
44 return existingAnimation instanceof TimelineDisplayTransformPanAnimation;
47 takeOverFor: function(existing, timestamp, target) {
48 var remainingDeltaXOnExisting = existing.goalPanX - target.panX;
49 var remainingDeltaYOnExisting = existing.goalPanY - target.panY;
50 var remainingTimeOnExisting = timestamp - (
51 existing.startTimeMs + existing.durationMs);
52 remainingTimeOnExisting = Math.max(remainingTimeOnExisting, 0);
54 this.deltaX += remainingDeltaXOnExisting;
55 this.deltaY += remainingDeltaYOnExisting;
56 this.durationMs += remainingTimeOnExisting;
59 start: function(timestamp, target) {
60 this.startTimeMs = timestamp;
61 this.startPanX = target.panX;
62 this.startPanY = target.panY;
65 tick: function(timestamp, target) {
66 var percentDone = (timestamp - this.startTimeMs) / this.durationMs;
67 percentDone = tvcm.clamp(percentDone, 0, 1);
69 target.panX = tvcm.lerp(percentDone, this.startPanX, this.goalPanX);
71 target.panY = tvcm.lerp(percentDone, this.startPanY, this.goalPanY);
72 return timestamp >= this.startTimeMs + this.durationMs;
76 return this.startPanX + this.deltaX;
80 return this.startPanY + this.deltaY;
85 * Zooms in/out on a specified location in the world.
87 * Zooming in and out is all about keeping the area under the mouse cursor,
88 * here called the "focal point" in the same place under the zoom. If one
89 * simply changes the scale, the area under the mouse cursor will change. To
90 * keep the focal point from moving during the zoom, the pan needs to change
91 * in order to compensate. Thus, a ZoomTo animation is given both a focal
92 * point in addition to the amount by which to zoom.
95 * @extends {tvcm.ui.Animation}
96 * @param {Number} goalFocalPointXWorld The X coordinate in the world which is
98 * @param {Number} goalFocalPointXView Where on the screen the
99 * goalFocalPointXWorld should stay centered during the zoom.
100 * @param {Number} goalFocalPointY Where the panY should be when the zoom
102 * @param {Number} zoomInRatioX The ratio of the current scaleX to the goal
105 function TimelineDisplayTransformZoomToAnimation(
106 goalFocalPointXWorld,
111 this.goalFocalPointXWorld = goalFocalPointXWorld;
112 this.goalFocalPointXView = goalFocalPointXView;
113 this.goalFocalPointY = goalFocalPointY;
114 this.zoomInRatioX = zoomInRatioX;
115 if (opt_durationMs === undefined)
116 this.durationMs = kDefaultPanAnimatoinDurationMs;
118 this.durationMs = opt_durationMs;
120 this.startTimeMs = undefined;
121 this.startScaleX = undefined;
122 this.goalScaleX = undefined;
123 this.startPanY = undefined;
124 this.goalPanY = undefined;
127 TimelineDisplayTransformZoomToAnimation.prototype = {
128 __proto__: tvcm.ui.Animation.prototype,
131 return this.startPanY != this.goalPanY;
134 canTakeOverFor: function(existingAnimation) {
138 takeOverFor: function(existingAnimation, timestamp, target) {
139 this.goalScaleX = target.scaleX * this.zoomInRatioX;
142 start: function(timestamp, target) {
143 this.startTimeMs = timestamp;
144 this.startScaleX = target.scaleX;
145 this.goalScaleX = this.zoomInRatioX * target.scaleX;
146 this.startPanY = target.panY;
149 tick: function(timestamp, target) {
150 var percentDone = (timestamp - this.startTimeMs) / this.durationMs;
151 percentDone = tvcm.clamp(percentDone, 0, 1);
153 target.scaleX = tvcm.lerp(percentDone, this.startScaleX, this.goalScaleX);
154 if (this.affectsPanY) {
155 target.panY = tvcm.lerp(
156 percentDone, this.startPanY, this.goalFocalPointY);
159 target.xPanWorldPosToViewPos(
160 this.goalFocalPointXWorld, this.goalFocalPointXView);
161 return timestamp >= this.startTimeMs + this.durationMs;
166 TimelineDisplayTransformPanAnimation:
167 TimelineDisplayTransformPanAnimation,
168 TimelineDisplayTransformZoomToAnimation:
169 TimelineDisplayTransformZoomToAnimation