SwiftUI SecureField:如何实现与 UIKit 中相同的字符模糊行为?

Posted

技术标签:

【中文标题】SwiftUI SecureField:如何实现与 UIKit 中相同的字符模糊行为?【英文标题】:SwiftUI SecureField: How to achieve the same character obscuring behaviour as in UIKit? 【发布时间】:2020-12-02 15:53:16 【问题描述】:

我的问题是 SwiftUI 中的 SecureField 在任何时候都不会显示用户输入的字符,它只是在输入每个字符时直接显示“•”符号 - 而在 UIKit 中,UITextField ( with isSecureTextEntry = true) 显示最新的字符一秒钟,然后将其隐藏在“•”后面。

我公司的 UX 测试人员要求我恢复“旧行为” - 但这种行为似乎不是任何公共 API 的一部分。

有趣的是,这也适用于使用 UIViewRepresentable 注入 SwiftUI 的 UITextField 自定义类 - 它们以上述“SwiftUI 方式”运行。那么在 SwiftUI 中针对所有安全的UITextField 行为进行了一些上下文行为修改?我必须将我的 SwiftUI 表单完全重写为完整的 UIViewController 才能恢复行为(以模式推送 UIViewControllers with secure UITextFields do 表现出所需的行为。)

这是 SwiftUI 中的一种副业错误吗?我在 ios13 和 14 中看到 SwiftUI 的情况相同。有人看到解决方法或解决方案吗?

-编辑-

在下面@Asperi 的精彩解释之后,我注意到我使用UIViewRepresentable 注入到SwiftUI 中的UITextField 自定义类通过在updateUIView 调用中不必要地设置文本绑定来强制这种行为。使用协调器仅处理文本逻辑为我解决了使用此方法时的问题。

【问题讨论】:

【参考方案1】:

观察到的效果是由于立即应用于绑定字符串状态和立即反应/重建视图。

为了带来期望的行为,我们需要以某种方式推迟状态更新,从而让 SecuredField/UITextField 有机会在不与状态同步的情况下更新自身。

这是一个可能方向的演示(它并不理想,但有一条路要走)。使用 Xcode 12.1 / iOS 14.1 测试。

struct DemoSecureFieldView: View 
    @State private var password = "demo"

    var textBinding: Binding<String>  
        Binding(get:  password ,
            set:  value in
                // more logic can be added to delay _only_ if new symbol added,
                // and force apply if next symbol came fast
                DispatchQueue.main.asyncAfter(deadline: .now() + 0.25) 
                    password = value
                
            
        )
    
    var body: some View 
        VStack 
            SecureField("Placeholder", text: textBinding)
                    .textFieldStyle(RoundedBorderTextFieldStyle())
                    .padding()
        .background(Color.pink)
    

【讨论】:

太好了,谢谢!结果证明我通过UIViewRepresentable 进行的UITextField 注入使这变得更加容易,我只是通过在updateUIView 中设置我的文本绑定值来将其连接“太紧”。但我有一个协调员,所以无论如何这都是不必要的。 它在 iOS 15 中不起作用

以上是关于SwiftUI SecureField:如何实现与 UIKit 中相同的字符模糊行为?的主要内容,如果未能解决你的问题,请参考以下文章

SwiftUI SecureField 跟踪活动/非活动状态

在 SwiftUI 中向 TextField/SecureField 添加图像,向占位符文本添加填充

SwiftUI - 在禁用的 SecureField 中检测水龙头?

SecureField 的 .newPassword 选择强密码不使用 SwiftUI 和 iOS14

在 SwiftUI 视图中的 TextField 后面使用多个 SecureField 时的奇怪行为

如何将 UISearchController 与 SwiftUI 集成