jeneser / ionic-super-bar

Transparent statusBar and awesome toolBar DEMO in ionic
MIT License
176 stars 42 forks source link

Issue with input behind keyboard #18

Open jayserdny opened 6 years ago

jayserdny commented 6 years ago

The implementation of the following code breaks ionic behavior to move the focused input above the keyboard:

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) { getWindow().getDecorView().setSystemUiVisibility( View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN | View.SYSTEM_UI_FLAG_LAYOUT_STABLE); } It took me hours to figure out that it was causing this estrange behavior.

I am looking for a workaround for this issue.

jeneser commented 6 years ago

Hi, I'm not sure what's going on. Can you provide some pictures or GIFs of these estrange behavior?

jayserdny commented 6 years ago

Sure, I will create a repo reproducing the issue generated by this modification.

jayserdny commented 6 years ago

I just added an ion-footer to the main page along with a ion-input. First image is without your implementation. You can notice how the footer stays above the keyboard when it is opened. It is an expected behavior. However, with you implementation (refer to images 2 and 3), they keyboard hides the ion-footer. Why does this happens? Because when Ionic is in full screen mode (which is what you made), it does not push the view to keep the focused element in the view.

You can also check this repo for a better reference Ionic-super-bar folk

img1 img2 img3

pcsantana commented 5 years ago

Hi! I am facing the same problem! I tried to use the solution provided by @jayserdny , using FLAG_TRANSLUCENT_STATUS instead. But for some reason, the affects only applied after a input focused, or the window resized (eg. rotate the screen). Is the same problem as described in this issue opened in the cordova-plugin-fullscreen repo. I do not know why, but the example works nice. I tried to figure out what could be different, but no success until now.

Any advices? Thank you!

jayserdny commented 5 years ago

@pcsantana hello,

I wrote a tutorial on how to fix the keyboard issue :)

https://jayserdny.github.io/ionic/ionic-drawer-behind-status-bar/

pcsantana commented 5 years ago

Hi @jayserdny!

Really helpful! I will check and come back to give you some feedback. Thank you!

pcsantana commented 5 years ago

@jayserdny , thank you for the support. Unfortunately your tutorial did not worked for me. My problem isn't only for the inputs in the footer, but any input in the content that can be in the bottom part of the screen.

Also, status bar effect only applied after an input focused (I did not figure out why).

But I found a workaround using a helper method to set a padding bottom when the keyboard come up. Using this, I can set again the tags

View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN | View.SYSTEM_UI_FLAG_LAYOUT_STABLE

that give me the feature to change the opacity value of the status bar (using the FLAG_TRANSLUCENT_STATUS, I can not change or remove the "background protection" over the status bar);

So, see the entire code:

MainActivity.java

package <your.package>;

import android.graphics.Rect;
import android.os.Build;
import android.os.Bundle;
import android.support.v4.view.OnApplyWindowInsetsListener;
import android.support.v4.view.ViewCompat;
import android.support.v4.view.WindowInsetsCompat;
import android.view.View;
import android.view.ViewTreeObserver;

import org.apache.cordova.CordovaActivity;

public class MainActivity extends CordovaActivity
{
    @Override
    public void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);

        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {

            getWindow().getDecorView().setSystemUiVisibility(
                    View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN |
                            View.SYSTEM_UI_FLAG_LAYOUT_STABLE);

            final View contentView = findViewById(android.R.id.content);

            enableKeyboardHelper(contentView);
        }

        // enable Cordova apps to be started in the background
        Bundle extras = getIntent().getExtras();
        if (extras != null && extras.getBoolean("cdvStartInBackground", false)) {
            moveTaskToBack(true);
        }

        // Set by <content src="index.html" /> in config.xml
        loadUrl(launchUrl);
    }

    /**
     * Based on:
     * https://stackoverflow.com/a/52622795/6031927
     * https://github.com/mikepenz/MaterialDrawer/blob/aa9136fb4f5b3a80460fe5f47213985026d20c88/library/src/main/java/com/mikepenz/materialdrawer/util/KeyboardUtil.java
     */
    private void enableKeyboardHelper(final View contentView) {
        if(contentView != null) {
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {

                ViewCompat.setOnApplyWindowInsetsListener(contentView , new OnApplyWindowInsetsListener() {
                    @Override
                    public WindowInsetsCompat onApplyWindowInsets(View v, WindowInsetsCompat insets) {
                        v.setPadding(0, 0, 0, insets.getSystemWindowInsetBottom());
                        return insets;
                    }
                });

            } else {
                getWindow().getDecorView().getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
                    @Override
                    public void onGlobalLayout() {
                        Rect r = new Rect();
                        //r will be populated with the coordinates of your view that area still visible.
                        getWindow().getDecorView().getWindowVisibleDisplayFrame(r);

                        //get screen height and calculate the difference with the useable area from the r
                        int height = getWindow().getDecorView().getContext().getResources().getDisplayMetrics().heightPixels;
                        int diff = height - r.bottom;

                        //if it could be a keyboard add the padding to the view
                        if (diff != 0) {
                            // if the use-able screen height differs from the total screen height we assume that it shows a keyboard now
                            //check if the padding is 0 (if yes set the padding for the keyboard)
                            if (contentView.getPaddingBottom() != diff) {
                                //set the padding of the contentView for the keyboard
                                contentView.setPadding(0, 0, 0, diff);
                            }
                        } else {
                            //check if the padding is != 0 (if yes reset the padding)
                            if (contentView.getPaddingBottom() != 0) {
                                //reset the padding of the contentView
                                contentView.setPadding(0, 0, 0, 0);
                            }
                        }
                    }
                });
            }
        }
    }
}

I hope it help someone! Thanks