9

Android 中关于淡入淡出的问题有很多,但都包括动画。我的问题是关于使用 ViewPager 的 OnPageChangeListener 进行淡入淡出。

我有一个 ViewPager 可以有无限数量的视图,但实际上使用大约 6 或 7 个视图。那里没有太多事情发生。

ViewPager 中的每个视图都有一个背景位图,它应该固定并与下一个(或上一个)视图的背景交叉淡入淡出,而不是与视图的其余部分一起滚动。

为了实现这一点,我将背景解耦并添加到 ArrayList 并稍后将它们分配给 ImageViews。但是由于我不想冒险让我的 Activity 最终得到许多 ImageViews,所以我想到了以下结构:

<FrameLayout 
    android:id="@+id/backgroundContainer"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <ImageView
        android:id="@+id/bottomImage"
        android:layout_height="match_parent"
        android:layout_width="match_parent"
        android:scaleType="center" />

    <ImageView
        android:id="@+id/middleImage"
        android:layout_height="match_parent"
        android:layout_width="match_parent"
        android:scaleType="center" />

    <ImageView
        android:id="@+id/topImage"
        android:layout_height="match_parent"
        android:layout_width="match_parent"
        android:scaleType="center" />

</FrameLayout>

然后将 aOnPageChangeListener分配给 ViewPager 以将背景分配给 ImageView。

@Override
public void onPageSelected(int position) {
    MyLog.i(TAG, "PAGE SELECTED: " + position);

    if(position == 0) {
        _bottomBackground.setImageBitmap(null);
        _topBackground.setImageBitmap(_backgroundStack.get(position+1));
    } else if (position == NUM_ITEMS-1) {
        _bottomBackground.setImageBitmap(_backgroundStack.get(position-1));
        _topBackground.setImageBitmap(null);
    } else {
        _bottomBackground.setImageBitmap(_backgroundStack.get(position-1));
        _topBackground.setImageBitmap(_backgroundStack.get(position+1));
    }

    _middleBackground.setImageBitmap(_backgroundStack.get(position));            

    // Make the top front background transparent 
    _topBackground.setAlpha(0f);
    _currentBackgroundPosition = position;
}

如果我只想交换背景,这很好用。当用户滑动 ViewPager 时,我希望背景相互淡入淡出。我已经为向前滚动工作了淡入淡出,但我不明白为什么向后滚动的淡入淡出并没有给出好的结果。在向后滚动期间,中间背景应该淡入底部背景。

恐怕我错过了什么。我从不更改底部背景的 alpha,但日志结果始终显示与getAlpha()中间背景完全相同的值。

@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
    if(_currentBackgroundPosition == position) {
        // scroll forward
        _topBackground.setAlpha(positionOffset)
    } else {
        //scroll backward
        _middleBackground.setAlpha(positionOffset);               
    }

    MyLog.i(TAG, "Bottom BackgroundAlpha: " + _bottomBackground.getAlpha());
    MyLog.i(TAG, "Middle BackgroundAlpha: " + _middleBackground.getAlpha());
    MyLog.i(TAG, "Top BackgroundAlpha: " + _topBackground.getAlpha());
}

等等!还有一件事我真的无法弄清楚如何解决。虽然向前滚动淡入淡出工作。背景中有超短的闪烁。我认为这是因为我设置onPageSelected方法的方式而发生的。

还有另一种方法可以创建/修复此行为吗?

4

1 回答 1

29

ViewPager.PageTransformer是你的朋友。我将对您尝试的方法采取不同的方法,但这会导致我理解您想要的结果 - 向左/向右滑动会滑动内容,但会在两个不移动的背景图像之间消失。

中的每个都FragmentViewPager具有如下布局:

<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
    <ImageView
        android:id="@+id/image_view"
        android:layout_height="match_parent"
        android:layout_width="match_parent"
        android:scaleType="center" />
    <LinearLayout
        android:id="@+id/content_area"
        android:orientation="vertical"
        android:layout_width="match_parent"
        android:layout_height="match_parent">
        <!-- content goes here -->
    </LinearLayout>
</FrameLayout>

您将创建一个PageTransformer根据滑动位置操作布局的方法:

public class CustomPageTransformer implements ViewPager.PageTransformer {
    public void transformPage(View view, float position) {
        int pageWidth = view.getWidth();
        View imageView = view.findViewById(R.id.image_view);
        View contentView = view.findViewById(R.id.content_area);

        if (position < -1) { // [-Infinity,-1)
            // This page is way off-screen to the left
        } else if (position <= 0) { // [-1,0]
            // This page is moving out to the left

            // Counteract the default swipe
            view.setTranslationX(pageWidth * -position);
            if (contentView != null) {
                // But swipe the contentView
                contentView.setTranslationX(pageWidth * position);
            }
            if (imageView != null) {
                // Fade the image in
                imageView.setAlpha(1 + position);
            }

        } else if (position <= 1) { // (0,1]
            // This page is moving in from the right

            // Counteract the default swipe
            view.setTranslationX(pageWidth * -position);
            if (contentView != null) {
                // But swipe the contentView
                contentView.setTranslationX(pageWidth * position);
            }
            if (imageView != null) {
                // Fade the image out
                imageView.setAlpha(1 - position);
            }
        } else { // (1,+Infinity]
            // This page is way off-screen to the right
        }
    }
}

最后把它PageTransformer连接到你的ViewPager

mViewPager.setPageTransformer(true, new CustomPageTransformer());

我已经在现有应用程序中对其进行了测试,只要片段布局具有透明背景,它就可以正常工作。

于 2014-05-07T19:28:56.860 回答