当前位置: 首页 > 科技观察

Android软键盘的控制方法,以及开发中遇到的一些问题

时间:2023-03-12 22:58:03 科技观察

Android提供了windowSoftInputMode属性来控制输入法软键盘窗口与主Activity窗口的交互,分为窗口大小调整系列和输入法软键盘显示控制系列。窗口大小调整系列:这一系列参数用来控制Activity主窗口在软键盘弹出时的调整策略,因为如果不调整主窗口,当前输入的控件可能会被软键盘挡住.adjustPan:Activity的主窗口不会调整大小为输入法腾出空间,但是窗口的内容会自动上下晃动,保证当前获得焦点的控件不会被键盘挡住,然后用户可以看到他们输入的内容。与adjustResize模式相比,它不是很令人满意,因为用户必须关闭输入法才能与被输入法遮挡的控件进行交互。adjustResize:Activity的主窗口将调整大小以为输入法腾出空间。adjustUnspecified:当前模式没有明确指定Activity使用adjustPan或者adjustResize,系统会自动选择一个模式。选择结果是如果当前ActivityWindow中有可以滚动自身内容的控件,比如ScrollView,那么选择结果就是adjustResize。因为它认为滚动可以让Window的内容即使在很小的范围内也可见。Activity的默认模式就是这种模式。adjustNoting:活动的窗口没有改变。两种模式下屏幕-主窗口-主窗口内容-软键盘的关系如下:具体效果如下:无滚动内容,adjustPan:无滚动内容,adjustResize:无滚动内容,adjustUnspecified==adjustPan有滚动内容(ScrollView),adjustPan有滚动内容(ScrollView),adjustResize有滚动内容(ScrollView),adjustUnspecified==adjustResize输入法软键盘显示控制系列:这一系列参数用来控制当一个东西包含Window(Activity,Dialog等)显示在屏幕上前端软键盘的显示或隐藏策略。stateUnspecified:系统根据当前具体情况选择相应的模式。stateUnchanged:软键盘保持之前的状态(之前的Activity或Dialog在屏幕最前端时软键盘的状态),不改变,无论之前的状态是显示还是隐藏。stateHidden:当用户主动进入当前界面时,软键盘隐藏。离开上一界面,返回当前界面,不能算作“主动进入”。被动进入时,保持之前的状态。stateAlwaysHidden:只要用户进入界面,软键盘就会隐藏,无论是主动进入(新启动界面)还是被动进入(离开上一界面,返回当前界面)。stateVisible:当用户主动进入当前界面时,显示软键盘。离开上一界面,返回当前界面,不能算作“主动进入”。被动进入时,保持之前的状态。stateAlwaysVisible:只要用户进入界面,就会显示软键盘,无论是主动进入(新启动界面)还是被动进入(离开上一个界面,返回当前界面)。关于一些华为手机的bug今天遇到了一个bug。是这样的。在部分华为手机上,除了第一次点击输入框外,adjustPan参数会生效(软键盘可以正常弹出输入框),后面从第二次开始,无论怎么点击,adjustPan参数无效。布局模型大致如下:效果是这样的:经过很长时间的淘汰(很辛苦),终于找到了bug的触发点,就是下面两句:android:gravity="center"android:inputType="numberDecimal"经过长时间的验证,我得出一个结论:在一些华为机型上,在这种布局模型,如果在EditText中设置了inputType参数(不是none),那么,当重力值一定的时候,就会出现这个问题。一般情况如下:红色表示无效,绿色表示有效(工作正常)。当不指定这两个参数时,是可以工作的,因为这两个属性默认值的组合是可以工作的,上图中的蓝色方块。(备注:不是所有的case都完全匹配,如果有类似的case,可以按需匹配,查看结果)可以在源码中找到这两个属性的默认值:attrs.xmlthemes.xml@style/Widget.EditTextattrs.xml/***特殊内容类型,当没有指定明确类型时。*这应该被解释为意味着目标输入连接*不丰富,它不能像候选文本或*检索当前文本那样处理和显示事物,所以输入法需要运行*有限的“生成按键事件”模式,如果它支持的话。不是那个某些*输入方法可能不支持它,例如基于语音的输入*方法可能无法生成键事件,即使设置了此*标志。*/publicstaticfinalintTYPE_NULL=0x00000000;一个需求满足一个需求,一般模型是:有一个界面,里面有一个输入框和两个按钮,分别控制输入框里的数字加减,如下图:输入框的变化,无论是手动输入还是按钮控件,都会开始刷新工作。刷新的时候会弹出一个对话框,需求是这样的。手动输入时,此时会触发。刷新时显示输入法,但显示对话框后消失,输入法隐藏。使用按钮控制时,没有问题,因为整个过程中,输入法是隐藏的。所以要求是对话框显示后消失,输入法能保持开始刷新时的状态。解决问题:当当前Activity设置为stateUnchanged时,并没有达到想要的效果,因为dialog所在的窗口没有设置这个属性,所以需要将dialog的窗口设置为stateUnchanged,方法是:getWindow().setSoftInputMode()然后就可以了。