Android:使用ObjectAnimator将View转换为View维度的小数值

oro*_*akr 40 animation android

似乎旧的视图动画(translate,scale等等)不再被AnimationInflaterICS 接受了.我在阅读4.0.4的代码,并明确预计只有XML元素set,objectAnimator,animator.

即使http://developer.android.com/guide/topics/resources/animation-resource.html上的文档继续包含视图动画,它们似乎也已弃用.例如,尝试使用它们会导致错误java.lang.RuntimeException: Unknown animator name: translate.

因此,有必要使用Android ObjectAnimator.但是,它不接受自身或其父级(translationX例如,宽度)的关联维度的小数值,就像旧视图动画在表单中所做的那样"75%p".

ObjectAnimator通过以编程方式获取片段的大小来在运行时手动构建是不可行的,因为它FragmentTransaction仅接受由渣油指定的声明性动画.

我的目标是在屏幕外翻译一个填满整个Activity的Fragment(我基本上是在两个片段之间进行转换).这是现有的TranslationAnimation实现(由于某些原因slide_in_right.xml,它与其对应物slide_out_left.xml没有公开android.R.anim,因此我必须在我的代码库中复制它们):

<set xmlns:android="http://schemas.android.com/apk/res/android">
<translate
    android:fromXDelta="100%p"
    android:toXDelta="0"
    android:duration="@android:integer/config_mediumAnimTime"/>
</set>
Run Code Online (Sandbox Code Playgroud)

我的API级别设置为14.

谢谢!

小智 51

实际上,对象动画师接受小数值.但也许你不理解objectAnimator的基本概念,或者更普遍的是一个值动画师.值动画制作器将为与属性相关的值(例如颜色,屏幕上的位置(X,Y),alpha参数或任何您想要的值)设置动画.要创建这样的属性(在xFraction和yFraction的情况下),您需要构建自己的与此属性名称关联的getter和setter.假设您想将FrameLayout从0%转换为整个屏幕大小的25%.然后,您需要构建一个包装FrameLayout对象并编写getter和setter的自定义View.

public class SlidingFrameLayout extends FrameLayout
{
    private static final String TAG = SlidingFrameLayout.class.getName();

    public SlidingFrameLayout(Context context) {
        super(context);
    }

    public SlidingFrameLayout(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    public float getXFraction()
    {
        int width = getWindowManager().getDefaultDisplay().getWidth();
        return (width == 0) ? 0 : getX() / (float) width;
    }

    public void setXFraction(float xFraction) {
        int width = getWindowManager().getDefaultDisplay().getWidth();
        setX((width > 0) ? (xFraction * width) : 0);
    }
}
Run Code Online (Sandbox Code Playgroud)

然后您可以使用xml方式声明对象动画制作者将xFraction放在属性xml属性下并使用AnimatorInflater对其进行充气

<?xml version="1.0" encoding="utf-8"?>
<objectAnimator 
xmlns:android="http://schemas.android.com/apk/res/android"
android:propertyName="xFraction" 
android:valueType="floatType"
android:valueFrom="0"
android:valueTo="0.25" 
android:duration="500"/>
Run Code Online (Sandbox Code Playgroud)

或者你可以只使用java行代码

ObjectAnimator oa = ObjectAnimator.ofFloat(menuFragmentContainer, "xFraction", 0, 0.25f);
Run Code Online (Sandbox Code Playgroud)

希望它能帮到你!

奥利维尔

  • 现在这个百万美元的问题:为什么这些属性在3.0中添加新属性时没有添加到Android中?这似乎是对我的一个重大疏忽. (57认同)
  • 可以使用`ValueAnimator`代替具有frationX/Y属性的子类,并安装`AnimatorUpdateListener`,其`onAnimationUpdate()`方法将执行必要的计算并设置动画内容的属性.我认为它比创建视图/布局子类更好. (5认同)

she*_*pya 9

Android SDK实现FragmentTransaction期待一段Animator时间,由于一些不明原因,支持库实现需要一个Animation,如果你从支持库使用Fragment实现你的翻译动画将会工作


Joh*_*nes 8

对于那些试图创建像和的视图动画的人来说,这是一个重要的难题.translatescale

属性动画位于名为" animator " 的目录中:res/animator/filename.xml

但是,视图动画必须放在一个简称为" anim " 的目录中: res/anim/filename.xml

我首先将我的视图动画放在"animator"文件夹中,并对Android Studio抱怨translate如何不是有效元素感到困惑.所以,,视图动画不会被弃用.由于一些令人困惑的原因,他们只是有自己的位置.