16b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh/*
26b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh * Copyright (C) 2018 The Android Open Source Project
36b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh *
46b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh * Licensed under the Apache License, Version 2.0 (the "License");
56b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh * you may not use this file except in compliance with the License.
66b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh * You may obtain a copy of the License at
76b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh *
86b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh *      http://www.apache.org/licenses/LICENSE-2.0
96b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh *
106b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh * Unless required by applicable law or agreed to in writing, software
116b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh * distributed under the License is distributed on an "AS IS" BASIS,
126b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
136b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh * See the License for the specific language governing permissions and
146b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh * limitations under the License.
156b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh */
166b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikhpackage com.android.systemui.qs.touch;
176b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh
186b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh/**
196b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh * Utility methods for overscroll damping and related effect.
206b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh *
216b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh * Copied from packages/apps/Launcher3/src/com/android/launcher3/touch/OverScroll.java
226b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh */
236b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikhpublic class OverScroll {
246b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh
256b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh    private static final float OVERSCROLL_DAMP_FACTOR = 0.07f;
266b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh
276b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh    /**
286b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh     * This curve determines how the effect of scrolling over the limits of the page diminishes
296b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh     * as the user pulls further and further from the bounds
306b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh     *
316b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh     * @param f The percentage of how much the user has overscrolled.
326b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh     * @return A transformed percentage based on the influence curve.
336b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh     */
346b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh    private static float overScrollInfluenceCurve(float f) {
356b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh        f -= 1.0f;
366b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh        return f * f * f + 1.0f;
376b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh    }
386b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh
396b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh    /**
406b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh     * @param amount The original amount overscrolled.
416b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh     * @param max The maximum amount that the View can overscroll.
426b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh     * @return The dampened overscroll amount.
436b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh     */
446b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh    public static int dampedScroll(float amount, int max) {
456b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh        if (Float.compare(amount, 0) == 0) return 0;
466b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh
476b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh        float f = amount / max;
486b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh        f = f / (Math.abs(f)) * (overScrollInfluenceCurve(Math.abs(f)));
496b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh
506b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh        // Clamp this factor, f, to -1 < f < 1
516b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh        if (Math.abs(f) >= 1) {
526b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh            f /= Math.abs(f);
536b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh        }
546b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh
556b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh        return Math.round(OVERSCROLL_DAMP_FACTOR * f * max);
566b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh    }
576b3b4f49a5b53fbf937f66e5f3ba03d23980e52cAmin Shaikh}
58