奇怪的闪烁与DashPathEffect动画 [英] Weird flickering with DashPathEffect animation

查看:452
本文介绍了奇怪的闪烁与DashPathEffect动画的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我试图与DashPathEffect路径动画。必须能够多次重放它,使用一个按钮。

I'm trying to make a path animation with DashPathEffect. Have to be able to replay it multiple times, using a button.

:// WWW .curious-creature.org /十二分之二千零十三/ 21 / Android的配方-4-路径跟踪/

Based on http://www.curious-creature.org/2013/12/21/android-recipe-4-path-tracing/

我的问题是,动画效果很好的前10次左右,那么路径去疯狂和它开始闪烁,以相反的顺序或整理它不必去

My problem is, the animation works well the first 10 times or so, then the path goes crazy and it starts flickering, going in the reverse order or finishes where it doesn't have to.

我登录动画的值,并传递到路径的价值观,他们看起来是正确的,没有跳跃或其他任何怪异。我不知道是什么原因造成的问题。

I logged the values of the animation and the values passed to the path and they look correct, no jumps or anything weird. I have no idea what is causing the issues.

这是code:

public class Test extends View {

    private float mDrag;

    private MyPath path1;

    private int mDuration;

    //just some shape
    private static Path makeDragPath(int radius) {
        Path p = new Path();
        RectF oval = new RectF(10.0f, 10.0f, radius * 2.0f, radius * 2.0f);

        float cx = oval.centerX();
        float cy = oval.centerY();
        float rx = oval.width() / 2.0f;
        float ry = oval.height() / 2.0f;

        final float TAN_PI_OVER_8 = 0.414213562f;
        final float ROOT_2_OVER_2 = 0.707106781f;

        float sx = rx * TAN_PI_OVER_8;
        float sy = ry * TAN_PI_OVER_8;
        float mx = rx * ROOT_2_OVER_2;
        float my = ry * ROOT_2_OVER_2;

        float L = oval.left;
        float T = oval.top;
        float R = oval.right;
        float B = oval.bottom;

        p.moveTo(R, cy);
        p.quadTo(      R, cy + sy, cx + mx, cy + my);
        p.quadTo(cx + sx, B, cx, B);
        p.quadTo(cx - sx,       B, cx - mx, cy + my);
        p.quadTo(L, cy + sy, L, cy);
        p.quadTo(      L, cy - sy, cx - mx, cy - my);
        p.quadTo(cx - sx, T, cx, T);


        return p;
    }




    public Test(Context context, AttributeSet attrs) {
        super(context, attrs);

        init();
    }




    public static class MyPath {
        private static final Region sRegion = new Region();
        private static final Region sMaxClip = new Region(
                Integer.MIN_VALUE, Integer.MIN_VALUE,
                Integer.MAX_VALUE, Integer.MAX_VALUE);

        final Path path;
        final Paint paint;
        final float length;
        final Rect bounds;

        MyPath(Path path, Paint paint) {
            this.path = path;
            this.paint = paint;

            PathMeasure measure = new PathMeasure(path, false);
            this.length = measure.getLength();

            sRegion.setPath(path, sMaxClip);
            bounds = sRegion.getBounds();
        }


    }


    private static PathEffect createPathEffect2(float pathLength, float phase) {

        //I modified the original approach using phase, to use only path instead because later I want to animate also the starting point and phase alone is not enough for this

        float full = phase * pathLength;

        return new DashPathEffect(new float[] {full, Float.MAX_VALUE}, //on, off
                0);
    }

    ObjectAnimator current;


    public void startAnim() {
        if (current != null) {
            current.cancel();
        }

        current = ObjectAnimator.ofFloat(Test.this, "drag", 0.0f, 1.0f).setDuration(mDuration);
        current.start();
    }

    private void scalePath(Path path, float scale) {
        Matrix scaleMatrix = new Matrix();
        scaleMatrix.setScale(scale, scale);
        path.transform(scaleMatrix);
    }

    private void init() {

        Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
        paint.setStyle(Paint.Style.STROKE);

        paint.setStrokeWidth(8.0f);
        paint.setColor(0xffffffff);

        mDuration = 3000;

        Path p1 = makeDragPath(40);
        scalePath(p1, 3);

        path1 = new MyPath(p1, paint);


        startAnim();
    }

    public float getDrag() {
        return mDrag;
    }

    public void setDrag(float drag) {

        mDrag = drag;

        path1.paint.setPathEffect(createPathEffect2(path1.length, mDrag));

        invalidate();
    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);

        canvas.drawColor(Color.BLACK); //doesn't help

        canvas.drawPath(path1.path, path1.paint);
    }

}

在我的活动:

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_my);

    final Test test = (Test)findViewById(R.id.test);

    Button button = (Button)findViewById(R.id.startTest);
    button.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            test.startAnim();
        }
    });
}

XML:

<Button
    android:id="@+id/startTest"
    android:layout_width="200dp"
    android:layout_alignParentBottom="true"
    android:layout_alignParentLeft="true"
    android:layout_height="60dp" />

<com.example.ivanschuetzd.myapplication.Test
    android:id="@+id/test"
    android:layout_width="100dp"
    android:layout_height="100dp"
    android:layout_alignParentBottom="true"
    android:layout_alignParentRight="true"
    android:background="#000000"
    />

你知道吗?或者,也许不同的方法来使这种动画与任意路径?谢谢!

Any idea? Or maybe a different approach to make this kind of animation with an arbitrary path? Thanks!

推荐答案

刚刚发现了一个解决方案。
显然问题是硬件加速即与DashPathEffect有所手推车。
只需拨打

Just found a solution for that. Apparently the problem is the hardware acceleration that is somewhat buggy with the DashPathEffect. Just call

setLayerType(View.LAYER_TYPE_SOFTWARE, null);

在你看来,这应该修复它。

in your view and that should fix it.

这篇关于奇怪的闪烁与DashPathEffect动画的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆