美文网首页android收集Android技术知识Android知识
那些年,我们爬过的坑--Andriud TV篇(一)

那些年,我们爬过的坑--Andriud TV篇(一)

作者: dorn19978 | 来源:发表于2017-02-22 01:07 被阅读370次

从去年开始,从事Android TV开发已经大半年了,期间遇到过各种各样的坑,最严重、最难解决的莫过于焦点问题。痛定思痛,决定把TV开发中遇到的各种坑一一分享出来,让更多的人不再爬我所爬过的坑。

列表焦点问题

在TV开发中,VerticalGridView是谷歌专门为Android TV适配的RecyclerView,VerticalGridView很好的解决了列表的焦点问题,但是如果使用不当,很容易出现item子项焦点错乱问题。

在TV开发中尽量尽可能不适用没有优化过的RecyclerView!!!!!

小坑-----item焦点无法获取问题

进入列表界面,我希望的是按上下左右按键,item将能取得焦点,实现放大效果,但是我的实际效果如图所示,按上下键,变成了列表上下滚动,而不是我希望实现的item放大。

列表item无法获取焦点
mList.requestFocus();
View child = mList.getChildAt(0);
if (child != null){
  child.requestFocus();
}

在列表里面,无论我如何获取焦点,item子项目都获取不到焦点,找了好多种方法都无法完美解决。最后发现,只要在item的xml根节点添加android:focusable="true"便能完美解决。</br>
吐血啊...

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:focusable="true">
    ...
</LinearLayout>

中坑-----列表获取item总数错误问题

在使用VerticalGridView,如果item的数量需要滑动才能显示完成,那么在你获取列表item总数时就会出现一个有趣的现象:
在VerticalGridView中无论你调用那个方法,你都不能准确获取到列表中Item的总数量。
如果你需要获取列表中Item的总数量,只能采取曲线救国的方案:利用Adapter来获取总数。

如下图所示,我列表item总数为16。


获取Item总数
Log.d(TAG, "COUNT_1 ==> " + mList.getLayoutManager().getChildCount());
Log.d(TAG, "COUNT_2 ==> " + mList.getChildCount());
Log.d(TAG, "COUNT_3 ==> " + mAdapter.getItemCount());
log打印

在使用上述的三种方法中,只有第三种才能准确获取列表中Item准确的数量。出现这问题的原因是:

  • VerticalGridView.getLayoutManager().getChildCount();只能获取当前列表中当前可见的所有item。
  • VerticalGridView.getChildCount();为ViewGrounp的重写方法,而在RecyclerView缓存原理中,RecyclerView只会显示当前所有可见的View,所以这个方法的效果和第一种方法得出的结果是一致的。

大坑-----手动请求Item焦点错乱问题

有的时候,我们需要让指定的item获取焦点,如果你的列表有4行,但是当前屏幕只显示了3行,这个时候,如果需要请求焦点的item恰好处于第4行,那么当你使用

mList.getLayoutManager().getChildAt(postion).requestFocus();

去让指定的item获取焦点,这个时候会出现空指针异常,原因和上面list获取item总数错误的原因一致。
解决这个问题的方案为:先让VerticalGridView移动到该item,然后再处理item焦点请求。
如下代码所示:

mList.scrollToPosition(14);
View v = mList.getLayoutManager().getChildAt(14);
if (v == null) {
  L.d(TAG, "null");
} else {
  v.requestFocus();
}
指定Item焦点请求问题

神坑-----手贱给VerticalGridView添加LayoutManager导致的问题

如果你使用VerticalGridView或者HorizontalGridView,是不需要自己添加LayoutManager的,如果你手贱添加LayoutManager,并且当你想让指定的Item获取焦点,则会导致Item焦点错乱,然后按上下左右键,焦点和预期不一致。
如下图所示,我向第14个item请求焦点,最终发现,第14个item焦点获取失败,按上下左右键,焦点和预期不一致。


Item焦点错乱问题

解决方案:
去掉手贱添加的LayoutManager!!!

相关文章

  • 那些年,我们爬过的坑--Andriud TV篇(一)

    从去年开始,从事Android TV开发已经大半年了,期间遇到过各种各样的坑,最严重、最难解决的莫过于焦点问题。痛...

  • 谈谈那些年自己爬过的坑

    来简书很多天了,也写了一些文字,总不能让自己满意。每天想好的主题在脑子里过一遍,回家提笔想写,结果转瞬即逝。于是报...

  • React Native爬过的那些坑

    1,执行init时切记不要在前面加上sudo(否则新项目的目录所有者会变为root而不是当前用户,导致一系列权限问...

  • UAP平台开发之路-那些年爬过的坑

    笔记,仅供参考学习,如有疑问,请留言一起探讨.!!!.. 推荐论坛:UDN开发者论坛 配置管理 --开发配置:开发...

  • 那些年,爬过的山

    那些年,领略过崂山北九水的山清水秀。也领略过招远罗山风景区的秀美。记得山上有个井,那泉水清凉可口,入口甘甜。昆嵛山...

  • 至那些年,我们一起爬过的钢管

    那些年,我们一起爬过的钢管。。。。。。 早就想写这么一篇文章了,可总是抬不起笔。直到今天我的学生给我打电话,说觉得...

  • iOS - 爬过的坑

    长时间运行的线程可能需要新建额外的autoreleasepool来频繁的释放它的对象. 取决于实际代码表现, 适当...

  • 记爬过的坑

    坑一、 在使用jQuey()选择器方法选元素的时候含有特殊字符(. [ ] * 等)之类,如jQuery(“#m...

  • 微信 Android 视频编码爬过的那些坑

    来源 微信 Android 视频编码爬过的那些坑 Android的视频相关的开发,大概一直是整个Android生态...

  • Android TV开发-按键焦点

    欢迎大家入坑.大家好,我是冰雪情缘,已经在 Android TV开发爬坑多年,也是一名TV开发开源爱好者. And...

网友评论

  • CHN_Liao:VerticalGridView如何监听是否显示最后一个item?找不到findLastItemPosition的方法
  • xtl1889:有源码吗?我用VerticalGridView时出现,当焦点在最右测item时,在点击向有按钮,焦点不会发生变化,当给有焦点的item设置背景时,item位置错乱。
    代码如下:
    @Override
    public void onBindViewHolder(RecyclerView.ViewHolder holder, final int position) {
    final TestViewHolder testViewHolder= (TestViewHolder) holder;
    testViewHolder.textView.setText(getItem(position));

    testViewHolder.linearLayout.setOnFocusChangeListener(new View.OnFocusChangeListener() {
    @Override
    public void onFocusChange(View view, boolean b) {
    if (b){
    testViewHolder.textView.setBackgroundResource(R.drawable.text_selectbackground_shape);
    Toast.makeText(mContext,"-----"+position+"-----",Toast.LENGTH_SHORT).show();
    }else {
    testViewHolder.textView.setBackground(null);
    }
    }
    });
    }
    希望楼主指点一下,谢谢!!

本文标题:那些年,我们爬过的坑--Andriud TV篇(一)

本文链接:https://www.haomeiwen.com/subject/kvvlwttx.html