创建自定义库

时间:2012-09-28 09:23:32

标签: android android-gallery

我想创建一个自定义图库,其中图库中心最多的视图显示缩小动画。所以当我滚动我的画廊时,来到中心的物品将会变焦。所以我需要知道的是:

  1. 如何在图库中找到中心项目。(如果显示5个项目,我需要第3个项目作为中心项目。)
  2. 当滚动发生时,如何设置动画以获得平滑的凸出效果?

1 个答案:

答案 0 :(得分:0)

在使用队列的管道结构的帮助下,我结合了图库的addViewToLayout方法得到了它。

代码:

自定义图库类

public class NGallery extends Gallery {

private Pipe<View> childViews;
private int pipeSize;
private View previousAnimatedView;
private boolean isScrollLeft;

public NGallery(Context context, AttributeSet attrs) {
    super(context, attrs);
    final Timer tmr = new Timer();
    TimerTask task = new TimerTask() {

        @Override
        public void run() {
            initialize();
            if (pipeSize > 0) {
                tmr.cancel();
            }
        }
    };
    tmr.scheduleAtFixedRate(task, 100, 100);
}

private void initialize() {
    View childView = getChildAt(0);
    if (childView != null && childView.getWidth() > 0) {
        pipeSize = getWidth() / childView.getWidth();
        childViews = new Pipe<View>(pipeSize);
    }
}

@Override
protected boolean addViewInLayout(View child, int index,
        android.view.ViewGroup.LayoutParams params,
        boolean preventRequestLayout) {
    View viewToAnimate = getViewToAnimate(child);
    if (viewToAnimate != null) {
        if (previousAnimatedView != null) {
            previousAnimatedView.clearAnimation();
        }
        viewToAnimate.requestFocus();
        AnimationSet animationSet = getAnimationSet(viewToAnimate);
        viewToAnimate.startAnimation(animationSet);
        previousAnimatedView = viewToAnimate;
    }
    return super
            .addViewInLayout(child, index, params, preventRequestLayout);
}

@Override
public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX,
        float distanceY) {
    isScrollLeft = distanceX > 0;
    return super.onScroll(e1, e2, distanceX, distanceY);
}

private AnimationSet getAnimationSet(View viewToAnimate) {
    AnimationSet animationSet = new AnimationSet(false);

    Animation scaleAnimation = new ScaleAnimation(1, 1.5f, 1, 1.5f);
    scaleAnimation.setDuration(100);
    animationSet.addAnimation(scaleAnimation);

    Animation transAnimation = new TranslateAnimation(0, 0, 0, 25);
    transAnimation.setDuration(100);
    animationSet.addAnimation(transAnimation);

    animationSet.setFillAfter(true);

    return animationSet;
}

private View getViewToAnimate(View child) {
    if (childViews != null) {
        if (isScrollLeft) {
            childViews.addFirst(child);
        } else {
            childViews.addLast(child);
        }
        return childViews.getCenterItem();
    } else {
        return null;
    }
}

}

管道类:

public class Pipe<E> {

private LinkedList<E> list;
private int pipeSize;

public Pipe(int size) {
    list = new LinkedList<E>();
    pipeSize = size;
}

public E getItemAt(int position) {
    return list.get(position);
}

public E getCenterItem() {
    int pos = pipeSize / 2;
    if (pos < list.size()) {
        return list.get(pos);
    } else {
        return null;
    }
}

public void addFirst(E item) {
    if (list.size() >= pipeSize) {
        list.removeLast();
    }
    list.addFirst(item);
}

public void addLast(E item) {
    if (list.size() >= pipeSize) {
        list.removeFirst();
    }
    list.addLast(item);
}

}