Android でのクロスフェードに関して多くの質問がありますが、それらにはすべてアニメーションが含まれています。私の質問は、ViewPager の OnPageChangeListener を使用したクロスフェードについてです。
無制限の数のビューを持つことができる ViewPager がありますが、実際には約 6 または 7 ビューを使用します。そこにはあまり進んでいません。
ViewPager の各ビューには背景ビットマップがあり、ビューの残りの部分と一緒にスクロールするのではなく、固定して次の (または前の) ビューの背景とクロスフェードする必要があります。
これを実現するために、背景を分離して ArrayList に追加し、後でそれらを ImageViews に割り当てました。しかし、アクティビティが多数の ImageView で終わる可能性を危険にさらしたくないので、次の構造を考えました。
<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>
次に、OnPageChangeListener
ViewPager に a が割り当てられ、背景が ImageViews に割り当てられます。
@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をスワイプしている間、背景が互いにクロスフェードするようにします。前方スクロールのフェードは機能していますが、後方スクロールのフェードがどういうわけか良い結果をもたらさない理由がわかりません。後方スクロール中に、中央の背景が下部の背景にフェードインする必要があります。
私は何かが欠けているのではないかと心配しています。下の背景のアルファを変更することはありませんが、ログの結果は常に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());
}
そして待って!修正方法が本当にわからないことがもう1つあります。前方スクロールフェードは機能していますが。バックグラウンドで非常に短いちらつきがあります。これは、メソッドの設定方法が原因で発生していると思いonPageSelected
ます。
この動作を作成/修正する別の方法はありますか?