[iOS] 13 이슈 대응 및 변경 사항 공유

728x90
반응형

 

안녕하세요.

 

iOS13 대응을 진행하면서 몇 가지 변경사항 및 급한 불을 끌 수 있는 이슈 방안에 대해서 적어보려고 합니다.

💡KVC 금지

*** Terminating app due to uncaught exception 'NSGenericException',
 reason: 'Access to UISearchBar's _searchField ivar is prohibited. This is an application bug'
*** Terminating app due to uncaught exception 'NSGenericException',
 reason: 'Access to UITextField's _placeholderLabel ivar is prohibited. This is an application bug'

 

KVC코드가 들어가있는 소스에 Xcode11로 빌드해보면 위와 같은 에러들이 나타나며 앱이 죽어 당황하셨을겁니다.

iOS 13으로 변경됨에 따라 시스템이 KVC를 통한 접근을 금지 하는듯 합니다.

 

예전엔 placeholder의 색을 변경시키고자할때 해당 객체의 키값을 찾아서 변경 가능했지만,

객체의 키값을 가지고 접근하는 방식을 금지하는 방향으로 바꼈습니다.

또, 아래와 같이 키를 가지고 접근하는 방법으로 작성했다면 iOS13에서는 앱이 죽는 현상이 나타나죠

//textField의 placeholder 색을 변경 방법
[textfield setValue:[UIColor red] forKeyPath:@"_placeholderLabel.textColor"];

//searchbar에서 textfield를 접근하는 방법
searchBar.value(forKey: "_searchField") as? UITextField { ... }

 

  • 해결 방안

 

textField의 placeholder의 색을 변경 방법

대응 방안은 NSStringAttributedString을 활용.

textfield.attributedPlaceholder = [[NSAttributedString alloc] initWithString:placeholer
				attributes:@{NSForegroundColorAttributeName: colorGray}];
[textfield setAttributedPlaceholder:textfield.attributedPlaceholder];

 

searchBar에서 textField를 접근 방법

대응 방안으로는 searchTextField가 iOS13에서 새로 생김으로써 더이상 key를 가지고 접근하지 않아도 됩니다.

let searchField = searchController.searchBar.searchTextField

 

 

 

💡다크모드 막기 (2가지)

다크모드 적용은 애플에서 강력하게 권고하는 사항이기 때문에 다크모드를 막는것은 일시적인 방법입니다.

대체로 2가지 방법이 있습니다.

 

1. plist에 추가

      User Interface Style - Light 추가

2. 코드 삽입

if #available(iOS 13.0, *) {
    self.window?.overrideUserInterfaceStyle = .light
} 

 

 

 

💡다크모드 Detecting 방법

모드 전환이 된 순간에 호출되는 메서드!

  -> unspecified, light, dark

override func traitCollectionDidChange(_ previousTraitCollection: UITraitCollection?) {
    super.traitCollectionDidChange(previousTraitCollection)

    if #available(iOS 12.0, *) {
      let userInterfaceStyle = traitCollection.userInterfaceStyle
      print(userInterfaceStyle)

	  // unspecified, light, dark

    }
}

 

 

💡StatusBar 접근 방법

이것 또한 아래와 같이 KVC로 접근해서 statusBar를 가져왔다고 하면 앱이 죽어 당황하셨을 겁니다.

//StatusBar를 가져오는 방법
UIApplication.shared.value(forKey: "statusBar") as? UIView

 

이러한 에러가 뜨죠

Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'App called -statusBar or -statusBarWindow on UIApplication: this code must be changed as there's no longer a status bar or status bar window. Use the statusBarManager object on the window scene instead.'

 

이젠 iOS13부터는 statusBarManager 객체를 사용해서 접근해야 됩니다!

 

UIStatusBarManager - UIKit | Apple Developer Documentation

A Boolean value indicating whether the status bar is currently hidden.

developer.apple.com

statusBarManager를 이용해서 statusBarFrame에 접근이 가능하므로써 Color를 조작할 수 있습니다.

override func viewDidAppear(_ animated: Bool) {
    super.viewDidAppear(animated)

    if #available(iOS 13.0, *) {
      let window = UIApplication.shared.windows.first { $0.isKeyWindow }
      let statusBarManager = window?.windowScene?.statusBarManager

      let statusBarView = UIView(frame: statusBarManager?.statusBarFrame ?? CGRect.zero)
      statusBarView.backgroundColor = UIColor.red

      window?.addSubview(statusBarView)

    } else {
      let statusBarView = UIApplication.shared.value(forKey: "statusBar") as? UIView
      statusBarView?.backgroundColor = .blue
    }

}

 

추가로 iOS 13에서 keywindow가 deprecated될 예정이기 때문에 windows로 대체 됩니다.

즉 기존에 window를 찾던 코드가 아래와 같이 변경될겁니다.

//before:
let window = UIApplication.shared.keyWindow

//after:
let window = UIApplication.shared.windows.first { $0.isKeyWindow }

 

💡Modal Presentation Style

iOS13부터 Modal presentation Style의 디폴트 값이 full screen이 아닌 'automaic'으로 변경되었습니다.

XCode11업데이트 후 13.0으로 빌드 해보니 모달 형식이 아래와 같이 'page sheet'형태로 나타나는걸 볼 수 있으셨을 겁니다.

 

그렇다면 automatic은 무엇일까요?

세로화면에선 page sheet, 가로화면에선 full screen형태의 타입을 나타냅니다!

 

즉, 디폴드가 automatic으로 바꼈으니 이전 버전의 모달형식처럼 full screen으로 바꿔야한다면 전체를 바꿔야합니다

vc.modalPresentationStyle = .fullScreen

 

 

💡Card-Style의 sheet modal 라이프 사이클

FirstVC와 SecondVC 두가지의 뷰컨트롤러가 있고, FirstVC에서 어떠한 버튼을 눌렀을때 SecondVC modal이 나타난다고 가정해보자.

 

  • 기존의 fullscreen style의 모달 라이프 사이클

/* FullScreen Present */

-------------- [SecondVC : viewDidLoad] --------------

-------------- [FirstVC : viewWilldisappear] --------------

-------------- [SecondVC : viewWillAppear] --------------

-------------- [SecondVC : viewDidAppear] --------------

-------------- [FirstVC : viewDidDisappear] --------------

/* FullScreen Dismiss */

-------------- [SecondVC : viewWilldisappear] --------------

-------------- [FirstVC : viewWillAppear] --------------

-------------- [FirstVC : viewDidAppear] --------------

-------------- [SecondVC : viewDidDisappear] --------------

 

 

  • sheet style의 모달 라이프 사이클

 

/* Sheet Present */

-------------- [SecondVC : viewDidLoad] --------------

-------------- [SecondVC : viewWillAppear] --------------

-------------- [SecondVC : viewDidAppear] --------------


/* Sheet Dismiss */

-------------- [SecondVC : viewWilldisappear] --------------

-------------- [SecondVC : viewDidDisappear] --------------

 

위의 그림에 볼 수 있듯이, 기존 fullscreen의 라이프 사이클과 다르게 firstVC에는 전혀 영향을 주지 않고 firstVC앞에 독립적으로 띄워지는 모달형식인걸 볼 수 있습니다.

디폴트값이 automatic인 만큼 가로 세로화면을 구현하는 앱일때 알아두시면 유용할 것 같습니다.

 

 

💡UISegmentedControl의 변화

iOS13에서 UIKit 구성요소 중 UISegmentedControl, UISwift, UIStepper, UISlider가 기존과 조금? 다르게 새로운 디자인으로 등장했습니다.

 

그 중 UISegmentedControl이 iOS13에서 변화가 생겼습니다. iOS7부터 등장한 "tintColor"로는 더 이상 Color를 변경 할 수 없습니다.

"SelectedSegmentTintColor"라는 새로운 속성을 사용하면 슬라이딩 제어의 색상을 변경할 수 있습니다.

 

    segmented.setTitleTextAttributes([NSAttributedString.Key.foregroundColor : UIColor.white],
                                     for: .selected)

    if #available(iOS 13.0, *) {
      segmented.selectedSegmentTintColor = .blue
    } else {
      segmented.tintColor = .blue
    }

 

 

💡App Store Review Guideline

2020년 4월부터 모든 새로운 앱과 앱 업데이트는 iOS 13 SDK로 구축되어야 하며 아이폰 XS Max 이상의 전체 화면 설계를 지원해야 한다고 보도했습니다.

https://9to5mac.com/2019/09/10/apple-april-2020-ios-13-sdk-deadline/

 

Apple sets April 2020 deadline for developers to build apps with iOS 13 SDK - 9to5Mac

Apple today has asked developers to begin to submit their updated applications for iOS 13. The company touts that developers can implement Dark Mode, Sign in with Apple, ARKit 3, and more. Starting in April 2020, Apple says all new apps and app updates wil

9to5mac.com

 

그 중 iOS13에서 Apple ID를 가지고 계정을 생성할 수 있는 "Sign in with Apple"의 기능이 새로 생겼습니다.

즉, 2020년 4월까지 앱을 업데이트하거나, 배포하기 위해서는 "Sign in with Apple" 로그인 기능이 꼭 들어가야 된다는 뜻이죠.

https://developer.apple.com/news/?id=09122019b

 

New Guidelines for Sign in with Apple - News - Apple Developer

Make it easy for users to sign in to your apps and websites using the Apple ID they already have. With privacy and security features built-in, Sign in with Apple is a great way to help users set up an account, sign in, and engage with your app quickly and

developer.apple.com

 

 

💡NSBluetoothPeripheralUsageDescription 키 값 변경

iOS 13이상 버전부터 블루투스에 접근 하기 위한 권한 키값이 변경되었습니다.

Privacy - Bluetooth Peripheral Usage Description -> Privacy - Bluetooth Always Usage Description

 

iOS 13 이전 호환성을 위해 2가지를 추가해줘야 합니다.

 

https://developer.apple.com/documentation/bundleresources/information_property_list/nsbluetoothalwaysusagedescription

 

 

 

iOS13이 등장하면서 많은 기능이 나왔듯이 많은 이슈도 생겼네요.

찾은 방법들을 공유하려고 하니, 수정해야될 부분이나 다른 이슈사항 알려주시면 감사하겠습니다. :]

반응형