[Swift] JSON 데이터로 Table View 만들기

Ryan (Geonhee) Son·2021년 4월 20일
0

Study Stack

목록 보기
6/34

지난 포스팅에서는 JSON 디코딩을 지원하는 타입을 만들어 보았습니다. 이번에는 디코딩된 JSON 데이터를 활용해서 Table View를 만들어보겠습니다!

Table View와 Cell UI 구성

  • 먼저 스토리보드에서 View ControllerTable View를 올려 놓습니다.

  • 화면에서 Table View가 존재할 위치를 잡습니다.

  • Table View CellTable View 위에 올려둡니다.

  • Cell을 선택(클릭)해서 Attributes InspectorReuse Identifier의 이름을 설정해줍니다.

Table View의 코드를 작성하기 위한 타입 생성 및 관련 코드 작성

  • Cocoa Touch Class 형식으로 UIViewController 타입을 가진 파일을 하나 만듭니다. 초기 View ControllerTable View로 만들고 싶을 경우에는 새로 만들지 않고 기존 파일을 활용하셔도 됩니다.

생성한 ViewController에 JSON 데이터를 디코딩하기 위한 코드를 추가합니다. Table View를 연결할 IBOutlet도 함께 만들어줄게요.

class ViewController: UIViewController {
  // MARK: - Properties
  @IBOutlet private weak var tableView: UITableView!
  private var artworks: [Artwork] = []
  
  // MARK: - View life cycle
    override func viewDidLoad() {
      super.viewDidLoad()

      let decodedResult: Result = ExpoJSONDecoder.decode(to: [Artwork].self,from: ExpoData.artworks)
      
      switch decodedResult {
      case .success(let result):
        artworks = result
      case .failure(let error):
        debugPrint(error)
      }
    }
}

Outlet 연결

그리고 스토리보드에서 미리 만들어둔 View ControllerIdentity InspectorClass란에 새로 만든 View Controller의 이름을 작성합니다.

Connections Inspector으로 이동해서 만들어준 IBOutlet과 UI 요소로 만들어둔 Table View를 이어줍니다.

Custom Cell 세부 UI 구성

여기에서 tableViewCell에 들어갈 내용이 Basic, Right Detail 등 기본적으로 제공되는 스타일로 커버가 가능한 경우는 해당 스타일을 이용하시면 됩니다. 하지만 저처럼 그림과 제목, 짧은 설명과 이동 아이콘까지 여러 내용을 Cell에 넣고 싶으시다면 UI 요소를 활용해 직접 Cell을 디자인해보세요.

Custom Cell 타입 생성 및 관련 Outlets 작성

직접 Custom Cell을 만들어주신 경우, Cocoa Touch Class 형식으로 UITableViewCell 타입을 가진 파일을 하나 만들고, 데이터를 넣어줄 요소들을 IBOutlet으로 정의한 다음 스토리보드에서 CellCustom Class를 지정해주고, 각 IBOutlet을 UI 요소와 연결해주세요.

import UIKit

class ArtworkTableViewCell: UITableViewCell {
  @IBOutlet weak var thumbnailImageView: UIImageView!
  @IBOutlet weak var titleLabel: UILabel!
  @IBOutlet weak var shortDescriptionLabel: UILabel!
}

Table View delegate 및 dataSource 지정을 위한 프로토콜 채택

계속해서 TableView와 함께 일해줄 delegatedataSource를 지정해주어야 하는데요, 사전 작업으로 UITableViewDelegateUITableViewDataSource 프로토콜을 채택해주고 각 프로토콜의 요구사항을 충족시켜주어야 해요.

요구사항을 보니 UITableViewDataSource 프로토콜에 optional로 표기되지 않은 두 가지 메서드를 구체화해주는 것이네요.

  func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    code
  }
  
  func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    code
  }

프로토콜 요구사항 충족을 위한 메서드 구현

첫 번째 메서드는 tableView(_:numbersOfRowsInSection:)로, 한 섹션에 몇 개의 열(Row)가 들어갈 것인가를 알려주는 메서드에요. 두 번째 메서드인 tableView(_:cellForRowAt:)tableView의 각 열에 들어갈 셀(Cell)의 데이터를 채워 UITableViewCell 타입으로 반환하는 메서드입니다. 작성된 코드를 보시면 어떤 내용인지 바로 이해가 되실거에요.

// MARK: - Table view data source
extension ViewController: UITableViewDataSource {
  func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    return artworks.count // 디코딩된 데이터의 배열 요소 갯수를 열 개수로 반환
  }
  
  func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    // Reuseable Cell 선언
    let cell: ArtworkTableViewCell = tableView.dequeueReusableCell(
      withIdentifier: "artworkCell",
      for: indexPath
    ) as! ArtworkTableViewCell 
    
    // Reuseable Cell에 데이터 할당
    cell.thumbnailImageView.image = UIImage(named: artworks[indexPath.row].imageName)
    cell.titleLabel.text = artworks[indexPath.row].name
    cell.shortDescriptionLabel.text = artworks[indexPath.row].shortDescription
    
    return cell
  }
}

delegate 및 dataSource 지정

이전 포스팅에서 다룬 적이 있지만 delegateTable View 대신에 스크롤링 지원을 위해 셀의 높이를 계산한다든지 셀이 선택되는 등 테이블과의 상호작용을 다루어주고, dataSource는 테이블에 데이터와 셀을 제공하는 역할을 수행합니다. 이 친구들은 두 가지 방법으로 지정해줄 수 있어요. 둘 중에 하나만 하셔도 됩니다.

  1. 코드를 이용한 방법
    Table View를 구현하고자하는 View Controller에 아래와 같은 코드를 작성합니다.
override func viewDidLoad() {
  super.viewDidLoad()
  tableView.delegate = self
  tableView.dataSource = self
}
  1. 스토리보드를 이용한 방법
  • 스토리보드의 뷰 컨트롤러에서 테이블을 선택합니다.
  • 아래 화면과 같이 Connections inspector 탭에서 dataSourcedelegateView Controller에 연결합니다.

확인

이제 오토 레이아웃을 조금 적용해주면 아래와 같은 화면을 확인하실 수 있습니다. 세부 화면으로 이동할 때 데이터를 이동시키는 등 세부 화면으로의 이동 방법은 다음 포스팅에서 다루도록 하겠습니다~!

profile
합리적인 해법 찾기를 좋아합니다.

0개의 댓글