安卓沉浸状态栏下 PreferenceFragment 弹出的输入对话框无法跟随键盘上移的解决办法

编程入门 行业动态 更新时间:2024-10-26 06:36:56

安卓沉浸状态栏下 PreferenceFragment <a href=https://www.elefans.com/category/jswz/34/1771144.html style=弹出的输入对话框无法跟随键盘上移的解决办法"/>

安卓沉浸状态栏下 PreferenceFragment 弹出的输入对话框无法跟随键盘上移的解决办法

背景介绍

在不沉浸状态栏时,当PreferenceFragmentCompat中有EditTextPreference时,点击该条目呼出的输入对话框将跟随键盘上移,但一旦在styles.xml中设置

<item name="android:windowTranslucentStatus">true</item>
<item name="android:windowTranslucentNavigation">true</item>

也就是沉浸状态栏或导航栏后,再呼出对话框时则无法上移。

历史回顾

这是一个2013年的陈年老bug1,从谷歌引入沉浸状态栏这个特性至今,该bug从未被修复,并且在stackoverflow也有不少帖子2,大致是通过手动上移控件的方式解决问题。

我的问题

这些帖子大多是针对自定义View上的EditText,所以自定义比较轻松,集大成者莫过于这个GitHub的回答,几乎可以适应一切布局,但在系统包装好的PreferenceFragmentCompat下,这个代码仅能检测到键盘呼出后的高度改变,却无法自动上移输入框。

解决办法

在综合上面的资料之后,结合PreferenceFragmentCompat的特性,我写出了最终解法,可能不是完美的办法,但是工作正常。

package xxx.yyy.zzzimport android.animation.ObjectAnimator
import android.graphics.Rect
import android.os.Bundle
import android.util.Log
import android.view.View
import android.view.Window
import androidx.annotation.Keep
import androidx.preference.EditTextPreference
import androidx.preference.EditTextPreferenceDialogFragmentCompat
import androidx.preference.Preference
import androidx.preference.PreferenceFragmentCompat
import xxx.yyy.zzz.R
import java.lang.Thread.sleepclass SettingsFragment: PreferenceFragmentCompat() {override fun onCreatePreferences(savedInstanceState: Bundle?, rootKey: String?) {setPreferencesFromResource(R.xml.pref_setting, rootKey)}override fun onDisplayPreferenceDialog(preference: Preference) {if (preference is EditTextPreference) {Log.d("MySF", "preference is EditTextPreference")val f = EditTextPreferenceDialogFragmentCompat.newInstance(preference.key)f.setTargetFragment(this, 0)f.show(parentFragmentManager, null)Thread {var diff = 0var cnt = 0while (diff == 0 && cnt++ < 20) {sleep(50)if (f.dialog == null) continueval v = view?:return@Thread// .javaval r = Rect()//r will be populated with the coordinates of your view that area still visible.v.getWindowVisibleDisplayFrame(r)//get screen height and calculate the difference with the useable area from the rval height = v.context.resources.displayMetrics.heightPixelsdiff = height - r.bottomLog.d("MySF", "diff: $diff")}Log.d("MySF", "diff out while: $diff")if (diff <= 0) return@ThreadLog.d("MySF", "f.dialog is ${f.dialog}")f.activity?.runOnUiThread {f.dialog?.window?.apply {val attr = attributesLog.d("MySF", "animate from ${attr.y} to ${attr.y-diff/2}")ObjectAnimator.ofInt(WindowAttributeSetter(this), "y", attr.y, attr.y-diff/2).setDuration(233).start()}}}.start()return}super.onDisplayPreferenceDialog(preference)}inner class WindowAttributeSetter(private val window: Window) {@Keepfun setY(y: Int) {val attr = window.attributesattr.y = yLog.d("MySF", "set y to $y")window.attributes = attr}}
}

  1. Keyboard don’t resize the screen when android:windowTranslucentStatus=true ↩︎

  2. Keyboard hiding EditText when android:windowTranslucentStatus=true ↩︎

更多推荐

安卓沉浸状态栏下 PreferenceFragment 弹出的输入对话框无法跟随键盘上移的解决办法

本文发布于:2023-11-17 03:26:26,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1636971.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:弹出   解决办法   对话框   状态栏   键盘

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!