Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit e9bf7c84 authored by TreeHugger Robot's avatar TreeHugger Robot Committed by Android (Google) Code Review
Browse files

Merge "Introduce PathInterpolator to native animators"

parents f7c77a3c 9e9eeeeb
Loading
Loading
Loading
Loading
+12 −1
Original line number Diff line number Diff line
@@ -25,6 +25,9 @@ import android.util.PathParser;
import android.view.InflateException;

import com.android.internal.R;
import com.android.internal.view.animation.HasNativeInterpolator;
import com.android.internal.view.animation.NativeInterpolatorFactory;
import com.android.internal.view.animation.NativeInterpolatorFactoryHelper;

/**
 * An interpolator that can traverse a Path that extends from <code>Point</code>
@@ -42,7 +45,8 @@ import com.android.internal.R;
 *     path.lineTo(1f, 1f);
 * </pre></blockquote></p>
 */
public class PathInterpolator extends BaseInterpolator {
@HasNativeInterpolator
public class PathInterpolator extends BaseInterpolator implements NativeInterpolatorFactory {

    // This governs how accurate the approximation of the Path is.
    private static final float PRECISION = 0.002f;
@@ -229,4 +233,11 @@ public class PathInterpolator extends BaseInterpolator {
        float endY = mY[endIndex];
        return startY + (fraction * (endY - startY));
    }

    /** @hide **/
    @Override
    public long createNativeInterpolator() {
        return NativeInterpolatorFactoryHelper.createPathInterpolator(mX, mY);
    }

}
+1 −0
Original line number Diff line number Diff line
@@ -32,5 +32,6 @@ public final class NativeInterpolatorFactoryHelper {
    public static native long createDecelerateInterpolator(float factor);
    public static native long createLinearInterpolator();
    public static native long createOvershootInterpolator(float tension);
    public static native long createPathInterpolator(float[] x, float[] y);
    public static native long createLutInterpolator(float[] values);
}
+15 −0
Original line number Diff line number Diff line
@@ -18,6 +18,7 @@

#include "jni.h"
#include <nativehelper/JNIHelp.h>
#include <cutils/log.h>
#include "core_jni_helpers.h"

#include <Interpolator.h>
@@ -62,6 +63,19 @@ static jlong createOvershootInterpolator(JNIEnv* env, jobject clazz, jfloat tens
    return reinterpret_cast<jlong>(new OvershootInterpolator(tension));
}

static jlong createPathInterpolator(JNIEnv* env, jobject clazz, jfloatArray jX, jfloatArray jY) {
    jsize lenX = env->GetArrayLength(jX);
    jsize lenY = env->GetArrayLength(jY);
    LOG_ALWAYS_FATAL_IF(lenX != lenY || lenX <= 0, "Invalid path interpolator, x size: %d,"
            " y size: %d", lenX, lenY);
    std::vector<float> x(lenX);
    std::vector<float> y(lenY);
    env->GetFloatArrayRegion(jX, 0, lenX, x.data());
    env->GetFloatArrayRegion(jY, 0, lenX, y.data());

    return reinterpret_cast<jlong>(new PathInterpolator(std::move(x), std::move(y)));
}

static jlong createLutInterpolator(JNIEnv* env, jobject clazz, jfloatArray jlut) {
    jsize len = env->GetArrayLength(jlut);
    if (len <= 0) {
@@ -88,6 +102,7 @@ static const JNINativeMethod gMethods[] = {
    { "createDecelerateInterpolator", "(F)J", (void*) createDecelerateInterpolator },
    { "createLinearInterpolator", "()J", (void*) createLinearInterpolator },
    { "createOvershootInterpolator", "(F)J", (void*) createOvershootInterpolator },
    { "createPathInterpolator", "([F[F)J", (void*) createPathInterpolator },
    { "createLutInterpolator", "([F)J", (void*) createLutInterpolator },
};

+1 −0
Original line number Diff line number Diff line
@@ -298,6 +298,7 @@ LOCAL_SRC_FILES += \
    tests/unit/MeshStateTests.cpp \
    tests/unit/OffscreenBufferPoolTests.cpp \
    tests/unit/OpDumperTests.cpp \
    tests/unit/PathInterpolatorTests.cpp \
    tests/unit/RenderNodeDrawableTests.cpp \
    tests/unit/RecordingCanvasTests.cpp \
    tests/unit/RenderNodeTests.cpp \
+33 −0
Original line number Diff line number Diff line
@@ -88,6 +88,39 @@ float OvershootInterpolator::interpolate(float t) {
    return t * t * ((mTension + 1) * t + mTension) + 1.0f;
}

float PathInterpolator::interpolate(float t) {
    if (t <= 0) {
        return 0;
    } else if (t >= 1) {
        return 1;
    }
    // Do a binary search for the correct x to interpolate between.
    size_t startIndex = 0;
    size_t endIndex = mX.size() - 1;

    while (endIndex > startIndex + 1) {
        int midIndex = (startIndex + endIndex) / 2;
        if (t < mX[midIndex]) {
            endIndex = midIndex;
        } else {
            startIndex = midIndex;
        }
    }

    float xRange = mX[endIndex] - mX[startIndex];
    if (xRange == 0) {
        return mY[startIndex];
    }

    float tInRange = t - mX[startIndex];
    float fraction = tInRange / xRange;

    float startY = mY[startIndex];
    float endY = mY[endIndex];
    return startY + (fraction * (endY - startY));

}

LUTInterpolator::LUTInterpolator(float* values, size_t size)
    : mValues(values)
    , mSize(size) {
Loading