Skip to content

Embedded Android views can't bring up the keyboard #19718

@amirh

Description

@amirh
Contributor

To make sure that Flutter can always bring up the keyboard I made the window of virtual display's presentation non focusable.
As a result the embedded Android views cannot bring up the keyboard.

We should figure out if there's some window trickery we can do to let the unfocused window bring up the keyboard. Alternatively see if it's possible to dynamically select the focused window when delivering input events.

Activity

fujinjun

fujinjun commented on Dec 5, 2018

@fujinjun

anyone solved this problem?

added
frameworkflutter/packages/flutter repository. See also f: labels.
engineflutter/engine repository. See also e: labels.
on Dec 17, 2018
added this to the Goals milestone on Dec 17, 2018

62 remaining items

dcov

dcov commented on Mar 29, 2019

@dcov

Is there an open issue, or a place for the community to discuss possible solutions? I'd like to collaborate with others on this instead of everyone going off on and building their own solutions.

@amirh You mentioned that you guys have a team that is starting to work on this, is there any way we can help them out?

amirh

amirh commented on Mar 30, 2019

@amirh
ContributorAuthor

I put together a (very rough and hacky) POC prototype for input connection proxying, it's far from being something we can land but it confirms that this approach works:

ime

POC code

Engine: https://github.com/amirh/engine/tree/ime_poc
WebView plugin: https://github.com/amirh/plugins/tree/ime_poc

Unresolved issues

Detecting that a platform view wants IME

The major piece that is still unresolved is how to determine that a platform view is asking for the keyboard, for this POC I injected JS into the webview that listens to focus events, ideally we could come up with something more generic, I experimented with View#setOnFocusChangedListener but it didn't seemed to get triggered whenever the webview wanted to show the keyboard(I'm thinking this may be because the embedded view is the only focusable view in the VD, if that is the case we may workaround by adding a dummy focusable view just so the webview can be non focused).

I'm guessing that as a last resort we can expose a requestFocus as part of the engine plugins API, and leave it to the plugin to trigger it(I think that at least for most webview use cases a JavaScript workaround similar to the one in the prototype should be enough).

WebView prior to Android N

For performance reasons prior to Android N the webview input connection is proxied internally which allows it to handle the input connection not on the main thread.
WebView#onCreateInputConnection is pulling some tricks to make its proxy view the input connection target and make the IMM call onCreateInputConnection on the proxy view from the dedicated IME thread.
On these Android versions WebView#onCreateInputConnection returns null, which breaks the prototype.

To workaround this I believe we should be able to cache the real input connection target reference that is passed to checkInputConnectionProxy

Resizing the platform view

Resizing a platform view on Android involves moving it from one virtual display to another.
It seems that open input connections are lost when this is done.

This is a common use case as opening the soft keyboard results in resizing the FlutterView and thus likely resizing the WebView.

In the POC I just set a fixed size for the WebView(without it you need to tap on the webview's text field again after the keyboard opens). I believe that this can be fixed just by restarting the input connection as the last step of the resize sequence.

Next steps

We should keep exploring all of our current ideas for a generic way to detect that a platform view wants to show keyboard. Without a generic way we will have to add a public API to the Android embedding. Since removing the API later will be a breaking change I want to feel certain that there isn't a better way before adding such API. Specifically I think it will be useful to experiment with a pure Android app that has a text field and a webview, and see if we can determine when the webview gets and loses text focus, and how can we programmatically make it lose focus.

After the triggering question is resolved we can move forward with a real implementation, this should probably involve sending the "webview wants keyboard focus" event to the framework so that the framework's focus tree is updated accordingly, and then having the framework tell the engine what's the current input target (FlutterView or one of the platform views). The framework should also trigger "clear focus" on the platform view when appropriate.

krsolutions

krsolutions commented on Apr 1, 2019

@krsolutions

Hi Amirh,

We can't able to find the code snippet for webview issue, can you please post working webview snippet here.

LuisThein

LuisThein commented on Apr 8, 2019

@LuisThein

A hacky workaround for the webview would be to use Javascript and JavascriptChannels to manually listen for the focus of certain input fields and then open the keyboard on a hidden TextInput.
Heres a little example: https://github.com/LuisThein/webview_flutter_textinput

pushangupta

pushangupta commented on Apr 8, 2019

@pushangupta

Any solutions so far? Its too long now!

dcov

dcov commented on Apr 16, 2019

@dcov

@amirh
I have a working prototype here: https://github.com/dcov/engine/tree/fix-android-ime

There are still some things I haven't worked out like restarting the input when the virtual display resizes, or hiding the keyboard when the platform view loses focus. It can also be cleaned up a bit, but in general it works without having to expose an API to the plugins, so it's a start.

159 remaining items

Loading
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

a: annoyanceRepeatedly frustrating issues with non-experimental functionalitya: platform-viewsEmbedding Android/iOS views in Flutter appsc: new featureNothing broken; request for a new capabilitycustomer: crowdAffects or could affect many people, though not necessarily a specific customer.customer: googleVarious Google teamsengineflutter/engine repository. See also e: labels.frameworkflutter/packages/flutter repository. See also f: labels.p: webviewThe WebView pluginpackageflutter/packages repository. See also p: labels.platform-androidAndroid applications specifically

Type

No type

Projects

No projects

Relationships

None yet

    Development

    No branches or pull requests

      Participants

      @andyduke@madmat@Pash237@zoechi@sldboy

      Issue actions

        Embedded Android views can't bring up the keyboard · Issue #19718 · flutter/flutter