简体   繁体   English

如何真正获得 Android 中的导航栏高度

[英]How to REALLY get the navigation bar height in Android

I own a HTC One A9 which has the ability to hide the navigation bar.我拥有一台能够隐藏导航栏的 HTC One A9。 In my app, I need to get the height of the navigation bar and set a padding corresponding to it.在我的应用程序中,我需要获取导航栏的高度并设置与之对应的填充。 Here's my problem now: When I hide the navigation bar, the padding is still being set (even Snapchat has this problem).这是我现在的问题:当我隐藏导航栏时,内边距仍在设置中(即使 Snapchat 也有这个问题)。 My question is: Is there alternative code to this one that makes it work?我的问题是:是否有替代代码使其工作?

public static int getNavBarHeight(Context context) {
    int result = 0;
    int resourceId = context.getResources().getIdentifier("navigation_bar_height", "dimen", "android");
    if (resourceId > 0) {
        result = context.getResources().getDimensionPixelSize(resourceId);
    }
    return result;
}

Thanks for your help!感谢您的帮助!

This is the code I use to get the navigation bar size.这是我用来获取导航栏大小的代码。 Its height will be in Point.y它的高度将在 Point.y

Credit to this answer归功于这个答案

public static Point getNavigationBarSize(Context context) {
    Point appUsableSize = getAppUsableScreenSize(context);
    Point realScreenSize = getRealScreenSize(context);

    // navigation bar on the right
    if (appUsableSize.x < realScreenSize.x) {
        return new Point(realScreenSize.x - appUsableSize.x, appUsableSize.y);
    }

    // navigation bar at the bottom
    if (appUsableSize.y < realScreenSize.y) {
        return new Point(appUsableSize.x, realScreenSize.y - appUsableSize.y);
    }

    // navigation bar is not present
    return new Point();
}

public static Point getAppUsableScreenSize(Context context) {
    WindowManager windowManager = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
    Display display = windowManager.getDefaultDisplay();
    Point size = new Point();
    display.getSize(size);
    return size;
}

public static Point getRealScreenSize(Context context) {
    WindowManager windowManager = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
    Display display = windowManager.getDefaultDisplay();
    Point size = new Point();

    if (Build.VERSION.SDK_INT >= 17) {
        display.getRealSize(size);
    } else if (Build.VERSION.SDK_INT >= 14) {
        try {
            size.x = (Integer)     Display.class.getMethod("getRawWidth").invoke(display);
            size.y = (Integer) Display.class.getMethod("getRawHeight").invoke(display);
    } catch (IllegalAccessException e) {} catch     (InvocationTargetException e) {} catch (NoSuchMethodException e) {}
    }

    return size;
}

Edit: To answer your question I had to use this function since I wanted to add ResideMenu to my app, but ended getting a weird empty margin at the bottom of my app, because of the navigation bar.编辑:为了回答您的问题,我必须使用此功能,因为我想将 ResideMenu 添加到我的应用程序中,但由于导航栏的原因,我的应用程序底部最终出现了一个奇怪的空白边距。

So I edited this function added by ResideMenu like this:所以我编辑了这个由 ResideMenu 添加的函数,如下所示:

@Override
protected boolean fitSystemWindows(Rect insets) {
    // Applies the content insets to the view's padding, consuming that content (modifying the insets to be 0),
    // and returning true. This behavior is off by default and can be enabled through setFitsSystemWindows(boolean)
    // in API14+ devices.

    int bottomPadding = insets.bottom;

    Point p = getNavigationBarSize(getContext());

    if (Build.VERSION.SDK_INT >= 21 && p.x != 0) {
        Resources resources = getContext().getResources();
        int resourceId = resources.getIdentifier("navigation_bar_height", "dimen", "android");
        if (resourceId > 0) {
            bottomPadding += resources.getDimensionPixelSize(resourceId);
        }
    }

    this.setPadding(viewActivity.getPaddingLeft() + insets.left, viewActivity.getPaddingTop() + insets.top,
            viewActivity.getPaddingRight() + insets.right, viewActivity.getPaddingBottom() + bottomPadding);
    insets.left = insets.top = insets.right = insets.bottom = 0;
    return true;
}

Hope that will help you.希望这会帮助你。

Use following code to get Navigation bar.使用以下代码获取导航栏。 However, you need to consider Multi window mode as well as whether Navigation bar is at the bottom or on left side or right side of the window.但是,您需要考虑多窗口模式以及导航栏是在窗口的底部还是左侧或右侧。

getNavigationBarHeight(){
    Resources resources = context.getResources();
    int resourceId = resources.getIdentifier("navigation_bar_height", "dimen", "android");
    if (resourceId > 0) {
        return resources.getDimensionPixelSize(resourceId);
    }
    return 0;
}

Here is the simplest answer.这是最简单的答案。 You just need to pass the rootView of the activity.您只需要传递活动的rootView The heights will be 0 if the the bars are not shown.如果未显示条形,则高度将为0

View rootView;
ViewCompat.setOnApplyWindowInsetsListener(rootView, (v, insets) -> {
    final int statusBarHeight = insets.getInsets(WindowInsetsCompat.Type.statusBars()).top; // in px
    final int navigationBarHeight = insets.getInsets(WindowInsetsCompat.Type.navigationBars()).bottom; // in px

    // do something with the heights

    return WindowInsetsCompat.CONSUMED;
});
    fun Context.isSoftNavigationBarAvailable(): Boolean {
        val navBarInteractionModeId = resources.getIdentifier(
                  "config_navBarInteractionMode",
                  "integer",
                  "android"
        )
        if (navBarInteractionModeId > 0 && resources.getInteger(navBarInteractionModeId) > 0) {
            // nav gesture is enabled in the settings
            return false
        }
        val appUsableScreenSize = Point()
        val realScreenSize = Point()
        val defaultDisplay = (getSystemService(Context.WINDOW_SERVICE) as WindowManager).defaultDisplay
        defaultDisplay.getSize(appUsableScreenSize)
        defaultDisplay.getRealSize(realScreenSize)
        return appUsableScreenSize.y < realScreenSize.y }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM