iOS 15.1真机Sign in with Apple模态视图关闭动画异常如何修复
问题原因
该异常是iOS 15.0 ~ 15.1版本系统自带的Bug,属于AuthenticationServices框架的适配问题,和开发者的业务代码实现逻辑无关,苹果官方已经在iOS 15.2及后续系统版本中修复了该问题。你测试到其他接入该功能的App也存在相同表现,也验证了这是系统层面的共性问题。
模拟器上表现正常是因为模拟器的系统渲染逻辑和真机存在差异,该异常只会在iOS 15.0~15.1的真机上出现。
修复方案
方案1:版本适配(推荐)
直接对系统版本做判断,仅在iOS 15.2及以上版本使用原生SignInWithAppleButton,低于该版本的用户可以引导升级系统,或者降级使用自定义Apple登录按钮触发授权流程,该方案不会被苹果审核驳回。
方案2:修改现有布局(适配iOS15.0/15.1)
你当前代码中给承载按钮的VStack添加了ignoresSafeArea(.all)修饰符,是触发该系统Bug的常见诱因,可以做如下调整:
- 移除全局
ignoresSafeArea(.all)修饰符,替换为仅对需要忽略安全区的视图单独添加,或者仅忽略指定边缘的安全区,比如ignoresSafeArea(.container, edges: .bottom)。 - 如果必须要全局忽略安全区,可以使用UIKit的
ASAuthorizationAppleIDButton包装成SwiftUI视图使用,规避SwiftUI原生组件的适配问题,参考代码如下:
import SwiftUI import AuthenticationServices struct AppleSignInButtonWrapper: UIViewRepresentable { typealias UIViewType = ASAuthorizationAppleIDButton var onRequest: (ASAuthorizationAppleIDRequest) -> Void var onCompletion: (Result<ASAuthorization, Error>) -> Void func makeUIView(context: Context) -> ASAuthorizationAppleIDButton { let button = ASAuthorizationAppleIDButton(type: .signIn, style: .black) button.addTarget(context.coordinator, action: #selector(Coordinator.tapAction), for: .touchUpInside) return button } func updateUIView(_ uiView: ASAuthorizationAppleIDButton, context: Context) {} func makeCoordinator() -> Coordinator { Coordinator(self) } class Coordinator: NSObject, ASAuthorizationControllerDelegate, ASAuthorizationControllerPresentationContextProviding { let parent: AppleSignInButtonWrapper init(_ parent: AppleSignInButtonWrapper) { self.parent = parent } @objc func tapAction() { let request = ASAuthorizationAppleIDProvider().createRequest() parent.onRequest(request) let controller = ASAuthorizationController(authorizationRequests: [request]) controller.delegate = self controller.presentationContextProvider = self controller.performRequests() } func presentationAnchor(for controller: ASAuthorizationController) -> ASPresentationAnchor { UIApplication.shared.windows.first { $0.isKeyWindow }! } func authorizationController(controller: ASAuthorizationController, didCompleteWithAuthorization authorization: ASAuthorization) { parent.onCompletion(.success(authorization)) } func authorizationController(controller: ASAuthorizationController, didCompleteWithError error: Error) { parent.onCompletion(.failure(error)) } } } // 原视图中替换使用即可 struct ContentView: View { var body: some View { VStack { AppleSignInButtonWrapper( onRequest: signInWithAppleOnRequest, onCompletion: signInWithAppleOnComplete ) .frame(height: 50) } .ignoresSafeArea(.all) } func signInWithAppleOnRequest(request: ASAuthorizationAppleIDRequest) { request.requestedScopes = [.fullName, .email] } func signInWithAppleOnComplete(result: Result<ASAuthorization, Error>) { // 保留原有业务逻辑即可 } }
内容的提问来源于stack exchange,提问作者Yi-Hsiu Lee
相关产品推荐
相关产品推荐

