iOS 11 禁用密码自动填充附件视图选项?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/45452170/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-31 09:22:20  来源:igfitidea点击:

iOS 11 disable password autofill accessory view option?

iosswiftios11

提问by zumzum

As of now I would like to opt out of the new option iOS 11 gives, that is to suggest passwords in the app. When I run the app on iOS 11 I get the autofill option on top of the keyboard and my username and password textfield don't even show up.

截至目前,我想退出 iOS 11 提供的新选项,即在应用程序中建议密码。当我在 iOS 11 上运行该应用程序时,我在键盘顶部获得了自动填充选项,我的用户名和密码文本字段甚至没有出现。

So, my question is, how can I disable the new password autofill feature all together so the key on the keyboard is not shown at all and the overall behavior is the same as pre iOS 11?

所以,我的问题是,如何一起禁用新密码自动填充功能,以便根本不显示键盘上的键并且整体行为与 iOS 11 之前的相同?

enter image description here

在此处输入图片说明

回答by Baran Emre

iOS 11 & 12 & 13 - Swift 4.2 & 5(Updated):

iOS 11 & 12 & 13 - Swift 4.2 & 5(更新):

if #available(iOS 12, *) {
    // iOS 12 & 13: Not the best solution, but it works.
    passwordTextField.textContentType = .oneTimeCode
} else {
    // iOS 11: Disables the autofill accessory view. 
    // For more information see the explanation below.
    emailTextField.textContentType = .init(rawValue: "")
    passwordTextField.textContentType = .init(rawValue: "")
}


iOS 11explanation:

iOS 11解释:

Make sure you setup all of your UITextFieldobjects like this.

确保UITextField像这样设置所有对象。

If you have for example an UITextFieldobject where the user must enter his email address and another one where the user must enter his password assign UITextContentType("")to both of their textContentTypeproperty. Otherwise it will not work and the autoFill accessory view will still be shown.

例如,如果您有一个UITextField对象,用户必须输入他的电子邮件地址,另一个对象则用户必须输入他的密码,分配UITextContentType("")给他们的两个textContentType属性。否则它将无法工作,并且仍会显示自动填充附件视图。

回答by Gal Shahar

iOS 12seems to recognise password textFields also by isSecureTextEntryproperty and not just by textContentTypeproperty, so making this accessory view disappear is not really possible unless you both set textContentType to nothing, and remove the secureEntry feature (and cause a security flaw in your app) which then prevents iOS 12 to recognise the textField as a password textField and show this annoying accessory view.

iOS 12似乎也通过isSecureTextEntry属性而不是仅通过textContentType属性识别密码文本字段,因此除非您将 textContentType 设置为空并删除 secureEntry 功能(并导致您的应用程序中的安全漏洞),否则实际上不可能使此附件视图消失然后阻止 iOS 12 将 textField 识别为密码 textField 并显示这个烦人的附件视图。

In my case the accessory caused a bug which made my app unresponsive when tapped (Which also got my app rejected in app review process). So I had to remove this feature. I didn't want to give on up this security feature so I had to solve things by my self.

在我的情况下,附件导致了一个错误,使我的应用程序在点击时没有响应(这也让我的应用程序在应用程序过程中被拒绝)。所以我不得不删除这个功能。我不想放弃这个安全功能,所以我不得不自己解决问题。

The idea is to remove the secureEntry feature but add it by yourself manually. It did worked:

这个想法是删除 secureEntry 功能,但手动添加它。它确实有效:

enter image description here

在此处输入图片说明



It can be done like that:

可以这样做:

Swift 4 way:

斯威夫特 4 种方式:

First, as answered here, set textContentTypeto nothing:

首先,正如这里所回答的,设置textContentType为空:

if #available(iOS 10.0, *) {
    passwordText.textContentType = UITextContentType("")
    emailText.textContentType = UITextContentType("")
}

Than, declare a String variable which will later contain our textField real content:

然后,声明一个 String 变量,该变量稍后将包含我们的 textField 真实内容:

var passwordValue = ""

var passwordValue = ""

Add a target to the passwordTextField, which will be called each time the textField content changes:

给 passwordTextField 添加一个目标,每次 textField 内容改变时都会调用它:

passwordText.addTarget(self, action: #selector(textFieldDidChange(_:)), for: .editingChanged)

Now That's what will do the magic, declare the function that will handle the text replacements:

现在这就是魔术,声明将处理文本替换的函数:

@objc func textFieldDidChange(_ textField: UITextField) {
    if textField.text!.count > 1 {
        // User did copy & paste
        if passwordValue.count == 0 { // Pasted into an empty textField
            passwordValue = String(textField.text!)
        } else { // Pasted to a non empty textField
            passwordValue += textField.text!.substring(from: passwordValue.count)
        }
    } else {
        // User did input by keypad
        if textField.text!.count > passwordValue.count { // Added chars
            passwordValue += String(textField.text!.last!)
        } else if textField.text!.count < passwordValue.count { // Removed chars
            passwordValue = String(passwordValue.dropLast())
        }
    }
    self.passwordText.text = String(repeating: "?", count: self.passwordText.text!.count)
}

Finally, Set textField's autocorrectionTypeto .noto remove predictive text:

最后,设置文本域的autocorrectionType.no去除预测文本:

passwordText.autocorrectionType = .no

That's it, use passwordValueto perform your login.

就是这样,用于passwordValue执行您的登录。

Hope it'll help someone.

希望它会帮助某人。

UPDATE

更新

It catches pasted values also, forgot to add it before.

它也捕获粘贴的值,之前忘记添加它。

回答by gebirgsb?rbel

The feature can be disabled by specifying a content type that is neither username nor password. For example, if the user should enter an email address, you could use

可以通过指定既不是用户名也不是密码的内容类型来禁用该功能。例如,如果用户应该输入电子邮件地址,您可以使用

usernameTextField?.textContentType = .emailAddress

回答by Mikhail Zinov

You can add extension for UITextContentType like this

您可以像这样为 UITextContentType 添加扩展名

extension UITextContentType {
    public static let unspecified = UITextContentType("unspecified")
}

after that, you can use it

之后,你可以使用它

if #available(iOS 10.0, *) {
    passwordField.textContentType = .unspecified
}

回答by Ammad

A very simple approach in ios11 worked for me. Suppose your iboutlets are usernametextfield and passwordtextfield. In viewDidLoad() function of your viewcontroller that holds the both outlest use the following code

ios11 中的一个非常简单的方法对我有用。假设您的 iboutlets 是 usernametextfield 和 passwordtextfield。在您的视图控制器的 viewDidLoad() 函数中,它包含两个最重要的使用以下代码

usernametextfield.textContentType = UITextContentType("")
passwordtextfield.textContentType = UITextContentType("")

After this you wont see autofill accessory option when you tap on your textfields.

在此之后,当您点击文本字段时,您将不会看到自动填充附件选项。

回答by Matheus Domingos

Objective-C

目标-C

if (@available(iOS 10, *)){
    self.tfEmail.textContentType = @"";
    self.tfPassword.textContentType = @"";
}

This worked for me.

这对我有用。

回答by Sahil

Autofill is by default enabled for users. iOS saves all passwords in the keychain and make them available in keyboard in your apps. UITextViewand UITextFieldautomatically considered for AutoFill password. you can disable by specifying a content type that is neither username nor password but if the content type info already stored in keychain it will show in the quick bar. so better to assign empty UITextContentTypetype and it will not show quickbar.

默认情况下为用户启用自动填充。iOS 将所有密码保存在钥匙串中,并在您的应用程序的键盘中提供它们。UITextViewUITextField自动考虑自动填充密码。您可以通过指定既不是用户名也不是密码的内容类型来禁用,但如果内容类型信息已存储在钥匙串中,它将显示在快速栏中。所以最好分配空UITextContentType类型,它不会显示快速栏。

Example:

例子:

  if #available(iOS 10.0, *) {
  self.textField.textContentType = UITextContentType("")
  } else {
  // Fallback on earlier versions
 }

回答by no_fate

This worked for ios 12 and 10:

这适用于 ios 12 和 10:

if (@available(iOS 10, *)) {
    passwordTextField.textContentType = UITextContentTypeStreetAddressLine2;
}

if (@available(iOS 12, *)) {
    passwordTextField.textContentType = UITextContentTypeOneTimeCode;
}

回答by ashish

in response to @Gal Shahar Answer.

回应@Gal Shahar 的回答。

iOS 12recognise password textFields by isSecureTextEntryproperty and not just by textContentTypeproperty.

iOS 12isSecureTextEntry属性识别密码文本字段,而不仅仅是按textContentType属性。

Way Around to bypass Auto-fill Suggestion.

绕过自动填充建议的方法。

  1. set isSecureTextEntryproperty to false.
  1. isSecureTextEntry属性设置为 false。

self.passwordTextField.secureTextEntry = NO;

self.passwordTextField.secureTextEntry = NO;

  1. Add a UITextField Delegate Method and enable the isSecureTextEntryproperty.
  1. 添加 UITextField 委托方法并启用该isSecureTextEntry属性。
- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string {
    if (textField == self.passwordTextField && !self.passwordTextField.secureTextEntry) {
        self.passwordTextField.secureTextEntry = YES;
    }

    return YES;
}

NOTE: - Do NOTUse shouldBeginEditingUITextField delegate method it Will Still show Auto-filling Suggestion. Do NOTUse textFieldDidChangeUITextField delegate method it Will Auto-delete the first charachter as the it Will happen after the first charachter is displayed. And 'secureTextEntry' will empty the field.

注: -执行使用shouldBeginEditing的UITextField委托方法它仍然会显示自动填充建议。千万不要使用textFieldDidChange的UITextField委托方法它会自动删除第一charachter为显示第一charachter后,它会发生。'secureTextEntry' 将清空该字段。

回答by Denis Kutlubaev

Objective C version:

目标 C 版本:

if (SYSTEM_VERSION_GREATER_THAN_OR_EQUAL_TO(@"10.0")) {
    self.passwordTextField.textContentType = @"";
    self.confirmPasswordTextField.textContentType = @"";
}

where

在哪里

#define SYSTEM_VERSION_EQUAL_TO(v)                  ([[[UIDevice currentDevice] systemVersion] compare:v options:NSNumericSearch] == NSOrderedSame)
#define SYSTEM_VERSION_GREATER_THAN(v)              ([[[UIDevice currentDevice] systemVersion] compare:v options:NSNumericSearch] == NSOrderedDescending)
#define SYSTEM_VERSION_GREATER_THAN_OR_EQUAL_TO(v)  ([[[UIDevice currentDevice] systemVersion] compare:v options:NSNumericSearch] != NSOrderedAscending)
#define SYSTEM_VERSION_LESS_THAN(v)                 ([[[UIDevice currentDevice] systemVersion] compare:v options:NSNumericSearch] == NSOrderedAscending)
#define SYSTEM_VERSION_LESS_THAN_OR_EQUAL_TO(v)     ([[[UIDevice currentDevice] systemVersion] compare:v options:NSNumericSearch] != NSOrderedDescending)