Android系统中是否有一种方法可以检测软件(也就是Android。“软”)键盘在屏幕上可见吗?
当前回答
试试这段代码,它真的工作,如果keyboardshow是显示的,那么这个函数返回真值....
private final String TAG = "TextEditor";
private TextView mTextEditor;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_editor);
mTextEditor = (TextView) findViewById(R.id.text_editor);
mTextEditor.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
isKeyboardShown(mTextEditor.getRootView());
}
});
}
private boolean isKeyboardShown(View rootView) {
/* 128dp = 32dp * 4, minimum button height 32dp and generic 4 rows soft keyboard */
final int SOFT_KEYBOARD_HEIGHT_DP_THRESHOLD = 128;
Rect r = new Rect();
rootView.getWindowVisibleDisplayFrame(r);
DisplayMetrics dm = rootView.getResources().getDisplayMetrics();
/* heightDiff = rootView height - status bar height (r.top) - visible frame height (r.bottom - r.top) */
int heightDiff = rootView.getBottom() - r.bottom;
/* Threshold size: dp to pixels, multiply with display density */
boolean isKeyboardShown = heightDiff > SOFT_KEYBOARD_HEIGHT_DP_THRESHOLD * dm.density;
Log.d(TAG, "isKeyboardShown ? " + isKeyboardShown + ", heightDiff:" + heightDiff + ", density:" + dm.density
+ "root view height:" + rootView.getHeight() + ", rect:" + r);
return isKeyboardShown;
}
其他回答
@iWantScala的回答很棒,但不适合我 rootView.getRootView().getHeight()总是有相同的值
一种方法是定义两个变量
private int maxRootViewHeight = 0;
private int currentRootViewHeight = 0;
添加全局监听器
rootView.getViewTreeObserver()
.addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
currentRootViewHeight = rootView.getHeight();
if (currentRootViewHeight > maxRootViewHeight) {
maxRootViewHeight = currentRootViewHeight;
}
}
});
然后检查
if (currentRootViewHeight >= maxRootViewHeight) {
// Keyboard is hidden
} else {
// Keyboard is shown
}
工作正常
这对我很有用。也许这对于所有版本来说都是最好的方法。
这将是有效的,使键盘可见性的属性,并观察这个变化延迟,因为onGlobalLayout方法调用多次。此外,检查设备旋转和windowSoftInputMode是否为adjustNothing也很好。
boolean isKeyboardShowing = false;
void onKeyboardVisibilityChanged(boolean opened) {
print("keyboard " + opened);
}
// ContentView is the root view of the layout of this activity/fragment
contentView.getViewTreeObserver().addOnGlobalLayoutListener(
new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
Rect r = new Rect();
contentView.getWindowVisibleDisplayFrame(r);
int screenHeight = contentView.getRootView().getHeight();
// r.bottom is the position above soft keypad or device button.
// if keypad is shown, the r.bottom is smaller than that before.
int keypadHeight = screenHeight - r.bottom;
Log.d(TAG, "keypadHeight = " + keypadHeight);
if (keypadHeight > screenHeight * 0.15) { // 0.15 ratio is perhaps enough to determine keypad height.
// keyboard is opened
if (!isKeyboardShowing) {
isKeyboardShowing = true
onKeyboardVisibilityChanged(true)
}
}
else {
// keyboard is closed
if (isKeyboardShowing) {
isKeyboardShowing = false
onKeyboardVisibilityChanged(false)
}
}
}
});
final View activityRootView = findViewById(R.id.rootlayout);
activityRootView.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
Rect r = new Rect();
activityRootView.getWindowVisibleDisplayFrame(r);
int screenHeight = activityRootView.getRootView().getHeight();
Log.e("screenHeight", String.valueOf(screenHeight));
int heightDiff = screenHeight - (r.bottom - r.top);
Log.e("heightDiff", String.valueOf(heightDiff));
boolean visible = heightDiff > screenHeight / 3;
Log.e("visible", String.valueOf(visible));
if (visible) {
Toast.makeText(LabRegister.this, "I am here 1", Toast.LENGTH_SHORT).show();
} else {
Toast.makeText(LabRegister.this, "I am here 2", Toast.LENGTH_SHORT).show();
}
}
});
在Android中,你可以通过ADB shell进行检测。我写下并使用了这个方法:
{
JSch jsch = new JSch();
try {
Session session = jsch.getSession("<userName>", "<IP>", 22);
session.setPassword("<Password>");
Properties config = new Properties();
config.put("StrictHostKeyChecking", "no");
session.setConfig(config);
session.connect();
ChannelExec channel = (ChannelExec)session.openChannel("exec");
BufferedReader in = new BufferedReader(new
InputStreamReader(channel.getInputStream()));
channel.setCommand("C:/Android/android-sdk/platform-tools/adb shell dumpsys window
InputMethod | findstr \"mHasSurface\"");
channel.connect();
String msg = null;
String msg2 = " mHasSurface=true";
while ((msg = in.readLine()) != null) {
Boolean isContain = msg.contains(msg2);
log.info(isContain);
if (isContain){
log.info("Hiding keyboard...");
driver.hideKeyboard();
}
else {
log.info("No need to hide keyboard.");
}
}
channel.disconnect();
session.disconnect();
} catch (JSchException | IOException | InterruptedException e) {
e.printStackTrace();
}
}
}
你可以参考这个答案- https://stackoverflow.com/a/24105062/3629912
每次都很管用。
adb shell dumpsys window InputMethod | grep "mHasSurface"
如果软件键盘可见,它将返回true。
推荐文章
- 警告:API ' variable . getjavacompile()'已过时,已被' variable . getjavacompileprovider()'取代
- 安装APK时出现错误
- 碎片中的onCreateOptionsMenu
- TextView粗体通过XML文件?
- 如何使线性布局的孩子之间的空间?
- DSL元素android.dataBinding。enabled'已过时,已被'android.buildFeatures.dataBinding'取代
- ConstraintLayout:以编程方式更改约束
- PANIC: AVD系统路径损坏。检查ANDROID_SDK_ROOT值
- 如何生成字符串类型的buildConfigField
- Recyclerview不调用onCreateViewHolder
- Android API 21工具栏填充
- Android L中不支持操作栏导航模式
- 如何在TextView中添加一个子弹符号?
- PreferenceManager getDefaultSharedPreferences在Android Q中已弃用
- 在Android Studio中创建aar文件