Status Update
Comments
pa...@google.com <pa...@google.com>
ch...@gmail.com <ch...@gmail.com> #2
First of all thanks for this detailed issue.
This issue had been investigated thoroughly when it was first reported internally. The surprising detail in this report is that the issue is not reproducible before 1.7
. I will look into this.
The main problem with POBox is the fact that it is deprecated. Since 2021 Sony has been shipping new Xperia devices with Gboard pre-installed. Although we are aware that there is still a considerable amount of users still using POBox, the described behavior is caused by POBox's noncompliant behavior with InputConnection
and InputMethodManager
documentation. However, this is understandable since TextView
implementation was also not respecting the behavior that is expected from Editors.
Ultimately we have decided to enforce the documented behavior with specifically regards to when editors should call InputMethodManager.updateSelection
. Also, although unconfirmed, there were traces of possible custom code being included in Sony OEM images that changed how InputMethodManager was notified from TextView. If POBox also depended on something like this, it would be impossible for Compose code to replicate the same unknown behavior.
ap...@google.com <ap...@google.com> #3
Or is that option not available?
Even if the root cause is POBox, from the perspective of the app's customers, it looks like an app bug, so this issue is a blocker against updating Jetpack Compose.
pa...@google.com <pa...@google.com> #4
Just to be sure, it is dangerous to replace Compose TextField with Android View EditText as a workaround for this issue.
Compose 1.7 has a bug that causes ANR when the focus is on EditText.
Another View-related bug in Compose 1.7 is that an Android View is focused by calling FocusManager.clearFocus().
Perhaps there is a lack of testing of Compose 1.7 in combination with Android View. There is also a possibility that there are other fatal bugs related to View.
In other words, the only options for apps targeting the Japanese market that require POBox support are to continue using Compose 1.6 or to use EditText in combination with various workarounds.
Description
Build #AI-192.6817.14.36.5959023, built on October 22, 2019
Runtime version: 1.8.0_212-release-1586-b4-5784211 amd64
VM: OpenJDK 64-Bit Server VM by JetBrains s.r.o
Linux 5.0.0-32-generic
GC: ParNew, ConcurrentMarkSweep
Memory: 1981M
Cores: 8
Registry: ide.new.welcome.screen.force=true, debugger.watches.in.variables=false
Non-Bundled Plugins: CheckStyle-IDEA
Version of Gradle Plugin: 4.0.0-alpha01
Version of Gradle: 5.6.1
Version of Kotlin: 1.3.60-eap-25
OS: Ubuntu 19.04
-----------
Steps to Reproduce:
1. UnZIP the attached project and import it into Android Studio
2. Run the app
3. Start recording a screencast (e.g., from Android Studio)
4. Tap the "Show Popup" button to show an empty Popup
5. Wait a moment
6. Tap the "Show Popup" button again to dismiss that Popup
7. Stop recording the screencast
8. Look at the screencast
Expected Results: The screencast to be completely empty, as we are recording the functionality of an activity that has FLAG_SECURE set
Actual Results: The Popup appears in the screencast when that "Show Popup" button was clicked, and vanishes from the screencast when that "Show Popup" button was clicked again
The attached MP4 is a screencast taken of this app, using a Pixel 4 running Android 10.
----
If you are going to create a Window with WindowManager, you need to see whether we are in a secure window now and propagate that secure status. Otherwise, we wind up in the same situation that we have with the View-based UI framework, where FLAG_SECURE misses lots of content (menus, Spinner, dialogs, toasts, etc.), because we do not control those windows and cannot set FLAG_SECURE on them. See
PopupLayout has access to composeView. If that View is owned by an activity, you can find the activity's window, see if it has FLAG_SECURE set upon it, and if so put FLAG_SECURE on the window created by the PopupLayout. This is not ideal, as it will not handle some edge cases (e.g., composeView is not owned by an activity) but AFAIK there is no way for a View to get its Window (or that window's flags) in all cases.
A more flexible possibility is to have a WindowSecurityPolicy enum, with values like:
- NORMAL for an insecure window
- SECURE for a secure window
- INHERIT to use the aforementioned "see what the current window uses" approach
Then, have Popup() take a WindowSecurityPolicy parameter, defaulted to INHERIT. This would allow developers that are directly calling Popup() to positively specify a policy if desired. If the policy is SECURE, or it is INHERIT and the current window has FLAG_SECURE set, apply FLAG_SECURE to the window created by the Popup.
My concern with Popup in particular is that it might get used elsewhere within the Compose libraries. If Popup (and DropdownPopup) were only ever going to be used directly by outside developers, you could say that it is up to us to implement SecurePopup and SecureDropdownPopup. However, my guess is that Compose will use Popup internally, which exacerbates the problem if Popup cannot handle FLAG_SECURE itself. For example, if a Frobozz composable supplied by Compose uses Popup internally, now you are asking the community to maintain a SecureFrobozz that uses a SecurePopup. We wind up having community-maintained parallel composables to those in Compose itself, just to address security issues.
Thanks for considering this!