Как я могу получить мягкую высоту клавиатуры на Android?

В эти дни я разрабатывал проект для Android с использованием libgdx. Вопрос возник в течение периода. когда появится программная клавиатура, некоторые виды будут закрыты, поэтому я хочу получить высоту для решения этой ошибки.

я знаю, что для решения этой проблемы можно использовать мягкий режим ввода при использовании Android API для разработки проекта, предоставляет ли libgdx какой-либо способ?

2 ответа

У меня есть рабочее решение, которым я хотел бы поделиться.

Во-первых, нет способа получить высоту мягкой клавиатуры из API libgdx. Вы должны написать платформо-специфичный код. Взаимодействие с конкретным кодом платформы довольно просто - не волнуйтесь! Прочтите это руководство на официальной вики libgdx.

Следующий код является нативным кодом Android, который должен быть помещен в модуль libgdx android gradle:

import android.graphics.Rect;
import android.view.View;
import android.view.ViewTreeObserver;
import android.view.Window;
import com.badlogic.gdx.backends.android.AndroidApplication;

/**
 * Container for platform-specific android implementation.
 */
public class PlatformSpecificAndroidImpl implements PlatformSpecificService {
    private AndroidApplication androidApplication;
    private AndroidGlobalLayoutListener globalLayoutListener;

    public PlatformSpecificAndroidImpl(AndroidApplication androidApplication) {
        this.androidApplication = androidApplication;
    }

    /**
     * Initialize platform services. This method should be called from the gdx applications "create()" method.
     */
    @Override
    public void init() {
        globalLayoutListener = new AndroidGlobalLayoutListener(androidApplication);
        Window window = androidApplication.getWindow();
        if (window != null) {
            View decorView = window.getDecorView();
            if (decorView != null) {
                View rootView = decorView.getRootView();
                if (rootView != null) {
                    ViewTreeObserver viewTreeObserver= rootView.getViewTreeObserver();
                    if (viewTreeObserver != null) {
                        viewTreeObserver.addOnGlobalLayoutListener(globalLayoutListener);
                    }
                }
            }
        }
    }

    /**
     * Get the window height that is really usable, subtracting the soft-keyboard if open.
     * @return usable window height
     */
    @Override
    public int getUsableWindowHeight() {
        if (globalLayoutListener != null) {
            return globalLayoutListener.getHeight();
        }
        return 0;
    }

    private static class AndroidGlobalLayoutListener implements ViewTreeObserver.OnGlobalLayoutListener {
        private AndroidApplication androidApplication;
        private int height;

        private AndroidGlobalLayoutListener(AndroidApplication androidApplication) {
            this.androidApplication = androidApplication;
        }

        @Override
        public void onGlobalLayout() {
            height = 0;
            Window window = androidApplication.getWindow();
            if (window != null) {
                View currentFocus = window.getCurrentFocus();
                if (currentFocus != null) {
                    View rootView = currentFocus.getRootView();
                    if (rootView != null) {
                        Rect rect = new Rect();
                        rootView.getWindowVisibleDisplayFrame(rect);
                        height = rect.bottom;
                    }
                }
            }
        }

        public int getHeight() {
            return height;
        }
    }
}

Из основного модуля libgdx теперь вы можете вызывать метод getUsableWindowHeight() через интерфейс PlatformSpecificService. Возвращает высоту экрана (в пикселях) минус высота программной клавиатуры.

Почему я использовал OnGlobalLayoutListener и не вычислял высоту непосредственно в методе получения, когда он запрашивается? Ну, в моем варианте это немного более элегантное решение.

Есть еще один момент, о котором следует знать: открытие программной клавиатуры с помощью Gdx.input.setOnscreenKeyboardVisible(true); предполагает асинхронное общение. Если вам случится позвонить getUsableWindowHeight() непосредственно после setOnscreenKeyboardVisible вы по-прежнему получите полную высоту экрана, потому что клавиатура еще не открылась.

Да, вы можете, с помощью Viewtree Observer и слушателя глобального макета, просто попробуйте выполнить следующие шаги

  1. Получить корневой вид вашего макета
  2. получите наблюдателя Viewtree для этого корня и добавьте прослушиватель глобального макета поверх этого.

Теперь, когда отображается программная клавиатура, Android изменяет размер экрана, и вы будете получать вызов от слушателя. Это единственное, что вам теперь нужно сделать, это вычислить разницу между высотой, которую ваш корневой вид имеет после изменения размера и исходного размера. Если разница больше 150, считайте, что клавиатура раздута.

Ниже приведен пример кода

root.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener(){
     public void onGlobalLayout(){
           int heightDiff = root.getRootView().getHeight()- root.getHeight();
           // IF height diff is more then 150, consider keyboard as visible.  
        }
  });
Другие вопросы по тегам