animation底部纸张的布局变化

在我的应用程序中,我使用了一个底层(来自支持库),这非常棒。 现在我想animation布局的变化,而工作表被拖动。 为此,我创build了BottomSheetCallback的子类(这通常是Fragment的内部类,所以并不是所有在这个类中使用的对象都在这里初始化):

 public class MyBehavior extends BottomSheetBehavior.BottomSheetCallback { Transition transition; float lastOffset = 0; Scene scene; public PlayerBehavior() { TransitionInflater inflater = TransitionInflater.from(getContext()); transition = inflater.inflateTransition(R.transition.player); //transition.setDuration(300); scene = fullLayout; transition.setInterpolator(new Interpolator() { @Override public float getInterpolation(float v) { return lastOffset; } }); } @Override public void onStateChanged(@NonNull View bottomSheet, int newState) { if(newState == BottomSheetBehavior.STATE_DRAGGING) { TransitionManager.go(scene, transition); } } @Override public void onSlide(View bottomSheet, final float slideOffset) { scene = (slideOffset > lastOffset) ? smallLayout : fullLayout; lastOffset = slideOffset; } } 

正如你所看到的,我还创build了两个Scene从不同的布局文件和一个自定义的Transition到与TransitionManager场景之间的animation。 我的问题是Transition应该基于slideOffset参数(在0-1的范围内),但是TransitionManager在后台使用通常基于Android的时间的Animation类。

我试图创build自定义Intapolator,但是这不能正常工作。 那么我怎样才能创build一个基于外部variables而不是按时间的转换呢?

Solutions Collecting From Web of "animation底部纸张的布局变化"

基于你的描述,我认为你正在试图实现像谷歌地图底部表行为的东西。 底部表单被拖动时,布局会发生变化。

如果这是你正在努力实现的,那么你不需要强制定制animation,因为底部对话框本身在父协调器布局中包含这些animation行为。

这里是我如何实现相同的行为的示例代码。 当底部表单被拖动到全屏尺寸时,它也会使FloatingActionButton不可见:

  1. 创build一个你想在主布局中使用的bottomomsdialog

     public class CustomBottomDialog extends BottomSheetDialogFragment { String mSomeName; @Override public void onCreate(@Nullable Bundle savedInstanceState) { super.onCreate(savedInstanceState); // if some arguments are passed from the calling activity mSomeName = getArguments().getString("some_name"); } @Nullable @Override public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) { View bottomSheet = inflater.inflate(R.layout.bottomsheet_layout, container, false); // initialise your bottomsheet_layout items here TextView tvName = bottomSheet.findViewById(R.id.display_name); tvName.setText(mSomeName); tvName.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View view) { // do something here ((MainActivity)getActivity()).doSomething(); } }); return bottomSheet; } } 
  2. bottomsheet_layout:

     <android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" xmlns:app="http://schemas.android.com/apk/res-auto" android:layout_width="match_parent" android:layout_height="match_parent"> <android.support.design.widget.FloatingActionButton android:id="@+id/nav" android:layout_width="wrap_content" android:layout_height="wrap_content" android:src="@drawable/navigation_tilt_grey" app:backgroundTint="@color/colorAccent" app:elevation="3dp" app:fabSize="normal" android:layout_marginEnd="@dimen/activity_horizontal_margin" app:layout_anchor="@+id/live_dash" app:layout_anchorGravity="top|right" /> <!--BottomSheet--> <android.support.v4.widget.NestedScrollView android:id="@+id/live_dash" android:layout_width="match_parent" android:layout_height="wrap_content" android:background="#F3F3F3" android:clipToPadding="true" app:layout_behavior="android.support.design.widget.BottomSheetBe havior" tools:layout_editor_absoluteY="150dp"> <!--Include your items here, the height of all items combined will take the main screen layout size with animation--> </android.support.v4.widget.NestedScrollView> </android.support.design.widget.CoordinatorLayout> 
  3. 从你的活动中调用这个BottomSheet:

     public void notifyBottomSheet(String somename){ BottomSheetDialogFragment customDialogFragment = new CustomBottomDialog(); Bundle args = new Bundle(); args.putString("some_name", somename); customDialogFragment.setArguments(args); customDialogFragment.show(getSupportFragmentManager(), customDialogFragment.getTag()); customDialogFragment.setCancelable(false); // if you don't wish to hide } 

    希望这解决了你正在努力实现的目标。

要轻松地将某些东西从屏幕底部滑出,可以使用以下代码:

 final int activityHeight = findViewById(android.R.id.content).getHeight(); cardContainer.animate().yBy(activityHeight - cardContainer.getY()).setDuration(SLIDE_OUT_DURATION); 

cardContainer是您试图滑出屏幕的视图。

完整的例子见这个博客文章 。 请注意,您也可以使用translationY而不是yBy 。 另一种更通用的方法是使用这个代码:

 public static ViewPropertyAnimator slideOutToBottom(Context ctx, View view) { final int screenHeight = ctx.getResources().getDisplayMetrics().heightPixels; int[] coords = new int[2]; view.getLocationOnScreen(coords); return view.animate().translationY(screenHeight - coords[Y_INDEX]).setDuration(SLIDE_OUT_DURATION); } public static ViewPropertyAnimator slideInFromBottom(Context ctx, View view) { final int screenHeight = ctx.getResources().getDisplayMetrics().heightPixels; int[] coords = new int[2]; view.getLocationOnScreen(coords); view.setTranslationY(screenHeight - coords[Y_INDEX]); return view.animate().translationY(0).setDuration(SLIDE_IN_DURATION).setInterpolator(new OvershootInterpolator(1f)); } 
 ## Translation Animation ## <?xml version="1.0" encoding="utf-8"?> <set xmlns:android="http://schemas.android.com/apk/res/android" android:interpolator="@android:anim/accelerate_decelerate_interpolator" android:fillAfter="true" > <translate android:fromYDelta="100%p" android:toYDelta="-30%p" android:duration="900" /> </set> 

## 主要活动 ##

 @Override protected void onResume() { super.onResume(); Animation am= AnimationUtils.loadAnimation(this,R.anim.fadeout); tv5.startAnimation(am); Animation myanim= AnimationUtils.loadAnimation(this,R.anim.translate); tv1.startAnimation(myanim); myanim.setStartOffset(500); Animation animation= AnimationUtils.loadAnimation(this,R.anim.translate); animation.setStartOffset(1000); tv2.startAnimation(animation); Animation an= AnimationUtils.loadAnimation(this,R.anim.translate); an.setStartOffset(1500); tv3.startAnimation(an); Animation ab= AnimationUtils.loadAnimation(this,R.anim.translate); ab.setStartOffset(2000); tv4.startAnimation(ab); Animation ac= AnimationUtils.loadAnimation(this,R.anim.fadein); ac.setStartOffset(2500); btn1.startAnimation(ac); } 

我不确定这是否是你想要的,但也许不使用过渡,你可以使用函数animate()因为使用这个函数,你可以改变所有关于你的animation(时间,可视性等)的东西。