Search
🔨

Xcode 템플릿 생성 및 활용 방법

부제
카테고리
iOS
세부 카테고리
협업
Combine 카테고리
최종편집일
2022/09/20 13:29
작성중
관련된 포스팅
생성 일시
2022/09/20 13:27
태그

Xcode 템플릿

왜 사용하게 되었는지

MARK 주석 기능을 활용해서 코드를 자주 분리했는데,
이를 팀 코드 컨벤션으로 사용하고자 하였습니다.
하지만 같은 내용의 주석을 반복해서 타이핑하는 나 자신을 보니 자괴감이 들어 무슨 방법이 없을까 고민했죠
검색을 해보니 Xcode 템플릿을 만들어서 사용하면 이를 해결할 수 있더군요!

구성요소

하나의 템플릿은 하나의 폴더로 묶입니다
Xcode 템플릿 파일의 구성요소는 위와 같이 4개입니다.
1.
___FILEBASENAME___.swift : 템플릿 자체 파일
2.
Template 아이콘 파일
3.
TemplateInfo.plit : 템플릿의 정보에 관한 파일
___FILEBASENAME___ 라는 문구는 템플릿을 사용해 파일을 만들 떄, 사용자가 입력한 파일의 이름으로 대치되는 Place Holder 라고 생각하시면됩니다.

만드는법

1. 템플릿 파일 작성

//___FILEHEADER___ import UIKit class ___FILEBASENAMEASIDENTIFIER___: BaseViewController { //MARK: - Properties //MARK: - LifeCycle override func viewDidLoad() { super.viewDidLoad() configureUI() } //MARK: - Selectors //MARK: - Helpers func configureUI() { //레이아웃 구성 } } //MARK: - Preview import SwiftUI struct ___FILEBASENAMEASIDENTIFIER___Representable: UIViewControllerRepresentable { typealias UIViewControllerType = ___FILEBASENAMEASIDENTIFIER___ func makeUIViewController(context: Context) -> ___FILEBASENAMEASIDENTIFIER___ { return ___FILEBASENAMEASIDENTIFIER___() } func updateUIViewController(_ uiViewController: ___FILEBASENAMEASIDENTIFIER___, context: Context) {} } @available(iOS 13.0.0, *) struct ___FILEBASENAMEASIDENTIFIER___Preview: PreviewProvider { static var previews: some View { ___FILEBASENAMEASIDENTIFIER___Representable() } }
Swift
복사
___FILEBASENAMEASIDENTIFIER___ : 템플릿을 사용해 파일을 만들 때, 파일의 이름으로 대치되는 PlaceHoler
//___FILEHEADER___ : 파일의 헤더가 자동으로 위치하게 되는 PlaceHolder 입니다. 건드릴 필요 없죠

템플릿 작성 팁

팀 내부적으로 필수적으로 상속받아야 하는 클래스가 있다면 이를 템플릿에 작성시, 실수로 상속하지 않는 실수를 피할 수 있습니다. 예 : BaseViewController
팀 내부의 코드를 정리하는 컨벤션을 정해 이를 MARK 주석으로 작성하면 팀원들의 코드를 읽기 편해집니다.
1.
프로퍼티
2.
라이프사이클 이벤트
3.
셀렉터
4.
헬퍼 함수
5.
프리뷰 관련 코드
를 분리하는 용도로 사용하였습니다.
코드를 찾기 쉬워집니다.
UIKit 에서 PreView 를 보기위한 코드를 따로 추가할 필요없이 템플릿화해서 사용할 수도 있습니다.
필수적으로 구현하고자하는 헬퍼함수를 미리작성해두는 것도 좋습니다. 예 : configureUI() → UI 의 레이아웃을 구성하는 코드를 분리하는 용도.

사용법

위와 같이 열심히 만든 템플릿을
Luke.xctemplate 2.zip
16.2KB
위 파일을 압축해제하여 아래 경로에 추가해준다.
터미널에서 아래 명령어를 실행하면 간편하다.
cd /Applications/Xcode.app/Contents/Developer/Platforms/iPhoneOS.platform/Developer/Library/Xcode/Templates/iOS/Source open .
Bash
복사
위와 같이 템플릿을 추가해준다.
Xcode 를 껐다 켠다.
귀여운 Luke 템플릿이 추가되어 있는 걸 볼 수 있다.
이름을 바꾸어 파일 생성

잘 적용된 모습

컨벤션에 맞는 코드 예시

class LukeViewController: UIViewController { //MARK: - Properties 데이터, UI와 같은 프로퍼티 UI 객체만의 특성을 초기화해줄 때, 클로져형태로 초기화해주게 됩니다. private let data: Data = Data() let label: UILabel = { let label = UILabel() label.text = "Hello World!" return label }() let imageView: UIImageView = { let imageView = UIImageView() imageView.contentMode = .scaleToFill imageView.image = UIImage(systemName: "person.fill") return imageView }() //lazy를 써야 addtarget 이 제대로 작동합니다. private lazy var actionButton: UIButton = { let button = UIButton(type: .system) button.setTitle("Tweet", for: .normal) button.titleLabel?.textAlignment = .center button.titleLabel?.font = UIFont.boldSystemFont(ofSize: 16) button.setTitleColor(.white, for: .normal) button.frame = CGRect(x: 0, y: 0, width: 100, height: 40) button.layer.cornerRadius = 32 / 2 button.backgroundColor = .link //action 에 대한 target 을 버튼으로 지정합니다. button.addTarget(self, action: #selector(didActionButtonTap), for: .touchUpInside) return button }() //MARK: - LifeCycle : View 의 라이프사이클 이벤트를 핸들링 하는 부분입니다. override func viewDidLoad() { super.viewDidLoad() view.backgroundColor = .white configureUI() } //MARK: - Selectors : 타겟에 대한 액션을 정의하는 부분입니다. ( 없다면 생략 가능 ) @objc func didActionButtonTap() { //버튼에 대한 action 이 들어가게 됩니다. uploadData() } //MARK: - Helpers 헬퍼함수를 정의하는 부분입니다. func configureUI() { //MARK: 레이아웃을 짜는 로직이 들어가게 됩니다. let safeArea = view.safeAreaLayoutGuide view.addSubview(label) label.translatesAutoresizingMaskIntoConstraints = false label.centerXAnchor.constraint(equalTo: safeArea.centerXAnchor).isActive = true label.centerYAnchor.constraint(equalTo: safeArea.centerYAnchor, constant: -100).isActive = true view.addSubview(imageView) imageView.makeTop(equalTo: label.bottomAnchor, constant: 20) imageView.makeHorizontal(equalTo: view, constant: 30) imageView.makeHeight(equalTo: label.heightAnchor, constant: 100) view.addSubview(actionButton) actionButton.translatesAutoresizingMaskIntoConstraints = false actionButton.centerXAnchor.constraint(equalTo: label.centerXAnchor).isActive = true actionButton.topAnchor.constraint(equalTo: imageView.bottomAnchor, constant: 20).isActive = true actionButton.heightAnchor.constraint(equalToConstant: 60).isActive = true actionButton.widthAnchor.constraint(equalToConstant: 300).isActive = true } func uploadData() { //헬퍼 함수 예시 } }
Swift
복사