/*
* Copyright (C) 2013 Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.tabcarousel;
import android.annotation.TargetApi;
import android.os.Build;
import android.support.v4.view.ViewPager;
import android.view.View;
import android.widget.AbsListView;
import android.widget.AbsListView.OnScrollListener;
/**
* Handles scrolling back of a list tied to a header.
* <p>
* This is used to implement a header that scrolls up with the content of a list
* to be partially obscured.
*/
public class BackScrollManager implements OnScrollListener {
/**
* {@code #onScrollStateChanged(AbsListView, int)} listener
*/
private final ScrollableHeader mScrollableHeader;
/**
* The carousel header
*/
private final CarouselContainer mCarousel;
/**
* The position of the {@link ViewPager} to scroll to
*/
private final int mPageIndex;
/* Constructor for <code>VerticalScrollListener</code> */
/**
* @param carouselHeader The {@link CarouselContainer} to move
* @param scrollableHeader Capture onScrollStateChanged
* @param pageIndex The position of the {@link ViewPager} this is used in
*/
public BackScrollManager(CarouselContainer carouselHeader, ScrollableHeader scrollableHeader,
int pageIndex) {
// Initialize the scoll listener
mScrollableHeader = scrollableHeader;
// Initialize the header
mCarousel = carouselHeader;
// Match the pager positions
mPageIndex = pageIndex;
}
/**
* {@inheritDoc}
*/
@TargetApi(Build.VERSION_CODES.HONEYCOMB)
@Override
public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount,
int totalItemCount) {
// Don't move the carousel if: 1) It is already being animated
if (mCarousel == null || mCarousel.isTabCarouselIsAnimating()) {
return;
}
// If the FIRST item is not visible on the screen, then the carousel
// must be pinned
// at the top of the screen.
if (firstVisibleItem != 0) {
mCarousel.moveToYCoordinate(mPageIndex, -mCarousel.getAllowedVerticalScrollLength());
return;
}
final View topView = view.getChildAt(firstVisibleItem);
if (topView == null) {
return;
}
final float y = view.getChildAt(firstVisibleItem).getTop();
final float amtToScroll = Math.max(y, -mCarousel.getAllowedVerticalScrollLength());
mCarousel.moveToYCoordinate(mPageIndex, amtToScroll);
}
/**
* {@inheritDoc}
*/
@Override
public void onScrollStateChanged(AbsListView view, int scrollState) {
if (mScrollableHeader != null) {
mScrollableHeader.onScrollStateChanged(view, scrollState);
}
}
/**
* Defines the header to be scrolled
*/
public interface ScrollableHeader {
/**
* Used to capture
* {@code BackScrollManager#onScrollStateChanged(AbsListView, int)} in
* case you need to pause your disk cache while scrolling.
*/
public void onScrollStateChanged(AbsListView view, int scrollState);
}
}