输入法的定义

输入法,就是用来输入字符(包括英文,俄文,中文)的工具。输入法你可以看成是一种字符发生器,它将输入数据触摸事件或者按键事件转化为其他更丰富的字符。
1、系统可以有多个输入法;
2、只有一个是激活的;
3、输入法同一时  间只能服务一个程序。

IMMS(InputMethodManagerService)

这是整个系统当中,一切与输入法有关的地方的总控制中心。它通过管理下面三个模块来实现系统的输入法框架。
1、/frameworks/base/services/java/com/android/server/wm/WindowManagerService
      负责显示输入法,接收用户事件。
2、/frameworks/base/core/java/android/inputmethodservice/InputMethodService
     输入法内部逻辑,键盘布局,选词等,最终把选出的字符通过commitText提交出来。
3、/frameworks/base/core/java/android/view/inputmethod/InputMethodManager
     由UI控件(View,TextView,EditText等)调用,用来操作输入法。比如,打开,关闭,切换输入法等。

下面说一下InputMethodManagerService这个控制中心是怎么样与三个模块交互的。

1、与WindowManagerSerivce的交互。

首先,InputMethodManagerService在初始化时,会调用IWindowManager.Stub.asInterface(ServiceManager.getService(Context.WINDOW_SERVICE)),得到IWindowManager这个代理,然后通过IWindowManager与WindowManagerService交互。比如下面这些操作:

调用mIWindowManager.addWindowToken(mCurToken, WindowManager.LayoutParams.TYPE_INPUT_METHOD),让WindowManagerService显示输入法界面。

调用mIWindowManager.removeWindowToken(mCurToken)让输入法界面关闭。

调用mIWindowManager.inputMethodClientHasFocus(client)判断输入法是否聚焦。

2、与InputMethodService的交互。

InputMethodManagerService在内部维护着一个ArrayList<InputMethodInfo> mMethodList。这个列表会在服务启动时通过PackageManager查询当前系统中的输入法程序来得到。与之对应的,每一个输入法程序的AndroidManifest.xml中都会有一个Service,而每个Service中都会有标记来告诉系统,自己是个输入法程序。下面这个是从系统自带的例子Samples/SoftKeyboard/AndroidManifest.xml中的取出来的:

<manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.example.android.softkeyboard"><application android:label="@string/ime_name"><service android:name="SoftKeyboard"android:permission="android.permission.BIND_INPUT_METHOD"><intent-filter><action android:name="android.view.InputMethod" /></intent-filter><meta-data android:name="android.view.im" android:resource="@xml/method" /></service></application>
</manifest>

另外,InputMethodManagerService内部还有一个PackageReceiver,当系统中有程序的安装、删除、重启等事件发生时,会更新mMethodList。InputMethodManagerService打开,关闭,切换输入法时,其实就是在操作mMethodList中某个InputMethodInfo。把InputMethodInfo中的代表某个输入法的InputMethodService启动或者销毁,就实现了输入法的打开和关闭。

3、与InputMethodManager的交互

InputMethodManager中会包含一个IInputMethodManager,这个东西就是InputMethodManagerService的代理,打开关闭输入法这些操作就是由InputMethodManager中的某些方法调用IInputMethodManager中相应的方法来实现的。比如:

mService.getInputMethodList()获取输入法列表。

mService.updateStatusIcon(imeToken, packageName, iconId)更新输入法图标,即屏幕上方状态栏中的输入法图标。

mService.finishInput(mClient)隐藏当前输入法。这所以不说关闭输入法,是因为输入法服务启动起来以后,只有在系统关闭或者切换输入法时才会关闭。

mService.showSoftInput(mClient, flags, resultReceiver)打开当前输入法。

IMF简介

1、程序获得焦点时,就会通过InputMethodManager向InputMethodManagerService通知自己获得焦点并请求绑定自己到当前输入法上;
2、同时,当程序的某个需要输入法的view比如EditorView获得焦点时就会通过InputMethodManager向InputMethodManagerService请求显示输入法;
3、这时InputMethodManagerService收到请求后,会将请求的EditText的数据通信接口发送给当前输入法,并请求显输入法。输入法收到请求后,就显示自己的UI dialog,同时保存目标view的数据结构,当用户实现输入后,直接通过view的数据通信接口将字符传递到对应的View。

InputMethodManager

每个程序有一个InputMethodManager实例,这个是程序和InputMethodManagerService通信的接口,该实例在ViewRootImpl初始化的时候创建。
    public ViewRootImpl(Context context, Display display) {mContext = context;mWindowSession = WindowManagerGlobal.getWindowSession();}public static IWindowSession getWindowSession() {synchronized (WindowManagerGlobal.class) {if (sWindowSession == null) {try {//这个进程的InputMethodManager实例就生成了InputMethodManager imm = InputMethodManager.getInstance();IWindowManager windowManager = getWindowManagerService();} catch (RemoteException e) {Log.e(TAG, "Failed to open window session", e);}}return sWindowSession;}}public static InputMethodManager getInstance() {synchronized (InputMethodManager.class) {if (sInstance == null) {// InputMethodManager其实就是一个Binder service的proxyIBinder b = ServiceManager.getService(Context.INPUT_METHOD_SERVICE);IInputMethodManager service = IInputMethodManager.Stub.asInterface(b);sInstance = new InputMethodManager(service, Looper.getMainLooper());}return sInstance;}}

InputMethodService

1、主要实现的功能

包括输入法内部逻辑,键盘布局,选词等,最终把选出的字符通过commitText提交出来。实现输入法的基础就是名为InputMethodService的类,比如要实现一个谷歌输入法,就是要extends本类。

2、如何实现

InputMethodService是InputMethod的一个完整实现,可以再在其基础上扩展和定制。它的主要方法如下:
onInitializeInterface() 顾名思义,它在初始化界面的时候被调用,而一般是由于配置文件的更改导致该函数的执行
onBinndInput() 它在另外的客户端和该输入法连接时调用
onStartInput() 非常重要的一个回调,它在编辑框中用户已经开始输入的时候调用。比如,当点击一个输入框,我们需要根据这个输入框的信息,设置输入法的一些特性。
onCreateInputView() 返回一个层次性的输入视图,而且只是在这个视图第一次显示的时候被调用
onCreateCandidatesView() 同onCreateInputView(),只不过创建的是候选框的视图。
onCreateExtractTextView() 比较特殊,是在全屏模式下的一个视图。
onStartInputView() 在输入视图被显示并且在一个新的输入框中输入已经开始的时候调用。

关于android输入法相关推荐

  1. Android输入法遮挡了输入框,使用android:fitsSystemWindows=“true“后界面顶部出现白条解决方案

    Android输入法遮挡了输入框,使用android:fitsSystemWindows="true"后界面顶部出现白条解决方案 参考文章: (1)Android输入法遮挡了输入框 ...

  2. android弹出输入框不影响布局,android 输入法弹出后,不影响activity原有布局

    android输入法弹出框有时会遮挡原有的布局,使得输入法弹出框弹出时,原布局消失,现介绍android:windowSoftInputMode的一些属性: 在AndroidManifest.xml文 ...

  3. android 输入法的显示和隐藏

    Android输入法的显示和隐藏方法 今天上午一直纠结于一个动画效果后EditText输入法无法弹出的问题,现在终于解决,解决方法是这样的 1.为EditText添加click事件 2.click事件 ...

  4. 写一个Android输入法01——最简步骤

    本文演示用Android Studio写一个最简单的输入法.界面和交互都很简陋,只为剔肉留骨,彰显写一个Android输入法的要点. 1.打开Android Studio创建项目,该项目和普通APP的 ...

  5. android 输入法如何启动流程_android输入法02:openwnn源码解析01—输入流程

    android 输入法 02:openwnn 源码解析 01-输入流程 之后要开始 android 日文输入法的测试,因此现在开始研究 android 输入法.之前两 篇文章已经对 android 自 ...

  6. 实现一个Android输入法

    原文来自 Android Developer Guide,本文为原文翻译,如有错误,欢迎指出. 输入法(IME:Input method editor)是一个能够让用户输入文本的工具.Android提 ...

  7. 浅谈Android输入法(IME)架构

    简介: 输入法 (IME) 是一种可让用户输入文本的用户控件.Android 提供了一种可扩展的输入法框架.借助该框架,应用可以为用户提供备选输入法,例如屏幕键盘,甚至语音输入.安装所需的 IME 后 ...

  8. android输入法框架分析,Android与iOS输入法开发框架比较谈

    对于任何一个使用手机的人,有一样工具是不可能缺少的,它既不是微信之类的社交工具,也不是支付宝之类的金融工具(事实上这两个都越界了),而是输入法这样的输入工具.更重要的是,输入法还是一种特权工具,因为它 ...

  9. android弹出输入法内存,android 输入法导致内存泄露问题

    该方法侵入太高,必须重新EditText,如果我们直接使用一个第三方的控件包含了EditText,那么这么做就没有意义,所以放弃了这种方案,然后我又想出了其他方案,Android 输入法导致内存泄露以 ...

  10. 2022-09-06 Android输入法顶起输入框,遮挡RecyclerView

    背景 IM项目中的会话界面,一般就是顶部一个标题,底部是输入区域,中间显示消息列表. 微信的会话界面中,进入会话界面,有以下几点: 隐藏输入法 当消息数量能占满屏幕时,底部显示最后一条,依次往上排列 ...

最新文章

  1. stm32跑马灯实验
  2. html5游戏 糖果派对,糖果派对, 第三层的游戏攻略, 怎玩才能合理的获得比较高的得分?...
  3. 【算法】漫画:如何找到链表的倒数第n个结点?
  4. python采用单例模式游戏_Python实现Singleton模式的方式详解
  5. 一位头发发白的神人教你怎么写程序,运维,买电脑,写文章,平面设计!
  6. 程序人生:一个员工的离职成本到底有多高,看完你就懂了!
  7. java中PL层_安装pljava - RuralHunter的个人空间 - OSCHINA - 中文开源技术交流社区
  8. OpenDiscussion_DataDrivenDesign
  9. x3-02 java_Day13 -- Java流程控制02
  10. iOS 6 的5个新特性创建杀手级应用
  11. @async 默认线程池_SpringBoot 线程池的使用
  12. 自制 移动端 纯原生 Slider滑动插件
  13. 【Python爬虫】使用urllib.request下载已知链接的网络资源
  14. LeetCode 130 被围绕的区域
  15. Error : Failed to get convolution algorithm. This is probably because cuDNN failed to initialize, so
  16. mapreduce实现——腾讯大数据QQ共同好友推荐系统【你可能认识的人】
  17. StanfordDB class自学笔记 (6) 关系代数
  18. gyp ERR! stack Error: Can't find Python executable python, you can set the PYT HON env variable.
  19. 合理使用计算机教学反思,生物学课堂中采用计算机多媒体的教学反思
  20. qq离线linux,QQ For Linux 我哭了,官方版

热门文章

  1. 邯郸 java高级_一个高级java工程师的进阶之路
  2. js正则表达式匹配空格
  3. ubuntu16.04系统死机,鼠标可移动,但点击无反应,键盘无反应,解决办法总结
  4. linux版本剪辑软件下载,OpenShot Video Editor(电脑后期视频编辑软件) V2.4.3 Linux版
  5. java相机开发_控制相机  |  Android 开发者  |  Android Developers
  6. mac系统使用cmake和ninja快速安装llvm
  7. Anaconda安装python 虚拟环境
  8. centos su命令
  9. sudo和su命令的联系和区别详解
  10. python报考软考哪个比较好_软考中级考哪个比较好