Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

박스오피스II [STEP 2] Jusbug, Redmango #107

Open
wants to merge 12 commits into
base: ic_9_jusbug2
Choose a base branch
from

Conversation

JusBug
Copy link

@JusBug JusBug commented Aug 16, 2023

@inwoodev
제임스 안녕하세요!
이번에도 어김없이 레이아웃 잡는 게 쉽지 않았습니다.🥲
꼼꼼한 리뷰 잘 부탁드립니다🙏

고민했던 점

<CollectionView 하단에 버튼 추가>

🤯 문제상황
기존에는 CollectionViewSafe area 영역까지 크기를 설정했기 때문에 하단에 화면모드변경 버튼을 추가하려면 CollectionView의 높이를 다시 잡아주어야 했습니다. 하지만 레이아웃 설정이 충돌이 나면서 변경이 되지 않는 문제가 있었습니다.

🔥 해결방법
기존의 Constraint'에서 잡아줬던 Safe area` 설정을 제거하고 height 값을 직접 넣어주면서 해결할 수 있었습니다.


<iconCell 레이아웃 설정>

🤯 문제상황
iconCell을 생성한 뒤 그대로 뷰를 그리게 되면 각셀은 뷰의 left, right에 붙어있고 각 cell의 간격도 격차가 커서 View와 cell그리고 cell 간의 레이아웃을 잡아줘야 하는 문제가 있었습니다.

🔥 해결방법
UICollectionViewDelegateFlowLayout 프로토콜을 채택하여 셀의 너비와 높이, 뷰와 셀의 간격 그리고 셀의 라인 값을 설정해주며 전체적인 listCelliconCell의 레이아웃을 잡아주었습니다.

extension MainViewController: UICollectionViewDelegateFlowLayout {
    func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
        let viewWidth = collectionView.bounds.width
        let viewHeight = collectionView.bounds.height
        
        if isIconMode {
            let cellWidth = (viewWidth - 20 * 3) / 2
            return CGSize(width: cellWidth, height: cellWidth)
        } else {
            return CGSize(width: viewWidth, height: viewHeight / 9)
        }
    }
    
    func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, insetForSectionAt section: Int) -> UIEdgeInsets {
        if isIconMode {
            return UIEdgeInsets(top: 20, left: 20, bottom: 20, right: 20)
        } else {
            return UIEdgeInsets.zero
        }
    }
    
    func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumLineSpacingForSectionAt section: Int) -> CGFloat {
        if isIconMode {
            return 10
        } else {
            return 0
        }
    }
}

<cell 경계선 설정>

🤯 문제상황
각 셀들을 구분짓기 위해서 기존에는 단순하게 셀의 간격을 두고backgroundColor를 넣어 경계가 보이도록 설정하였는데 이번에는 각 셀들에 layer에 너비를 주고 컬러를 넣어 경계선이 보이도록 수정했습니다. 하지만 셀들이 서로 겹치는 layer에서는 경계선들의 두께가 불규칙적으로 상이해지는 문제가 발생했습니다.

override func layoutSubviews() {
    super.layoutSubviews()
    self.layer.borderWidth = 1
    self.layer.borderColor = UIColor.black.cgColor
}

🔥 해결방법
isIconMode 변수에 따라 willSet을 통해 값이 변경되기 직전, 즉 화면모드가 변경되기 직전에 레이아웃을 설정해주는 로직을 구현했습니다. UICollectionViewFlowLayout 아이콘 모드의 레이아웃을 잡아주고, UICollectionLayoutListConfiguration은 리스트 모드의 레이아웃을 잡아주고 있습니다. 여기 리스트 모드에서는 appearance.plain으로 주게 되면서 리스트 셀들의 경계선이 그어지고 일렬로 표시되는 레이아웃을 갖게되면서 문제를 해결할 수 있었습니다.

var isIconMode: Bool = false {
    willSet(newVal){
       changeLayout(newValue: newVal)
    }
}

private func configureFlowLayout() {
    let layout = UICollectionViewFlowLayout()
    collectionView.setCollectionViewLayout(layout, animated: false)
}

private func configureListLayout() {
    let configuration = UICollectionLayoutListConfiguration(appearance: .plain)
    let layout = UICollectionViewCompositionalLayout.list(using: configuration)
    collectionView.setCollectionViewLayout(layout, animated: false)
}

private func changeLayout(newValue: Bool) {
    if newValue == true {
        configureFlowLayout()
    } else {
        configureListLayout()
    }
}


####<cell의 크기를 벗어난 Label.text 처리>
🤯 문제상황
영화 제목이 긴 경우에는 하단의 다른 내용들이 밀려 정보가 가려지고, 관객수가 커지는 경우에는 셀의 범위를 벗어나 Label의 내용이 ...으로 잘리게되는 문제가 발생하였습니다.

영화제목의 길이로 인한 내용 잘림

많은 관객수로 인한 내용 잘림

🔥 해결방법
영화 제목은 allowsDefaultTighteningForTruncation을 이용하여 label의 너비를 초과하는 경우에도 텍스트를 조절하여 label에 맞게 표시하고, 관객수 정보는 adjustsFontSizeToFitWidth 속성을 이용하여 label의 내용이 잘릴 때 자동으로 폰트사이즈를 조절하도록 하였고 추가적으로 셀의 크기는 정해져 있기 때문에 label의 라인의 갯수를 따로 지정해주어 최대한 모든 정보가 담기도록 문제를 해결했습니다.

audiNumberLabel.adjustsFontSizeToFitWidth = true
audiNumberLabel.numberOfLines = 1

movieNameLabel.allowsDefaultTighteningForTruncation = true
movieNameLabel.numberOfLines = 2

조언을 얻고 싶은 점

🤯 문제상황
글씨 크기를 변경시킬 경우 list모드에서 일부 셀이 뭉개지는 상황이 발생했습니다. 무엇이 문제인지 감이 오지 않아 구체적으로 질문할 수 없는점 양해 부탁드립니다. 이런 트러블 슈팅이 발생하는 이유가 궁금합니다.

Copy link

@inwoodev inwoodev left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Step 2 까지 훌륭하게 진행하신 여러분께 박수를 👏👏👏👏

두 분이서 해결하신 부분을 살펴보니 정말 많이 고민하신 흔적이 보였어요~! 그래서 그런지 별로 코멘트 드릴게 없더라구요 ㅎㅎ

조언을 얻고 싶은 점
🤯 문제상황
글씨 크기를 변경시킬 경우 list모드에서 일부 셀이 뭉개지는 상황이 발생했습니다. 무엇이 문제인지 감이 오지 않아 구체적으로 질문할 수 없는점 양해 부탁드립니다. 이런 트러블 슈팅이 발생하는 이유가 궁금합니다.

요 부분만 좀 말씀 드리자면 음...이거는 제 여러분이 해결하는 과정 중에서 답을 찾으실 수 있을거라 생각해요.

🔥 해결방법
isIconMode 변수에 따라 willSet을 통해 값이 변경되기 직전, 즉 화면모드가 변경되기 직전에 레이아웃을 설정해주는 로직을 구현했습니다. UICollectionViewFlowLayout 아이콘 모드의 레이아웃을 잡아주고, UICollectionLayoutListConfiguration은 리스트 모드의 레이아웃을 잡아주고 있습니다. 여기 리스트 모드에서는 appearance를 .plain으로 주게 되면서 리스트 셀들의 경계선이 그어지고 일렬로 표시되는 레이아웃을 갖게되면서 문제를 해결할 수 있었습니다.

요 부분에서 컬랙션뷰 크기 관련해서 조금 더 고민 해 보시면 이 부분은 충분히 해결하실 수 있다고 생각합니다~! 만약에 도저히 못 찾겠다 하는 부분이 있으시다면 디스코드에서 한 번 같이 얘기해 보시죠~!!

고생하셨습니다~!!! :)

Comment on lines +11 to +14
@IBOutlet weak var rankNumberLabel: UILabel!
@IBOutlet weak var movieNameLabel: UILabel!
@IBOutlet weak var rankInfoLabel: UILabel!
@IBOutlet weak var audiNumberLabel: UILabel!

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

외부에서 접근하는 경우가 있을까요~?

나머지 프로퍼티들도 한 번씩 더 고민 해 보셔도 좋을듯합니다 :)

Comment on lines +21 to +26
override func layoutSubviews() {
super.layoutSubviews()
self.layer.borderWidth = 1
self.layer.borderColor = UIColor.black.cgColor
self.layer.cornerRadius = 10
}

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

요 함수는 언제 호출될까요?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

  • layoutSubview():하위 뷰들의 레이아웃이 조정되는 시점에 호출
  • viewWillLayoutSubview(): 하위 뷰의 레이아웃이 조정되기 직전에 호출
  • viewDIdLayoutSubview(): 하위 뷰의 레이아웃이 조정된 후에 호출

Comment on lines +23 to +25
init?(rawValue: Int) {
self = rawValue > 0 ? .upArrow : .downArrow
}

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

실패하는 경우가 있을까요~?

configureTitle()
initRefresh()
}

private func configureFlowLayout() {
let layout = UICollectionViewFlowLayout()

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

UICollectionViewFlowLayout은 뭐고 UICollectionViewDelegateFlowLayout은 뭘까요~? 어째서 둘 다 활용하신걸까요~?
(요건 공부하신 부분을 공유 받고자 드리는 질문이에요 :) )

Comment on lines +16 to +20
var isIconMode: Bool = false {
willSet(newVal){
changeLayout(newValue: newVal)
}
}
Copy link

@inwoodev inwoodev Aug 16, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

willSet을 활용하셨군요~ 👍👍👍 훌륭한 방법으로 문제를 해결하셨습니다~!!!~!!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants