在 android 中。焦点的获取和事件几乎相同,有一个分发机制。一般来说View 树上上层节点的 ViewGroup 比底层节点的 View 有更高的优先级获取焦点。这体如今 ViewGroup 有一个属性 descendantFocusability 可以用来控制焦点获取的优先级。 该属性的值有三种:

  • beforeDescendants:ViewGroup 会优先其子类控件而获取到焦点,假设父控件不获取焦点,子控件才可能会获得焦点
  • afterDescendants:仅仅有当其子类控件不须要获取焦点时。ViewGroup 才可能获取焦点
  • blocksDescendants:viewgroup 会堵塞子类控件获得焦点。不管 ViewGroup 是否获取焦点,子控件都不可以获得焦点

怎样推断 View 是否可以获取焦点

由于上面的原因。推断一个 View 是否有可能获得焦点。就与它全部的父节点有关系了,所以 View 的 hasFocusable 方法实现例如以下:

public boolean hasFocusable() {
if (!isFocusableInTouchMode()) {
for (ViewParent p = mParent; p instanceof ViewGroup; p = p.getParent()) {
final ViewGroup g = (ViewGroup) p;
if (g.shouldBlockFocusForTouchscreen()) {
return false;
}
}
}
return (mViewFlags & VISIBILITY_MASK) == VISIBLE && isFocusable();
}
  1. 在触摸模式下假设不可获取焦点。先遍历 View 的全部父节点,假设有一个父节点设置了堵塞子 View 获取焦点,那么该 View 就不可能获取焦点
  2. 在触摸模式下假设不可获取焦点,而且没有父节点设置堵塞子 View 获取焦点。和在触摸模式下假设可以获取焦点,那么才推断 View 自身的 visiable 和 focusable 属性,来决定是否可以获取焦点。不可见的 View 当然也不能获取焦点,所以仅仅有 visiable 和 focusable 同一时候为 true,该View 才可能获取焦点

怎样推断 ViewGroup 是否可以获取焦点

推断一个 ViewGroup 是否可能获取到焦点,也与它的子 View 有关系了。假设子 View 可以获取焦点,辣么。就行算作这个 ViewGroup 也可能获取(消耗)焦点,所以 ViewGroup 的 hasFocusable 方法实现例如以下:

public boolean hasFocusable() {
if ((mViewFlags & VISIBILITY_MASK) != VISIBLE) {
return false;
} if (isFocusable()) {
return true;
} final int descendantFocusability = getDescendantFocusability();
if (descendantFocusability != FOCUS_BLOCK_DESCENDANTS) {
final int count = mChildrenCount;
final View[] children = mChildren; for (int i = 0; i < count; i++) {
final View child = children[i];
if (child.hasFocusable()) {
return true;
}
}
} return false;
}

依据上面的源代码可知,推断 ViewGroup 是否可以获取焦点就简单多了

  1. 假设 ViewGroup visiable 和 focusable 都为 true,就算可以获取焦点
  2. 假设不满足第 1 点,假设子 View 节点可以获取焦点,该 ViewGroup 也算能获取焦点(通过递归实现)
  3. 否则。就算作不可以获取到焦点
  4. ViewGroup 自己可以获取焦点,全然没有考虑是否在触摸模式的情况。不晓得是不是 google project师的 bug,快到 google groups 提问 ^-^!

View 是否可以获取焦点的实际应用

View 是否可以获取焦点。通常在 AbsListView 的 OnItemClickListener,EditText,Button 的使用和 key 事件分发中会应用到。

比方 ListView 的 OnItemClickListener,仅仅有在 ListView 的 ItemView 不能获取到 focus 的情况下。才会调用 OnItemClickListener 的 onItemClick 方法。详细代码可以參考 AbsListView 的 onTouchUp 方法:

private void onTouchUp(MotionEvent ev) {
switch (mTouchMode) {
case TOUCH_MODE_DOWN:
case TOUCH_MODE_TAP:
case TOUCH_MODE_DONE_WAITING:
......
该省就省。我是省略代码切割符 ^_^
......
if (inList && !child.hasFocusable()) {
if (mPerformClick == null) {
mPerformClick = new PerformClick();
} final AbsListView.PerformClick performClick = mPerformClick;
performClick.mClickMotionPosition = motionPosition;
performClick.rememberWindowAttachCount(); ......
该省就省,我是省略代码切割符 ^_^
......
mTouchModeReset = new Runnable() {
@Override
public void run() {
mTouchModeReset = null;
mTouchMode = TOUCH_MODE_REST;
child.setPressed(false);
setPressed(false);
if (!mDataChanged && !mIsDetaching && isAttachedToWindow()) {
performClick.run();
}
}
};
postDelayed(mTouchModeReset,
ViewConfiguration.getPressedStateDuration());
} else {
mTouchMode = TOUCH_MODE_REST;
updateSelectorState();
}
return;
} else if (!mDataChanged && mAdapter.isEnabled(motionPosition)) {
performClick.run();
}
}
}
......
该省就省,我是省略代码切割符 ^_^
......
}

从上面代码的第 9 行可知。ListView 的 ItemView 的 hasFocusable 方法必须返回 fasle,才会运行 performClick.run(),才会运行到 OnItemClickListener 的 onItemClick 方法。

这也就是为什么通常我们在使用 ListView 的 OnItemClickListener 方法的时候要把 Item 布局文件的根节点的 descendantFocusability 属性设置为 blocksDescendants,而且该节点的 focusable 属性不能为 true。

View 和 ViewGroup 的 hasFocusable的更多相关文章

  1. Android View和ViewGroup

    View和ViewGroup Android的UI界面都是由View和ViewGroup及其派生类组合而成的. 其中,View是所有UI组件的基类,而 ViewGroup是容纳这些组件的容器,其本身也 ...

  2. 自定义View和ViewGroup

    为了扫除学习中的盲点,尽可能多的覆盖Android知识的边边角角,决定对自定义View做一个稍微全面一点的使用方法总结,在内容上面并没有什么独特的地方,其他大神们的博客上面基本上都有讲这方面的内容,如 ...

  3. 自定义View_1_关于View,ViewGroup的测量和绘制流程

    自定义View(1) ------ 关于View,ViewGroup的测量和绘制流程 在Android当中,自定义控件属于比较高级的知识体系,今天我们就一起研究研究关于自定义View的那点事,看看它到 ...

  4. View、ViewGroup (转)

    Android原理揭秘系列之View.ViewGroup (转) Android的UI界面都是由View和ViewGroup及其派生类组合而成的.其中,View是所有UI组件的基类,而ViewGrou ...

  5. android 应用架构随笔四(View、ViewGroup)

    View表示了用户界面的基本构建模块. 一个View占用了屏幕上的一个矩形区域并且负责界面绘制和事件处理.手机屏幕上所有看得见摸得着的都是View. Activity是四大组件中唯一一个用来和用户进行 ...

  6. Android(java)学习笔记95:Android原理揭秘系列之View、ViewGroup

    作过Android 应用开发的朋友都知道,Android的UI界面都是由View和ViewGroup及其派生类组合而成的.其中,View是所有UI组件的基类,而ViewGroup是容纳这些组件的容器, ...

  7. android应用的界面编程----View与ViewGroup的概念

    1 UI OverView Android中所有的UI元素都是通过View与ViewGroup来构建的,View是指屏幕中一块可与用户进行交互的空白,类似于java界面编程中的JPanel.为了界面布 ...

  8. 自定义控件(视图)1期笔记01:View 和 ViewGroup

    1.View 和 ViewGroup 图解关系: 2. View 和 ViewGroup 关系和作用: (1) 关系: • 继承关系 • 组合关系 (2) 作用:      • View的作用: 提供 ...

  9. View,viewgroup,viewstub总结

    :first-child { margin-top: 0; } blockquote > :last-child { margin-bottom: 0; } img { border: 0; m ...

随机推荐

  1. DotNetCore.1.0.1-VS2015Tools.Preview2.0.3 相关问题及解决办法

    本月16号,MS发布了 .NET Core 1.1.作为一个用贯MS产品的小盆友,我第一时间就把相关的安装包下载下来了,然后果断安装(入坑). 我猜你来看这篇博客可能遇到了和我一样的问题. 问题0:正 ...

  2. swift语言点评十-Value and Reference Types

    结论:value是拷贝,Reference是引用 Value and Reference Types Types in Swift fall into one of two categories: f ...

  3. 优动漫PAINT个人版绘制树叶教程

    超详细树叶绘制法,更有配套绘树小TIPE!让你画树So Easy~一秒变身,画树达人! 优动漫PAINT个人版软件下载:http://www.dongmansoft.com/chanpin.html ...

  4. checkbox控制显示隐藏

    显示文本框<input type = "checkbox" id="checkbox" onclick="on_hide();"/&g ...

  5. Hadoop_HDFS-基础知识摘要

    Hadoop典型应用有:搜索.日志处理.推荐系统.数据分析.视频图像分析.数据保存等.0.数据要首先分块 Block:将一个文件进行分块,通常是64M. NameNode:--管理节点保存整个文件系统 ...

  6. HDU-4296 Buildings 贪心 从相邻元素的相对位置开始考虑

    题目链接:https://cn.vjudge.net/problem/HDU-4296 题意 有很多板子,每一个板子有重量(w)和承重(s)能力 现规定一块板子的PDV值为其上所有板子的重量和减去这个 ...

  7. maven 安装jar包

    1 下载maven: 下载路径: http://mirrors.hust.edu.cn/apache/maven/maven-3/3.5.0/binaries/apache-maven-3.5.0-b ...

  8. python学习笔记:第四天

    day04: 一.计算求值 num += 1 等价于 num = num + 1num -= 1 等价于 num = num - 1num *= 2 等价于 num = num * 2num /= 2 ...

  9. 紫书 习题 11-3 UVa 820 (最大流裸题)

    注意这道题是双向边, 然后直接套模板就ok了. #include<cstdio> #include<algorithm> #include<vector> #inc ...

  10. [luogu]P4312 [COCI 2009] OTOCI / 极地旅行社(LCT)

    P4312 [COCI 2009] OTOCI / 极地旅行社 题目描述 不久之前,Mirko建立了一个旅行社,名叫"极地之梦".这家旅行社在北极附近购买了N座冰岛,并且提供观光服 ...