windowSoftInputMode="adjustResize" not working with translucent action/navbar windowSoftInputMode="adjustResize" not working with translucent action/navbar android android

windowSoftInputMode="adjustResize" not working with translucent action/navbar


You are missing the following property:

android:fitsSystemWindows="true"

in the root RelativeLayout of the fragment .xml layout.

Update:

Last year there was an interesting talk by Chris Bane that explains in good detail how this works:

https://www.youtube.com/watch?v=_mGDMVRO3iE


There's a related bug report here. I've found a workaround that, from limited testing, seems to do the trick with no repercussions. Add a custom implementation of your root ViewGroup (I almost always am using FrameLayout, so this is what I've tested with) with the logic below. Then, use this custom layout in place of your root layout, and ensure you set android:fitsSystemWindows="true". You can then just call getInsets() any time after layout (e.g. add an OnPreDrawListener) to adjust the rest of your layout to account for the system insets, if desired.

import android.content.Context;import android.graphics.Rect;import android.os.Build;import android.util.AttributeSet;import android.widget.FrameLayout;import org.jetbrains.annotations.NotNull;/** * @author Kevin *         Date Created: 3/7/14 * * https://code.google.com/p/android/issues/detail?id=63777 *  * When using a translucent status bar on API 19+, the window will not * resize to make room for input methods (i.e. * {@link android.view.WindowManager.LayoutParams#SOFT_INPUT_ADJUST_RESIZE} and * {@link android.view.WindowManager.LayoutParams#SOFT_INPUT_ADJUST_PAN} are * ignored). *  * To work around this; override {@link #fitSystemWindows(android.graphics.Rect)}, * capture and override the system insets, and then call through to FrameLayout's * implementation. *  * For reasons yet unknown, modifying the bottom inset causes this workaround to * fail. Modifying the top, left, and right insets works as expected. */public final class CustomInsetsFrameLayout extends FrameLayout {    private int[] mInsets = new int[4];    public CustomInsetsFrameLayout(Context context) {        super(context);    }    public CustomInsetsFrameLayout(Context context, AttributeSet attrs) {        super(context, attrs);    }    public CustomInsetsFrameLayout(Context context, AttributeSet attrs, int defStyle) {        super(context, attrs, defStyle);    }    public final int[] getInsets() {        return mInsets;    }    @Override    protected final boolean fitSystemWindows(@NotNull Rect insets) {        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {            // Intentionally do not modify the bottom inset. For some reason,             // if the bottom inset is modified, window resizing stops working.            // TODO: Figure out why.            mInsets[0] = insets.left;            mInsets[1] = insets.top;            mInsets[2] = insets.right;            insets.left = 0;            insets.top = 0;            insets.right = 0;        }        return super.fitSystemWindows(insets);    }}

Since fitSystemWindows was deprecated, please refer to the answer below to complete the workaround.


@kcoppock answer is really helpful, but fitSystemWindows was deprecated in API level 20

So since API 20 (KITKAT_WATCH) you should override onApplyWindowInsets

@Overridepublic final WindowInsets onApplyWindowInsets(WindowInsets insets) {    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT_WATCH) {        return super.onApplyWindowInsets(insets.replaceSystemWindowInsets(0, 0, 0,                insets.getSystemWindowInsetBottom()));    } else {        return insets;    }}