创建输入法| Android 开发者
文章推薦指數: 80 %
输入法(IME) 是一种可让用户输入文本的用户控件。
Android 提供了一种可扩展的输入法框架。
借助该框架,应用可以为用户提供备选输入法,例如屏幕键盘, ...
平台
AndroidStudio
GooglePlay
Jetpack
Kotlin
文档
新闻
Language
English
BahasaIndonesia
Deutsch
Español
Español–AméricaLatina
Français
Português–Brasil
TiếngViệt
Türkçe
Русский
ภาษาไทย
中文–简体
中文–繁體
日本語
한국어
文档
概览
指南
参考文档
示例
设计和质量
平台
AndroidStudio
GooglePlay
Jetpack
Kotlin
文档
概览
指南
参考文档
示例
设计和质量
新闻
应用基础知识
简介
构建首个应用概览创建Android项目运行您的应用构建简单的界面启动另一个Activity
应用基础知识
应用资源概览处理配置变更
本地化本地化您的应用使用pseudolocale测试您的应用Unicode和国际化支持语言和语言区域解决方案复杂的XML资源
资源类型概览动画颜色状态列表可绘制对象布局菜单字符串样式字体更多类型
应用清单文件概览
Android提供了一种可扩展的输入法框架。
借助该框架,应用可以为用户提供备选输入法,例如屏幕键盘,甚至语音输入。
安装所需的IME后,用户可以从系统设置中选择要使用的IME,并在整个系统中使用该IME;同时只能启用一个IME。
如要向Android系统添加IME,您需要创建一个Android应用,其中包含一个扩展InputMethodService的类。
此外,您通常需要创建一个“设置”Activity,以向IME服务传递选项。
您还可以定义一个设置界面,使其作为系统设置的一部分显示。
本指南涵盖以下内容:
IME生命周期
在应用清单中声明IME组件
IMEAPI
设计IME界面
将文本从IME发送到应用
使用IME子类型
如果您以前没有处理过IME,则应先阅读入门文章屏幕输入法。
注意:从Android 11开始,平台允许IME以内嵌方式(而不是使用下拉菜单)显示自动填充建议。
如需详细了解自动填充服务如何支持此功能,请参阅将自动填充功能与键盘集成。
IME生命周期
下图显示了IME的生命周期:
图1.IME的生命周期。
以下各部分介绍了如何实现与遵循此生命周期的IME相关联的界面和代码。
在清单中声明IME组件
在Android系统中,IME是包含一项特殊IME服务的Android应用。
应用的清单文件必须声明该服务,请求必需的权限,提供一个与操作action.view.InputMethod匹配的Intent过滤器,并提供定义IME特征的元数据。
此外,要提供可让用户修改IME行为的设置界面,您可以定义一个可通过系统设置启动的“设置”Activity。
以下代码段声明了一项IME服务。
它请求了BIND_INPUT_METHOD权限以让该服务可以将IME连接到系统,设置了一个与android.view.InputMethod操作匹配的Intent过滤器,并定义了IME的元数据:
它有一个适用于ACTION_MAIN的Intent过滤器,指示该Activity是IME应用的主入口点:
输入法API
android.inputmethodservice和android.view.inputmethod软件包中提供了IME专用的类。
KeyEvent类对于处理键盘字符非常重要。
IME的核心部分是一个服务组件,即一个扩展InputMethodService的类。
除了实现正常的服务生命周期之外,该类还提供具有以下用途的回调:提供IME的界面,处理用户输入,以及向当前处于焦点的字段提供文本。
默认情况下,InputMethodService类提供有关管理IME状态和可见性以及与当前输入字段进行通信的大部分实现。
以下类也很重要:
BaseInputConnection
定义从InputMethod返回到接收其输入的应用的通信渠道。
您可以使用该类读取光标周围的文本,将文本提交至文本框,然后将原始按键事件发送到应用。
应用应扩展该类,而不是实现基接口InputConnection。
KeyboardView
用于呈现键盘和响应用户输入事件的View的扩展。
键盘布局由Keyboard的实例指定,您可以在XML文件中定义该实例。
设计输入法界面
IME有两个主要视觉元素:输入视图和候选视图。
您只需要实现与您要设计的输入法相关的元素。
输入视图
输入视图是指用户以点击按键、手写或手势的形式输入文本的界面。
当IME首次显示时,系统会调用onCreateInputView()回调。
在此方法的实现中,您可以创建要在IME窗口中显示的布局,并将布局返回系统。
以下代码段是一个实现onCreateInputView()方法的示例:
Kotlin
overridefunonCreateInputView():View{
returnlayoutInflater.inflate(R.layout.input,null).apply{
if(thisisMyKeyboardView){
setOnKeyboardActionListener(this@MyInputMethod)
keyboard=latinKeyboard
}
}
}
Java
@Override
publicViewonCreateInputView(){
MyKeyboardViewinputView=
(MyKeyboardView)getLayoutInflater().inflate(R.layout.input,null);
inputView.setOnKeyboardActionListener(this);
inputView.setKeyboard(latinKeyboard);
returninputView;
}
在此示例中,MyKeyboardView是KeyboardView(呈现Keyboard)的自定义实现的一个实例。
候选视图
候选视图是指IME显示可能的字词更正或文字建议供用户选择的界面。
在IME生命周期中,系统会在准备好显示候选视图时调用onCreateCandidatesView()。
在此方法的实现中,可以返回显示文字建议的布局;如果您不想显示任何内容,可以返回null。
Null响应是默认行为,因此如果您不提供建议,则无需实现此方法。
界面设计注意事项
此部分介绍了一些具体的IME界面设计注意事项。
处理多种屏幕尺寸
IME的界面必须能够针对不同的屏幕尺寸进行缩放,并且还必须处理横向和纵向屏幕方向。
在非全屏IME模式下,留出足够的空间供应用显示文本字段和任何关联的上下文,以使IME占用不超过一半的屏幕空间。
在全屏IME模式下,不存在此问题。
处理不同的输入类型
通过Android文本字段,您可以设置特定的输入类型,例如自由格式的文本、数字、网址、电子邮件地址以及搜索字符串。
当实现新的IME时,您需要检测每个字段的输入类型,并为其提供相应的界面。
不过,您无需设置IME来检查用户针对输入类型输入的文本是否有效;这项工作由拥有相应文本字段的应用负责。
例如,以下是随Android平台提供的拉丁语IME针对文本和电话号码输入提供的界面的屏幕截图:
图2.拉丁语IME输入类型。
当输入字段获得焦点并且您的IME启动时,系统会调用onStartInputView(),并传入一个EditorInfo对象,其中包含有关输入类型和文本字段的其他属性的详情。
在该对象中,inputType字段包含文本字段的输入类型。
inputType字段是一个包含各种输入类型设置的位模式的int。
如要针对文本字段的输入类型测试该字段,请使用常量TYPE_MASK_CLASS遮盖它,如下所示:
Kotlin
inputTypeandInputType.TYPE_MASK_CLASS
Java
inputType&InputType.TYPE_MASK_CLASS
输入类型位模式可以具有以下值之一:
TYPE_CLASS_NUMBER
用于输入数字的文本字段。
如前面的屏幕截图所示,拉丁语IME显示了适用于此类型的字段的数字键盘。
TYPE_CLASS_DATETIME
用于输入日期和时间的文本字段。
TYPE_CLASS_PHONE
用于输入电话号码的文本字段。
TYPE_CLASS_TEXT
用于输入所有受支持字符的文本字段。
InputType的参考文档中对这些常量进行了更详细的介绍。
inputType字段可以包含其他位,以指示文本字段类型的变体,例如:
TYPE_TEXT_VARIATION_PASSWORD
用于输入密码的TYPE_CLASS_TEXT的变体。
输入法将显示装饰标志,而不是实际文本。
TYPE_TEXT_VARIATION_URI
用于输入网址以及其他统一资源标识符(URI)的TYPE_CLASS_TEXT的变体。
TYPE_TEXT_FLAG_AUTO_COMPLETE
TYPE_CLASS_TEXT的变体,用于输入应用从字典、搜索或其他工具“自动填充”的文本。
在测试这些变体时,请务必使用相应的常量遮盖inputType。
InputType的参考文档中列出了可用的遮盖常量。
注意:在您自己的IME中,请确保在将文本发送到密码字段时对其进行正确处理。
在界面中的输入视图和候选视图中隐藏密码。
另请注意,您不应将密码存储在设备上。
如需了解详情,请参阅安全设计指南。
向应用发送文本
当用户使用您的IME输入文本时,您可以通过以下方式向应用发送文本:发送单个按键事件,或在应用的文本字段中修改光标周围的文本。
在任何一种情况中,您都要使用InputConnection的实例来提供文本。
如要获取该实例,请调用InputMethodService.getCurrentInputConnection()。
修改光标周围的文本
在处理对文本字段中现有文本的修改时,您可以使用BaseInputConnection中提供的一些更实用的方法,包括:
getTextBeforeCursor()
返回CharSequence,其中包含当前光标位置之前请求数量的字符
getTextAfterCursor()
返回CharSequence,其中包含当前光标位置之后请求数量的字符。
deleteSurroundingText()
删除当前光标位置前后指定数量的字符。
commitText()
将CharSequence提交至文本字段并设置一个新的光标位置。
例如,以下代码段展示了如何将光标左侧的四个字符替换为文本“Hello!”:
Kotlin
currentInputConnection.also{ic:InputConnection->
ic.deleteSurroundingText(4,0)
ic.commitText("Hello",1)
ic.commitText("!",1)
}
Java
InputConnectionic=getCurrentInputConnection();
ic.deleteSurroundingText(4,0);
ic.commitText("Hello",1);
ic.commitText("!",1);
在提交之前书写文本
如果您的IME执行文本预测或需要多个步骤来书写某个字形或字词,则您可以在文本字段中显示进度(直到用户提交相应字词),然后将部分文本替换为已完成的文本。
在将文本传递至setComposingText()时,您可以通过向文本添加“span”对其进行特殊处理。
以下代码段展示了如何在文本字段中显示进度:
Kotlin
currentInputConnection.also{ic:InputConnection->
ic.setComposingText("Composi",1)
ic.setComposingText("Composin",1)
ic.commitText("Composing",1)
}
Java
InputConnectionic=getCurrentInputConnection();
ic.setComposingText("Composi",1);
ic.setComposingText("Composin",1);
ic.commitText("Composing",1);
以下屏幕截图展示了这一过程向用户显示的情况:
图3.在提交之前书写文本。
拦截硬件按键事件
即使输入法窗口未获得明确的焦点,它也会先接收硬件按键事件,并且可以选择是使用这些事件,还是将其转发到应用。
例如,您可能需要使用方向键在界面中导航,以便在书写文本期间选择候选项。
您可能还需要点按返回键,以便关闭来自输入法窗口的任何弹出式窗口。
如要拦截硬件按键,请替换onKeyDown()和onKeyUp()。
请务必对您不想自行处理的按键调用super()方法。
创建IME子类型
借助子类型,IME可以提供多种受支持的输入模式和语言。
子类型可以代表以下内容:
语言区域,例如en_US或fr_FR。
输入模式,例如语音输入、键盘输入或手写输入。
特定于IME的其他输入样式、形式或属性,例如10键键盘布局或QWERTY键盘布局。
模式基本上可以是任何文本,例如“keyboard”、“voice”等。
子类型还可以提供这些模式的组合。
子类型信息用于通知栏中提供的IME切换器对话框以及IME设置。
通过此信息,框架还可以直接调出IME的特定子类型。
在构建IME时,请使用子类型工具,因为它可以帮助用户识别不同的IME语言和模式并在它们之间切换。
您可以使用
以下代码段定义了一个具有两个子类型的IME:用于美国英语语言区域的键盘子类型,以及用于法国法语语言区域的另一种键盘子类型:
以下两个代码段演示了此过程。
第一个代码段显示了输入法的XML文件的一部分:
字符串资源label_subtype_generic(由输入法界面定义用来设置子类型的标签)定义为:
例如,在任何英语语言区域中,显示名都是“English(UnitedStates)”。
从通知栏中选择IME子类型
Android系统会管理所有IME提供的所有子类型。
IME子类型被视为它们所属IME的模式。
在通知栏中,用户可以为当前设置的IME选择一个可用的子类型,如以下屏幕截图所示:
图4.从通知栏中选择IME子类型。
图5.在系统设置中设置子类型偏好设置。
从系统设置中选择IME子类型
用户可以在“系统设置”区域的“语言和输入法”设置面板中控制子类型的使用方式。
图6.为IME选择语言。
在IME子类型之间切换
通过在键盘上提供切换键(例如地球形状的语言图标),可以让用户在多个IME子类型之间轻松切换。
这样做可以极大地提高键盘的易用性,并且有助于避免用户产生不满。
如要启用此类切换,请执行以下步骤:
在输入法的XML资源文件中声明supportsSwitchingToNextInputMethod="true"。
您的声明应类似于以下代码段:
如果该方法返回true,则显示一个切换键。
当用户点按该切换键时,调用switchToNextInputMethod(),向第二个参数传递false。
False值会告知系统以同样的方式处理所有子类型,无论它们属于哪种IME。
指定true则会要求系统循环切换当前IME中的子类型。
注意:在Android5.0(API级别21)之前的版本中,switchToNextInputMethod()无法感知supportsSwitchingToNextInputMethod属性。
如果用户在没有切换键的情况下切换到某个IME,可能会卡在该IME中,无法轻松从中切换出来。
IME一般注意事项
在实现IME时,还需要考虑以下事项:
为用户提供一种直接通过IME界面设置选项的方式。
由于设备上可能安装了多个IME,因此请为用户提供一种可以直接从输入法界面切换到其他IME的方式。
快速调出IME界面。
预加载或按需加载任何大型资源,以便用户可以在点按文本字段后立即看到IME。
缓存用于输入法后续调用的资源和视图。
相反,您应在输入法窗口隐藏之后立即释放较大的内存分配,以便应用可以有足够的内存来运行。
考虑在IME处于隐藏状态几秒钟后使用延迟消息来释放资源。
确保对于与IME相关联的语言或语言区域,用户可以输入尽可能多的字符。
请注意,用户可能会在密码或用户名中使用标点符号,因此您的IME必须提供多种不同的字符,以允许用户输入密码并访问设备。
ContentandcodesamplesonthispagearesubjecttothelicensesdescribedintheContentLicense.JavaisaregisteredtrademarkofOracleand/oritsaffiliates.
Lastupdated2021-05-03UTC.
[]
[]
微信
在微信上关注“GoogleDevelopers”
Twitter
在Twitter上关注@AndroidDev
YouTube
在YouTube上访问“AndroidDevelopers”频道
关于Android
Android
Enterprise
安全
源代码
支持
报告平台错误
报告文档错误
GooglePlaysupport
参加调查研究
文档
开发者指南
设计指南
API参考
示例
AndroidStudio
Android
Chrome
Firebase
GoogleCloudPlatform
所有产品
隐私权政策
许可
品牌指南
ICP证合字B2-20070004号
通过电子邮件接收资讯和提示
订阅
Language
English
BahasaIndonesia
Deutsch
Español
Español–AméricaLatina
Français
Português–Brasil
TiếngViệt
Türkçe
Русский
ภาษาไทย
中文–简体
中文–繁體
日本語
한국어
延伸文章資訊
- 1Gboard - Google 鍵盤- Google Play 應用程式
- 2创建输入法| Android 开发者
输入法(IME) 是一种可让用户输入文本的用户控件。Android 提供了一种可扩展的输入法框架。借助该框架,应用可以为用户提供备选输入法,例如屏幕键盘, ...
- 3Creating an Input Method | Android Developers
An input method editor (IME) is a user control that enables users to enter text. Android provides...
- 4android系统ime指令_接私活 - CSDN博客
介绍几种android系统中ime的shell指令:enable指定的输入法root@kylin32:/data/anr # ime enable com.iflytek.inputmethod...
- 5TRIME - GitHub
同文安卓輸入法平臺3.x/Android-rime/Rime Input Method Engine for Android - GitHub - osfans/trime: 同文安卓輸入法平臺...