原文英文链接如下:
Touch Mode
Designing and developing user interfaces for Android is very different from doing so in a regular desktop environment. Because Android runs applications on mobile devices, application designers and developers must deal with numerous constraints that are not always obvious. To help you design and develop better applications, we are publishing a new series of posts focusing on Android user interfaces. In this series, we will give you design guides and tools, development tips, and explain the fundamental principles of the Android UI toolkit. The goal here is simple: we want to help you design and develop a great user experience. To start off this series, I'd like to introduce touch mode, one of the most important principles of the UI toolkit.
The touch mode is a state of the view hierarchy that depends solely on the user interaction with the phone. By itself, the touch mode is something very easy to understand as it simply indicates whether the last user interaction was performed with the touch screen. For example, if you are using a G1 phone, selecting a widget with the trackball will take you out of touch mode; however, if you touch a button on the screen with your finger, you will enter touch mode. When the user is not in touch mode, we talk about the trackball mode, navigation mode or keyboard navigation, so do not be surprised if you encounter these terms. Finally, there is only one API directly related to touch mode, .
Sounds easy enough right? Oddly enough, touch mode is deceivingly simple and the consequences of entering touch mode are far greater than you might think. Let's look at some of the reasons why.
Android系统上设计和开发用户交互体验不同于一般的桌面环境。Android应用程序运行在移动设备上,应用的设计和开发者必须处理众多的制约因素,这些因素看起来并不明显。为了帮助你设计与开发出更好用户体验的Android应用程序,我们将会推出一个新的系列文章专注于Android用户体验。在这个系列中,我们将给你介绍设计指南和工具,开发的技巧,和解释Android UI工具包最基本的原理。我们的目的很简单:我们想要帮助你设计与开发一个很好的用户体验。开始这个系列文章,我首先将要介绍Touch mode,它是工具箱中最重要的一个原理之一。
Touch mode是View的一种状态,它只依赖用户与手机的交互。对于Touch mode自己来说,Touch mode是一个非常容易理解的,因为它简单的表明了用户最后一次交互是否是触摸屏幕。举个例子,比如你用G1手机,用轨迹球选择一个小部件将会使你离开touch mode这个模式。然而,如果你用手指触摸屏幕上的一个按钮,你将会进入触摸模式。用户不在触摸模式下,比如我们谈论到的轨迹球,导航模式,键盘导航,请不要感到惊讶如果你遇到这些术语。最后,这里只有一个API直接涉及到触摸模式,View.isInTouchMode();
听起来很容易,奇怪的是,触摸模式带有一些欺骗性质。进入触摸模式带来的影响远远大于你的想象。接下来让我们看一些原因:
Touch Mode, Selection, and Focus
Designing a UI toolkit for mobile devices is difficult because of the various interaction mechanisms they provide. Some devices offer only 12 keys, some have a touch screen, some require a stylus, some have both a touch screen and a keyboard. In that regard, it is a great benefit for the Android development community that the first commercially available device, the G1, offers multiple forms of input using a touch screen, a trackball, and a keyboard. Because the user can interact with applications using three different mechanisms, we had to think very hard about all the possible issues that could arise. One issue led us to create the touch mode.
Imagine a simple application, for example, that shows a list of text items. The user can freely navigate through the list using the trackball and they can also scroll and fling the list using their finger. The issue in this scenario is the selection. If I select an item at the top of the list and then fling the list towards the bottom, what should happen to the selection? Should it remain on the item and scroll off the screen? In this case, what would happen if I then decide to move the selection with the trackball? Or worse, if I press the trackball to act upon the currently selected item, which is not shown on screen anymore. After careful considerations, we decided to remove the selection altogether.
In touch mode, there is no focus and no selection. Any selected item in a list of in a grid becomes unselected as soon as the user enters touch mode. Similarly, any focused widgets become unfocused when the user enters touch mode.
为移动设备设计一个UI工具箱是一件困难的事,因为移动设备可以提供各种各样的交互机制。一些设备可以提供仅只有12个按键的键盘,一些设设备只有触摸屏,一些设备有手写笔,一些设备既有触摸屏,又有键盘。G1手机提供了多种形式的输入,比如触摸屏,轨迹球,键盘。因为用户与应用程序的交互可以用不同的方式,我们不得不努力的考虑所有可能出现的问题。其中一个问题使我们创建触摸模式。
假象一个简单的应用,比如ApiDemos里面ListView展示了一个文本列表。用户可以自由的导航这个列表使用轨迹球或者通过手指滚动列表。这里的问题是列表中每一项被选中状态的问题。如果我选中这个列表最顶部的一项然后向底部滑动,选中状态将会发生什么情况?它会一直在那个item还是离开屏幕?在这个用例中,如果我用轨迹球移动这个选中项将会发生什么?更糟糕的是,如果按下轨迹求执行向上的操作,当前列表项会不被显示。经过慎重考虑,我们决定完全取消该列表项的选中状态。
在触摸模式下,view没有焦点与选中状态。任何在列表中选中状态的列表项将会变成没有选中状态项一旦用户进入触摸模式。任何获取焦点状态的组件将会失去焦点一旦用户进入触摸模式。
To make things more natural for the user, the framework knows how to resurrect the selection/focus whenever the user leaves touch mode. For instance, in the example above, if the user were to use the trackball again, the selection would reappear on the previously-selected item. This is why some developers are confused when they create a custom view and start receiving key events only after moving the trackball once: their application is in touch mode, and they need to use the trackball to exit touch mode and resurrect the focus.
The relationship between touch mode, selection, and focus means you must not rely on selection and/or focus to exist in your application. A very common problem with new Android developers is to rely on . In touch mode, this method will return . You should instead use or the .
为了使用户体验更加自然,Android框架层知道怎样恢复选中或者焦点状态当用户离开触摸模式时。比如在上面的例子中,如果用户再次使用轨迹球,选中状态会重新出现在前一个已经选中状态的item项上。这就是为什么一些开发者感到困惑的地方,当他们自己自定义了一个view,在滚动轨迹球之后,可以开始接受一些关键的事件:应用处在touch mode模式,用户需要使用轨迹球退出触摸模式并且重新获取焦点。
触摸模式,选择/焦点状态,意味着触摸模式下,你不能够依赖选中或者焦点状态存在你的应用中。一个非常普遍的问题Android新手依赖ListView的方法获取选中状态的item,如果在触摸模式下,这个方法将会返回不合法的位置。你应该使用点击事件或者choice mode替代这个方法。
Focusable in Touch Mode
Now that you know focus doesn't exist in touch mode, I must explain that it's not entirely true. Focus can exist in touch mode but in a very special way we call focusable in touch mode. This special mode was created for widgets that receive text input, like or, when filtering is enabled, . This is why the user can type text inside a text field without first selecting it with the trackball or their finger. When a user touches the screen, the application will enter touch mode if it wasn't in touch mode already. What happens during the transition to touch mode depends on what the user touched, and what currently has focus. If the user touches a widget that is focusable in touch mode, that widget will receive focus. Otherwise, any currently focused widget will not retain focus unless it is focusable in touch mode.
现在你知道触摸模式下不会存在焦点,我必须解释一下那种情况不是完全的正确。焦点可以存在在触摸模式下而是我们通过一个非常特殊的方式获取可以获取焦点在触摸模式下。这种特殊的模式被创建于组件接受文本的输入,比如EditText或者ListView过滤文本item。这就是为什么用户能够输入文本并没有第一次选择它用轨迹求或者手指。当用户触摸屏幕时,应用程序将会进入触摸模式如果它没有在触摸模式。到触摸模式这个过程发生了什么依赖与用户的触摸行为和当前是否有焦点。如果用户触摸了一个组件,该组件在触摸模式下可以获取焦点,那个组件可以接受焦点事件。否则,任何当前获取焦点的组件不能够保持焦点除非它在触摸模式下可以获取焦点。
is a property that you can set yourself either from code or XML. However, it should be used sparingly and only in very specific situations as it breaks consistency with Android normal behavior. A game is a good example of an application that can make good use of the focusable in touch mode property. MapView, if used in fullscreen as in Google Maps, is another good example of where you can use focusable in touch mode correctly.
Below is another example of a focusable in touch mode widget. When the user taps an AutoCompleteTextView's suggestion with his finger, the focus remains on the input text field:
触摸模式下可以获取焦点是一个属性,你可以通过xml文件或者代码设置这个属性。然而,它应该被谨慎使用,因为它打破了Android普通行为的一致性。游戏开发是一个好的例子当在触摸模式下可以获取焦点。MapView,如果设置全屏模式下也是一个好的例子在触摸模式获取焦点。
用户轻按一个AutoCompleteTextView ,焦点一直保持在该组件上。
New Android developers often think that focusable in touch mode is the solution they need to "fix" the problem of disappearing selection/focus. We really encourage you to think very hard before using it. If used incorrectly, it can make your application behave differently from the rest of the system and simply throw off the user's habits. The Android framework contains all the tools you need to handle user interactions without using "focusable in touch mode". For example, instead of trying to make ListView always keep its selection, simply use the appropriate . And if you feel that the framework does not suit all your need, feel free to or .
Android新手经常认为触摸模式下可以获取焦点可以解决他们的问题当该组件没有出现选中或者焦点状态时。我们不推荐你那样使用它。如果运用得不正确,它将会导致你的应用程序行为不一样与系统并且脱离用户的实际行为。Android框架包含了所有的工具处理用户交互在触摸模式下获取焦点。比如,listview你可以使用choice mode代替它。
Touch Mode Cheat Sheet
Do:
- Remain consistent with the core applications
- Use the appropriate feature if you need persistent selection (radio button, check box, ListView's choice mode, etc.)
- Use focusable in touch mode if you write a game
Don't:
- Do not try to keep the focus or selection in touch mode
触摸模式小结:
可以做:
保持一直性同核心应用一样
使用合适的特性如果你想保持持久的选中状态
使用触摸模式下获取焦点在游戏应用中
不可以做:
不要尝试保持焦点或者选中状态在触摸模式下