Андроид. Иногда не удается скрыть панель навигации

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

Вот код MainActivity:

package com.example.ui_test;

import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.RelativeLayout;

public class MainActivity extends Activity {

private final String DEBUG_TAG = "UI TEST";
int uiOptions = 0;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    RelativeLayout r = (RelativeLayout) findViewById(R.id.main_layout);
    r.setOnClickListener(new OnClickListener() {
        public void onClick(View v) {
            toggleUiVisibility();
        }
    });

    View decorView = getWindow().getDecorView();
    decorView.setOnSystemUiVisibilityChangeListener(new View.OnSystemUiVisibilityChangeListener() {
        @Override
        public void onSystemUiVisibilityChange(int visibility) {
            Log.d(DEBUG_TAG, "Visibility changed. New flags: " + Integer.toString(visibility, 2));
            uiOptions = visibility;
        }
    });
}

protected void toggleUiVisibility() {
    uiOptions ^= View.SYSTEM_UI_FLAG_HIDE_NAVIGATION;        
    getWindow().getDecorView().setSystemUiVisibility(uiOptions);
    Log.d(DEBUG_TAG, "Set visibility to: " + Integer.toString(uiOptions, 2));
};

}

Я пробовал с разными макетами (без представлений, TextView, полноэкранный ImageView), разницы в поведении нет. Это вывод LogCat, посмотрите на 6 строку. Событие onSystemUiVisibilityChange не зарегистрировано после вызова setSystemUiVisibility():

09-21 18:24:19.871: D/UI TEST(3901): Visibility changed. New flags: 0
09-21 18:24:21.139: D/UI TEST(3901): Set visibility to: 10
09-21 18:24:21.171: D/UI TEST(3901): Visibility changed. New flags: 10
09-21 18:24:23.478: D/UI TEST(3901): Visibility changed. New flags: 0
09-21 18:24:24.321: D/UI TEST(3901): Set visibility to: 10
09-21 18:24:25.245: D/UI TEST(3901): Set visibility to: 0
09-21 18:24:25.927: D/UI TEST(3901): Set visibility to: 10
09-21 18:24:25.959: D/UI TEST(3901): Visibility changed. New flags: 10
09-21 18:24:33.625: D/UI TEST(3901): Visibility changed. New flags: 0
09-21 18:24:35.458: D/UI TEST(3901): Set visibility to: 10
09-21 18:24:35.490: D/UI TEST(3901): Visibility changed. New flags: 10
09-21 18:24:36.607: D/UI TEST(3901): Visibility changed. New flags: 0
09-21 18:24:38.294: D/UI TEST(3901): Set visibility to: 10
09-21 18:24:38.326: D/UI TEST(3901): Visibility changed. New flags: 10

Я использую устройство Android 5.1.1 и 22 целевого/минимального уровня API.


person Alan Kazbekov    schedule 21.09.2015    source источник


Ответы (1)


Ок, оказывается это фича, а не баг. И проблема была в интервале между setSystemUiVisibility последовательными звонками не в быстром тапе по экрану. Мне пришлось копаться в источниках Android, и я нашел это:

...

// We don't allow the system's nav bar to be hidden
// again for 1 second, to prevent applications from
// spamming us and keeping it from being shown.
 newVal = mForceClearedSystemUiFlags |
          View.SYSTEM_UI_FLAG_HIDE_NAVIGATION;
 if (mForceClearedSystemUiFlags != newVal) {
     mForceClearedSystemUiFlags = newVal;
     changed = true;
     mHandler.postDelayed(mClearHideNavigationFlag, 1000);
 }

...

Это HideNavInputEventReceiver в PhoneWindowManager.java. Я также воспроизвел эту «ошибку» в приложении «Альбом» на Xperia Z2.

person Alan Kazbekov    schedule 26.09.2015
comment
Ты заслужил медаль. - person Matt Robertson; 19.09.2018