• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2022 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package android.window;
18 
19 import static com.android.window.flags.Flags.FLAG_PREDICTIVE_BACK_SWIPE_EDGE_NONE_API;
20 import static com.android.window.flags.Flags.FLAG_PREDICTIVE_BACK_TIMESTAMP_API;
21 import static com.android.window.flags.Flags.predictiveBackTimestampApi;
22 
23 import android.annotation.FlaggedApi;
24 import android.annotation.FloatRange;
25 import android.annotation.IntDef;
26 
27 import java.lang.annotation.Retention;
28 import java.lang.annotation.RetentionPolicy;
29 
30 /**
31  * Object used to report back gesture progress.
32  * Holds information about the touch event, swipe direction and the animation progress that
33  * predictive back animations should seek to.
34  */
35 public final class BackEvent {
36     /** Indicates that the edge swipe starts from the left edge of the screen */
37     public static final int EDGE_LEFT = 0;
38     /** Indicates that the edge swipe starts from the right edge of the screen */
39     public static final int EDGE_RIGHT = 1;
40     /**
41      * Indicates that the back event was not triggered by an edge swipe back gesture. This applies
42      * to cases like using the back button in 3-button navigation or pressing a hardware back
43      * button.
44      */
45     @FlaggedApi(FLAG_PREDICTIVE_BACK_SWIPE_EDGE_NONE_API)
46     public static final int EDGE_NONE = 2;
47 
48     /** @hide */
49     @IntDef({
50             EDGE_LEFT,
51             EDGE_RIGHT,
52             EDGE_NONE,
53     })
54     @Retention(RetentionPolicy.SOURCE)
55     public @interface SwipeEdge{}
56 
57     private final float mTouchX;
58     private final float mTouchY;
59     private final float mProgress;
60     private final long mFrameTimeMillis;
61 
62     @SwipeEdge
63     private final int mSwipeEdge;
64 
65     /** @hide */
fromBackMotionEvent(BackMotionEvent backMotionEvent)66     public static BackEvent fromBackMotionEvent(BackMotionEvent backMotionEvent) {
67         if (predictiveBackTimestampApi()) {
68             return new BackEvent(backMotionEvent.getTouchX(), backMotionEvent.getTouchY(),
69                     backMotionEvent.getProgress(), backMotionEvent.getSwipeEdge(),
70                     backMotionEvent.getFrameTimeMillis());
71         } else {
72             return new BackEvent(backMotionEvent.getTouchX(), backMotionEvent.getTouchY(),
73                     backMotionEvent.getProgress(), backMotionEvent.getSwipeEdge());
74         }
75     }
76 
77     /**
78      * Creates a new {@link BackEvent} instance with a frame time of 0.
79      *
80      * @param touchX Absolute X location of the touch point of this event.
81      * @param touchY Absolute Y location of the touch point of this event.
82      * @param progress Value between 0 and 1 on how far along the back gesture is.
83      * @param swipeEdge Indicates which edge the swipe starts from.
84      */
BackEvent(float touchX, float touchY, float progress, @SwipeEdge int swipeEdge)85     public BackEvent(float touchX, float touchY, float progress, @SwipeEdge int swipeEdge) {
86         mTouchX = touchX;
87         mTouchY = touchY;
88         mProgress = progress;
89         mSwipeEdge = swipeEdge;
90         mFrameTimeMillis = 0;
91     }
92 
93     /**
94      * Creates a new {@link BackEvent} instance.
95      *
96      * @param touchX Absolute X location of the touch point of this event.
97      * @param touchY Absolute Y location of the touch point of this event.
98      * @param progress Value between 0 and 1 on how far along the back gesture is.
99      * @param swipeEdge Indicates which edge the swipe starts from.
100      * @param frameTimeMillis frame time of the back event.
101      */
102     @FlaggedApi(FLAG_PREDICTIVE_BACK_TIMESTAMP_API)
BackEvent(float touchX, float touchY, float progress, @SwipeEdge int swipeEdge, long frameTimeMillis)103     public BackEvent(float touchX, float touchY, float progress, @SwipeEdge int swipeEdge,
104             long frameTimeMillis) {
105         mTouchX = touchX;
106         mTouchY = touchY;
107         mProgress = progress;
108         mSwipeEdge = swipeEdge;
109         mFrameTimeMillis = frameTimeMillis;
110     }
111 
112     /**
113      * Returns a value between 0 and 1 on how far along the back gesture is. This value is
114      * driven by the horizontal location of the touch point, and should be used as the fraction to
115      * seek the predictive back animation with. Specifically,
116      * <ol>
117      * <li>The progress is 0 when the touch is at the starting edge of the screen (left or right),
118      * and animation should seek to its start state.
119      * <li>The progress is approximately 1 when the touch is at the opposite side of the screen,
120      * and animation should seek to its end state. Exact end value may vary depending on
121      * screen size.
122      * </ol>
123      * <li> After the gesture finishes in cancel state, this method keeps getting invoked until the
124      * progress value animates back to 0.
125      * </ol>
126      * In-between locations are linearly interpolated based on horizontal distance from the starting
127      * edge and smooth clamped to 1 when the distance exceeds a system-wide threshold.
128      */
129     @FloatRange(from = 0, to = 1)
getProgress()130     public float getProgress() {
131         return mProgress;
132     }
133 
134     /**
135      * Returns the absolute X location of the touch point, or NaN if the event is from
136      * a button press.
137      */
getTouchX()138     public float getTouchX() {
139         return mTouchX;
140     }
141 
142     /**
143      * Returns the absolute Y location of the touch point, or NaN if the event is from
144      * a button press.
145      */
getTouchY()146     public float getTouchY() {
147         return mTouchY;
148     }
149 
150     /**
151      * Returns the screen edge that the swipe starts from.
152      */
153     @SwipeEdge
getSwipeEdge()154     public int getSwipeEdge() {
155         return mSwipeEdge;
156     }
157 
158     /**
159      * Returns the frameTime of the BackEvent in milliseconds. Useful for calculating velocity.
160      */
161     @FlaggedApi(FLAG_PREDICTIVE_BACK_TIMESTAMP_API)
getFrameTimeMillis()162     public long getFrameTimeMillis() {
163         return mFrameTimeMillis;
164     }
165 
166     @Override
equals(Object other)167     public boolean equals(Object other) {
168         if (this == other) {
169             return true;
170         }
171         if (!(other instanceof BackEvent)) {
172             return false;
173         }
174         final BackEvent that = (BackEvent) other;
175         return mTouchX == that.mTouchX
176                 && mTouchY == that.mTouchY
177                 && mProgress == that.mProgress
178                 && mSwipeEdge == that.mSwipeEdge
179                 && mFrameTimeMillis == that.mFrameTimeMillis;
180     }
181 
182     @Override
toString()183     public String toString() {
184         return "BackEvent{"
185                 + "mTouchX=" + mTouchX
186                 + ", mTouchY=" + mTouchY
187                 + ", mProgress=" + mProgress
188                 + ", mSwipeEdge=" + mSwipeEdge
189                 + ", mFrameTimeMillis=" + mFrameTimeMillis
190                 + "}";
191     }
192 }
193