importUIKitclassViewController:UIViewController,UICollectionViewDataSource{// 임의로 지정해준 셀의 갯수varnumberObCell:Int=10letcellIdentifier:String="cell"funccollectionView(_collectionView:UICollectionView,numberOfItemsInSectionsection:Int)->Int{// 10개의 셀이 생길것이다.returnself.numberObCell}funccollectionView(_collectionView:UICollectionView,cellForItemAtindexPath:IndexPath)->UICollectionViewCell{letcell:UICollectionViewCell=collectionView.dequeueReusableCell(withReuseIdentifier:self.cellIdentifier,for:indexPath)returncell}overridefuncviewDidLoad(){super.viewDidLoad()// Do any additional setup after loading the view.}}
동적으로 데이터 추가해보기
이제 셀을 클릭하면 자동으로 셀이 생성되도록 만들어볼 것이다.
importUIKitclassViewController:UIViewController,UICollectionViewDataSource,UICollectionViewDelegate{// 임의로 지정해준 셀의 갯수varnumberObCell:Int=10letcellIdentifier:String="cell"funccollectionView(_collectionView:UICollectionView,numberOfItemsInSectionsection:Int)->Int{// 10개의 셀이 생길것이다.returnself.numberObCell}funccollectionView(_collectionView:UICollectionView,cellForItemAtindexPath:IndexPath)->UICollectionViewCell{letcell:UICollectionViewCell=collectionView.dequeueReusableCell(withReuseIdentifier:self.cellIdentifier,for:indexPath)returncell}funccollectionView(_collectionView:UICollectionView,didSelectItemAtindexPath:IndexPath){// 컬렉션뷰의 아이템을 선택하게 되면 셀의 갯수를 1개씩 늘려주는 메서드self.numberObCell+=1collectionView.reloadData()}overridefuncviewDidLoad(){super.viewDidLoad()// Do any additional setup after loading the view.}}
위 코드들을 실행할때 해당 뷰 컨트롤러에 DataSource와 Delegate를 연결해주는 것 잊지말자!
컬렉션뷰는 유연하고 변경 가능한 레이아웃을 사용하여 데이터 아이템의 정렬된 세트를 표시하는 수단이다.
컬렉션뷰의 가장 일반적인 용도는 데이터 아이템을 그리드와 같은 형태로 표현한다. 더불어 다양한 방법으로 컬렉션뷰의 레이아웃을 사용자 정의할 수 있다.
컬렉션뷰의 구성요소
셀(Cell) : 컬렉션뷰의 주요 콘텐츠를 표시
컬렉션뷰는 컬렉션뷰 데이터 소스 객체에서 표시할 셀에 대한 정보를 가져온다.
각 셀은 UICollectionViewCell 클래스의 인스턴스 또는 UICollectionViewCell을 상속받은 클래스의 인스턴스
보충 뷰(Supplementary views) : 섹션에 대한 정보를 표시
셀과 달리 보충 뷰는 필수는 아니며, 사용법과 배치 방식은 사용되는 레이아웃 객체가 제어한다 > 헤더와 푸터를 예로!
데코레이션 뷰(Decoration views) : 콘텐츠가 스크롤 되는 컬렉션뷰에 대한 배경을 꾸밀 때 사용
레이아웃 객체는 데코레이션 뷰를 사용하여 커스텀 배경 모양을 구현할 수 있다
레이아웃 객체(Layout Object) : 레이아웃 객체는 컬렉션뷰 내의 아이템 배치 및 시각적 스타일을 결정
컬렉션뷰 데이터 소스 객체가 뷰와 표시할 콘텐츠를 제공한다면, 레이아웃 객체는 크기, 위치 및 해당 뷰의 레이아웃과 관련된 특성들을 결정
컬렉션뷰 구현을 이루기 위한 클래스 및 프로토콜
컬렉션뷰를 사용하여 콘텐츠를 화면에 표시하기 위해서 컬렉션뷰는 여러 가지 다른 객체들과 협력한다. 예를 들어, 컬렉션뷰는 컬렉션뷰 데이터 소스 객체로부터 표시할 콘텐츠의 정보를 얻어오고, 사용자와의 상호작용을 처리하기 위해 컬렉션뷰 델리게이트 객체를 사용한다
최상위 포함 및 관리 (Top level containment)
UICollectionView / UICollectionViewController : UICollectionView는 컬렉션뷰의 콘텐츠가 보이는 영역을 정의하며, UICollectionViewController는 컬렉션뷰를 관리하는 뷰 컨트롤러이다. UICollectionViewController는 선택적으로 사용 가능!
콘텐츠 관리
UICollectionViewDataSource protocol / UICollectionViewDelegate protocol : 데이터 소스 객체는 컬렉션뷰와 관련된 중요한 객체이며, 필수적으로 제공해야 한다. 데이터 소스는 컬렉션뷰의 콘텐츠를 관리하고 해당 콘텐츠를 표시하기 위한 뷰를 제공하며 컬렉션뷰 델리게이트 객체는 사용자와의 상호작용과 셀 강조 표시 및 선택 등을 관리한다.
표시(Presentation)
UICollectionReusableView / UICollectionViewCell : 컬렉션에 표시된 모든 뷰는 UICollectionReusableView 클래스의 인스턴스여야 한다. 이 클래스는 컬렉션뷰에서 사용 중인 뷰 재사용 메커니즘을 지원하며, 새로운 뷰를 만드는 대신, 뷰를 재사용하여 성능을 향상시킨다.
레이아웃(Layout)
UICollectionViewLayout / UICollectionViewLayoutAttribute / UICollectionViewUpdateItem : UICollectionViewLayout의 서브클래스는 레이아웃 객체라고 하며 컬렉션 뷰 내부의 셀 및 재사용 가능한 뷰의 위치, 크기 및 시각적 속성을 정의한다. UICollectionViewLayoutAttributes는 레이아웃 프로세스 중에 컬렉션뷰에 셀과 재사용가능한 뷰를 표시하는 위치와 방법을 알려주며, 레이아웃 객체 아이템이 삽입, 삭제, 혹은 컬렉션뷰 내에서 이동할 때마다 레이아웃 객체는 UICollectionViewUpdateItem 클래스의 인스턴스를 받는다.
플로우 레이아웃(Flowlayout)
UICollectionViewFlowLayout / UICollectionViewDelegatFlowLayout protocol : 그리드 혹은 다른 라인기반(lined-based) 레이아웃을 구현하는 데 사용된다. 클래스를 그대로 사용하거나 동적으로 커스터마이징할 수 있는 플로우 델리게이트 객체와 함께 사용할 수 있다.
컬렉션뷰와 관련된 클래스 및 프로토콜
UICollectionView : 사용자에게 보여질 컬렉션 형태의 뷰
UICollectionViewCell : UICollectionView 인스턴스에 제공되는 데이터를 화면에 표시하는 역할을 담당
UICollectionReusableView : 뷰 재사용 메커니즘을 지원
UICollectionViewFlowLayout : 컬렉션뷰를 위한 디폴트 클래스로, 그리드 스타일로 셀들을 배치하도록 설계되어있다. scrollDirection 프로퍼티를 통해 수평 및 수직 스크롤을 지원
UICollectionViewLayoutAttributes : 컬렉션뷰 내의 지정된 아이템의 레이아웃 관련 속성을 관리
UICollectionViewDataSource 프로토콜 : 컬렉션뷰에 필요한 데이터 및 뷰를 제공하기 위한 기능을 정의한 프로토콜
UICollectionViewDelegate 프로토콜 : 컬렉션뷰에서 아이템의 선택 및 강조 표시를 관리하고 해당 아이템에 대한 작업을 수행할 수 있는 기능을 정의한 프로토콜
UICollectionViewDelegateFlowLayout 프로토콜 : UICollectionViewLayout 객체와 함께 그리드 기반 레이아웃을 구현하기 위한 기능을 정의한 프로토콜
컬렉션뷰 셀
컬렉션뷰의 셀은 냉장고 속에 있는 반찬통으로 생각할 수 있다. 컬렉션뷰라는 냉장고가 있고, 냉장고 안에는 실제 반찬(콘텐츠)을 담고 있는 컬렉션뷰 셀이라는 반찬통이 있다고 생각할 수 있다.
컬렉션뷰 셀은 데이터 아이템을 화면에 표시
하나의 셀은 하나의 데이터 아이템을 화면에 표시
컬렉션뷰 셀은 두 개의 배경을 표시하는 뷰와 하나의 콘텐츠를 표시하는 뷰로 구성되어 있다. 두 개의 배경뷰는 셀이 선택되었을 때 사용자에게 시각적인 표현을 제공하기 위해 사용
셀의 레이아웃은 컬렉션뷰의 레이아웃 객체에 의해 관리
컬렉션뷰 셀은 뷰의 재사용 메커니즘을 지원
일반적으로 컬렉션뷰 셀 클래스의 인스턴스는 직접 생성하지 않는다.
대신 특정 셀의 하위 클래스를 컬렉션뷰 객체에 등록한 후, 컬렉션뷰 셀 클래스의 새로운 인스턴스가 필요할 때, 컬렉션의 dequeueReusableCell(withReuseIdentifier:for:) 메서드를 호출
스토리보드를 사용하여 셀을 구성하면 컬렉션뷰에 따로 셀 클래스를 등록할 필요는 없습니다.
UICollectionViewCell 클래스
컬렉션뷰 셀의 구성요소 관련 프로퍼티
var contentView: UIView : 셀의 콘텐츠를 표시하는 뷰
var backgroundView: UIView? : 셀의 배경을 나타내는 뷰
이 프로퍼티는 셀이 처음 로드되었을 경우와 셀이 강조 표시되지 않거나 선택되지 않을 때 항상 기본 배경의 역할을 한다
var selectedBackgroundView: UIView? : 셀이 선택되었을 때 배경뷰 위에 표시되는 뷰
이 프로퍼티는 셀이 강조 표시되거나 선택될 때마다 기본 배경 뷰인 backgroundView를 대체하여 표시
컬렉션뷰 셀의 상태 관련 프로퍼티
var isSelected: Bool : 셀이 선택되었는지를 나타냄 > 셀이 선택되어있지 않다면 이 프로퍼티의 값은 false
var isHighlighted: Bool : 셀의 하이라이트 상태를 나타냄 > 하이라이트 되어있지 않다면 기본 값은 false
컬렉션뷰 셀의 드래그 상태 관련 메서드
// 셀의 드래그 상태가 변경되면 호출funcdragStateDidChange(_:)
드래그의 상태는 UICollectionViewCellDragState의 열거형으로 표현되고 none, lifting, dragging의 3가지 상태를 갖는다.
컬렉션뷰 셀 vs 테이블뷰 셀
컬렉션뷰를 학습하면서 앞서 배웠던 테이블뷰와 비슷한 점이 많지 않았나요? 그렇다면 컬렉션뷰 셀과 테이블뷰 셀에는 어떠한 차이점이 있는지 알아볼까요?
테이블뷰 셀의 구조는 콘텐츠 영역과 액세서리뷰 영역으로 나뉘었지만, 컬렉션뷰 셀은 배경뷰와 실제 콘텐츠를 나타내는 콘텐츠뷰로 나뉘었습니다.
테이블뷰 셀은 기본으로 제공되는 특정 스타일을 적용할 수 있지만 컬렉션뷰 셀은 특정한 스타일이 따로 없습니다.
테이블뷰 셀은 목록형태로만 레이아웃 되지만, 컬렉션뷰 셀은 다양한 레이아웃을 지원합니다.
내비게이션 아이템은 내비게이션바의 콘텐츠를 표시하는 객체로, 뷰 컨트롤러가 전환될 때마다 내비게이션바는 하나의 공동 객체지만 내비게이션 아이템은 각각의 뷰 컨트롤러가 가지고 있는 프로퍼티이다.
즉, 내비게이션바가 내비게이션 컨트롤러와 연관이 있다면 내비게이션 아이템은 해당 뷰 컨트롤러와 연관이 있으며 보통 내비게이션바에서 보여지는 중앙 타이틀, 좌측 바 버튼, 우측 바 버튼 등이 내비게이션 아이템의 프로퍼티이다.
주요 프로퍼티
title : 내비게이션바에 표시되는 내비게이션 아이템의 제목. 기본값은 nil
vartitle:String?{getset}
backBarButtonItem : 내비게이션바에서 뒤로 버튼이 필요할 때 사용할 바 버튼 항목
varbackBarButtonItem:UIBarButtonItem?{getset}
hidesBackButton : 뒤로 버튼이 숨겨져 있는지를 결정하는 부울 값
varhidesBackButton:Bool{getset}
주요 메서드
// setHidesBackButton(_:animated:) : 뒤로 버튼이 숨겨져 있는지를 설정하고, 전환 애니메이션 효과 적용funcsetHidesBackButton(_hidesBackButton:Bool,animated:Bool)
내비게이션 아이템 커스터마이징
내비게이션 아이템은 크게 좌, 우 바 버튼 아이템과 중앙 타이틀 영역이 있다.
좌측 바 버튼, 우측 바 버튼 아이템의 경우 타입은 UIBarButtonItem 이며 상황에 따라서 커스텀 뷰를 넣어서 구현할 수도 있다.
프로퍼티
// titleView : 중앙 타이틀 영역의 뷰vartitleView:UIView?{getset}// Tip : 중앙 타이틀 영역에 뷰를 상속받은 (UILabel, UIView, UIImageView 등등) 클래스들을 표현할 수 있습니다.leftBarButtonItems:좌측아이템영역의UIBarButtonItem의바버튼아이템배열varleftBarButtonItems:[UIBarButtonItem]?{getset}// leftBarButtonItem : 좌측 아이템 영역의 UIBarButtonItem 중에 가장 좌측 바 버튼 아이템varleftBarButtonItem:UIBarButtonItem?{getset}// rightBarButtonItems : 우측 아이템 영역의 UIBarButtonItem의 바 버튼 아이템 배열varrightBarButtonItems:[UIBarButtonItem]?{getset}// rightBarButtonItem : 우측 아이템 영역의 UIBarButtonItem 중에 가증 우측 바 버튼 아이템varrightBarButtonItem:UIBarButtonItem?{getset}
메서드
// setLeftBarButtonItems(_:animated:) : 좌측 아이템 영역에 UIBarButtonItem 타입의 객체들을 순차적으로 설정하고 애니메이션 효과를 적용funcsetLeftBarButtonItems(_items:[UIBarButtonItem]?,animated:Bool)// setLeftBarButton(_:animated:) : 좌측 아이템 영역에 UIBarButtonItem 타입의 객체를 설정하고 애니메이션 효과를 적용funcsetLeftBarButton(_item:UIBarButtonItem?,animated:Bool)// setRightBarButtonItems(_:animated:) : 우측 내비게이션 아이템 영역에 UIBarButtonItem 타입의 객채들을 순차적으로 설정하고 애니메이션 효과를 적용funcsetRightBarButtonItems(_items:[UIBarButtonItem]?,animated:Bool)//setRightBarButton(_:animated:) : 우측 아이템 영역에 UIBarButtonItem 타입의 객체를 설정하고 애니메이션 효과를 적용funcsetRightBarButton(_item:UIBarButtonItem?,animated:Bool)
바 버튼 아이템
바 버튼 아이템은 UIToolbar 또는 UINavigationBar (backBarButtonItem,leftBarButtonItem,rightBarButtonItem등)에 배치할 수 있는 특수한 버튼이다. 제목이나 이미지를 보여줄 수 있고 미리 UIBarButtonItem.SystemItem 열거형에 정의된 여러 스타일 중 하나의 스타일로 선택할 수도 있다.
Tip: iOS 11에서는 UIBarButtonItem을 오토레이아웃 제약 없이 내비게이션 아이템으로 추가하면 바 버튼 아이템의 프레임이 예상치 못한 크기로 나올 수 있다.
이럴 땐 UIBarButtonItem 객체에 적절한 오토레이아웃 제약을 추가한 후 내비게이션 아이템으로 설정하면 설정한 제약에 따라 알맞은 크기로 볼 수 있다.
주요 프로퍼티
title : 아이템에 표시되는 제목
vartitle:String?{getset}
image : 아이템에 표시되는 이미지
varimage:UIImage?{getset}
style : 아이템의 스타일
varstyle:UIBarButtonItem.Style{getset}
width : 아이템의 너비 값
varwidth:CGFloat{getset}
tintColor : 아이템에 적용할 색상
vartintColor:UIColor?{getset}
주요 상수
UIBarButtonItem.Style : 아이템 스타일 정의
UIBarButtonItem.SystemItem : 바 버튼 아이템에 대한 시스템 제공 스타일