R.animator objectAnimators 不支持 Fragment add/remove 动画
R.animator with objectAnimators aren't working with Fragment add/remove animations
我不知道为什么这总是很难开始工作。我正在使用 AppCompat 库和 android.app.Fragment
。我尝试添加动画以在 left/right 中滑动新片段(就像 iOS 那样),但是当添加片段时,它们会立即添加/删除,没有任何动画。
我做错了什么?
getFragmentManager()
.beginTransaction()
.setCustomAnimations(R.animator.slide_in_from_right, R.animator.slide_out_to_the_left)
.add(R.id.navrootlayout, fragment)
.addToBackStack(null)
.commit();
res/animator/slide_in_from_right.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<objectAnimator
android:interpolator="@interpolator/decelerate_cubic"
android:valueFrom="1"
android:valueTo="0"
android:valueType="floatType"
android:propertyName="xFraction"
android:duration="3000"/>
</set>
res/animator/slide_out_to_the_left.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<objectAnimator
android:interpolator="@interpolator/decelerate_cubic"
android:valueFrom="0"
android:valueTo="-1"
android:valueType="floatType"
android:propertyName="xFraction"
android:duration="3000"/>
</set>
我什至将动画的持续时间设置为 3000(即 3 秒),这样我就可以明确地看到它是否在使用,但实际上并没有。添加片段时根本没有任何动画。我拍下了它发生的屏幕视频,新片段立即出现(并最终消失)。
我发现我做错了什么。我从某处的示例中获取了动画 xml 文件,而该示例并没有提到我需要自己实现 xFraction
属性。我错误地认为这是一种内置行为,可以理解 xFraction 和 x 是相关的,类似于旧样式 res/anim
样式动画允许您使用百分比值作为动画的方式 start/end值。
但是,不。为此,您必须创建布局的子类并自己添加 xFraction
属性。我就是这样做的。
package com.mydomain.myapp;
import android.content.Context;
import android.util.AttributeSet;
import android.widget.RelativeLayout;
public class SlideableLayout extends RelativeLayout {
public SlideableLayout(Context context) {
super(context);
}
public SlideableLayout(Context context, AttributeSet attrs) {
super(context, attrs);
}
public SlideableLayout(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
public float getXFraction() {
final int width = getWidth();
if (width != 0) {
return getX() / getWidth();
} else {
return getX();
}
}
public void setXFraction(float xFraction) {
final int width = getWidth();
if (width > 0) {
setX(xFraction * width);
} else {
setX(-10000);
}
}
}
然后,对于我想要在屏幕上和屏幕外设置动画的每个片段,我使用 SlideableLayout
作为根布局。
<?xml version="1.0" encoding="utf-8"?>
<com.mydomain.myapp.SlideableLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@android:color/holo_blue_bright"
>
</com.mydomain.myapp.SlideableLayout>
我不知道为什么这总是很难开始工作。我正在使用 AppCompat 库和 android.app.Fragment
。我尝试添加动画以在 left/right 中滑动新片段(就像 iOS 那样),但是当添加片段时,它们会立即添加/删除,没有任何动画。
我做错了什么?
getFragmentManager()
.beginTransaction()
.setCustomAnimations(R.animator.slide_in_from_right, R.animator.slide_out_to_the_left)
.add(R.id.navrootlayout, fragment)
.addToBackStack(null)
.commit();
res/animator/slide_in_from_right.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<objectAnimator
android:interpolator="@interpolator/decelerate_cubic"
android:valueFrom="1"
android:valueTo="0"
android:valueType="floatType"
android:propertyName="xFraction"
android:duration="3000"/>
</set>
res/animator/slide_out_to_the_left.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<objectAnimator
android:interpolator="@interpolator/decelerate_cubic"
android:valueFrom="0"
android:valueTo="-1"
android:valueType="floatType"
android:propertyName="xFraction"
android:duration="3000"/>
</set>
我什至将动画的持续时间设置为 3000(即 3 秒),这样我就可以明确地看到它是否在使用,但实际上并没有。添加片段时根本没有任何动画。我拍下了它发生的屏幕视频,新片段立即出现(并最终消失)。
我发现我做错了什么。我从某处的示例中获取了动画 xml 文件,而该示例并没有提到我需要自己实现 xFraction
属性。我错误地认为这是一种内置行为,可以理解 xFraction 和 x 是相关的,类似于旧样式 res/anim
样式动画允许您使用百分比值作为动画的方式 start/end值。
但是,不。为此,您必须创建布局的子类并自己添加 xFraction
属性。我就是这样做的。
package com.mydomain.myapp;
import android.content.Context;
import android.util.AttributeSet;
import android.widget.RelativeLayout;
public class SlideableLayout extends RelativeLayout {
public SlideableLayout(Context context) {
super(context);
}
public SlideableLayout(Context context, AttributeSet attrs) {
super(context, attrs);
}
public SlideableLayout(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
public float getXFraction() {
final int width = getWidth();
if (width != 0) {
return getX() / getWidth();
} else {
return getX();
}
}
public void setXFraction(float xFraction) {
final int width = getWidth();
if (width > 0) {
setX(xFraction * width);
} else {
setX(-10000);
}
}
}
然后,对于我想要在屏幕上和屏幕外设置动画的每个片段,我使用 SlideableLayout
作为根布局。
<?xml version="1.0" encoding="utf-8"?>
<com.mydomain.myapp.SlideableLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@android:color/holo_blue_bright"
>
</com.mydomain.myapp.SlideableLayout>