一步一步学习Android TV/盒子开发(三)

本文主要说的就是在TV开发中常遇到的问题总结

焦点丢失问题

在使用ListView、GridView及RecyclerView时有时会出现,这时需要在xml中,添加

android:descendantFocusability="afterDescendants"
  • 1
  • 2

这里会有三种方式分别为

  • beforeDescendants:viewgroup会优先其子类控件而获取到焦点

  • afterDescendants:viewgroup只有当其子类控件不需要获取焦点时才获取焦点

  • blocksDescendants:viewgroup会覆盖子类控件而直接获得焦点

在使用自定义组合控件是可以用代码设置,如下

setDescendantFocusability(FOCUS_BLOCK_DESCENDANTS);
  • 1
  • 2

控件调用bringToFront失效,导致焦点错乱问题

源码中:

  • View

    public void bringToFront() {
        if (mParent != null) {
            mParent.bringChildToFront(this); // 是调用父布局的 bringChildToFront
        }
    }
    
  • ViewGroup

  • 所以可以将你要置顶的子控件和最后一个要绘制的控件交换位置, 因为最后绘制的子控件是在最上面的。

    setChildrenDrawingOrderEnabled(true)
    
    @Override
    protected int getChildDrawingOrder(int childCount, int i) {
        if (position != -1) {
            if (i == childCount - 1)
            return position;
        if (i == position) 
            return childCount - 1;
        }
        return i;
    }
    
  • ViewUtil

    public class ViewUtil {
        private final ViewGroup viewGroup;
        private int position;
    
        public ViewUtil(ViewGroup group) {
            this.viewGroup = group;
        }
    
        public void bringChildToFront(ViewGroup vg, View child) {
            position = vg.indexOfChild(child);
            if (position != -1) {
                vg.postInvalidate();
            }
        }
    
        public void bringChildToFront(View child) {
            if (viewGroup == null) {
                return;
            }
            position = viewGroup.indexOfChild(child);
            if (position != -1) {
                viewGroup.postInvalidate();
            }
        }
    
        public int getChildDrawingOrder(int childCount, int i) {
            if (position != -1) {
                if (i == childCount - 1)
                    return position;
                if (i == position)
                    return childCount - 1;
            }
            return i;
        }
    }
    
  • 在Android5.0以后可以通设置控件的Z坐标达到相同的效果

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
        ViewCompat.setElevation(view, 1);
    } else {
        if (view.getParent() instanceof BringChildLinearLayout) {
            BringChildLinearLayout layout = (BringChildLinearLayout) view.getParent();
            layout.bringChildToFront(view);
        }
    }
    

跑马灯失效

  • 自定义TextView实现跑马灯时,设置单行时用“maxLines=1”不生效,应该使用“singleLine=true”(过期的API)。

猜你喜欢

转载自blog.csdn.net/weixin_40441128/article/details/82150352
今日推荐