最近在开发一个ICNTV海外 TV端的项目,遇到一个小需求。

 具体功能描述: 最左边布局一个ListView 用于显示分类列表,右侧布局一个gridview 用于展示视频列表信息。 当从listview 切换到gridview时再返回时,会选择离当前焦点位置最近的Item 作为下一个焦点的捕获点。onFocusChanged源码,

   final ListAdapter adapter = mAdapter;
        int closetChildIndex = -1;
        int closestChildTop = 0;
        if (adapter != null && gainFocus && previouslyFocusedRect != null) {
            previouslyFocusedRect.offset(mScrollX, mScrollY);


            // Don't cache the result of getChildCount or mFirstPosition here,
            // it could change in layoutChildren.
            if (adapter.getCount() < getChildCount() + mFirstPosition) {
                mLayoutMode = LAYOUT_NORMAL;
                layoutChildren();
            }


            // figure out which item should be selected based on previously
            // focused rect
            Rect otherRect = mTempRect;
            int minDistance = Integer.MAX_VALUE;
            final int childCount = getChildCount();
            final int firstPosition = mFirstPosition;


            for (int i = 0; i < childCount; i++) {
                // only consider selectable views
                if (!adapter.isEnabled(firstPosition + i)) {
                    continue;
                }


                View other = getChildAt(i);
                other.getDrawingRect(otherRect);
                offsetDescendantRectToMyCoords(other, otherRect);

               //遍历listview的child,并获取direction方向的距离
                int distance = getDistance(previouslyFocusedRect, otherRect, direction);


                if (distance < minDistance) {
                    minDistance = distance;
                    closetChildIndex = i;
                    closestChildTop = other.getTop();
                }
            }
        }


        if (closetChildIndex >= 0) {
            setSelectionFromTop(closetChildIndex + mFirstPosition, closestChildTop);
        } else {
            requestLayout();
        }



此时,需要重写onFocusChanged,记录焦点改变时的位置,当listview获取焦点时,调用listview的setSelectionFromTop方法。如果调用setSelection会出现滑动效果。

protected void onFocusChanged(boolean gainFocus, int direction,
Rect previouslyFocusedRect) {
int lastSelectItem = getSelectedItemPosition();
super.onFocusChanged(gainFocus, direction, previouslyFocusedRect);
if (gainFocus) {
//获取焦点离开前的selection位置聚listview顶端位置,通过setSelectionFromTop方法,避免出现滑动效果。
View other = getChildAt(lastSelectItem);
int top = (other== null) ? 0 : other.getTop();
setSelectionFromTop(lastSelectItem, top);
}
}
Logo

智屏生态联盟致力于大屏生态发展,利用大屏快应用技术降低开发者开发、发布大屏应用门槛

更多推荐