Repository navigation
Compose Android keyboardType and secureTextEntry into one input type - #59014
Open
YevheniiKotyrlo wants to merge 2 commits into
Open
YevheniiKotyrlo wants to merge 2 commits into
YevheniiKotyrlo wants to merge 2 commits into
Conversation
keyboardType="visible-password" sets TYPE_TEXT_VARIATION_VISIBLE_PASSWORD with no input class, and setKeyboardType applies its flags with TYPE_MASK_CLASS as the mask to clear, so the field is committed with class TYPE_NULL, which Android documents as not editable. The url arm had the same omission until react#58505; this gives visible-password the TYPE_CLASS_TEXT the email-address and url arms already set. The test masked its reading with generalKeyboardTypeFlags, which excludes TYPE_TEXT_VARIATION_PASSWORD, so it compared 0x10 and passed with the class missing. It now asserts the class and the variation exactly.
keyboardType and secureTextEntry both write the class and variation of the
staged input type, each with bit edits applied in the order the props
arrive. A variation is a value within its class, not a set of flags: 0x10
is TYPE_TEXT_VARIATION_URI in the text class and
TYPE_NUMBER_VARIATION_PASSWORD in the number class. Depending on that
order:
- secureTextEntry={false} clears the url and visible-password variations.
- email-address with secureTextEntry commits
TYPE_TEXT_VARIATION_WEB_EDIT_TEXT, which is not masked.
- secureTextEntry set after autoCapitalize="words" or "characters" commits
text + URI, which is not masked, because checkPasswordType reads the
capitalization flags as the number flags they share bits with.
- Changing keyboardType keeps the previous variation (url then
email-address commits EMAIL_SUBJECT) and the previous number flags.
- phone-pad with secureTextEntry commits a variation the phone class does
not define.
Both setters now only stage their value, and onAfterUpdateTransaction
resolves the class and variation once, before reconcileAutoCapitalize
reads the class, the way autoCapitalize is already deferred. A secure field
takes the password variation of its class, and a class without one keeps
its keyboard.
This branch has not been deployed
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary:
Depends on #59013; the first commit here is that PR.
keyboardTypeandsecureTextEntryboth write the class and variation of the staged input type, each with bit edits applied in the order the props arrive. A variation is a value within its class rather than a set of flags (0x10isTYPE_TEXT_VARIATION_URIin the text class andTYPE_NUMBER_VARIATION_PASSWORDin the number class), so the committed input type depends on that order:secureTextEntry={false}clears theurlandvisible-passwordvariations.email-addresswithsecureTextEntrycommitsTYPE_TEXT_VARIATION_WEB_EDIT_TEXT, whichTextViewdoes not mask.secureTextEntryset afterautoCapitalize="words"or"characters"commits text + URI, whichTextViewdoes not mask either:checkPasswordTypereads the capitalization flags as the number flags they share bits with (🐛 [Android][TextInput] when combine secureTextEntry + autoCapitalize props #28709).keyboardTypekeeps the previous variation and number flags:urlthenemail-addresscommitsTYPE_TEXT_VARIATION_EMAIL_SUBJECT(Changing TextInput keyboardType from visible-password does not unset the underlying flags (Android) #17248), andnumericthennumber-padkeeps the signed decimal keys.phone-padwithsecureTextEntrycommits a variation the phone class does not define.Both setters now only stage their value, and
onAfterUpdateTransactionresolves the class and variation once, beforereconcileAutoCapitalizereads the class, the same deferralautoCapitalizealready uses. A secure field takes its class's password variation; a class without one keeps its keyboard, sophone-padstays unmasked as before.Changelog:
[ANDROID] [FIXED] - Fix keyboardType and secureTextEntry overwriting each other's input type
Test Plan:
Seven cases in
ReactTextInputPropertyTest; the order-dependent ones apply the two setters in both orders within one transaction. With #59013 alone, six fail (first failure of each):testSecureTextEntryFalseKeepsTheKeyboardVariationInEitherPropOrder(url, keyboard first)0x110x01testSecureTextEntryMasksEveryTextKeyboardInEitherPropOrder(email-address)0x810xA1testSecureTextEntryStaysMaskedWithWordCapitalization0x810x11testChangingTheKeyboardTypeReplacesItsVariationAndNumberFlags0x210x31testRevealingAPasswordRestoresTheKeyboardVariation0x110x01testSecureTextEntryLeavesAKeyboardWithNoPasswordVariationAsItIs0x030x13testSecureTextEntryUsesTheNumberPasswordForNumberKeyboardspasses before and after; giving number keyboards the text password makes it fail alone../gradlew :packages:react-native:ReactAndroid:testDebugUnitTest -PenableWarningsAsErrors=true -Preact.internal.useHermesStable=true: 681 tests, 0 failures.node ./scripts/format-kotlin.js --checkpasses.secureTextEntry={false}: on a Galaxy S23 (Android 14) the focused editor'sEditorInforeadsTYPE_CLASS_TEXTwithTYPE_TEXT_VARIATION_URIforkeyboardType="url"and withTYPE_TEXT_VARIATION_VISIBLE_PASSWORDforkeyboardType="visible-password"; without it,visible-passwordreadTYPE_NULLwith no variation.build_android).